This content originally appeared on DEV Community and was authored by Sajjad Rahman
The Power of Transactions & ACID . Before a Data Engineer can design reliable data systems or move petabytes through ETL pipelines, one question always echoes:
How does a database keep data accurate and safe — even when hundreds of things happen at the same time?
The answer lies in transactions and the ACID properties — the unshakable pillars that make relational databases like PostgreSQL so reliable.
What Is a Transaction?
A transaction is a sequence of one or more database operations (INSERT, UPDATE, DELETE, etc.) that act as a single logical unit of work.
Rule: A transaction must fully succeed or fully fail — there’s no halfway.
Think of it as a sealed envelope — you either deliver it completely or destroy it; you never send half a letter.
Why It Matters
Without transactions, systems would constantly fall into inconsistent states:
Money deducted from one account but never credited to another.
Inventory reduced but the order never created.
User deleted but their related records still exist elsewhere.
Transactions keep your system trustworthy and predictable.
Example: Money Transfer Scenario
You send 1000 BDT to your friend:
1⃣ Your balance decreases by 1000.
2⃣ Your friend’s balance increases by 1000.
If step 1 succeeds but step 2 fails → inconsistent state (you lose money).
A transaction ensures:
Either both succeed, or
both roll back (cancelled)
That’s Atomicity in action — all or nothing.
Transaction Lifecycle in PostgreSQL
Every transaction goes through five predictable stages:
Stage | Description | Example |
---|---|---|
Active | Transaction is running; statements executing. | You start transferring money. |
Partially Committed | All commands run but not yet saved. | Balance reduced, waiting to finalize. |
Committed | Changes are permanently stored. | Both accounts updated successfully. |
Failed | An error occurred before commit. | Network error or insufficient funds. |
Terminated | Transaction ends (success or rollback). | Process closed. |
This lifecycle guarantees data safety even under heavy system load.
ACID — The Pillars of Reliable Databases
What Is ACID?
ACID stands for Atomicity, Consistency, Isolation, and Durability —
four principles that make transactions predictable, recoverable, and safe.
Let’s break them down
A — Atomicity (All or Nothing)
Concept | Explanation |
---|---|
Meaning | Treat every transaction as a single unit — it either completes fully or doesn’t happen at all. |
Why It Matters | Prevents partial changes that corrupt data. |
Example | Debit from A, credit to B. If credit fails, debit is rolled back. |
Under the Hood | Databases use logs and checkpoints to undo incomplete transactions. |
No half-done operations.
C — Consistency (Follow the Rules)
Concept | Explanation |
---|---|
Meaning | The database must always move from one valid state to another. |
Why It Matters | Ensures that rules, constraints, and relationships stay true. |
Example | Age can’t be negative. Email must be unique. Foreign keys must match. |
Under the Hood | Constraints are verified before commit; invalid data = rollback. |
Data always obeys the rules.
I — Isolation (Don’t Disturb Others)
Concept | Explanation |
---|---|
Meaning | Each transaction behaves as if it’s running alone. |
Why It Matters | Prevents interference between concurrent users. |
Example | Two people buy the last item — isolation ensures only one succeeds. |
Under the Hood | Controlled through isolation levels: Read Uncommitted → Serializable. Higher isolation = more safety (and more cost). |
Transactions run independently — like private sessions.
D — Durability (It Stays Forever)
Concept | Explanation |
---|---|
Meaning | Once committed, data is safe — even after a crash or restart. |
Why It Matters | Guarantees persistence of committed changes. |
Example | PostgreSQL’s Write-Ahead Log (WAL) ensures recovery after system failure. |
Under the Hood | Uses logs, checkpoints, and replication to preserve data. |
Committed = permanent.
Why ACID Matters
Without ACID, your database becomes chaos in disguise:
Data could vanish midway through a transaction.
Tables might drift into inconsistent states.
Queries could return half-truths or outdated values.
Under heavy load, transactions might overwrite or corrupt each other.
ACID transforms chaos into order.
It’s what allows banks, hospitals, and analytics systems to trust every single bit of data.
Remember: every failed constraint or rejected transaction isn’t a problem — it’s your database defending its integrity. When a rule fails, Consistency and Atomicity are doing their job.
Consistency Models — Immediate vs Eventual
Model | Definition | Example Use Case | Explanation |
---|---|---|---|
Immediate Consistency | Once committed, all users instantly see the new data. | ![]() |
After sending 1000 BDT, your friend’s balance updates immediately. |
Eventual Consistency | Temporary differences allowed across replicas; all copies sync eventually. | ![]() |
Post a photo — visible to some users right away, others after sync delay. |
Choose the model that fits your workload:
- Need accuracy + safety → Immediate Consistency
- Need speed + scalability → Eventual Consistency
Read Anomalies — When Isolation Breaks Down
When multiple transactions run at once, weak isolation can cause strange behavior:
Phenomenon | Definition | Scenario | Explanation |
---|---|---|---|
Dirty Read | Reading uncommitted data from another transaction. | You see your friend’s new balance before they commit. | May show rolled-back data. PostgreSQL prevents this. |
Non-Repeatable Read | Same query returns different results within one transaction. | You read 1000 BDT → another updates to 2000 BDT → you re-read → 2000. | Value changed mid-transaction. |
Phantom Read | Re-running a query returns a different number of rows. | You count 5 orders → another adds 1 → you count again → 6. | New rows appeared during your transaction. |
Higher isolation reduces anomalies — at the cost of speed.
Transaction Isolation Levels (PostgreSQL)
Level | Prevents | Allows | Best For |
---|---|---|---|
Read Uncommitted | Nothing | Dirty reads | ![]() |
Read Committed (Default) | Dirty reads | Non-repeatable & phantom reads | General workloads — balanced choice. |
Repeatable Read | Dirty + Non-repeatable reads | Phantom reads | Analytical queries, consistent snapshots. |
Serializable | All anomalies | None | ![]() |
Banking Scenario Example
Two users withdraw from the same account (1000 BDT):
BEGIN TRANSACTION ISOLATION LEVEL SERIALIZABLE;
UPDATE accounts SET balance = balance - 1000 WHERE id = 1;
COMMIT;
-
Read Committed: both might withdraw — race condition
-
Serializable: only one withdrawal succeeds
Quick Recap
Concept | Safe? | Speed | Ideal Use Case |
---|---|---|---|
Immediate Consistency | ![]() |
![]() |
Banking, inventory |
Eventual Consistency | ![]() |
![]() |
Social media, caching |
Serializable | ![]() |
![]() |
Finance, critical data |
Read Committed | ![]() |
![]() |
Default workloads |
Visual Summary — From Transactions to Reliable Systems
🧠 START → Understanding Reliable Databases
↓
📦 Transaction
• Group of operations acting as one (e.g., money transfer)
↓
⚖ ACID Properties — Ensure Reliability
├── 🔸 Atomicity → All or none succeed
├── 🔸 Consistency → Database remains valid
├── 🔸 Isolation → Independent transactions
└── 🔸 Durability → Data stays permanent
↓
🔍 Concurrency & Anomalies
├── Dirty Read → Read uncommitted data
├── Non-Repeatable Read → Changing results
└── Phantom Read → Changing row counts
↓
🧱 Isolation Levels (PostgreSQL)
├── Read Committed → Default, safe & fast
├── Repeatable Read → Consistent snapshots
└── Serializable → Full protection
↓
🏦 Consistency Models (Distributed)
├── Immediate Consistency → Banking
└── Eventual Consistency → Social apps
↓
🧩 Choose Wisely
├── Accuracy → Immediate + Serializable
└── Scale → Eventual + Read Committed
↓
🎯 END → Reliable, Scalable & Consistent Data Systems
Let’s Connect!
If you found this guide helpful, I’d love to hear from you!
Follow or reach out to me on social media
GitHub – Check out my projects & experiments
LinkedIn – Let’s grow our dev network
YouTube – Watch tutorials & dev tips
X (Twitter) – Follow for quick updates & threads
Feel free to comment, share, or drop a question — I’d love to connect with fellow learners and builders!
This content originally appeared on DEV Community and was authored by Sajjad Rahman