Following
the third part of my "Defining SOA" posts
Udi Dahan left the following two questions:
How does this [layers - ARGO] play with two services talking with each other? One pubs
to the other's subs?The other requests to the first's response?
How valuable is the layered abstraction?
Considering
Udi and me usually see things eye to eye. I guess that if I managed to
get him confused, more clarification is warrant :) I'll do that in two
posts, this one which will explain the concept of layers and the next
which will explain why it is paramount to SOA (and answer the two
questions)
Usually when I review an architecture one of the
first (sometimes the only) architectural artifact I am shown is a
"layered diagram" of the architecture e.g. something like the following:

These sort of half layers/half block diagrams with or without the
common 3 layers (which also appear in the diagram above) of "UI"
"Business" and "Data" give the whole idea of layers a bad name
The
key differentiator between layers and just a bunch of blocks is the
limitations on the allowed communication paths between the components
(layers vs. blocks). In the previous post I quoted an old (2005)
definition I had for layers where I said the following
"Typically a layered is allowed to call only the layer below it and be
called only by the layer above it (but there are variants e.g. a layer
can call to any layer below it; vertical layers that can call multiple
layers; etc. -- all is fine as long as the layers communication paths
are limited by some rules)."
Alas, I was too quick on the Copy/past and everything in the brackets
(bold) is wrong - it should actually say - "but there's another variant
where layers are allowed to call the layer above it
or below
it". The other variants (like a layer that can all any below it) just
muddy the water, makes it hard to distinguish between layers and
regular components and thus make layers seem unimportant. consider the
following diagram:

So, in the above diagram the relations are the Component D and
Component C know each other. Component D is made of two layers (A and
B). Note that a more proper representation should also explain the
relations allowed between the layers i.e. is it unidirectional or
bidirectional (unless there's a common convention in the project)
Why is the distinction between layers and other type of components
important? because Layering gives you some benefits which "just
components" don't:
1. Layers allow information hiding. Since we don't know the inner working of what's beyond the layer
2. Layers allow separation - Things beyond the immediate layer are
hidden from each other. This means that things which are beyond the
layers are loosely coupled in a way that allows for flexibility and
the addition of capabilities. for instance adding a firewall between
your computer and the internet.
3. Layers allows changing the abstraction level - since layers are
hierarchical in nature, moving through the layer "stack" you can
increase or decrease the level of abstraction you use. This allows
expressing complex ideas with simple building blocks. The best known
example for this is the TCP/IP stack moving from an abstraction level
close to the hardware of the network interface layer to the application
level protocols such as HTTP
On the downsides - layers hurt performance by adding latency. Also too
many layers introduce added complexity to the overall solution (e.g. it
is harder to debug).
It it interesting to note that Interfaces
are in fact leaky layer abstractions (vs. for example SOA contracts
which are not leaky) - since when you use an interface you still need
to instantiate the object which is otherwise hidden behind the "layer"
(interface). This is basically the reason we want something like
dependency injection (DI) - to help make the abstraction complete and
why languages like Ruby where the contract abstraction is complete -
you don't need DI (
I discussed Ruby and DI in another post)
Another
issue which I mentioned here is the difference between logical layers
and physical (or potentially physical) layers. I usually call the
first kind layers and the latter tiers. logical layers are local and
can assume a lot about their neighboring layers. Tiers or physical
layers can be distributed, which carries a lot of implications (
something I discussed here recently in relation to MS Volta)