Ayende @ Rahien

Oren Eini aka Ayende Rahien CEO of Hibernating Rhinos LTD, which develops RavenDB, a NoSQL Open Source Document Database.

Get in touch with me:

oren@ravendb.net

+972 52-548-6969

Posts: 7,360 | Comments: 50,755

Privacy Policy Terms
filter by tags archive
time to read 3 min | 488 words

I am having an interesting discussion in email with Evan Hoff, about the benefits of pub/sub architecture vs. request/reply. I want to state upfront that I see a lot of value in async one way messaging for a lot of the interactions in an application and across services. However, I am still skeptic about the push for pub/sub all the way.

To me, it seems like the request/reply model is a very natural one in many common scenarios. In most backend processing systems, I would tend to use pub/sub with sagas as both the easiest and most scalable solution. But in almost all cases that end up in the UI, this just doesn't make sense. Even if I want to fire several requests and then wait for all their reply, the model is still more natural than a pub/sub approach.

Note that the following code sample use imaginary API.

Let us go back to the displaying the available candidates. Using the request/reply model, I would have:

public void AvailableCandidates()
{
     var specifications = BuildSpecifications();
     var msg = bus.Process(new FindAvailableCandidateMessage(specifications));
     DisplayResults(msg.Results);
}

All of those are using the request / reply model.

The pub/sub model will look somewhat like this:

public void AvailableCandidates()
{
	var specifications = BuildSpecification();
	
	bus.Publish(new FindAvailableCandidatesMessage(specifications))
		.WaitForCallback(delegate(AvailableCandidatesMessage msg)
		{
			DisplayResults(msg.Results); 
		});
	
}

Or probably something like:

public void AvailableCandidates()
{
	var specifications = BuildSpecification();
	Guid correlationId = Guid.NewGuid();
	ManualResetEvent waitForReply = new ManualResetEvent(false);
	
	bus.SubscribeOnce<AvailableCandidatesMessage>(correlationId, delegate(AvailableCandidatesMessage msg)
		{
			DisplayResults(msg.Results); 
			waitForReply.Set();
		});
	bus.Publish(new FindAvailableCandidatesMessage(correlationId, specifications));
	waitForReply.WaitOne();
}

Notice that I am not saying anything about the way those are handled once they leave the client. In fact, some of the reasons that were mentioned to favor the pub/sub model is the flexibility that you get when adding more functionality. Such as adding auditing, or redirecting messages to different services based on the type of candidate, etc.

The problem is that I see not inherent need for pub/sub to make this work. In fact, I think that anything that publish a message and than waits for the callback message is a big API issue, because this is request/reply, but with harder to use API. Even if you are doing the wait in async manner, I still think that this is a bad idea.

In the context of a request/reply interaction, we can handle everything the way we would handle any other message:

image

In fact, from the perspective of the infrastructure, there is little need to distinguish those. A message going out will go out either via a request/reply channel or a one way output channel, with a reply maybe arrived through a one way input channel. We don't really care about that.

From my point of view, it makes a lot more sense than to wait for a callback.

Thoughts?

time to read 2 min | 202 words

Jeff Brown has a good post about information in software:

There is no technical reason preventing software applications from adopting common standards in the representation of their information.

[...snip...]

Would software interoperability improve if we could just agree on common meta-classes for data structures?

[...snip...]

In any case, it bothers me profoundly that software is so vertical. There is too little common ground. Each application contains a wealth of information but remains steadfastly inaccessible.

It is worth point out that most organization can't agree on what something as fundamental as the Customer within the organization. This is because different parts of the organization are responsible for different aspects of the customer, and they have radically different needs. 

As Jeff points out, software that is open & extensible usually carry a price tag of six figures as well as a hefty customization fee. That is just the nature of the beast, because being a generalist costs, because the business doesn't care if you you can handle fifty different ideas of customers, they want your to fit their idea of customer, do it well, and fit with the different view of a customer within the organization. That doesn't come easily.

time to read 1 min | 164 words

I wanted to run a Wiki at work, to handle all sort of issues.

I already am using Media Wiki, but this requires MySQL database, and I didn't want to have to install that. I tried to install Trac, and I did manage to install it, but afterward it was... "Okay, now what?"

I then found out about ScrewTurn via Avery, and decided to give it a shot. It has an installer that I downloaded, and in 5 minutes, I had a fully functional Wiki. The only issue that I had was that the installer didn't setup the file premissions, but that took a second to fix. I got it running, and it is a lot like MediaWiki, except that I don't have to do anything to get it to work. I am very impressed.

Now all that remains to see if I can put it to good use :-)

FUTURE POSTS

No future posts left, oh my!

RECENT SERIES

  1. re (32):
    16 Aug 2022 - How Discord supercharges network disks for extreme low latency
  2. Production postmortem (43):
    05 Aug 2022 - The allocating query
  3. Webinar recording (14):
    26 Jul 2022 - RavenDB & Messaging Transactions
  4. Recording (5):
    25 Jul 2022 - Build your own database at Cloud Lunch & Learn
  5. High performance .NET (7):
    19 Jul 2022 - Building a Redis Clone–Analysis II
View all series

Syndication

Main feed Feed Stats
Comments feed   Comments Feed Stats