Over a million developers have joined DZone.

gofor it

· Java Zone

What every Java engineer should know about microservices: Reactive Microservices Architecture.  Brought to you in partnership with Lightbend.

The gofor macro

I've started working on a series of open source library code for Clojure called Dragonmark that roughly falls into three categories: utilities, a distributed CSP library, and a sample web app that demonstrates distributed CSP.

So, why?

Mostly, I think that the semantics for interprocess communication should be the same as the semantics for local communication. Clojure's core.async library provides a really nice set of APIs to communicate asynchronously, have backpressure, and in general "do the right thing."

But core.async does not provide any interprocess communication. In fact, nothing in Clojure-land does a good job of abstracting the transport layer and maintaining the semantics of core.async.

So, Dragonmark.

Making core.async less verbose

If you're going to do core.async right, there's a pattern... create a channel to receive a reply, send a message, wait for a timeout or an answer, close the channel, if the answer came from the channel, do something, else, do an error.

Using Scala and LAFuture is really easy in a for comprehension. I wanted something similar in Clojure-land, so I wrote the gofor macro.

Here's an example:

  [a (foo channel {:thing value :other_thing other_value})]
  :let [b (+ a 1)]
  [c (baz other_channel)
   d (moose third_channel {:p b}
   :timeout 45000]
  (println a b c)
  :error (println &err &at))

The [a (foo channel {:thing value :other_thing other_value})] sends a message tochannel with {:_cmd "foo" :thing value :other_thing other_value :_return a_created_channel} and waits up to 30 seconds for an answer. If the answer doesn't arrive, the:error code is invoked and the comprehension is terminated. If the answer does come back, it's bound to a.

Next, we bind b to (a + 1).

Next, we kick off a parallel set of messages to other_channel and third_channel and wait up to 45 seconds for a response.

If we succeed, the (println a b c) code is executed.

It's a first pass at something that makes core.async more usable, especially in the case of cross-address space messaging where timeouts and failures should be expected and embraced.

Microservices for Java, explained. Revitalize your legacy systems (and your career) with Reactive Microservices Architecture, a free O'Reilly book. Brought to you in partnership with Lightbend.


Published at DZone with permission of David Pollak. See the original article here.

Opinions expressed by DZone contributors are their own.

The best of DZone straight to your inbox.

Please provide a valid email address.

Thanks for subscribing!

Awesome! Check your inbox to verify your email so you can start receiving the latest in tech news and resources.

{{ parent.title || parent.header.title}}

{{ parent.tldr }}

{{ parent.urlSource.name }}