Control Transaction Boundaries Between Layers

Control Transaction Boundaries Between Layers

hen developing a software solution on a three-layered architecture, an inevitable mismatch emerges between business transactions and system transactions. Business transactions stem from application requirements, and they are defined at the application/business layer, while system transactions (e.g., database transactions) are tied to a specific technology (SQL Server, MSMQ, etc.). No technology defines a business transaction; it’s just a description of a business process, which either fails or succeeds as a whole. This description is typically provided with domain-specific terminology and is best expressed in terms of object collaboration.

Since the layer where business transactions conceptually live has no direct access to the database, system transactions do not naturally map to business transactions.

In fact, the three-layered architecture requires you to encapsulate data-access code into a data layer to remove the database-access details from the business layer. You then use object-relational mapping routines (unless you use DataSets) on the border of the two layers to move data back and forth between the database and business objects.

Object-relation mapping routines undoubtedly make things easier by providing a bridge between objects and the database. However, they do not provide a robust, transparent way to define and control transactional boundaries at the business layer way (it’s just not their responsibility). If you do not anticipate this problem during your application design, your nice layered architecture will break once transactional requirements pop up. For instance, connection and database-related details (MSMQ details and so on) creep from the data layer into the business layer, typically as when connection and transaction ADO/ADO.NET objects are passed around the business entities (an error-prone practice).

A naïve, yet typical solution to the problem is hard-coding the dependency order among objects at design time. This is a bad idea for all but the simplest applications, because object collaboration paths vary across different application tasks. An object can be the root of a business transaction in one situation and a child in another depending on the day. Whenever it switches, you’ll have to chase down all the hard-coded assumptions in your code.

For these reasons, one of the main concerns application architects have is assuring ahead of time a robust, manageable framework for applications to map database transactions to business transactions. This way, each business object can focus on its tasks, committing and “rollbacking” its own job, oblivious to its transactional context.

The COM+ Option
A powerful, yet easy way to define transactions at the business-layer level is using COM+ declarative transactions. You just flag your business objects with the proper transactional requirements and the COM+/DTC infrastructure enlists database (and eventually MSMQ) connections into a single unit of work transparently. So you don’t have to coordinate the work of the data layer; each data layer component opens its own connection and fires data changes to the database. The DTC will commit or rollback the business transaction as a whole at the application layer.

This approach has its benefits and liabilities. The benefits include:

  • It lets you compose business components into transactionalunits easily. You can plug new components into the business transactionwithout intervening into the existing ones.
  • DTC-based transactions can spawn across process and machine boundaries.
  • DTC-based transactions can handle work distributed to more than one database server as a single transaction.

The liabilities include the following:

  • DTC-based transactions impose a performance overhead into the data access layer, about 30-40 percent on average. This is due to the fact that they have been designed to handle transactions across different databases (more exactly, across different resource managers).

I’ve personally used the COM+ approach often while working with VB6 in the pre-.NET era. I gave up some performance to gain more flexibility in my application design, even when no distributed databases were involved.

Thanks to .NET, you can now easily design a small framework that the data-access layer uses to accommodate transparent management of database transactions?without involving the DTC. This way, you can keep your focus on the business transaction scope, without incurring the overhead that COM+ transactions impose.

Enter the Connection Broker
The basic idea behind a connection broker is enabling you to roll your own library that centralizes and manages access to database resources (like the DTC does). The approach this article proposes defines two main classes that mediate the application code’s access to the actual connection and transaction objects. It doesn’t try to bring two or more connections into the same transaction as the DTC does.

The two classes are a SmartConnection class and a SmartTransaction class. The former implements IDbConnection and the latter IDbTransaction, so that they are (almost) indistinguishable from the classes the different .NET managed providers expose. Specifically, they will manage a single connection?and its associated transaction?for each execution scope. A proper algorithm will filter and monitor the access sequence to database resources, so that only the calls the logical root object places are actually forwarded to the underlying connection and transaction objects.

The business and data-access layers will use these two classes instead of the usual ones from .NET managed data providers. The SmartConnection class holds an internal reference to an actual connection, and the SmartTransaction class holds an internal reference to a transaction object. These classes blindly forward method calls via these internal references but for the Open, Close, Commit, and Rollback methods. Within these four methods, the two classes work their magic to behave as database connection and transaction brokers within a given execution scope.

Before delving into the implementation details, some explanation regarding the term “execution scope”: it encompasses, in its widest sense, all the work that different threads running on separate processes or machines perform. In a generic scenario, the transaction flow is a logical thread of execution that spawns across two or more processes. For example, consider a transaction that starts when a client calls into component C1 running on thread T1 on process P1. If component C1 creates and calls into a remote object C2 running on process P2, component C2 won’t of course share the same process or the same thread with the caller. However, C1 and C2 share the same logical thread of execution (see Figure 1). COM+ can actually trace such an execution pattern, and it guarantees that the DTC-based transaction will flow across the process (or network) boundaries.

Figure 1: Logical Thread of Execution

This article doesn’t cover the scenario above (even though it may come up in some large applications). Rather, it concentrates on the most common execution pattern in a three-layered application: the entire job performed by business and data objects that are hosted in a single process. The process hosting the business and data objects is a highly multithread environment, yet it guarantees thread isolation among objects activated by different clients?no matter which remoting technologies you choose (enterprise services, .NET remoting, or Web services). Each remote call executes within a random thread picked up from a thread pool (the .NET thread pool or the MTA thread pool) (see Figure 2).

Figure 2: Invoking Objects Remotely

Typically, the root business object executes its tasks by creating and calling into other business and data objects. If you don’t explicitly create a new thread, these new objects will all share the same thread as the original one that got the remote execution call. As you can see, even in a highly multithread environment, a thread scope of execution is sufficient for typical three-layered applications. This is exactly the scope the example connection broker in this article will support.

Author’s Note: Because connection objects cannot be marshaled by reference across processes and computers, COM+-based transactions are a must for transactions spawning more than one process. In fact, you can’t actually improve the proposed connection broker solution to handle this extended scenario.

Implementation Details
The downloadable code accompanying this article provides the entire implementation for the SmartConnection and SmartTransaction classes, along with an AuthorsBooks business object and a couple of data objects (DoAuthors and DoBooks). Note that the Author-Book business entity is implemented using an enhanced Dataset, which encapsulates validation logic into itself.

Let’s examine the SmartConnection class. To separate database resources at the thread level, mark the underlying connection object that the SmartConnection class manages by using the ThreadStatic attribute. One would be tempted to write code such as the following:

[ThreadStatic()]private static IDbConnection ms_RealConn =   new SqlConnection (); 

This won’t work since the CLR assigns the required value in only the first thread referencing the ms_RealConn variable. Whether this is a bug or not, you can workaround the issue by modifying the code as shown below. Additionally, make sure that no code accesses the ms_RealConn_private variable directly, but rather through the ms_RealConn property getter:

[ThreadStatic()]private static IDbConnection ms_RealConn_private ;private static IDbConnection ms_RealConn { get {  if (ms_RealConn_private == null)    ms_RealConn_private =      new SqlConnection ();   return ms_RealConn_private; }}

No synchronization is required since the variable has a thread scope.In the downloadable code included with this article, the SmartConnection class uses another framework-level component named DataAccess, which returns only provider-independent resources (i.e., IDbConnection instead of, say, SqlConnection). As shown in the code snippet below, a basic implementation could use a ThreadStatic counter so that in the Open method the connection is opened only when the counter is zero. Likewise, the Close method implementation closes the underlying connection only if the counter is equal to one:

public class SmartConnection : IDbConnection {... public void Open() {  if(ms_counter ==0)    ms_RealConn.Open ();   ms_counter +=1;    } public void Close() {  if(ms_counter ==1)    ms_RealConn.Close();   ms_counter -=1;    }...}

The SmartTransaction class would handle transactions in a similar way. This approach has a serious drawback, however: you have no way to detect when a business or data object forgets, for example, to call Close after it called Open or, even worse, to call Commit (or rollback) once it called BeginTransaction. In the latter case, the effects are a really disastrous. For example, the root object could call Commit, but the transaction wouldn’t actually commit since the counter is not equal to 1, meaning the whole job is doomed to be “rollbacked” by a transaction timeout later on without any notification to the client.

To overcome this issue, replace the simple counter with a Stack object and assign a Guid to each SmartConnection instance to uniquely identify it. In the Open method, instead of incrementing the counter, push the specific SmartConnection Guid to the Stack:

public class SmartConnection : IDbConnection {... public void Open() { if(ms_RealConnStack.Count ==0)   ms_RealConn.Open ();  ms_RealConnStack.Push(m_guid);    }...

In the Close method’s implementation you will try to match the Guid of the instance asking the connection to close with the Guid present at the top of the Stack. If they match, everything is okay, and if the Stack is empty once you’ve popped the Guid, you close the underlying connection. If the Guid doesn’t match, the method raises an exception to signal that a child object called Open but forgot to call Close. Essentially, it’s just like pairing opening and closing brackets in a programming language. The following code shows the implementation of the Close method of the SmartConnection class:

public class SmartConnection : IDbConnection {... public void Close() { if((Guid)(ms_RealConnStack.Peek())!=   m_guid)  throw new Exception (   "Invalid Sequence"); ms_RealConnStack.Pop();    if(ms_RealConnStack.Count ==0)   ms_RealConn.Close();  }...}

The implementation of the BeginTransaction, Commit, and Rollback methods follows the same logic to detect unmatched calls and sequence errors regarding the transaction start and outcome.

One of the last aspects to handle is detecting an incorrect call sequence within the same SmartConnection instance, such as when BeginTransaction is called before Open or Open is called twice. You can easily account for this problem by defining an instance-level ConnBrokerStatusEnum enum value that the broker checks before manipulating the ThreadStatic objects (see Listing 1). The SmartTransaction‘s ms_doomed flag prohibits a parent object from calling Commit if a child object has called RollBack.

Small Glitch in the Classes
Finally, a small problem slightly breaks the polymorphism of the SmartConnection and SmartTransaction classes. In the data-layer code, you need to assign the connection object and eventually the transaction object to a command object at some point. While the signature of the command’s connection property accepts any object implementing IDbConnection, you cannot pass a SmartConnection instance. Each provider-specific command instance casts the provided connection internally, throwing an exception if it doesn’t receive a connection object of the same provider. Obviously, the same problem applies to the command’s transaction property.

Instead of exposing the internal connection and transaction objects, you can resolve the issue by implementing the following methods in the SmartConnection and SmartTransaction methods, respectively:

public void SetConnectionToCommand(    IDbCommand p_command ) {  p_command.Connection =      ms_RealConnection ;}public void SetTransactionToCommand(IDbCommand     p_command ) {  p_command.Transaction =     ms_RealTransaction;}

Business Transactions with Less Overhead
The connection broker approach to transaction management fits the bill in most three-layered architectures. It incurs much less overhead than transactions based on COM+, so consider it in your application design when transaction boundaries are included into a single process and do not involve access to more than one resource manager.

Don’t be afraid to adopt this approach simply because you may need COM+ transactions in a future. Provided you follow a stateless approach in your business-layer design, you can easily switch to transactions based on COM+ later, by simply inheriting your business objects from the ServicedComponent class and instructing the connection broker to ignore all calls related to transaction control.

devx-admin

devx-admin

Share the Post:
India Web Development

Top Web Development Companies in India

In the digital race, the right web development partner is your winning edge. Dive into our curated list of top web development companies in India,

USA Web Development

Top Web Development Companies in USA

Looking for the best web development companies in the USA? We’ve got you covered! Check out our top 10 picks to find the right partner

Clean Energy Adoption

Inside Michigan’s Clean Energy Revolution

Democratic state legislators in Michigan continue to discuss and debate clean energy legislation in the hopes of establishing a comprehensive clean energy strategy for the

Chips Act Revolution

European Chips Act: What is it?

In response to the intensifying worldwide technology competition, Europe has unveiled the long-awaited European Chips Act. This daring legislative proposal aims to fortify Europe’s semiconductor

Revolutionized Low-Code

You Should Use Low-Code Platforms for Apps

As the demand for rapid software development increases, low-code platforms have emerged as a popular choice among developers for their ability to build applications with

India Web Development

Top Web Development Companies in India

In the digital race, the right web development partner is your winning edge. Dive into our curated list of top web development companies in India, and kickstart your journey to

USA Web Development

Top Web Development Companies in USA

Looking for the best web development companies in the USA? We’ve got you covered! Check out our top 10 picks to find the right partner for your online project. Your

Clean Energy Adoption

Inside Michigan’s Clean Energy Revolution

Democratic state legislators in Michigan continue to discuss and debate clean energy legislation in the hopes of establishing a comprehensive clean energy strategy for the state. A Senate committee meeting

Chips Act Revolution

European Chips Act: What is it?

In response to the intensifying worldwide technology competition, Europe has unveiled the long-awaited European Chips Act. This daring legislative proposal aims to fortify Europe’s semiconductor supply chain and enhance its

Revolutionized Low-Code

You Should Use Low-Code Platforms for Apps

As the demand for rapid software development increases, low-code platforms have emerged as a popular choice among developers for their ability to build applications with minimal coding. These platforms not

Cybersecurity Strategy

Five Powerful Strategies to Bolster Your Cybersecurity

In today’s increasingly digital landscape, businesses of all sizes must prioritize cyber security measures to defend against potential dangers. Cyber security professionals suggest five simple technological strategies to help companies

Global Layoffs

Tech Layoffs Are Getting Worse Globally

Since the start of 2023, the global technology sector has experienced a significant rise in layoffs, with over 236,000 workers being let go by 1,019 tech firms, as per data

Huawei Electric Dazzle

Huawei Dazzles with Electric Vehicles and Wireless Earbuds

During a prominent unveiling event, Huawei, the Chinese telecommunications powerhouse, kept quiet about its enigmatic new 5G phone and alleged cutting-edge chip development. Instead, Huawei astounded the audience by presenting

Cybersecurity Banking Revolution

Digital Banking Needs Cybersecurity

The banking, financial, and insurance (BFSI) sectors are pioneers in digital transformation, using web applications and application programming interfaces (APIs) to provide seamless services to customers around the world. Rising

FinTech Leadership

Terry Clune’s Fintech Empire

Over the past 30 years, Terry Clune has built a remarkable business empire, with CluneTech at the helm. The CEO and Founder has successfully created eight fintech firms, attracting renowned

The Role Of AI Within A Web Design Agency?

In the digital age, the role of Artificial Intelligence (AI) in web design is rapidly evolving, transitioning from a futuristic concept to practical tools used in design, coding, content writing

Generative AI Revolution

Is Generative AI the Next Internet?

The increasing demand for Generative AI models has led to a surge in its adoption across diverse sectors, with healthcare, automotive, and financial services being among the top beneficiaries. These

Microsoft Laptop

The New Surface Laptop Studio 2 Is Nuts

The Surface Laptop Studio 2 is a dynamic and robust all-in-one laptop designed for creators and professionals alike. It features a 14.4″ touchscreen and a cutting-edge design that is over

5G Innovations

GPU-Accelerated 5G in Japan

NTT DOCOMO, a global telecommunications giant, is set to break new ground in the industry as it prepares to launch a GPU-accelerated 5G network in Japan. This innovative approach will

AI Ethics

AI Journalism: Balancing Integrity and Innovation

An op-ed, produced using Microsoft’s Bing Chat AI software, recently appeared in the St. Louis Post-Dispatch, discussing the potential concerns surrounding the employment of artificial intelligence (AI) in journalism. These

Savings Extravaganza

Big Deal Days Extravaganza

The highly awaited Big Deal Days event for October 2023 is nearly here, scheduled for the 10th and 11th. Similar to the previous year, this autumn sale has already created

Cisco Splunk Deal

Cisco Splunk Deal Sparks Tech Acquisition Frenzy

Cisco’s recent massive purchase of Splunk, an AI-powered cybersecurity firm, for $28 billion signals a potential boost in tech deals after a year of subdued mergers and acquisitions in the

Iran Drone Expansion

Iran’s Jet-Propelled Drone Reshapes Power Balance

Iran has recently unveiled a jet-propelled variant of its Shahed series drone, marking a significant advancement in the nation’s drone technology. The new drone is poised to reshape the regional

Solar Geoengineering

Did the Overshoot Commission Shoot Down Geoengineering?

The Overshoot Commission has recently released a comprehensive report that discusses the controversial topic of Solar Geoengineering, also known as Solar Radiation Modification (SRM). The Commission’s primary objective is to

Remote Learning

Revolutionizing Remote Learning for Success

School districts are preparing to reveal a substantial technological upgrade designed to significantly improve remote learning experiences for both educators and students amid the ongoing pandemic. This major investment, which

Revolutionary SABERS Transforming

SABERS Batteries Transforming Industries

Scientists John Connell and Yi Lin from NASA’s Solid-state Architecture Batteries for Enhanced Rechargeability and Safety (SABERS) project are working on experimental solid-state battery packs that could dramatically change the

Build a Website

How Much Does It Cost to Build a Website?

Are you wondering how much it costs to build a website? The approximated cost is based on several factors, including which add-ons and platforms you choose. For example, a self-hosted

Battery Investments

Battery Startups Attract Billion-Dollar Investments

In recent times, battery startups have experienced a significant boost in investments, with three businesses obtaining over $1 billion in funding within the last month. French company Verkor amassed $2.1

Copilot Revolution

Microsoft Copilot: A Suit of AI Features

Microsoft’s latest offering, Microsoft Copilot, aims to revolutionize the way we interact with technology. By integrating various AI capabilities, this all-in-one tool provides users with an improved experience that not