Executive summary

Operational databases hold the current state of a business. Databricks's lakehouse, the Delta tables, materialized views, and SQL warehouses that Lakeflow pipelines build and serve, is well suited to historical analysis, large scans, backfills, feature engineering, training data, and other workloads that can tolerate delay.

Agents need something different when they are making operational decisions: current business objects they can retrieve quickly and combine without seeing contradictory versions of the underlying data.

This paper calls those business objects "context products." A context product turns raw operational records into a maintained representation of something an agent needs to understand, such as a customer, account, order, shipment, or approval state. It may depend on one source table or many, across databases and systems. What matters is the business object it presents and the fact that it stays current as source data changes.

Databricks can build and serve context products, and it offers more than one way to do each. A materialized view runs its defining query on a serverless pipeline, on a schedule, on a source-update trigger with a one-minute minimum interval, or inside a continuous pipeline at a trigger interval that defaults to one minute, and writes the result to Delta storage. Agents then read that result through a SQL warehouse, or through a copy that a second pipeline syncs into Lakebase, Databricks's managed Postgres, at a minimum interval of fifteen seconds. Each stage is a separate pipeline with its own schedule, its own compute, and its own view of when "now" is.

Materialize maintains context products on one tier and serves them from another, but the tiers share one logical timeline and the transformation is continuous. It ingests the same operational change streams from PostgreSQL (including Lakebase), MySQL, SQL Server, and Kafka, updates each context product on a transform cluster as changes arrive, and serves indexed reads from dedicated serving clusters, with every read at one consistent logical timestamp. It exposes those context products to agents directly through a built-in MCP server or plain SQL, keeps external search and vector indexes current by pushing precise deltas through its sinks, can push changes to agents, and can write finished context products to Unity Catalog as Iceberg tables so operational and historical workloads share one definition.

info

The main reasons to use Materialize for an agent context layer are freshness, consistency, scalable reads, and proactive updates. Operational changes become readable in about a second; every context product in a query is returned at the same logical timestamp; indexed reads scale to thousands per second while the underlying data changes, with no per-query charge; and agents can subscribe to changes rather than poll for them.

What is a context product?

A context product is a queryable business object derived from operational data and kept current as that data changes. For example, an account context product might combine the account record with open invoices, recent support activity, and current entitlements. An order context product might combine order state, inventory, payment status, and shipment events. An agent can retrieve one of these objects directly or combine several in a transaction.

A useful context product may come from a single table or from a much larger graph of joins, filters, aggregates, and window functions. The relevant considerations are end-to-end context latency, from a source commit to the moment an agent can read the result; whether related context products agree when the agent reads them; and what resources are required to serve many concurrent agents.

What a context layer is made of

A context layer has two parts. The first is the ontology, or knowledge graph: which objects exist, what they mean, how they join, which one is authoritative. An agent uses this to choose the right tool or write the right query. The second is the objects themselves: the maintained customer, order, or account record the agent actually reads. Databricks and Materialize both provide both parts. They differ in how each part is produced and in how tightly the two are bound together.

Ontology on Databricks. Genie Ontology, in public preview, is "the unified context layer that gives the Genie family of AI experiences a business-aware map of your organization." It combines modeled context (Unity Catalog metric views, domains, and Pages) with inferred context extracted from dashboards, SQL queries, and Genie usage. Databricks's managed MCP servers, also in public preview, expose Genie, Unity Catalog functions, an AI search server, and a Databricks SQL executor to agents. Databricks's documentation recommends the Genie path for analytics: "Genie resolves business terms through Genie Ontology, your governed semantic layer, which produces more accurate answers than an agent writing SQL directly." In both cases the agent's question becomes SQL against tables at query time.

Ontology on Materialize. The ontology pattern in the Materialize documentation is a curated table of join relationships. "Each row describes a single join: the columns in one table that reference columns in another," and an agent queries it through the MCP server's query tool before writing multi-table SQL. Above that sits the semantic-layer layout that the mz-ontology-design agent skill encodes: a shared raw database, a shared core database whose core.public schema is the documented ontology and the only core schema consumers may read, and one database per use case, with core.public.relationships as the relationship registry and COMMENT ON as the documentation contract. Those comments are what the MCP server surfaces to the agent as tool descriptions, and the columns of a view's index are surfaced as its preferred lookup keys.

Objects on Databricks. A materialized view refreshed on a schedule, then, for low-latency reads, copied into Lakebase by a second pipeline on a second schedule.

Objects on Materialize. An incrementally maintained view on a transform cluster, indexed on a serving cluster, updated as source changes arrive.

The practical difference is the freshness of the ontology's underlying context. On Databricks the ontology points at tables that were last refreshed at some earlier moment, and its purpose is to help an agent generate better SQL against them. On Materialize the ontology points directly to live context.

How the two systems maintain and serve live context

Question
Databricks
Materialize
How is context maintained
A materialized view is refreshed by a serverless Lakeflow pipeline, on a cron schedule or at a trigger interval in a continuous pipeline.
A materialized view is incrementally updated on a transform cluster and persisted to durable storage.
How is context served
A SQL warehouse reads the view, or a synced-table pipeline copies it into Lakebase Postgres and the agent reads the copy.
A dedicated serving cluster holds indexes on the materialized view and answers reads from memory.
What drives compute
The cadence of every stage: ingestion pipeline, refresh pipeline, sync pipeline, plus warehouse or Lakebase capacity.
The rate of source changes and the state held on the transform cluster, plus index size and read concurrency on the serving cluster.
What is the minimum refresh target
One minute: the minimum interval for TRIGGER ON UPDATE and the default trigger interval for complete queries in a continuous pipeline. Fifteen-second minimum on the Lakebase sync.
No scheduled refresh floor. Updates flow as source changes arrive.
What aligns data at read time
Each table is read at its own latest version. A Lakebase transaction is consistent over copies that were synced independently.
Every query reads all referenced products at one logical timestamp.

Building a context product on Databricks

There is no single Databricks component that maintains and serves a context product. The path from an operational commit to an agent's read is a chain of stages, each configured, scheduled, and billed on its own.

Ingestion

Lakeflow Connect provides managed CDC connectors for PostgreSQL, MySQL, SQL Server, and Oracle. The connector has two halves. An ingestion gateway "runs on classic compute, and it runs continuously to capture changes before change logs can be truncated in the source." An ingestion pipeline runs on serverless compute and applies the staged changes to Delta tables on its own schedule. Because the gateway never stops, "you provision and pay for its classic compute even when your ingestion pipeline is idle." A pipeline handles at most 250 tables.

How often the pipeline applies changes is the customer's choice, within limits. "There is no limit on how often you can schedule the ingestion pipeline to run. However, Databricks recommends at least 5 minutes between intervals because it takes some time for the serverless compute to start up." For PostgreSQL and SQL Server, "Databricks does not support running the ingestion pipeline in continuous mode"; only the gateway runs continuously. A newer integrated CDC pipeline, in Beta for SQL Server, MySQL, and Oracle and not available for PostgreSQL, can run continuously on always-on compute and applies changes "typically within a few minutes" in its speed-optimized mode, which is limited to 50 tables.

The materialized view

The context product itself is a materialized view. "Materialized views automatically create and use serverless pipelines to process refresh operations"; a SQL warehouse only coordinates. There are two ways to drive the refresh.

The first is a schedule or trigger on the view. SCHEDULE EVERY accepts only hours, days, and weeks. SCHEDULE CRON accepts a six-field expression with a seconds field. TRIGGER ON UPDATE "automatically refreshes a pipeline when upstream source data changes," throttled with AT MOST EVERY, and "the minimum trigger interval is 1 minute." Each firing is a serverless pipeline update that pays its own startup and planning overhead; "serverless workloads using standard performance mode typically start within four to six minutes after being triggered," and performance-optimized mode starts faster at a higher DBU rate.

The second is to define the view inside a continuous Lakeflow pipeline. "Continuous pipelines require an always-running cluster, which is more expensive but reduces processing latency." The pipelines.trigger.interval property controls how often a table is refreshed; its default is "five seconds for streaming queries" and "one minute for complete queries when all input data is from Delta sources." A materialized view is a complete query. The documentation positions continuous mode for "data updates desired between every 10 seconds and a few minutes."

Whether a refresh is incremental depends on the query and the platform. "Incremental refresh is only available when the compute you are connected to is serverless." Source tables need row tracking enabled, and change data feed is recommended. Joins, filters, GROUP BY, window functions with PARTITION BY, and CTEs can be incrementalized. Recursive CTEs, most non-deterministic functions, and SUM or AVG over floating-point columns fall back to a full recompute; Databricks recommends casting to DECIMAL. A cost model chooses between incremental and full refresh on each run unless a REFRESH POLICY overrides it.

Serving

Once the view exists, the customer chooses how agents read it.

A serverless SQL warehouse reads the view directly. Databricks suggests "a cluster for every 10 concurrent queries," with intelligent workload management adding clusters as queues form and a queue limit of 1,000. The warehouse auto-stops after ten minutes by default; the floor is five minutes in the UI and one minute through the API. This path has the fewest hops, but it puts a query planner and an analytical execution engine between the agent and a point lookup.

A Lakebase synced table copies the view into Postgres. Lakebase is "a fully managed Postgres database integrated into the Databricks platform," positioned "as an online feature store for ML models, or as a state store for agents." Synced tables "use managed Lakeflow pipelines to continuously update both the Unity Catalog synced table and the Postgres table with changes from the source table." The sync runs in one of three modes:

Mode
Databricks description
When Databricks recommends it
Performance note
Snapshot
"One-time copy of all data"
"Source changes >10% of rows per cycle"
"10x more efficient if modifying >10% of source data"
Triggered
"Scheduled updates that run on demand or at intervals"
"Source rows change on a known cadence"
"Good cost/lag balance. Expensive if run <5min intervals"
Continuous
"Real-time streaming with seconds of latency"
"Changes must appear in Lakebase in near real time"
"Lowest lag, highest cost. Minimum 15-second intervals"

Triggered and continuous modes require change data feed on the source. The sync writes at "approximately 150 rows per second per Capacity Unit (CU)" in continuous and triggered modes. A source table can feed up to 20 synced tables, and "each synced table uses up to 16 connections to your Lakebase database." The synced table needs a primary key; rows with null key columns are excluded, and duplicate keys fail the pipeline unless deduplication is configured. Only additive schema changes propagate. And "Databricks strictly recommends running only read queries" against a synced table.

note

Real-Time Mode for Structured Streaming, which Databricks documents at "end-to-end latency as low as five milliseconds," is not a path for context products. Its reference lists Delta as unsupported both as a source and as a sink, it does not run on serverless compute, and forEachBatch is unsupported. It is a stream processor beside the lakehouse, reading from and writing to Kafka, Kinesis, and Event Hubs.

Serving in Materialize

In Materialize, the context product is an incrementally updated materialized view. The recommended production layout uses three tiers of clusters. Source clusters ingest operational change streams from PostgreSQL, MySQL, SQL Server, and Kafka. Transform clusters maintain the materialized views and persist their results to durable storage. Serving clusters hold indexes on those views and answer reads from memory. A single cluster can do all three, but production deployments generally separate serving so that a heavy query or a rehydrating view cannot affect agent reads, and so that each tier scales independently. Unlike the Databricks chain, the tiers share one logical timeline: a read on the serving cluster sees exactly the state the transform cluster has produced, and the transformation runs continuously rather than on a refresh schedule.

Transform clusters are sized for the incoming change rate and the amount of maintained state. Serving clusters are sized for the indexes they hold and the read concurrency they absorb. Indexed reads do not add a per-query compute charge, so increasing the number of readers does not change the bill until the serving cluster needs to grow. In customer deployments, indexed serving clusters have handled thousands of reads per second while the underlying data changes, with tail latencies under 20 milliseconds on index reads.

Agents reach these context products without a custom API layer. Starting in v26.24, Materialize includes a built-in materialize-agent MCP server, in public preview, that runs inside the database. Its get_data_products tool lists materialized views and indexed views; get_data_product_details returns each one's JSON schema, column descriptions, and comments; read_data_product fetches rows; and an optional query tool runs arbitrary SELECT statements against objects the agent role can see. "Comments are surfaced to the agent to help it better understand when and how to use the data products," and when a view is indexed, "the indexed columns are surfaced to the agent as preferred lookup keys, enabling index point-lookups instead of index scans." Materialize recommends a dedicated cluster and schema for agent traffic, a functional role such as mcp_agent with USAGE on only that cluster and schema, and SELECT on only the curated data products, so agent reads are isolated from other workloads and from operational metadata.

The metadata an agent needs to compose products is part of the same layer. The ontology table documents join relationships, and the mz-ontology-design skill (installed with npx skills add MaterializeInc/agent-skills) gives a coding agent the rules for the raw, core, and use-case layering, the admission test for a public semantic object, the grain of entities, events, measurements, and relationship objects, and the COMMENT ON contract that becomes the MCP tool description.

info

Search and vector indexes as context. A search document or an embedding input is itself a context product: a view over the fields an agent will retrieve by, maintained incrementally as the records change. Materialize pushes precise deltas from that view to Elasticsearch and OpenSearch through a Kafka sink and Kafka Connect, and to turbopuffer through mz-tpuf-sink, so that "only the affected documents are rewritten" and embedding transforms run "only for the documents whose source columns actually changed, so embedding costs scale with what changed." On Databricks, a Delta Sync Index in AI Search follows a Delta source table; its continuous mode "keeps the index in sync with seconds of latency" on a dedicated always-on cluster, requires change data feed, and is standard-endpoint only. The index is as fresh as the lakehouse copy of the source, one more stage downstream of the refresh chain.

Serving comparison

The table compares the serving tier each system would use for agent reads: a Lakebase synced table on Databricks, since it is the path Databricks documents for low-latency application reads, and an indexed serving cluster on Materialize.

Dimension
Databricks: Lakebase synced table
Materialize: indexed serving cluster
Read scalability while data changes
Postgres point reads with indexes, read replicas, and autoscaling compute. The copy is fed by a sync pipeline at roughly 150 rows per second per CU, so write throughput into the serving tier, not read throughput, is the first thing to size.
Indexes are updated in memory as changes arrive, so a read after a change is served from the same index at the same latency. Customer deployments serve thousands of indexed reads per second while the data changes, with tail latencies under 20 ms.
Correctness at read time
A Postgres transaction is consistent over what has been synced. Each synced table has its own pipeline, so two context products can reflect different lakehouse versions inside one transaction. Nothing tells the agent how old the copy is.
Every query, and every read-only transaction, sees all context products at one logical timestamp. Bounded staleness returns an error instead of a result when the requested bound cannot be met.
Freshness of what is served
The last completed sync of the last completed refresh of the last completed ingestion run: at least the trigger interval plus fifteen seconds behind the lakehouse, and further behind the source.
About one second behind the source commit at the default timestamp interval, which can be lowered.
Cost of reads
Lakebase compute, billed in capacity-unit hours under the Database Serverless Compute SKU, plus the sync: "Databricks deploys a serverless Lakeflow Spark Declarative Pipeline in the background. You will be charged for the DBUs used by the pipeline." In continuous mode that pipeline never stops. Plus the refresh pipeline that feeds it.
A fixed hourly cluster with no per-query charge. Readers do not add to the transform cluster's bill. Flat until the serving cluster needs to grow.
Query flexibility
Full Postgres SQL over the synced copies, read-only. Anything not synced requires a warehouse query against the lakehouse, at lakehouse freshness.
Any SQL, with no time limit imposed by the serving tier. Indexed lookups by key are the fast path; an ad hoc join across context products runs as a one-shot dataflow at lower throughput. Long-running queries can be isolated on their own cluster.
Governance
Unity Catalog row filters and column masks are policy objects on the lakehouse tables; Postgres grants govern the synced copies.
Row-level and column-level access through RBAC, entitlement tables, and views. This is currently a documented pattern rather than a policy object.

Where the customer skips Lakebase and reads the materialized view from a serverless SQL warehouse, the freshness row improves by the sync interval and the correctness row gets worse: each table in a query is read at its own latest Delta version, with no transaction around them, and the read itself goes through query planning and an analytical executor sized in units of roughly ten concurrent queries per cluster.

End-to-end context latency

End-to-end context latency starts when the operational database commits a change. Both systems must ingest that change, update the relevant context product, and serve the result. The difference is the number of stages, the floor at each one, and what happens when a stage cannot meet its target.

Stage
Databricks
Materialize
Commit to raw data
Lakeflow Connect gateway captures the change continuously on classic compute; a serverless ingestion pipeline applies it to Delta on its schedule, with a recommended minimum of five minutes between runs and no continuous mode for PostgreSQL or SQL Server. The Beta integrated pipeline for SQL Server, MySQL, and Oracle applies changes "typically within a few minutes."
Native sources for PostgreSQL, MySQL, SQL Server, and Kafka read the upstream change stream continuously and assign each change a timestamp at the source's timestamp interval, one second by default and adjustable. There is no separate ingestion schedule or always-on gateway to provision.
Raw data to context product
Materialized view refresh on a serverless pipeline. One-minute default trigger interval for complete queries in a continuous pipeline; continuous mode positioned for updates every ten seconds to a few minutes. A refresh must finish before the next begins, and a full recompute takes as long as it takes.
Incremental view maintenance updates the materialized view as changes arrive. There is no refresh cycle to wait on and no distinction between a partial and a complete run; the view's freshness tracks the source's timestamp interval rather than a separate schedule.
Context product to serving store
Lakebase synced table, continuous mode: "seconds of latency," fifteen-second minimum interval, at roughly 150 rows per second per CU. (Skipped when reading from a warehouse.)
None. The serving cluster's index is the maintained view.
Serving store to agent
A Postgres read on Lakebase, or a warehouse query against the view.
An indexed read on the serving cluster. The index keeps the view's results in memory and updates them incrementally as changes arrive, so a point lookup by key returns the current result directly from memory instead of recomputing or scanning the underlying data.

In Databricks's best case, with the gateway running, the ingestion pipeline on its shortest practical schedule, the refresh pipeline in continuous mode at a short trigger interval, and the sync in continuous mode, end-to-end latency is several minutes, most of it in the ingestion stage, and every component is billing around the clock. A production configuration where each stage is tuned for cost lands at five to fifteen minutes. In Materialize, end-to-end context latency is about a second at the default one-second source timestamp interval, and that interval can be lowered.

note

An important distinction is enforceability. No stage in the Databricks chain can refuse to serve data that is older than the agent needs. A refresh that ran late still writes a valid Delta version; a sync that fell behind still leaves a readable Postgres row; a warehouse query against either returns a result with no indication of its age. Materialize can enforce a bounded-staleness requirement at query time through its bounded staleness isolation level. It returns data from a timestamp within the requested bound, never blocks waiting for inputs to catch up, and returns a serialization error if the bound cannot be met. The agent can then avoid acting on data of unknown age.

Read consistency across context products

Databricks and Materialize take different approaches to consistency, and the choice determines whether the context an agent assembles describes a single state of the business.

Delta Lake provides snapshot isolation for a single table: "Readers continue to see a consistent snapshot view of the table that the Databricks job started with, even when a table is modified during a job." The unit of that guarantee is the table. A query that joins two materialized views reads each at its own latest committed version, and if their refreshes finished at different moments, the query joins two different points in time. Within a single Lakeflow pipeline update, the tables in that pipeline are computed from inputs read at the start of the update, which aligns them with each other; the guarantee ends when the update does, and it never covered a view maintained by a different pipeline or a different team.

Multi-statement transactions extend the guarantee to several statements but keep the per-table unit: "When you access a table in a transaction, Databricks captures a consistent snapshot of that table at first access." Two tables first touched at different points in the transaction are snapshotted at different moments. Transactions are limited to Unity Catalog managed tables with catalog commits, which became generally available in May 2026, up to 100 tables, on Databricks Runtime 18.0 and above or a SQL warehouse; transactions on managed Iceberg tables are in private preview.

In Lakebase, a Postgres transaction is consistent over the synced tables it reads. But each synced table is maintained by its own pipeline, and nothing coordinates two of them. Two context products can be at different lakehouse versions, and the lakehouse versions themselves came from refreshes that finished at different times. The agent gets a consistent read of copies whose relative age is unknown.

Materialize assigns logical time as changes enter the system and preserves that time through computation. A query that reads several context products sees all of them at one timestamp. This remains true across isolation levels; the isolation choice changes the tradeoff between recency and latency, not whether the query is internally consistent.

Requirement
Databricks
Materialize
Products agree at read time
Only within one Lakeflow pipeline update. An agent query across independently refreshed views, or across independently synced Lakebase tables, has no equivalent guarantee.
Yes. Every query uses one logical timestamp across all referenced products.
Products agree across team boundaries
A view built by another pipeline is read at whatever version it last committed.
Independent streams share one logical timeline.
Staleness requirement
A refresh schedule and a sync interval to monitor after the fact.
A query-time contract. The query errors if the bound cannot be met.
Read after an upstream write
The write becomes visible after ingestion, refresh, and sync, which can take minutes.
Strict serializable isolation stays within seconds of wall-clock time. Real-time recency, a private preview option on strict serializable sessions that adds latency, guarantees the next read includes everything the upstream source had committed when the query arrived.
Behavior when the system is behind
Serves the last successful version at every stage while lag accumulates.
Depends on the isolation level the application chooses. Strict serializable waits for the required timestamp, bounded staleness rejects the read, and serializable serves the latest consistent state.
note

Materialize defaults to strict serializable isolation and recommends starting there. Use serializable isolation for latency-sensitive agent tool calls that do not need to wait for an update into Materialize to be reflected in the agent's context. When the next read must reflect the agent's own upstream write, enable real-time recency, currently in private preview, on a strict serializable session. When the application would rather fail than wait, use bounded staleness.

Writes and the read-after-write loop

Agents write. They open cases, reserve inventory, adjust balances, and then read context to decide what to do next. Where those writes land, and how quickly they come back around as context, shapes what kinds of agents a platform can support.

On Databricks, the write target for agent state is Lakebase. Databricks positions it "as a state store for agents," and it is a full Postgres, so the write itself is immediate. Getting that write back into a context product is not trivial. Lakebase Change Data Feed, in public preview, captures every insert, update, and delete from the write-ahead log into a Unity Catalog Delta history table, "batched and flushed every ~15 seconds"; the materialized view that depends on it refreshes at its trigger interval, no sooner than a minute; the synced table that serves it copies the new version back to Lakebase at the sync interval, no sooner than fifteen seconds. An agent that writes to Lakebase and then reads a context product from Lakebase is reading a copy that has not yet heard about its own write, for two minutes or more.

Lakebase is also closed to outside readers at the replication level. Its compatibility page states that "replicating data to or from a Lakebase database using native Postgres logical replication is not yet available," so the change data feed into Delta is the only way out.

Materialize does not take agent writes; it reads them from wherever they land. Native sources exist for PostgreSQL, MySQL, SQL Server, and Kafka, so an agent writing to any of those operational stores sees the change in its context products within about a second, in the same logical timeline as every other product, and under strict serializable isolation with real-time recency the next read is guaranteed to include it. The practical rule is to keep agent state in a store the context layer can read. Where that store is Postgres, MySQL, or SQL Server, Materialize reads it directly.

Push-based agents

Some agent architectures avoid polling to minimize reaction time and save tokens spent asking the same question multiple times. A change in the business, such as a payment failing or an order shipping, should wake the agent, and the agent should then read the rest of its context as of the same moment. That asks two things of the context layer: a way to deliver changes as they happen, and a way to tell the consumer when what it has received is complete.

Databricks has no primitive by which a client subscribes to a changing query result. The available paths are a Structured Streaming job reading a Delta table's change data feed, which delivers insert, update_preimage, update_postimage, and delete rows per commit but runs as a Spark job the customer keeps alive and cannot span a non-additive schema change; a Lakeflow job with a table-update trigger, which "checks for table updates, and when a table is updated, the job is run," watching up to ten tables, with settings for a minimum time between triggers and a wait after the last change but no documented detection latency; or a SQL alert that runs a query on a warehouse on a schedule set in minutes, hours, days, or weeks. Real-Time Mode, the lowest-latency streaming path Databricks offers, cannot read from or write to Delta, so it cannot emit changes from a context product. End to end, a push consumer learns of an operational change after ingestion, the refresh interval, and whichever trigger or poll interval it uses.

Materialize delivers changes with SUBSCRIBE, which streams inserts and deletes to a view, materialized view, source, or ad hoc query over the PostgreSQL wire protocol. Each update carries a logical timestamp, and progress messages report when a timestamp is complete, so a consumer can act on a consistent frontier and distinguish a quiet period from a stall. For many consumers, a Kafka sink emits the same changes with an upsert or Debezium envelope and exactly-once delivery by default.

tip

The Materialize MCP server is a pull interface today, so a push-driven agent is fed by a SUBSCRIBE consumer or a Kafka sink rather than by the MCP endpoint. Each subscription is its own dataflow on the serving cluster, so a large number of direct subscribers is better served by one Kafka sink and ordinary consumers.

Why agent workloads raise the bar

  • Agents often write to an operational system and immediately read context to decide what to do next. A minute of lag can break that feedback loop and make it impossible to build interactive agents with humans in the loop.
  • Stale data can cause an incorrect action, not merely an outdated display. A delayed dashboard is inconvenient; a refund approved against an old account state can be wrong.
  • Agents combine several business objects at the moment of decision. Those objects need to describe the same point in time.
  • An explicit freshness failure lets the application pause, retry, or escalate. A successful query that silently returns old data does not.
  • Concurrency comes from many agents issuing small reads, rather than a smaller number of analysts running exploratory queries.
  • Prepared context products reduce tokens as well as database work. They replace wide raw payloads, repeated text-to-SQL attempts, and polling with a direct call that returns only the context the agent needs.
tip

The live context layer guide goes into more detail on how a live, trustworthy context layer improves agent cost, speed, and task success. We found 76.5% fewer input tokens, 33.8% faster task completion, and a task success rate of 96.1% against 83.6% for an agent assembling the same context from source APIs.

Which workloads belong in each system

Use Materialize when
Use Databricks when
Agents repeatedly retrieve the same business objects, such as a customer, account, order, or shipment.
A query is exploratory and needs to scan historical data.
A task combines several context products and requires them to agree at read time.
The workload is a backfill, a feature-engineering job, a model training set, an evaluation set, or another large batch.
The agent writes to PostgreSQL, MySQL, SQL Server, or Kafka and needs the next read to reflect that change.
The agent keeps its state in Lakebase and does not need that state reflected in context within seconds.
The application must know whether the result is fresh enough to support an action.
Minutes of staleness are acceptable and reads are infrequent.
The workload consists of many concurrent, short reads.
A human is exploring data with Genie.
A search or vector index must reflect operational changes as they happen.
The question is genuinely novel and no maintained business object already answers it.

A practical routing rule is to use Materialize for named, maintained context products and Databricks for novel analytical questions. If a context product already answers the question, the agent should call it instead of generating SQL against raw tables.

For Materialize reads that combine multiple products, define a composite context product or issue indexed reads inside one read-only transaction. The first statement in a read-only transaction fixes which schemas later statements can reference, so place products that agents read together in the same schema. An unindexed ad hoc join creates a one-time dataflow and has materially lower throughput.

A combined architecture

Materialize and Databricks can consume the same operational databases and Kafka change streams. Materialize maintains the current business objects used by agents and operational applications. Databricks retains history and serves analytical and training workloads. Rather than create two parallel pipelines, Materialize can deliver finished context products to Databricks. There are two paths:

  • A native Iceberg sink writes exactly-once updates to Iceberg tables registered in Databricks Unity Catalog on AWS, or in Amazon S3 Tables. Each change carries _mz_timestamp and _mz_diff, so Databricks can reconstruct current state or keep the full change history.
  • A bulk export to Amazon S3 with COPY TO can be loaded on a schedule.

Either allows batch scoring, feature engineering, and historical analysis to use the same definitions as the live agent path.

The architecture runs the other way too. Where agents keep their state in a Postgres (including Lakebase), MySQL, or SQL Server database, Materialize ingests it directly, so the agent's own writes join its context products within seconds. Databricks keeps the history; Materialize keeps the live objects; neither definition is written twice. Lakebase can hold agent state in this design, with the caveat that until it exposes logical replication, state written there reaches context only through the Databricks chain.

This design avoids maintaining separate transformation logic for live and historical systems. It also removes the sync pipeline between the lakehouse and a serving copy, because the serving tier reads the maintained object directly. Both systems remain active, but they are active for different reasons: Materialize is sized for the rate of change and maintained state, while Databricks runs the pipelines and warehouses required to refresh and serve its copies.

The cost of serving fresh context

Databricks and Materialize charge for different parts of a context pipeline.

For a context layer that must stay within tens of seconds of the source on Databricks, the following components are running and billing continuously:

  • The Lakeflow Connect ingestion gateway, on classic compute, which runs whether or not the ingestion pipeline is.
  • The ingestion pipeline, on serverless, at whatever interval keeps bronze current.
  • The refresh pipeline for the materialized views, in continuous mode with an always-running cluster, or firing on a per-minute cron with per-run overhead.
  • The synced-table pipeline into Lakebase, in continuous mode.
  • Lakebase compute, billed in capacity-unit hours under the Database Serverless Compute SKU, sized first for sync write throughput at roughly 150 rows per second per CU and then for reads, with read replicas as needed. An instance whose scale-to-zero has been off for more than 24 hours is billed as Always-on at a lower baseline rate; one serving agents around the clock will be. Storage bills separately in Databricks Storage Units at 15 DSUs per GB-month.
  • Or, in place of the last two, a serverless SQL warehouse that agent traffic keeps from auto-stopping, adding clusters in steps of roughly ten concurrent queries.

Materialize's cost changes when source change volume or maintained state requires a larger transform cluster, or when read concurrency requires a larger serving cluster, not per query and not per stage. There is no sync pipeline because there is no serving copy, and there is no per-refresh overhead because there is no refresh.

For the same interactive workload Materialize is typically less expensive, but the architectural differences in freshness and consistency matter more.

Conclusion

Databricks can maintain and serve agent context, particularly when a team values platform consolidation, already keeps its history in the lakehouse, and can tolerate a minute or more between an operational change and the moment an agent can read its consequences. Lakebase is the right Databricks serving option for short, concurrent reads, and it is a capable state store for the agent's own writes.

Materialize is the stronger fit when an agent needs context that reflects operational changes within seconds, when several business objects must agree at the moment they are read, when the application must reject data that is too stale to support an action, or when search and vector indexes must track the business as it changes. A combined architecture lets Materialize serve that live context, reading from the same operational stores the agents write to, while Databricks remains the system for history, training, exploration, and large-scale analytical work.