Scalaz-Camel: fully leveraging ‘what Scala and Scalaz offers for functional programming.’
The Camel DSL partly tries to mimic a functional programming style without being able to offer application developers the full power of a functional programming language.
Scalaz-Camel is a new project that provides an alternative DSL to Camel’s existing Java DSL and Scala DSL, but what advantages does Scalaz-Camel have over the existing DSLs? JAXenter spoke to Talend software architect and Scalaz-Camel owner Martin Krasser.
JAXenter: What is the scalaz-camel project?
Martin Krasser: The scalaz-camel project is an attempt to combine enterprise integration patterns (EIPs) with functional programming (FP): integration solutions are composed from EIPs with a functional domain-specific language (DSL) that is based on the Scala programming language and the Scalaz functional programming library. For providing connectivity to other systems over different protocols and APIs, scalaz-camel uses the integration components from Apache Camel.
The scalaz-camel DSL is a set of combinators and composition operators, used to compose message processors and messaging endpoints to complete message processing routes. Components of message processing routes can be plain Scala functions, existing Camel message processors and endpoints as well as other routes or route fragments. Composition flexibility, extensibility of the DSL and idiomatic use of Scala and Scalaz have been important aspects in the design of the scalaz-camel DSL.
Further key features are support for non-blocking routing and asynchronous message processors. This was achieved with a continuation-passing style (CPS) API. CPS is mainly used internally, the DSL supports direct-style programming. Scalaz-camel also uses concurrency strategies to abstract over the way how messages are routed concurrently. Applications can either choose from a number of predefined concurrency strategies or implement highly specialized custom strategies, if needed. Configurable concurrency strategies and support for non-blocking routing are important prerequisites for building highly scalable and concurrent integration solutions.
Furthermore, messages are immutable objects in scalaz-camel so that they can be easily shared by concurrent messages processors. The project also provides a bridge to the mutable counterparts in Camel which allows a reuse of all existing Camel message processors and components/endpoints in scalaz-camel applications.
A more detailed overview of scalaz-camel features is given in the project’s Wiki,
JAXenter: How does the scalaz-camel DSL differ from Camel’s existing Java DSL and Scala DSL?
Martin Krasser: Camel’s Java and Scala DSL is a fluent API based on the builder pattern. In my opinion, the Camel DSL partly tries to mimic a functional programming style without being able to offer application developers the full power of a functional programming language. This is where the scalaz-camel DSL comes in. It fully leverages what Scala and Scalaz offers for functional programming: message processors and endpoint producers are (or can be converted to) first-class functions that can be composed in a monadic or applicative way. Monadic composition with the >=> operator is done for processors that depend on each other such as message processors in a pipeline, whereas applicative composition is done for message processors that can run independent of each other such as the destinations in a recipient-list, for example. For applicative composition, scalaz-camel offers special combinators (multicast, scatter, …).
One doesn’t need to be an FP expert to use the scalaz-camel DSL. Basic Scala knowledge is sufficient for getting started. This is comparable to using Scala’s List or Option without needing to know that these are monads.
Another important difference is that the scalaz-camel DSL is extensible. Adding a new integration pattern is as simple as defining a new function and importing that function. This allows, for example, other libraries to easily contribute DSL extensions from a subdomain, such as eHealth-Integration, without needing to modify scalaz-camel itself. This is in contrast to the Camel DSL which follows a more monolithic approach. Any extension to the DSL must be made in the core of Apache Camel which is a limitation for the evolution of other DSLs based on Apache Camel.
JAXenter: Can you give us an example use case of Scalaz-Camel?
Martin Krasser: Both scalaz-camel and Apache Camel can be used to achieve the same goal: construct integration solutions by combining EIPs and other message processors to larger message-processing applications. They only differ in their programming paradigms and idioms, where scalaz-camel follows the functional programming paradigm.
This means that all usage example of Apache Camel are also valid usage examples of scalaz-camel. A simple scalaz-camel usage example from the order processing domain is given in the project’s Wiki. It’s a tutorial for getting started with scalaz-camel. Further usage examples are given in the project’s test specifications.
JAXenter: What’s on your ‘to do’ list for the project?
Martin Krasser: For the upcoming 0.3 release I want to focus on the following items.
- Support for further enterprise integration patterns
– Support for transactions and redeliveries
– Akka integration
– More examples
– Performance profiling
– Documentation extensions
– Use of HawtDispatch
This list is preliminary. Any feedback, ideas and suggestions for improvements are highly welcome and can be added to the project’s issue tracker.