Skip to main content

Welcome to a Grasp lesson

Create a free account to keep studying and create your own study path.

Lesson 48

Understanding ACID Properties

Recommended resources

Hello! Welcome to the first lesson in our module on Transactions and Concurrency.

In the last module, we mastered the art of designing database schemas, focusing on how to structure data efficiently and without redundancy using normalization and junction tables. As we previewed, our focus now shifts from the structure of data to the safety and reliability of operations that change that data.

Imagine multiple users accessing an application at once—booking tickets, updating profiles, or posting comments. How does the database ensure that these simultaneous operations don't corrupt the data or lead to chaos? The answer lies in the concept of a transaction.

Today, we'll explore the foundational guarantee that makes modern databases so reliable. The learning outcome is to explain the ACID properties (Atomicity, Consistency, Isolation, and Durability) of a transaction. Understanding ACID is not just theoretical; it's the core reason why a Database Management System (DBMS) is profoundly more robust than simply storing data in files, a distinction that will be clear given your background in systems programming.

What is a Transaction?

Before we can understand its properties, we first need a clear definition of a transaction. At its core, a transaction is a sequence of one or more database operations (like SELECT, INSERT, UPDATE) that are executed as a single, logical unit of work.

Relational Database ACID Transactions (Explained by Example)

To start, let's get a clear definition of a transaction. This video from Hussein Nasser provides a great introduction to the concept.

Watch from the beginning until 03:07. Pay attention to the three key ideas: a transaction is a unit of work, it's defined by a beginning and an end, and it can either be committed (made permanent) or rolled back (undone).

As the video explained, you can think of a transaction as a wrapper around a set of operations. The entire set must succeed for any of the changes to be saved. If any part of it fails, the entire set is undone. This "all or nothing" behavior is the key to maintaining data integrity.

The two main outcomes of a transaction are:

  • COMMIT: If all operations within the transaction are successful, COMMIT is called to make the changes permanent in the database.
  • ROLLBACK: If any operation fails, or if an error is detected, ROLLBACK is called to undo all changes made since the transaction began, returning the database to the state it was in before the transaction started.

The ACID Properties: A Guarantee of Reliability

ACID is an acronym for four properties that together guarantee the reliability of database transactions. These properties are the cornerstone of most relational database systems like PostgreSQL, MySQL, and SQL Server.

Database ACID Properties Explained
This diagram provides a visual summary of the four ACID properties. **Atomicity** ensures transactions are all-or-nothing. **Consistency** ensures the database state remains valid. **Isolation** prevents concurrent transactions from interfering with each other. **Durability** guarantees that committed changes are permanent.

Let's break down each one.


A is for Atomicity

Atomicity ensures that a transaction is treated as a single, indivisible "atom" of work. All of the operations within the transaction either succeed, or none of them do. There is no in-between state.

ACID Properties in Databases With Examples

This short video from ByteByteGo gives a very clear illustration of the 'all-or-nothing' principle using a classic bank transfer example.

Please watch from 00:13 to 01:02 to see how atomicity prevents data inconsistencies if an operation fails midway through a transaction.

The importance of atomicity becomes clear when you contrast it with how a simple program might interact with files on a file system.

Extending ACID Semantics to the File System

This research paper, 'Extending ACID Semantics to the File System,' provides an excellent discussion that connects directly to your interest in low-level systems. We'll read a small part that highlights why atomicity is not a given in file systems.

Please read the paragraph titled Atomicity on the first page. Note the example of the Sendmail application and how a failed append operation can leave a file in a corrupted, partially-written state.

As the paper describes, without the transactional guarantee of atomicity, an application developer is responsible for writing complex error-handling code to manually clean up messes. A database transaction handles this automatically: if the system crashes during the bank transfer, the database's recovery process will see the incomplete transaction and roll it back entirely, ensuring no money is magically created or destroyed.


C is for Consistency

Consistency ensures that a transaction can only bring the database from one valid state to another. A transaction will not violate any of the database's integrity constraints, such as data types, NOT NULL constraints, foreign keys, or unique keys.

The database enforces these rules. For example:

  • If you try to insert text into an integer column, the transaction will fail.
  • If you try to create an order for a customer ID that doesn't exist, the transaction will fail (violating a foreign key constraint).
  • If a rule states that a bank account balance cannot be negative, a transaction that attempts to withdraw too much money will be blocked.

ACID Properties in Databases With Examples

Let's return to the ByteByteGo video for a concise explanation of consistency.

Watch from 00:52 to 01:33. The key takeaway is that consistency is about enforcing the rules you've defined for your data.

While atomicity is about the "all or nothing" nature of a transaction's operations, consistency is about the correctness of the data state before and after the transaction completes. An atomic transaction that violates a rule will be rolled back, thus preserving consistency.


I is for Isolation

Isolation is arguably the most complex property. It ensures that concurrent transactions (multiple transactions running at the same time) do not interfere with each other. From the perspective of any single transaction, it appears as if it is the only transaction running on the system.

Imagine two users trying to book the last seat on a flight simultaneously. Isolation prevents them from both seeing the seat as available and both successfully booking it. The DBMS manages this by, in effect, making one transaction wait until the other is finished.

ACID Properties in Databases With Examples

The ByteByteGo video also provides a great introduction to isolation and the problems it solves.

Watch from 01:33 to 02:22. This section introduces the concept and a key problem it solves: 'dirty reads.' We will explore the other anomalies and isolation levels in a future lesson, so focus on the main idea for now.

Your background in systems programming provides a perfect context for a classic security problem that isolation solves: the Time-of-Check-to-Time-of-Use (TOCTOU) bug.

Extending ACID Semantics to the File System

Let's read the section on Isolation from the file system research paper. It presents the TOCTOU problem, which is a fantastic real-world example of why isolation is critical.

Please read the paragraph titled Isolation on the second page. Focus on the example of a program checking for file permissions.

Without isolation, a malicious program could swap a safe file with a sensitive one (like /etc/passwd) in the tiny window of time after a privileged program checks permissions but before it opens the file. A database transaction that wraps the check and the open operation in an isolated transaction makes such a race condition impossible.


D is for Durability

Durability is the simplest property to understand, but one of the most important. It guarantees that once a transaction has been committed, its changes are permanent and will survive any subsequent system failure, such as a power outage or crash.

If you get a "Transaction successful" message from your bank's ATM, durability ensures that record is safe, even if the power to the entire bank goes out a millisecond later.

How is this possible? Databases don't immediately overwrite the main data files on disk. Instead, they use a technique called Write-Ahead Logging (WAL).

  1. Before making any change to the database, the change is first written to a log file on permanent storage (like an SSD or hard drive). This is a fast, sequential write.
  2. Only after the log entry is safely on disk is the COMMIT acknowledged as successful.
  3. Later, at an opportune time, the system applies these logged changes to the main database files.
Database Transaction Initiation with Write-Ahead Log (WAL)
This image illustrates the first step of a transaction using a Write-Ahead Log. The 'BEGIN' operation is first recorded in the WAL buffer in memory, which will then be flushed to the persistent log on disk before any changes are made to the main database tables. This ensures recovery is possible after a crash.

If the system crashes, the DBMS can scan this log upon restart, see the committed transaction in the log, and re-apply the changes to the database files if they weren't already, thus ensuring durability.

Test your understanding!

A social media application has a "follow" button. When User A clicks to follow User B, two things must happen in the database:

  1. User A's following_count in the users table is incremented by 1.
  2. User B's followers_count in the users table is incremented by 1.

Explain how each of the four ACID properties applies to making this "follow" operation reliable.

Show answer
  • Atomicity: Both UPDATE statements (incrementing the two counts) must succeed together. If the first one works but the second fails (e.g., due to a brief network blip), atomicity ensures the first update is rolled back. This prevents a state where User A is following one more person, but User B doesn't have a new follower. It's all or nothing.

  • Consistency: The transaction maintains the database's integrity. For example, if there's a constraint that followers_count cannot be negative, the database will enforce this. More subtly, it ensures the database transitions from one valid state (correct counts before the follow) to another (correct counts after the follow).

  • Isolation: If two different users try to follow User B at the exact same moment, isolation ensures these two transactions don't interfere. Without it, they might both read the same initial followers_count, both increment it by one, and both write back the same new value, causing one of the follows to be "lost." Isolation ensures the final count is correctly incremented by two.

  • Durability: Once the transaction to update both counts is committed, the new following_count and followers_count are permanent. Even if the server crashes immediately after, the change will not be lost. The database will recover the transaction from its log and ensure the counts are correct.


Conclusion

In this lesson, we established the critical importance of transactions for reliable data management. The ACID properties are not just abstract theory; they are the contractual guarantee a DBMS provides to ensure your data remains safe and correct, even under heavy use and in the face of system failures.

Key Takeaways:

  • A transaction is a single, logical unit of work that can be committed (saved) or rolled back (undone).
  • Atomicity ensures transactions are "all or nothing."
  • Consistency ensures transactions adhere to all database rules and constraints.
  • Isolation ensures concurrent transactions do not interfere with one another.
  • Durability guarantees that committed changes are permanent and survive crashes.
  • These properties are a primary differentiator that makes a DBMS far more robust for data management than a standard file system.

Preview of the Next Lesson:
Now that we understand the theory behind transactions, our next step is to learn how to control them in practice. In the next lesson, we will cover the SQL commands used to manage transaction boundaries explicitly: BEGIN, COMMIT, and ROLLBACK.