DuckDB-powered SQL executor for local AWS Athena and Firehose emulation
10K+
Any Cloud. Locally.
A lightweight DuckDB-powered SQL executor sidecar for Floci
floci-duck is the query engine behind Floci's Athena and Cost and Usage Reports support. It exposes a small HTTP interface that executes SQL through DuckDB, with S3-compatible storage wired in via the httpfs extension.
Written in Rust for minimal overhead. It is a sidecar, not a standalone emulator: Floci talks to it, you normally do not.
| Component | Role | Port |
|---|---|---|
| floci | AWS runtime | 4566 |
| floci-duck | DuckDB executor sidecar | 3000 |
The bundled docker-compose.yml brings up both Floci and floci-duck:
docker compose up --build
The executor is available at http://localhost:3000.
cargo build --release
./target/release/floci-duck
On startup floci-duck runs a preflight check that installs the httpfs DuckDB extension to local disk, so every later request loads it instantly with no network download. If preflight fails, for example on a first boot with no network, a warning is logged and the extension installs on the first request that needs it.
| Mode | Endpoint | Behavior |
|---|---|---|
| S3 Select | POST /query | Runs a query and returns rows as JSON |
| Firehose | POST /execute | Runs any SQL directly: DDL, DML, COPY, and so on |
| Athena | POST /execute with output_s3_path | Wraps the SQL in COPY … TO … FORMAT CSV and writes results to S3 |
Parquet, CSV, and JSON are read and written directly from and to S3.
GET /healthReturns 200 OK with body OK.
POST /queryExecutes a query and returns the result rows.
| Field | Type | Description |
|---|---|---|
sql | String | The SQL query to execute |
s3_endpoint | String | S3-compatible endpoint, for example http://floci:4566 |
s3_region | String, optional | Defaults to FLOCI_DUCK_S3_REGION or us-east-1 |
s3_access_key | String, optional | S3 access key ID |
s3_secret_key | String, optional | S3 secret access key |
s3_use_ssl | Boolean, optional | Auto-detected from the endpoint scheme if omitted |
s3_url_style | String, optional | path or vhost. Default path |
setup_sql | String, optional | SQL run before the main query, in the same session: views, temp tables, extensions |
{
"status": "success",
"rows": [
{ "id": 1, "name": "Alice", "amount": 99.5 }
]
}
On error, status is "error", message carries the details, and rows is omitted.
POST /executeExecutes a statement with no row output. Takes the same S3 fields as /query, plus:
| Field | Type | Description |
|---|---|---|
output_s3_path | String, optional | Enables Athena mode: results are exported here as CSV |
variables | Map, optional | Key-value pairs substituted into the SQL as {{key}} placeholders |
{
"sql": "SELECT name, count(*) FROM users GROUP BY 1",
"s3_endpoint": "http://floci:4566",
"output_s3_path": "s3://results-bucket/report.csv"
}
S3 credentials in the request body are optional when the matching FLOCI_DUCK_S3_* environment variables are set.
| Variable | Default | Description |
|---|---|---|
FLOCI_DUCK_PORT | 3000 | Port the server listens on |
FLOCI_DUCK_LOG | info | Log level: error, warn, info, debug, trace |
FLOCI_DUCK_EXT_DIR | (DuckDB default) | Extension directory, useful in Docker to persist extensions across restarts |
FLOCI_DUCK_S3_REGION | us-east-1 | Default S3 region |
FLOCI_DUCK_S3_ACCESS_KEY | flociadmin | Default S3 access key ID |
FLOCI_DUCK_S3_SECRET_KEY | flociadmin | Default S3 secret access key |
FLOCI_DUCK_S3_USE_SSL | auto | Auto-detected from the endpoint scheme if unset |
FLOCI_DUCK_S3_URL_STYLE | path | path or vhost |
Every request carries a correlation ID, taken from the incoming x-correlation-id header or generated as a UUID v4. It is propagated through every log line for that request, including those emitted deep inside the executor, and appears as a bare value inside the span context.
curl -X POST http://localhost:3000/query \
-H "Content-Type: application/json" \
-H "x-correlation-id: my-trace-id-123" \
-d '{ "sql": "SELECT 1", "s3_endpoint": "http://floci:4566" }'
duck-test is the integration test CLI. It needs a running server plus jq and curl, and the aws CLI for the init, parquet, and validate suites.
make dev-infra # bring up infrastructure and create S3 resources
./duck-test all # run every suite
./duck-test health query
./duck-test parquet --bucket my-bucket
./duck-test all -v # print full JSON responses
| Suite | What it tests |
|---|---|
init | Creates the S3 bucket and lists resources |
health | Server liveness |
query | Basic SELECT, NULLs, numeric types, setup_sql, correlation ID, error handling |
execute | Firehose mode, Athena mode (CSV to S3), variable substitution |
parquet | Full S3 round-trip: write, SELECT, filter, aggregate, DESCRIBE |
http | httpfs loads and S3 settings are applied |
validate | Downloads the latest result file from S3 and prints it |
all | Every suite in order |
All options can be set as flags or environment variables (FLOCI_DUCK_URL, FLOCI_DUCK_S3_ENDPOINT, and so on).
MIT. Part of the Floci ecosystem.
Content type
Image
Digest
sha256:eadf68e49…
Size
17.6 MB
Last updated
4 months ago
docker pull floci/floci-duckPulls:
3,116
Last week