intermediate

Delta Lake

10 min readLast updated: 2026-07-08

Overview

Delta Lake is an open-source storage layer that brings ACID transactions and time travel history to Apache Spark workloads.

What You Will Learn

In this lesson, you will learn:
  • ACID Transactions: How Delta guarantees reliable transactions in distributed environments.
  • Time Travel: Restoring and querying historical versions of data.
  • Schema Enforcement: Preventing column structure corruption.

Detailed Concept Explanation

Delta Lake runs on top of your existing cloud storage bucket or HDFS directory. Under the hood, Delta stores your data in standard Parquet files, but adds a Transaction Log (the _delta_log directory containing JSON transaction files).

Key Features

  • ACID Transactions: Ensures data updates either succeed completely or fail with no partial writes.
  • Schema Enforcement: Prevents writing data with invalid schemas, protecting tables from column corruption.
  • Time Travel: The transaction log tracks changes, allowing you to query previous versions of your table (e.g. AS OF version or timestamp).

Code Examples

Input Dataset Preview

Below is the transactions dataset:

userIdaction
101signup

Python (PySpark) Implementation

python
from pyspark.sql import SparkSession

spark = SparkSession.builder \
    .appName("DeltaTest") \
    .config("spark.sql.extensions", "io.delta.sql.DeltaSparkSessionExtension") \
    .config("spark.sql.catalog.spark_catalog", "org.apache.spark.sql.delta.catalog.DeltaCatalog") \
    .getOrCreate()

data = [(101, "signup")]
df = spark.createDataFrame(data, ["userId", "action"])

# Write to Delta table format
df.write.format("delta").mode("overwrite").save("table.delta")

# Read from Delta table format
delta_df = spark.read.format("delta").load("table.delta")
delta_df.show()

Expected Output

text
+------+------+
|userId|action|
+------+------+
|   101|signup|
+------+------+

Execution Plan Diagram (Python & Scala)

Execution Plan Diagram
SparkSession.builder
createDataFrame
write.format(delta)
read.format(delta)
show()

Scala Implementation

scala
import org.apache.spark.sql.SparkSession

val spark = SparkSession.builder()
  .appName("DeltaScala")
  .config("spark.sql.extensions", "io.delta.sql.DeltaSparkSessionExtension")
  .config("spark.sql.catalog.spark_catalog", "org.apache.spark.sql.delta.catalog.DeltaCatalog")
  .getOrCreate()

import spark.implicits._
val df = Seq((101, "signup")).toDF("userId", "action")

df.write.format("delta").mode("overwrite").save("table.delta")

val deltaDF = spark.read.format("delta").load("table.delta")
deltaDF.show()

Expected Output

text
+------+------+
|userId|action|
+------+------+
|   101|signup|
+------+------+

SQL Implementation

sql
-- Query historical version of a Delta table
SELECT * 
FROM delta.`table.delta` VERSION AS OF 1;

Expected Output

Executing this SQL query returns:

userIdaction
101signup

Common Mistakes

  • Deleting Delta Log Directory: Deleting the _delta_log directory. Doing this turns the Delta table back into standard Parquet files, losing transaction history, time travel capabilities, and metadata indexes.

Best Practices

  • Optimize regularly: Regularly run the OPTIMIZE command on your Delta tables to compact small partition files into larger ones, speeding up downstream reads.

Interview Perspective

What is the role of the transaction log in Delta Lake?

The transaction log is a single source of truth. Every read and write transaction is recorded as an ordered sequence of JSON commit files inside the _delta_log directory. When reading, Spark reads this log first to determine the active list of Parquet files to scan, providing ACID transactions, time travel, and rollback capabilities.


Interactive Challenges

Challenge 1: Read Delta version (Beginner)

Which format string key do you pass to spark.read.format() to read a Delta Lake table?

Related Topics