Getting started

Installation

Install @goenvless/sdk and check that your credential works, on any server-side JavaScript runtime.

npm install @goenvless/sdk

Installing for Python, Ruby or PHP instead? The Python SDK is pip install envless-sdk, see its installation page, the Ruby SDK is bundle add envless-sdk, see its installation page, and the PHP SDK is composer require envless/sdk, see its installation page.

Requirements

Node.js20 or newer
Bun, Deno, WorkersAny version with fetch and Web Crypto
TypeScript5.0 or newer, for the bundled declarations
DependenciesNone

The package ships ESM and CommonJS builds with separate .d.ts and .d.cts declarations, resolved per module condition so both import and require get correct types. It declares sideEffects: false so bundlers can drop the namespaces you never touch.

There are no Node built-ins anywhere in the bundle. Base64 goes through btoa/atob rather than Buffer, and all cryptography goes through crypto.subtle. That is what makes it safe to import inside an edge function or a Cloudflare Worker. It still refuses to construct where window and document both exist, unless you pass dangerouslyAllowBrowser: true.

Verify the install

me.get() is the only method with no scope requirement, which makes it the cheapest way to prove a credential is live before you build anything on it.

ts
import { EnvlessApiError, envless, init } from '@goenvless/sdk'

init({ token: process.env.ENVLESS_TOKEN })

try {
    const identity = await envless.me.get()

    console.log(`Authenticated as ${identity.user.email}`)
    console.log(`Workspace ${identity.workspaceId}`)
}

catch (error) {
    if (error instanceof EnvlessApiError && error.isAuth) {
        console.error('The API key is invalid, inactive, revoked, or its owner is no longer a member of the workspace.')
    }

    throw error
}

Every one of those failures comes back as HTTP 401 carrying an error code under auth., which is exactly what isAuth tests. 403 with auth.scope_missing cannot happen here, because this endpoint is the one route that carries no scope middleware.

Get an API key

Open the dashboard

Open Keys in the sidebar, under the workspace group. It is a top level page at /dashboard/keys, not part of Settings.

Create a key with the narrowest scopes that work

Scopes are per resource and per level, such as variables:read or projects:write. Grant only what the script needs. See Authentication.

Copy the secret immediately

The ev_sk_... value is shown exactly once and is unrecoverable. Reads afterwards only ever expose the non-secret prefix.

Store it as ENVLESS_TOKEN

Both init() and createClient() fall back to that variable, so you can call them with no arguments. Set it and you can skip init entirely: the first method call on envless builds the client for you.

An API key is bound to the workspace it was created in, and unless you pin it to a list of projectIds it reaches every project in that workspace. Do not ship it to a browser, and do not commit it.

If you need variables inside a running app, use a machine key with @goenvless/env instead, held to variables:read and pinned to the projects it needs. Scoping is per resource and per project, never per environment: the environment is picked at load time, not baked into the key.

On a runtime with no filesystem, that import has to be @goenvless/env/edge. The root entry, /server, /next, /vite and /register all reach a loader that statically imports node:fs, so none of them start inside a Worker or an edge function.

Next