MiniLake is een lokale emulator die de Databricks API nabootst, waardoor ontwikkelaars lokaal kunnen werken met tools zoals de databricks-sdk, Terraform en Asset Bundles zonder afhankelijk te zijn van cloud-accounts of budgetten.
Kernfunctionaliteiten:
- Echte uitvoering: In tegenstelling tot simpele mock-servers voert MiniLake SQL uit op DuckDB en draait het echte Spark-jobs in Docker-containers.
- Delta Lake & Unity Catalog: Ondersteunt echte Delta-bestanden (Parquet) en biedt volledige CRUD-functionaliteit voor catalogs, schema's en tabellen.
- Naadloze compatibiliteit: Werkt als een drop-in vervanging voor bestaande Databricks-clients; enkel de host-URL hoeft te worden gewijzigd.
- LLM-ondersteuning: Bevat een MCP-server met 67 tools, speciaal ontworpen om AI-agents veilig en kosteloos interactie te laten hebben met een lakehouse.
- Air-gapped design: De image is volledig self-contained en vereist geen internetverbinding tijdens runtime.
Belangrijkste beperkingen:
Het systeem is specifiek ontworpen voor individuele lokale ontwikkeling. Het biedt daarom geen authenticatie, geen toegangscontrole (permissions) en maakt gebruik van het DuckDB-dialect in plaats van Spark SQL voor statements.
MiniLake: De Databricks API op je eigen laptop
Installatie
Je kunt MiniLake installeren via pip:
pip install minilake && minilake --port 8000
Of draaien via Docker:
docker run -p 8000:8000 ghcr.io/dmux/minilake:latest
Na de installatie kun je de ingebouwde SQL-workspace openen via http://localhost:8000/ui/. De image downloadt tijdens runtime niets, waardoor het ook in air-gapped omgevingen werkt.
Drop-in vervanging voor:
- databricks-sdk (Python)
- Databricks CLI
- Terraform provider
- Asset Bundles
- PySpark + Delta
- MCP agents
Kerncijfers:
- 30+ geëmuleerde Databricks API-groepen, van Unity Catalog tot SCIM.
- 67 MCP-tools voor LLM-agents, geserveerd op dezelfde poort.
- 378+ tests aangedreven door de echte Databricks SDK (geen mocks).
- $0 cloud-uitgaven — alles draait op je eigen machine.
Wat MiniLake biedt
MiniLake is geen eenvoudige mock-server, maar een echte engine achter een API die is vormgegeven naar Databricks. Waar fake endpoints vaak foutieve code laten passeren, voert MiniLake SQL uit op DuckDB, schrijft echte Delta-bestanden en draait echte spark-submit jobs in containers. Een geslaagde lokale test is hierdoor daadwerkelijk representatief.
Unity Catalog voor het echt
Catalogs, schema's, tabellen en volumes met volledige CRUD-functionaliteit. Elke catalog is een eigen DuckDB-databasebestand, waardoor de adressering via catalog.schema.table native is en niet via een regex-rewrite gebeurt.
Echte uitvoering
- SQL die echt werkt: Statement-uitvoering op DuckDB met INLINE en EXTERNALLINKS dispositions, JSONARRAY / ARROW_STREAM / CSV-formaten en een resultaatmanifest met correcte kolomtypes.
- Echte Delta Lake-bestanden: EXTERNAL Delta-tabellen zijn genuine Parquet-bestanden inclusief een
deltalog/. INSERT, UPDATE en DELETE verlopen via een echte Spark-job; leesacties gaan via DuckDB's delta_scan().
- Jobs die echt worden uitgevoerd:
sparkpythontask voert spark-submit uit in een sibling container en retourneert de werkelijke stdout. Echte DAG-scheduling respecteert dependson en runif, waarbij onafhankelijke branches parallel lopen.
- Unity Catalog protocol voor Spark:
spark.table("cat.sch.tbl") wordt via de officiële UCSingleCatalog connector opgelost tegen MiniLake — hetzelfde protocol dat Spark gebruikt voor een echte workspace.
Naadloze compatibiliteit
- Ingebouwde SQL-workspace: Een Athena-stijl editor op
/ui met Monaco (inclusief catalog-aware completion), een gevirtualiseerd resultaatgrid, grafieken, CSV/JSON-export, opgeslagen queries, query-historie en een embedded JupyterLab.
- Terraform & Asset Bundles: Richt de databricks provider op localhost en
terraform apply creëert echte catalogs. Dit is geverifieerd in elke testrun: de echte provider wordt aangestuurd via apply, plan en destroy. Ook databricks bundle deploy en bundle run werken end-to-end.
- MCP-server voor agents: 67 tools, 8 resources en 4 prompts beschikbaar op
/mcp — inclusief composites die een sequentie van vijf calls samenvoegen tot één, en een SQL-dialect resource die voorkomt dat agents Spark SQL schrijven.
- Ontworpen voor CI: Eén
POST /_minilake/reset geeft elke test een schone workspace zonder de container te herstarten. De control plane wordt compleet gemaakt door /health, /ready en /services.
- Workspace, DBFS, Files, Secrets: Bestandsgebaseerde notebook- en bestandopslag met chunked uploads. Secrets hebben echte CRUD-functionaliteit, maar de waarden zijn alleen oplosbaar binnen de omgeving van een job, precies zoals bij Databricks.
- Air-gapped design: DuckDB's delta-extensie en de Delta / Unity Catalog jars zijn tijdens de build-tijd ingebakken. De image downloadt niets tijdens runtime, wat bewezen kan worden met
docker run --network none.
- Databricks-stijl foutmeldingen: Fouten worden teruggegeven als
{"errorcode", "message"}, zodat de SDK de normale typed exceptions kan raising. Alles wat buiten scope valt, geeft een duidelijke 501 NOTIMPLEMENTED terug in plaats van een overtuigende leugen.
Geen codeaanpassingen nodig
De migratie naar MiniLake bestaat enkel uit het wijzigen van de host. Omdat MiniLake de Databricks REST API op wire-niveau spreekt, blijven alle bestaande clients werken met dezelfde calls, response shapes en typed errors.
- Authenticatie: Elk token wordt geaccepteerd. Geen aanmelding, geen PAT, geen OAuth-proces nodig.
- Type-mapping: STRING, LONG, DECIMAL(10,2), ARRAY\<T>, MAP en STRUCT mappen naar DuckDB en keren terug als de
ColumnInfo van de SDK.
- Fysieke waarheid: Verklaarde kolomtypes die afwijken van de bestanden verliezen; mismatches zijn dus zichtbaar in plaats van dat ze worden aangenomen.
- Persistentie: Met
MINILAKE_PERSIST=1 wordt de status bij afsluiten gesnapped en bij opstarten hersteld.
Codevoorbeelden
Python SDK
from databricks.sdk import WorkspaceClient
from databricks.sdk.service.catalog import ColumnInfo, TableType
# De enige regel die afwijkt van productie
w = WorkspaceClient(host="http://localhost:8000", token="dev")
w.catalogs.create(name="sales")
w.schemas.create(name="store", catalog_name="sales")
w.tables.create(
name="orders", catalog_name="sales", schema_name="store",
table_type=TableType.MANAGED,
data_source_format="DELTA", storage_location="/data/sales/store/orders",
columns=[
ColumnInfo(name="id", type_text="BIGINT"),
ColumnInfo(name="customer", type_text="STRING"),
ColumnInfo(name="amount", type_text="DECIMAL(10,2)"),
],
)
wh = w.warehouses.create(name="dev", cluster_size="Small")
w.statement_execution.execute_statement(
warehouse_id=wh.id,
statement="INSERT INTO sales.store.orders VALUES (1, 'Ana', 459.90)",
)
result = w.statement_execution.execute_statement(
warehouse_id=wh.id,
statement="SELECT customer, amount FROM sales.store.orders",
)
print(result.result.data_array) # [['Ana', '459.90']] — echt opgeslagen
Spark & Delta
from pyspark.sql import SparkSession
UC = "http://localhost:8000"
spark = (
SparkSession.builder
.config("spark.sql.extensions", "io.delta.sql.DeltaSparkSessionExtension")
# Unity Catalog connector — three-part names resolve tegen MiniLake
.config("spark.sql.catalog.spark_catalog", "io.unitycatalog.spark.UCSingleCatalog")
.config("spark.sql.catalog.spark_catalog.uri", UC)
.config("spark.sql.catalog.sales", "io.unitycatalog.spark.UCSingleCatalog")
.config("spark.sql.catalog.sales.uri", UC)
.getOrCreate()
)
# Echte Delta-bestanden: parquet + _delta_log/, geschreven door echte Spark
spark.createDataFrame([(1, "a"), (2, "b")], ["id", "name"]) \
.write.format("delta").mode("overwrite").save("/data/delta/sales/store/events")
spark.sql("INSERT INTO sales.store.events VALUES (3, 'c')")
print(spark.table("sales.store.events").count()) # 3
Terraform
provider "databricks" {
host = "http://localhost:8000"
token = "dev"
}
resource "databricks_catalog" "sandbox" {
name = "sandbox"
comment = "Local sandbox catalog"
}
resource "databricks_schema" "things" {
catalog_name = databricks_catalog.sandbox.name
name = "things"
}
resource "databricks_sql_endpoint" "compute" {
name = "local-compute"
cluster_size = "Small"
}
# terraform apply -> creëert echte catalogs en echte DuckDB databases
# terraform destroy -> verwijdert deze
Asset Bundles
bundle:
name: my_pipeline
targets:
dev:
mode: development
workspace:
host: http://localhost:8000
resources:
jobs:
daily_load:
name: daily_load
tasks:
- task_key: main
spark_python_task:
python_file: ../src/load.py
# $ databricks bundle deploy -t dev
# $ databricks bundle run daily_load -t dev
Curl
# Check of de service up is
curl http://localhost:8000/_minilake/health
# Catalog aanmaken via de API
curl -X POST http://localhost:8000/api/2.1/unity-catalog/catalogs \
-H 'Content-Type: application/json' \
-d '{"name": "sales"}'
# SQL uitvoeren en rijen terugkrijgen
curl -X POST http://localhost:8000/api/2.0/sql/statements \
-H 'Content-Type: application/json' \
-d '{"warehouse_id": "dev", "statement": "SELECT 42 AS answer"}'
# Workspace opschonen voor de volgende test
curl -X POST http://localhost:8000/_minilake/reset
Hoe het werkt
MiniLake bestaat uit één proces op één poort met echte engines eronder. Een FastAPI-applicatie dient de Databricks REST-interface, de web-UI en het MCP-endpoint. Daarachter bevinden zich DuckDB, echte Delta-bestanden op schijf en Docker voor Spark.
De architectuur:
- Clients: (SDK, CLI, Terraform, PySpark, LLM-agents, Browser)
- MiniLake (FastAPI): Beheert de REST-surface, SQL-workspace en MCP-tools.
- Real Engines:
- DuckDB: Eén databasebestand per catalog.
- Delta Lake on disk: Parquet +
deltalog/.
- Docker → Apache Spark:
spark-submit in sibling containers.
Spark schrijft de bestanden — DuckDB leest exact dezelfde bytes.
Voor LLM-agents
MiniLake biedt agents een lakehouse dat ze niet kunnen slopen. Een normale Databricks workspace is lastig aan te sturen voor een agent: acties vereisen vaak vier calls, de SQL-dialecten kloppen vaak niet en fouten zijn soms stil. De MCP-server van MiniLake lost dit op zonder kosten bij fouten.
Beschikbare tools voor agents:
setup_fixture(): Catalog, schema en warehouse in één idempotente call.
seed_table(): Tabel inclusief exact de gevraagde rijen.
describecatalogtree(): De volledige hiërarchie in één keer, in plaats van tientallen calls.
runpythonscript(): Stage, submit naar echte Spark, poll en retourneer stdout.
Daarnaast zijn er 8 resources (waaronder een SQL-dialect gids om te voorkomen dat agents Spark SQL schrijven naar DuckDB) en 4 prompts die de regels vooraf definiëren.
Configuratie voor Claude Code:
claude mcp add --transport http minilake http://localhost:8000/mcp
Overzicht van Ondersteuning (Coverage)
Elke functionaliteit wordt ofwel echt uitgevoerd, of duidelijk gelabeld. Alles buiten scope geeft een 501 NOT_IMPLEMENTED terug.
| Service | Status | Betekenis |
| Unity Catalog | Real | Catalogs, schema's, tabellen, volumes, functies — elke catalog is een eigen DuckDB database. |
| UC grants | Unenforced CRUD | Met echte inheritie, maar privileges worden niet gecontroleerd. |
| UC functions | Real | SQL-functies worden echte DuckDB-macro's. |
| SQL statements | Real | Uitgevoerd op DuckDB; alle drie de formaten en beide dispositions. |
| EXTERNAL Delta tables | Real | Echte Delta-bestanden; writes via Spark-job, reads via delta_scan(). |
| Jobs | Real | spark-submit in sibling containers, echte DAG-scheduling en logs. |
| SQL warehouses | Real | Volledige CRUD en lifecycle; statements draaien ongeacht de status. |
| Query history & saved queries | Real | Server-backed, inclusief fouten. |
| Alerts | Real | Condities worden geëvalueerd tegen echte query-resultaten. |
| Workspace, DBFS & Files | Real | Bestandsgebaseerde opslag met chunked upload. |
| Secrets | Real | Echte CRUD; waarden alleen oplosbaar binnen job environment variables. |
| Web UI & notebooks | Real | Athena-stijl SQL-workspace op /ui en JupyterLab op /jupyter. |
| MCP server | Real | Opt-in via MINILAKE_MCP=1: 67 tools, 8 resources, 4 prompts. |
| Persistence | Real | MINILAKE_PERSIST=1 snapshot state als JSON bij afsluiten. |
| Clusters | State machine | CRUD plus timed lifecycle transitions; geen Spark compute (dit zit in Jobs). |
| Policies & instance pools | Unenforced CRUD | Validatie werkt zodat bundles deployen, maar er is geen compute om te beperken. |
| Permissions | Allow-all CRUD | Echte create/read/update, maar niets wordt afgedwongen. |
| Workspace admin | Unenforced CRUD | Git credentials, IP lists, etc. — wat een terraform apply aanraakt. |
| Identity & SCIM | Unenforced CRUD | Gebruikers, groepen en service principals; records, geen credentials. |
| Tokens | Unenforced CRUD | Waarde komt één keer terug, maar authenticeert niets. |
| Legacy SQL (preview/sql) | Real | Queries, alerts en dashboards via adapters over de moderne stores. |
| DLT, Model Registry, etc. | Not implemented | Retourneert 501 NOT_IMPLEMENTED. |
Beperkingen en Ontwerpopzetten (Straight Talk)
MiniLake is specifiek ontworpen voor één ontwikkelaar die lokaal werkt, niet als een shared, multi-tenant server.
- Geen authenticatie: Elk token wordt geaccepteerd en er is slechts één gebruiker. Stel dit nooit bloot buiten localhost.
- Geen toegangscontrole: De Permissions API is real CRUD die altijd alles toestaat. Een geslaagde test hier zegt niets over grants in een echte workspace.
- DuckDB, geen Spark SQL: Statements draaien op het dialect van DuckDB. Hiervoor is een dialect-resource in de MCP-server opgenomen.
- Geen Spark op clusters: De cluster-lifecycle is een state machine. Echte Spark-executie vindt plaats via Jobs in sibling containers.
- Single process, geen HA: DuckDB is single-writer, dus gelijktijdige load wordt geserialiseerd via een lock. Geschikt voor dev en CI, niet als deployment target.
- MANAGED tables zijn onzichtbaar voor Spark: Dit zijn DuckDB-tabellen zonder bestanden. Gebruik EXTERNAL Delta wanneer Spark de data moet kunnen zien.
MiniLake: De Databricks API op je eigen laptop
Installatie
Je kunt MiniLake installeren via pip:
pip install minilake && minilake --port 8000
Of draaien via Docker:
docker run -p 8000:8000 ghcr.io/dmux/minilake:latest
Na de installatie kun je de ingebouwde SQL-workspace openen via http://localhost:8000/ui/. De image downloadt tijdens runtime niets, waardoor het ook in air-gapped omgevingen werkt.
Drop-in vervanging voor:
- databricks-sdk (Python)
- Databricks CLI
- Terraform provider
- Asset Bundles
- PySpark + Delta
- MCP agents
Kerncijfers:
- 30+ geëmuleerde Databricks API-groepen, van Unity Catalog tot SCIM.
- 67 MCP-tools voor LLM-agents, geserveerd op dezelfde poort.
- 378+ tests aangedreven door de echte Databricks SDK (geen mocks).
- $0 cloud-uitgaven — alles draait op je eigen machine.
Wat MiniLake biedt
MiniLake is geen eenvoudige mock-server, maar een echte engine achter een API die is vormgegeven naar Databricks. Waar fake endpoints vaak foutieve code laten passeren, voert MiniLake SQL uit op DuckDB, schrijft echte Delta-bestanden en draait echte spark-submit jobs in containers. Een geslaagde lokale test is hierdoor daadwerkelijk representatief.
Unity Catalog voor het echt
Catalogs, schema's, tabellen en volumes met volledige CRUD-functionaliteit. Elke catalog is een eigen DuckDB-databasebestand, waardoor de adressering via catalog.schema.table native is en niet via een regex-rewrite gebeurt.
Echte uitvoering
- SQL die echt werkt: Statement-uitvoering op DuckDB met INLINE en EXTERNALLINKS dispositions, JSONARRAY / ARROW_STREAM / CSV-formaten en een resultaatmanifest met correcte kolomtypes.
- Echte Delta Lake-bestanden: EXTERNAL Delta-tabellen zijn genuine Parquet-bestanden inclusief een
deltalog/. INSERT, UPDATE en DELETE verlopen via een echte Spark-job; leesacties gaan via DuckDB's delta_scan().
- Jobs die echt worden uitgevoerd:
sparkpythontask voert spark-submit uit in een sibling container en retourneert de werkelijke stdout. Echte DAG-scheduling respecteert dependson en runif, waarbij onafhankelijke branches parallel lopen.
- Unity Catalog protocol voor Spark:
spark.table("cat.sch.tbl") wordt via de officiële UCSingleCatalog connector opgelost tegen MiniLake — hetzelfde protocol dat Spark gebruikt voor een echte workspace.
Naadloze compatibiliteit
- Ingebouwde SQL-workspace: Een Athena-stijl editor op
/ui met Monaco (inclusief catalog-aware completion), een gevirtualiseerd resultaatgrid, grafieken, CSV/JSON-export, opgeslagen queries, query-historie en een embedded JupyterLab.
- Terraform & Asset Bundles: Richt de databricks provider op localhost en
terraform apply creëert echte catalogs. Dit is geverifieerd in elke testrun: de echte provider wordt aangestuurd via apply, plan en destroy. Ook databricks bundle deploy en bundle run werken end-to-end.
- MCP-server voor agents: 67 tools, 8 resources en 4 prompts beschikbaar op
/mcp — inclusief composites die een sequentie van vijf calls samenvoegen tot één, en een SQL-dialect resource die voorkomt dat agents Spark SQL schrijven.
- Ontworpen voor CI: Eén
POST /_minilake/reset geeft elke test een schone workspace zonder de container te herstarten. De control plane wordt compleet gemaakt door /health, /ready en /services.
- Workspace, DBFS, Files, Secrets: Bestandsgebaseerde notebook- en bestandopslag met chunked uploads. Secrets hebben echte CRUD-functionaliteit, maar de waarden zijn alleen oplosbaar binnen de omgeving van een job, precies zoals bij Databricks.
- Air-gapped design: DuckDB's delta-extensie en de Delta / Unity Catalog jars zijn tijdens de build-tijd ingebakken. De image downloadt niets tijdens runtime, wat bewezen kan worden met
docker run --network none.
- Databricks-stijl foutmeldingen: Fouten worden teruggegeven als
{"errorcode", "message"}, zodat de SDK de normale typed exceptions kan raising. Alles wat buiten scope valt, geeft een duidelijke 501 NOTIMPLEMENTED terug in plaats van een overtuigende leugen.
Geen codeaanpassingen nodig
De migratie naar MiniLake bestaat enkel uit het wijzigen van de host. Omdat MiniLake de Databricks REST API op wire-niveau spreekt, blijven alle bestaande clients werken met dezelfde calls, response shapes en typed errors.
- Authenticatie: Elk token wordt geaccepteerd. Geen aanmelding, geen PAT, geen OAuth-proces nodig.
- Type-mapping: STRING, LONG, DECIMAL(10,2), ARRAY\<T>, MAP en STRUCT mappen naar DuckDB en keren terug als de
ColumnInfo van de SDK.
- Fysieke waarheid: Verklaarde kolomtypes die afwijken van de bestanden verliezen; mismatches zijn dus zichtbaar in plaats van dat ze worden aangenomen.
- Persistentie: Met
MINILAKE_PERSIST=1 wordt de status bij afsluiten gesnapped en bij opstarten hersteld.
Codevoorbeelden
Python SDK
from databricks.sdk import WorkspaceClient
from databricks.sdk.service.catalog import ColumnInfo, TableType
# De enige regel die afwijkt van productie
w = WorkspaceClient(host="http://localhost:8000", token="dev")
w.catalogs.create(name="sales")
w.schemas.create(name="store", catalog_name="sales")
w.tables.create(
name="orders", catalog_name="sales", schema_name="store",
table_type=TableType.MANAGED,
data_source_format="DELTA", storage_location="/data/sales/store/orders",
columns=[
ColumnInfo(name="id", type_text="BIGINT"),
ColumnInfo(name="customer", type_text="STRING"),
ColumnInfo(name="amount", type_text="DECIMAL(10,2)"),
],
)
wh = w.warehouses.create(name="dev", cluster_size="Small")
w.statement_execution.execute_statement(
warehouse_id=wh.id,
statement="INSERT INTO sales.store.orders VALUES (1, 'Ana', 459.90)",
)
result = w.statement_execution.execute_statement(
warehouse_id=wh.id,
statement="SELECT customer, amount FROM sales.store.orders",
)
print(result.result.data_array) # [['Ana', '459.90']] — echt opgeslagen
Spark & Delta
from pyspark.sql import SparkSession
UC = "http://localhost:8000"
spark = (
SparkSession.builder
.config("spark.sql.extensions", "io.delta.sql.DeltaSparkSessionExtension")
# Unity Catalog connector — three-part names resolve tegen MiniLake
.config("spark.sql.catalog.spark_catalog", "io.unitycatalog.spark.UCSingleCatalog")
.config("spark.sql.catalog.spark_catalog.uri", UC)
.config("spark.sql.catalog.sales", "io.unitycatalog.spark.UCSingleCatalog")
.config("spark.sql.catalog.sales.uri", UC)
.getOrCreate()
)
# Echte Delta-bestanden: parquet + _delta_log/, geschreven door echte Spark
spark.createDataFrame([(1, "a"), (2, "b")], ["id", "name"]) \
.write.format("delta").mode("overwrite").save("/data/delta/sales/store/events")
spark.sql("INSERT INTO sales.store.events VALUES (3, 'c')")
print(spark.table("sales.store.events").count()) # 3
Terraform
provider "databricks" {
host = "http://localhost:8000"
token = "dev"
}
resource "databricks_catalog" "sandbox" {
name = "sandbox"
comment = "Local sandbox catalog"
}
resource "databricks_schema" "things" {
catalog_name = databricks_catalog.sandbox.name
name = "things"
}
resource "databricks_sql_endpoint" "compute" {
name = "local-compute"
cluster_size = "Small"
}
# terraform apply -> creëert echte catalogs en echte DuckDB databases
# terraform destroy -> verwijdert deze
Asset Bundles
bundle:
name: my_pipeline
targets:
dev:
mode: development
workspace:
host: http://localhost:8000
resources:
jobs:
daily_load:
name: daily_load
tasks:
- task_key: main
spark_python_task:
python_file: ../src/load.py
# $ databricks bundle deploy -t dev
# $ databricks bundle run daily_load -t dev
Curl
# Check of de service up is
curl http://localhost:8000/_minilake/health
# Catalog aanmaken via de API
curl -X POST http://localhost:8000/api/2.1/unity-catalog/catalogs \
-H 'Content-Type: application/json' \
-d '{"name": "sales"}'
# SQL uitvoeren en rijen terugkrijgen
curl -X POST http://localhost:8000/api/2.0/sql/statements \
-H 'Content-Type: application/json' \
-d '{"warehouse_id": "dev", "statement": "SELECT 42 AS answer"}'
# Workspace opschonen voor de volgende test
curl -X POST http://localhost:8000/_minilake/reset
Hoe het werkt
MiniLake bestaat uit één proces op één poort met echte engines eronder. Een FastAPI-applicatie dient de Databricks REST-interface, de web-UI en het MCP-endpoint. Daarachter bevinden zich DuckDB, echte Delta-bestanden op schijf en Docker voor Spark.
De architectuur:
- Clients: (SDK, CLI, Terraform, PySpark, LLM-agents, Browser)
- MiniLake (FastAPI): Beheert de REST-surface, SQL-workspace en MCP-tools.
- Real Engines:
- DuckDB: Eén databasebestand per catalog.
- Delta Lake on disk: Parquet +
deltalog/.
- Docker → Apache Spark:
spark-submit in sibling containers.
Spark schrijft de bestanden — DuckDB leest exact dezelfde bytes.
Voor LLM-agents
MiniLake biedt agents een lakehouse dat ze niet kunnen slopen. Een normale Databricks workspace is lastig aan te sturen voor een agent: acties vereisen vaak vier calls, de SQL-dialecten kloppen vaak niet en fouten zijn soms stil. De MCP-server van MiniLake lost dit op zonder kosten bij fouten.
Beschikbare tools voor agents:
setup_fixture(): Catalog, schema en warehouse in één idempotente call.
seed_table(): Tabel inclusief exact de gevraagde rijen.
describecatalogtree(): De volledige hiërarchie in één keer, in plaats van tientallen calls.
runpythonscript(): Stage, submit naar echte Spark, poll en retourneer stdout.
Daarnaast zijn er 8 resources (waaronder een SQL-dialect gids om te voorkomen dat agents Spark SQL schrijven naar DuckDB) en 4 prompts die de regels vooraf definiëren.
Configuratie voor Claude Code:
claude mcp add --transport http minilake http://localhost:8000/mcp
Overzicht van Ondersteuning (Coverage)
Elke functionaliteit wordt ofwel echt uitgevoerd, of duidelijk gelabeld. Alles buiten scope geeft een 501 NOT_IMPLEMENTED terug.
| Service | Status | Betekenis |
| Unity Catalog | Real | Catalogs, schema's, tabellen, volumes, functies — elke catalog is een eigen DuckDB database. |
| UC grants | Unenforced CRUD | Met echte inheritie, maar privileges worden niet gecontroleerd. |
| UC functions | Real | SQL-functies worden echte DuckDB-macro's. |
| SQL statements | Real | Uitgevoerd op DuckDB; alle drie de formaten en beide dispositions. |
| EXTERNAL Delta tables | Real | Echte Delta-bestanden; writes via Spark-job, reads via delta_scan(). |
| Jobs | Real | spark-submit in sibling containers, echte DAG-scheduling en logs. |
| SQL warehouses | Real | Volledige CRUD en lifecycle; statements draaien ongeacht de status. |
| Query history & saved queries | Real | Server-backed, inclusief fouten. |
| Alerts | Real | Condities worden geëvalueerd tegen echte query-resultaten. |
| Workspace, DBFS & Files | Real | Bestandsgebaseerde opslag met chunked upload. |
| Secrets | Real | Echte CRUD; waarden alleen oplosbaar binnen job environment variables. |
| Web UI & notebooks | Real | Athena-stijl SQL-workspace op /ui en JupyterLab op /jupyter. |
| MCP server | Real | Opt-in via MINILAKE_MCP=1: 67 tools, 8 resources, 4 prompts. |
| Persistence | Real | MINILAKE_PERSIST=1 snapshot state als JSON bij afsluiten. |
| Clusters | State machine | CRUD plus timed lifecycle transitions; geen Spark compute (dit zit in Jobs). |
| Policies & instance pools | Unenforced CRUD | Validatie werkt zodat bundles deployen, maar er is geen compute om te beperken. |
| Permissions | Allow-all CRUD | Echte create/read/update, maar niets wordt afgedwongen. |
| Workspace admin | Unenforced CRUD | Git credentials, IP lists, etc. — wat een terraform apply aanraakt. |
| Identity & SCIM | Unenforced CRUD | Gebruikers, groepen en service principals; records, geen credentials. |
| Tokens | Unenforced CRUD | Waarde komt één keer terug, maar authenticeert niets. |
| Legacy SQL (preview/sql) | Real | Queries, alerts en dashboards via adapters over de moderne stores. |
| DLT, Model Registry, etc. | Not implemented | Retourneert 501 NOT_IMPLEMENTED. |
Beperkingen en Ontwerpopzetten (Straight Talk)
MiniLake is specifiek ontworpen voor één ontwikkelaar die lokaal werkt, niet als een shared, multi-tenant server.
- Geen authenticatie: Elk token wordt geaccepteerd en er is slechts één gebruiker. Stel dit nooit bloot buiten localhost.
- Geen toegangscontrole: De Permissions API is real CRUD die altijd alles toestaat. Een geslaagde test hier zegt niets over grants in een echte workspace.
- DuckDB, geen Spark SQL: Statements draaien op het dialect van DuckDB. Hiervoor is een dialect-resource in de MCP-server opgenomen.
- Geen Spark op clusters: De cluster-lifecycle is een state machine. Echte Spark-executie vindt plaats via Jobs in sibling containers.
- Single process, geen HA: DuckDB is single-writer, dus gelijktijdige load wordt geserialiseerd via een lock. Geschikt voor dev en CI, niet als deployment target.
- MANAGED tables zijn onzichtbaar voor Spark: Dit zijn DuckDB-tabellen zonder bestanden. Gebruik EXTERNAL Delta wanneer Spark de data moet kunnen zien.