Skip to content
WeftKitBeta

Security

WeftKit treats every operation as untrusted by default. The security model is enforced at the kernel level, not as an optional layer.

SecurityContext

Every database operation carries a SecurityContext that the engine resolves from the incoming connection. There are no anonymous operations. Clients attach the identity via the wire protocol's standard authentication handshake — password, JWT bearer, or mTLS.

bash
# Password-based connection to the Relational engine
psql "host=localhost port=20000 user=alice password=*** dbname=default"

# JWT bearer against the REST-based engines
curl -H "Authorization: Bearer $JWT" https://weftkit-kv:20004/items/abc

Every engine image enforces the same SecurityContext model internally. The overhead is < 20 nanoseconds per check.

Authentication

Every engine image supports three authentication backends; configure them via environment variables on the container:

Password / Token

bash
docker run -e WEFTKIT_AUTH=password \
           -e WEFTKIT_AUTH_USERS_FILE=/etc/weftkit/users.htpasswd \
           -v /etc/weftkit:/etc/weftkit:ro \
           weftkit/relational:0.1.0

JWT / OIDC

bash
docker run -e WEFTKIT_AUTH=jwt \
           -e WEFTKIT_JWT_JWKS_URI=https://auth.example.com/.well-known/jwks.json \
           weftkit/relational:0.1.0

mTLS (Mutual TLS)

bash
docker run -e WEFTKIT_AUTH=mtls \
           -e WEFTKIT_MTLS_CA=/etc/weftkit/tls/ca.crt \
           -v /etc/weftkit/tls:/etc/weftkit/tls:ro \
           weftkit/relational:0.1.0

Authorization

WeftKit uses role-based access control (RBAC) with fine-grained resource permissions.

Built-in Roles

| Role | Permissions | |------|-------------| | superuser | All operations | | read_write | SELECT, INSERT, UPDATE, DELETE | | read_only | SELECT only | | schema_admin | DDL operations | | no_access | Denied all |

Custom Roles

Declare roles in the engine's config file (mounted into the container). Example YAML:

yaml
# /etc/weftkit/roles.yaml
- name: analyst
  allow: [SELECT, "COPY TO"]
  deny:  [INSERT, UPDATE, DELETE]

Row-Level Security

sql
-- WeftKitRel: row-level security policy
CREATE POLICY tenant_isolation ON orders
  USING (tenant_id = current_setting('app.tenant_id'));

Encryption

At Rest

WeftKit encrypts data pages using AES-256-GCM. Each tenant can have a distinct key. Configure the key provider via container environment variables:

bash
docker run -d \
  -e WEFTKIT_ENCRYPTION=aes-256-gcm \
  -e WEFTKIT_KEY_PROVIDER=env \
  -e WEFTKIT_KEY=$(cat master.key | base64) \
  weftkit/relational:0.1.0

In Transit

TLS 1.3 is built into every engine image. Mount the certificate pair and point the engine at it via environment variables:

bash
docker run -d \
  -e WEFTKIT_TLS_CERT=/etc/weftkit/tls/server.crt \
  -e WEFTKIT_TLS_KEY=/etc/weftkit/tls/server.key \
  -e WEFTKIT_TLS_CA=/etc/weftkit/tls/ca.crt \
  -v /etc/weftkit/tls:/etc/weftkit/tls:ro \
  weftkit/relational:0.1.0

Multi-Tenancy

Every engine image isolates tenant data at the storage kernel level. The tenant identity is carried by the connection — password users can be assigned a default tenant, JWT tokens carry a tenant_id claim, and mTLS certificates carry the tenant in the subject DN.

bash
psql "host=localhost port=20000 user=alice@tenant-001 password=*** dbname=default" \
  -c "SELECT * FROM events;"

Tenants cannot access each other's data regardless of query construction — the kernel rejects cross-tenant page reads inside the engine image.

Audit Logging

Enable audit logging to record every security-relevant event:

bash
docker run -d \
  -e WEFTKIT_AUDIT=true \
  -e WEFTKIT_AUDIT_OUTPUT=/var/log/weftkit/audit.jsonl \
  -e WEFTKIT_AUDIT_EVENTS="auth,authz_deny,schema_change,data_export" \
  -v /var/log/weftkit:/var/log/weftkit \
  weftkit/relational:0.1.0

Each event includes: timestamp, identity, tenant, operation, resource, result, and source IP.

Credential Storage

WeftKit integrates with external secret managers:

  • Environment variables — simple deployments
  • HashiCorp Vaultkey_provider = "vault"
  • AWS KMSkey_provider = "kms", region + key ARN required
  • GCP Cloud KMSkey_provider = "gcp-kms"