☰ Required Configuration
The deployments relies on environment variables read from your shell. This table details those environment variables by alphabetical order.
For autoscaling/cluster actuation, the Operator consumes cloud credentials from
the Operator release values. With Plane deployment (plane up datalayer-operator),
the credentials are now injected through an Operator Helm-managed Secret
(datalayer-operator-cloud-credentials) and consumed by the Operator Pod.
When you run plane down datalayer-operator, Helm removes that Secret with the
release resources.
| Variable | Description |
|---|---|
| AWS_ACCESS_KEY_ID | Set the access key that gives access to the S3 bucket for the backups. |
| AWS_DEFAULT_PROFILE | Set the default profile that gives access to the S3 bucket for the backups. |
| AWS_DEFAULT_REGION | Set the defaul region that gives access to the S3 bucket for the backups. |
| AWS_REGION | Set the region of the S3 bucket for the backups. |
| AWS_SECRET_ACCESS_KEY | Set the secret key that gives access to the S3 bucket for the backups. |
| AZURE_TENANT_ID | Azure tenant identifier used by Operator cloud actuation and cloud APIs. |
| AZURE_CLIENT_ID | Azure application/service principal client identifier for Operator cloud actuation. |
| AZURE_CLIENT_SECRET | Azure application/service principal secret for Operator cloud actuation. |
| AZURE_SUBSCRIPTION_ID | Azure subscription identifier targeted by Operator scaling actions. |
| AZURE_RESOURCE_GROUP | Azure resource group name where scaling resources are provisioned/managed. |
| DATALAYER_CLOUD_PROVIDER | Cloud provider used by the Operator scaling executor (aws or azure). |
| DATALAYER_CLOUDER_URL | Base URL for Clouder API when Operator executes scaling through API mode. |
| DATALAYER_AUTHZ_ENGINE | Type of Authorization engine to use - possible value: none | openfga - default is openfga. |
| DATALAYER_CLUSTER_TYPE | The Kubernetes cluster type (this is only needed for advanced cases). Possible values are eks or ovh. |
| DATALAYER_CREDITS_PROVIDER | A string that defines up the addon providing the credits method within IAM for billing and usage. |
| DATALAYER_DOCKER_REGISTRY_HOST | Hostname of the OCI Registry that contains the Docker Images. |
| DATALAYER_DOCKER_REGISTRY | Full name of the OCI Registry that contains the Docker Images, e.g $DATALAYER_DOCKER_REGISTRY_HOST/datalayer |
| DATALAYER_DOCKER_REGISTRY_USERNAME | Username of the OCI Registry that contains the Docker Images. |
| DATALAYER_DOCKER_REGISTRY_PASSWORD | Password of the OCI Registry that contains the Docker Images. |
| DATALAYER_GITHUB_CLIENT_ID | If you enable authentication via GitHub, define the client id of the GitHub Application. |
| DATALAYER_GITHUB_CLIENT_SECRET | If you enable authentication via GitHub, define the client secret of the GitHub Application |
| DATALAYER_GRAFANA_ADMIN_PWD | Define the password for the Grafana service. |
| DATALAYER_HELM_REGISTRY_HOST | Hostname of the OCI Registry that contains the Helm Charts. |
| DATALAYER_HELM_REGISTRY | Full name of the OCI Registry that contains the Helm Charts, e.g $DATALAYER_HELM_REGISTRY_HOST/datalayer-charts |
| DATALAYER_HELM_REGISTRY_USERNAME | Username of the OCI Registry that contains the Helm Charts. |
| DATALAYER_HELM_REGISTRY_PASSWORD | Password of the OCI Registry that contains the Helm Charts. |
| DATALAYER_JWT_ISSUER | If you enable authentication via JSON Web Token (JWT), define the JWT issuer. e.g. https://dev.datalayer.io |
| DATALAYER_JWT_SECRET | If you enable authentication via JSON Web Token (JWT), define the JWT secret. |
| DATALAYER_JWT_ALGORITHM | If you enable authentication via JSON Web Token (JWT), define the JWT issuer. e.g. HS256 |
| DATALAYER_JWT_ALLOWED_ISSUERS | If you enable authentication via JSON Web Token (JWT), define the JWT allowed issuers. e.g. https://id.your-company.cloud |
| DATALAYER_JWT_DEFAULT_KID_ISSUER | If you enable authentication via JSON Web Token (JWT), define the JWT default key ID issuer. e.g. https://your-company.cloud/api/iam/v1/api-keys |
| DATALAYER_JWT_SKIP_3RD_TOKEN_SIGNATURE_VERIFICATION | If you enable authentication via JSON Web Token (JWT), define the JWT signature should be verified. Set true or false. |
| DATALAYER_CERT_ISSUER | The issuer for the certificates, e.g. letsencrypt or letsencrypt-prod. |
| DATALAYER_INGRESS_CLASS_NAME | The Ingress class name for the Operator, e.g. datalayer-traefik or nginx. |
| DATALAYER_IAM_API_KEY | Key used to protect the internal Kubernetes cluster communications. |
| DATALAYER_IAM_HOST | IAM internal Kubernetes service hostname + port. |
| DATALAYER_OPENFGA_REST_URL | |
| DATALAYER_OPENFGA_STORE_ID | |
| DATALAYER_OPENFGA_AUTHZ_MODEL_ID | |
| DATALAYER_OPERATOR_API_KEY | Set a secret to secure the internal connexions between the services. |
| DATALAYER_PUBSUB_ENGINE | Type of Pub/Sub engine to use - possible value: none | pulsar - default is pulsar. |
| DATALAYER_PULSAR_URL | Internal URL to pulsar broker e.g. pulsar://datalayer-pulsar-broker.datalayer-pulsar.svc.cluster.local:6650. |
| DATALAYER_USERS_PVC_NAME | Name of the permanent volume claim for user storage. |
| DATALAYER_VAULT_URL | Internal URL to the Vault service. |
| DATALAYER_VAULT_TOKEN | Token to access the Vault service. |
| DATALAYER_RUN_URL | The hostname of the public-facing services. You will need to update your DNS system to point the Load Balancer IP address to the hostname of the URL. The Load Balancer is created by the Ingress service. SSL certificates will be created by the cert-manager service for that hostname. |
| DATALAYER_RUNTIME_ENV | dev, qa or prod |
| DATALAYER_SMTP_HOST | Define the SMTP server hostname for email communications. |
| DATALAYER_SMTP_PORT | Define the SMTP server port number for email communications. |
| DATALAYER_SMTP_USERNAME | Define the SMTP server username for email communications. |
| DATALAYER_SMTP_PASSWORD | Define the SMTP server password for email communications. |
| DATALAYER_SOLR_USERNAME | Define the username to protect Solr. |
| DATALAYER_SOLR_PASSWORD | Define the password to protect Solr. |
| DATALAYER_SOLR_BACKUP_S3_BUCKET_NAME | Define the S3 bucket name for the Solr backups. |
| DATALAYER_SOLR_BACKUP_S3_BUCKET_REGION | Define the S3 bucket region for the Solr backups. |
| DATALAYER_CONTENTS_API_PORT | Contents REST port. The chart default is 9400. |
| DATALAYER_CONTENTS_FLIGHT_PORT | Contents Arrow Flight port. The chart default is 9401. |
| DATALAYER_CONTENTS_BRIDGE_PORT | Contents local-bridge relay port. The chart default is 9402. |
| DATALAYER_CONTENTS_REQUIRE_SOLR | When true, Contents readiness fails until Solr is reachable. |
| DATALAYER_CONTENTS_REQUIRE_VAULT | When true, Contents readiness fails until Vault is reachable. |
| DATALAYER_CONTENTS_DEPENDENCY_TIMEOUT_SECONDS | Timeout in seconds for each Contents readiness dependency probe. |
| DATALAYER_SOLR_ZK_HOST | ZooKeeper ensemble the Solr data-access layer connects through. Required by every Solr-backed service, including the Contents API and worker. |
| DATALAYER_SOLR_URL | Internal Solr HTTP endpoint polled by readiness probes. It does not replace DATALAYER_SOLR_ZK_HOST. |
| DATALAYER_SUPPORT_EMAIL | Define the email for support communications. e.g. support@your-company.io |
| KUBECONFIG | The path to your Kubeconfig file. |
| DATALAYER_OPENAI_API_VERSION | |
| DATALAYER_AZURE_OPENAI_CHAT_COMPLETION_ENDPOINT | |
| DATALAYER_AZURE_OPENAI_API_KEY | |
| OTEL_SDK_DISABLED | Disable OpenTelemetry instrumentation on service and use non-enriched logs (no metadata) [true or false]. |
| OTEL_EXPORTER_OTLP_METRICS_ENDPOINT | URL for exporting services metrics and traces to opentelemetry collector. |
| OTEL_EXPORTER_OTLP_TRACES_ENDPOINT | URL for exporting services metrics and traces to opentelemetry collector. |
Contents and Solr recovery settings
Deploy Contents with the standard IAM JWT, Solr, Vault and OpenTelemetry settings above. Supply passwords, signing material and provider credentials through Kubernetes Secrets or an external secret controller; do not commit them to Helm values.
Solr backup storage is selected by
DATALAYER_SOLR_BACKUP_S3_BUCKET_NAME,
DATALAYER_SOLR_BACKUP_S3_BUCKET_REGION and the AWS workload identity or
credential secret. Recurrence and retention are declarative fields in the
checked-in backup specifications: spec.recurrence.schedule and
spec.recurrence.maxSaved. Review them together with object-store versioning
and Vault retention before applying a production schedule.
See Datalayer Contents, Solr and Continuity.
Node Mount Gateway settings
The Node Mount Gateway binds home folders into runtime Pods that are already running, so a launch that mounts the Home Folder is served from the prewarmed pool instead of a cold Pod. It is off by default and has two halves, which are turned on in this order:
| Setting | Where | Meaning |
|---|---|---|
nodeMountGateway.enabled, nodeMountGateway.sharedFilesystemClaim | datalayer-node-mounts chart | Run the node agent and name the RWX claim it binds from. Installing the chart with the first and not the second fails. |
DATALAYER_NODE_MOUNT_GATEWAY_ENABLED | datalayer-operator, and plane up | Give pooled Pods the gateway volume and serve Home Folder launches from the pool. up.sh reads the same variable to set nodeMountGateway.enabled on the chart, so one export turns on both halves. |
DATALAYER_SHARED_FS_VOLUME_CLAIM_NAME | plane up | The claim up.sh passes as nodeMountGateway.sharedFilesystemClaim. Asking for the gateway without it fails the deploy rather than installing an agent with nothing to bind. |
DATALAYER_NODE_MOUNT_GATEWAY_READY_TIMEOUT_SECONDS | datalayer-operator | How long a launch waits for the node agent to confirm the mounts (default 20). |
DATALAYER_NODE_MOUNT_GATEWAY_MAX_MOUNTS_PER_POD | datalayer-operator | The most folders one sandbox may be granted (default 32). |
nodeMountGateway.maxMountsPerNode | datalayer-node-mounts chart | The most the node agent will hold at once (default 512). |
apiServer.cidr | datalayer-node-mounts chart, or DATALAYER_KUBERNETES_API_SERVER_CIDR for plane up | The control-plane address the agent's NetworkPolicy allows. The Pod watch is the agent's only input; without this egress it mounts nothing. |
Each mount kind is a switch of its own, off unless asked for, and each has
a variable plane up reads:
| Setting | Variable | Serves |
|---|---|---|
nodeMountGateway.credentials | DATALAYER_NODE_MOUNT_GATEWAY_CREDENTIALS | Nothing on its own: it lets the agent read a Secret a grant names, which the three below need. It is never implied by asking for a mount kind — reading a Secret is the one thing the agent does that its RBAC would otherwise forbid |
nodeMountGateway.buckets | DATALAYER_NODE_MOUNT_GATEWAY_BUCKETS | cloud-storage grants, through Mountpoint for S3 |
nodeMountGateway.localBridges | DATALAYER_NODE_MOUNT_GATEWAY_LOCAL_BRIDGES | local-bridge grants: a person's own folder into a running sandbox |
nodeMountGateway.repositories | DATALAYER_NODE_MOUNT_GATEWAY_REPOSITORIES | git grants: a pinned commit checked out on the node. A public repository needs no credential |
A grant of a kind whose switch is off is refused with a reason the user sees, not silently skipped — see what it can mount.
Deploy the node agent first. With the Operator setting on and no agent,
pooled Pods carry the volume and wait for mounts nobody makes. The nodes must
also have shared mount propagation on the kubelet directory
(findmnt -no PROPAGATION --target /var/lib/kubelet); without it a grant
succeeds on the node and is invisible in the sandbox.
Use any of the following command to generate tokens.
TOKEN=$(openssl rand -hex 32)
TOKEN=$(python -c "import secrets; print(secrets.token_hex(32))")
Jupyter MCP Server gateway settings
The Jupyter MCP Server gateway reads the
standard IAM JWT, Solr and OpenTelemetry settings above, plus the following.
Only DATALAYER_JUPYTER_MCP_SERVER_URL and the URLs of its dependencies are
normally exported for a deployment; the rest are chart values with working
defaults. Supply DATALAYER_IAM_API_KEY, DATALAYER_JWT_SECRET and the Solr
password through Kubernetes Secrets (jupyterMcpServer.envValueFrom), never in
Helm values.
| Variable | Default | Description |
|---|---|---|
DATALAYER_JUPYTER_MCP_SERVER_URL | https://mcp.datalayer.run/mcp | The resource identifier of the gateway: what a token's aud must name, what the RFC 9728 protected-resource metadata publishes, and what the ingress host is derived from. IAM must be deployed with the same value, since it stamps it into the audience of every OAuth token |
DATALAYER_JUPYTER_MCP_VERIFY_AUDIENCE | true | Refuse a token issued for another resource. Off only for a local run against a token minted before the resource URL was settled |
DATALAYER_IAM_URL | – | The authorization server. Required; gates readiness |
DATALAYER_IAM_API_KEY | – | Proves to IAM that the gateway is a Datalayer service, which is what lets it exchange a caller's gateway token (RFC 8693) for one the rest of the platform accepts. Without it, OAuth callers reach nothing. DATALAYER_OPERATOR_API_KEY is accepted as a fallback |
DATALAYER_SPACER_URL | DATALAYER_IAM_URL | Where notebooks and their permissions live |
DATALAYER_RUNTIMES_URL | DATALAYER_IAM_URL | Where a sandbox is asked for; provider-neutral |
DATALAYER_CONTENTS_URL | – | Where Contents runs: the runtimes plane, at its own public URL (https://r1.datalayer.run), never an assumed same-cluster service name. No fallback, and a value equal to DATALAYER_IAM_URL is reported as a misconfiguration |
DATALAYER_AI_AGENTS_URL | DATALAYER_IAM_URL | Where the gateway posts best-effort activity events for the feed |
DATALAYER_MCP_STORE | Solr when DATALAYER_SOLR_ZK_HOST is set, else memory | Which store holds handles, the worker directory and rate windows. solr in a cluster; memory only for a single local process. Any other value refuses to start |
DATALAYER_SANDBOX_ENVIRONMENT | ai-agents-env | The Datalayer environment a sandbox is launched into. Set it where a cluster offers different ones, such as a GPU environment |
DATALAYER_MCP_MAX_WORKERS | 50 | The most per-user worker processes one replica runs at once — the density limit of a replica. Capacity is added by adding pods |
DATALAYER_MCP_WORKER_IDLE_TIMEOUT | 900 | Seconds a worker may sit unused before it is reclaimed. A worker whose session has a task working is never idle |
DATALAYER_MCP_WORKER_START_TIMEOUT | 30 | Seconds to wait for a new worker to answer before giving up and quoting its last output |
DATALAYER_MCP_WORKER_ENTRY_TTL_SECONDS | 180 | Seconds a worker-directory entry lives after its last heartbeat, so a replica that is gone stops being forwarded to |
DATALAYER_MCP_REPLICA_ADDRESS | http://$POD_IP:4404, else loopback | The address other replicas forward to. Set this, or give the pod POD_IP through the downward API, or cross-replica forwarding never leaves the pod |
DATALAYER_MCP_BINDING_TTL_SECONDS | 86400 | Seconds a handle lives after it was last used; refreshed on every use |
DATALAYER_MCP_CALLS_PER_MINUTE_PER_USER | 300 | Tool calls one user may make in a minute; 0 no limit. Counted in Solr so the limit holds across replicas |
DATALAYER_MCP_CALLS_PER_MINUTE_PER_AGENT | 120 | The same, per OAuth client_id |
DATALAYER_MCP_DEPENDENCY_TIMEOUT | 10 | Seconds a call to a platform dependency may take before it is a timeout |
JUPYTER_MCP_TOKEN_VERIFIER_CLASS | datalayer_jupyter_mcp_server.verifier:DatalayerTokenVerifier | How the worker authenticates clients: Datalayer's own verifier, which accepts OAuth access tokens and personal access tokens |
DATALAYER_MCP_LOG_COLOR | true | Whether the request log is coloured; NO_COLOR also turns it off |
PORT | 4404 | The port the gateway listens on inside the pod; must agree with jupyterMcpServer.port |
See Datalayer Jupyter MCP Server for the
scaling values, the drain and the three Solr collections the gateway owns, and
Continuity for the mcp recovery unit.
Minimal Configuration
The minimal setup for IAM, Runtimes, and Operator is listed here with example values.
Create a ~/.datalayer/datalayerrc and source that file from ~/.bash_profile or similar based on your shell.
#!/usr/bin/env bash
# ~/.datalayer/datalayerrc
export DATALAYER_AUTHZ_ENGINE="none"
export DATALAYER_CDN_URL="https://datalayer.io"
export DATALAYER_CLUSTER_NAME="my-cluster"
export DATALAYER_CLUSTER_TYPE="eks"
export DATALAYER_CREDITS_PROVIDER="stripe"
export DATALAYER_DOCKER_REGISTRY="${DATALAYER_DOCKER_REGISTRY_HOST}/datalayer"
export DATALAYER_DOCKER_REGISTRY_HOST="my-registry.net"
export DATALAYER_DOCKER_REGISTRY_PASSWORD="..."
export DATALAYER_DOCKER_REGISTRY_USERNAME="..."
export DATALAYER_HELM_REGISTRY="${DATALAYER_HELM_REGISTRY_HOST}/datalayer-charts"
export DATALAYER_HELM_REGISTRY_HOST="my-registry.net"
export DATALAYER_HELM_REGISTRY_PASSWORD="..."
export DATALAYER_HELM_REGISTRY_USERNAME="..."
export DATALAYER_IAM_API_KEY="..."
export DATALAYER_INITIAL_USER_CREDITS=10
export DATALAYER_JWT_ALGORITHM="HS256"
export DATALAYER_JWT_ALLOWED_ISSUERS="https://my-id.datalayer.run"
export DATALAYER_JWT_ISSUER="https://my-id.datalayer.run"
export DATALAYER_JWT_SECRET="..."
export DATALAYER_JWT_SKIP_EXTERNAL_TOKEN_SIGNATURE_VERIFICATION=false
export DATALAYER_OPERATOR_API_KEY="..."
export DATALAYER_PUBSUB_ENGINE="none"
export DATALAYER_RUNTIME_ENV="prod"
export DATALAYER_RUN_URL=https://my-cluster.datalayer.run
export DATALAYER_SOLR_PASSWORD="..."
export DATALAYER_SOLR_USERNAME="admin"
export KUBECONFIG="~/.datalayer/my-cluster.yaml"
export OTEL_SDK_DISABLED=true
source ~/.datalayer/datalayerrc
Stripe Addon
The configuration for the Stripe Addon is listed here.
| Variable | Description |
|---|---|
| DATALAYER_STRIPE_API_KEY | Private Stripe API key. |
| DATALAYER_STRIPE_CHECKOUT_ROUTE | UI checkout route (default: checkout). |
| DATALAYER_STRIPE_JS_API_KEY | Public Stripe API key. |
| DATALAYER_STRIPE_TOPUP_PRODUCT_ID | Stripe product ID for one-time top-up prices. |
| DATALAYER_STRIPE_SUBSCRIPTION_PRODUCT_ID | Stripe product ID for monthly subscription plans required for top-up eligibility. |
| DATALAYER_STRIPE_WEBHOOK_SECRET | Stripe webhook secret. |
| DATALAYER_STRIPE_CUST_PORTAL_ID | Stripe Billing Portal configuration ID. |
| DATALAYER_STRIPE_CUST_PORTAL_URL | Stripe Billing Portal URL. |