To use varlock with other languages, install the standalone binary rather than a JS package manager, and run your app under varlock run. It loads and validates your environment, then runs your command with the resolved values injected into the process.
varlock run -- <your-command>Generated env modules
Section titled “Generated env modules”Varlock can generate a typed env module from your schema for several languages via per-language @generate*Env root decorators (see the Code generation guide for the full picture). Each generated file is a small, self-contained module with no hand-rolled JSON parsing, containing:
- a typed, coerced env object/type (numbers, booleans, parsed objects, not raw strings)
- a loader that reads the injected
__VARLOCK_ENVblob and returns those typed values - a
SENSITIVE_KEYSconstant listing which keys hold sensitive values, so you can build your own redaction or leak-scanning
It exposes only these primitives (no global singleton or imposed caching), so it stays idiomatic in each language. Pick your language for setup and usage:
| Language | Decorator | Guide |
|---|---|---|
| Python | @generatePythonEnv | Python |
| Rust | @generateRustEnv | Rust |
| Go | @generateGoEnv | Go |
| PHP | @generatePhpEnv | PHP |
Files are generated automatically on varlock load and varlock run, or explicitly via varlock codegen. The loaders read __VARLOCK_ENV, so run your program under varlock run, which always injects a plaintext blob. The generated loaders don’t decrypt, so they don’t support @encryptInjectedEnv (a JS/SSR build-output feature); if a loader is handed an encrypted blob it fails with a clear message rather than a raw parse error.
Note that varlock run --inject vars strips the __VARLOCK_ENV blob from the child process, so the generated loaders can’t work under it. Use the default injection mode (or --inject blob) when your program loads a generated module.
Languages without a generated module
Section titled “Languages without a generated module”For languages without a @generate*Env decorator yet (Ruby, Java, C#, Elixir, and others), you have two options, both of which work under varlock run:
Read individual env vars. Every config key is injected as a plain environment variable, so read them the way you normally would (ENV['KEY'] in Ruby, os.environ, getenv, etc.). These values are always strings (uncoerced), so parse numbers/booleans yourself.
Parse the blob yourself. For coerced values and metadata, read the __VARLOCK_ENV environment variable, a JSON object with a config map keyed by env var name. Skip entries with no value (unset optionals), and use isSensitive to build redaction:
// shape of __VARLOCK_ENV{ "config": { "DB_PORT": { "value": 5432, "isSensitive": false }, "API_KEY": { "value": "…", "isSensitive": true } }}The generated modules above do exactly this, and they’re the fastest path if your language is supported. We’re planning first-class helper libraries and more generated languages.
We are planning deeper integrations with other languages. Want to help us build these? Join our Discord.