Layers are not tiers

by Ben Hart 28. September 2008 15:49

I've been spending more time at the asp.net forums recently. Aside from a bit of shameless self-promotion, I do genuinely enjoy helping other people out. I'm fairly opinionated, and I'm distinctly aware that many of my opinions offend what others consider to be rules, so it's turning out to be an interesting exercise in diplomacy too.

One recurring question people seem to have relates to layered architectures. The questions typically ask about n-tier architecture, or mention data access tiers and the like. What's fairly common is the use of the term tier and layer, and these are used by many interchangeably. This is incorrect.

What's a tier?

When I was at uni, we spent some time learning about the evolution of system architectures. The course started with mainframes, went into the development of the client/server model, discussed 2-tier applications, and the evolution to n-tier. We learnt about things like CORBA, distributed processing, and a lot more stuff I quite quickly forgot. At the time, though, I had a clear idea of what a tier was.

Mainframe It was clear that original mainframes hosted the complete application, and that interaction with the system was through interfaces served directly from the host.

Client/Server (2-Tier) Client/server made a lot of sense, too, and were the systems that I began to develop. We had rich (well we thought so) user interfaces that connected directly to a centralised database. It was clear to me that this was 2-tiered, the database was hosted on one machine, and the system that needed the data on another. Processing was indeed distributed, even if a little heavy on the client. Having all the power of client machines let us do some amazing things, never dreamed of on the mainframe.

I never really got n-tier systems back then, mainly since I never developed any. I understood academically, though, that n-tier systems introduced another tier between the client (desktop app) and the server (database), to distribute even further the load.

A 3-Tier System Architecture

In this middle-tier data could be aggregated before being sent to the client, for one, resulting in less network traffic. Business processes could be orchestrated from this middle tier too, and databases could be locked down to prevent all these clients accessing them. The clients themselves could be trimmed down, since most direct data access had been rolled into this middle tier. The clients were more about presenting the data, and acted as the interface between the user and the middle tier. Having this middle tier results in a 3-tier architecture. Further tiers could be introduced too, and rather than specifying the number of tiers each time, it's much simpler to just call the architecture n-Tier.

An n-Tier System Architecture

The key aspect, though, is that the system as a whole is distributed across many computers, to centralise related functionality, and distribute processing.

When did it all go wrong?

I think it became confusing when people started calling the middle tier(s) the business logic tier. Despite often being accurate, this is not necessarily the case. If I had an n-tiered application, it is quite feasible that all business logic remained in the client, and that my middle tier only simplified data access, and prevented all the clients on the network interacting directly with a database. This might have violated some original vision of what the middle tier should be, but it is feasible nonetheless.

If we had never started calling this middle tier business logic, we likely would have avoided all the confusion when we try and extol the virtues of a layered application architecture.

Layers

When most of us started developing data-driven applications, we generally added some controls to a form, or perhaps emitted some html from a script, and used this to display data we retrieved from a database. We generally lumped connecting to the database with retrieving the data and displaying it all within the same script or class, and were likely quite pleased with the results.

Over time we learned that mixing all this code together became quite a headache. If we needed to connect to a different database we needed to change connection information in numerous places. When we changed a column name in our database we needed to change SQL statements all over the place. When our user informed us that a customer must have at least one address, we had to add checks into numerous 'controllers'. Our developers with a better eye for design (but completely ignorant of databases) kept accidentally breaking our data access when they tweaked the appearance of the UI. It became clear that code that delivered such different functionality should be separated, and that code that is similar should be grouped, and never repeated.

So we introduced layers into our applications. Data access follows distinct patterns, and relies on the same configuration, so having a data access layer was an immediate quick-win. When we need to change database connection information it was obvious to jump into the data access layer. All SQL statements reside there too, so changing column names became much easier.

Business rules tend to change as often as our database, so centralising these were obvious too. When the rule was introduced that customers must have an address, changing this in one place meant that all dependent user input was validated, eliminating the possibility that we forgot about a seldom used interface in the admin section, for example.

This left our UI to only concern itself with processing user input, and displaying the results. Designers can work on this without interfering with any other application logic. We can have multiple different UI technologies (windows and web) running the same business logic and data access, they just need to call the now encapsulated functionality.

These are the typical layers we see in an application, often called data access, business logic and user interface, separated as such because the separation is obvious. While I've moved away from these layers per se, they're still widely used, and are what most people refer to when discussing layers (and, misguidedly, tiers)

A Traditional Layered Architecture

The diagram above represents a system distributed across three tiers, with a layered application architecture evident in the web tier. The separation of layers in the web tier is logical, they need not run on a different machine or process to exhibit it. Typically we'd divide them into different assemblies, but not necessarily. If these related concepts were grouped into classes found in the App_Code folder on an ASP.NET web site, I'd still have to concede that the site is layered along these lines.

So why is a layer not a tier?

Simply because a layer is about the logical separation of related functionality. The separation allows a much higher level of reuse within an application, and ensures greater maintainability. If we've separated out these layers into assemblies, we can likely plug these into other projects, and reuse them without any further development. If you haven't layered your application into related functionality, you'd better close your browser and start right now.

A tier, on the other hand, is all about physical distribution. In .NET we'd be making extensive use of serialisation and remoting (or xml web services), and all things quite hard to maintain. We might get a lot of reuse, but this is at the cost of much greater complexity, and lower overall performance. Distributing an application across physical boundaries (across machines and/or processes) should not be a trivial decision to make.

And, in a nutshell, that's why I think we need to clear up the semantics of tiers and layers. One cannot be argued against, the other needs to be argued for. The sooner we all are talking about the same thing when discussing them, the better.

Update: Added a few diagrams, and elaborated on them based on suggestions from Jim Tollan.

Currently rated 4.6 by 5 people

  • Currently 4.6/5 Stars.
  • 1
  • 2
  • 3
  • 4
  • 5

Tags: , ,

.NET | Application Architecture | Design Patterns

Comments

Add comment


(Will show your Gravatar icon)  

biuquote
  • Comment
  • Preview
Loading



Powered by BlogEngine.NET 1.4.5.0
Theme by Mads Kristensen

About me...

I'm a passionate .NET developer, with C# my language of choice. I've been at it for a number of years now, and enjoy that I'll never shake the feeling I'm just starting out.

I love software, and I love building it even more. I love knowing that my work facilitates others', and that one line of code at a time, we're increasing our capability.

More...



Page List