CipherStashDocs
ReferenceCLI

stash eql

Reference for the `stash eql` commands.

Last updated

Generated from stash v1.1.1, via that release's own manifest --json. Run npx [email protected] --help to see the live command surface.

The stash eql command group.

eql preflight

Read-only: probes the connected role — superuser, membership of postgres, CREATE on the database and on public, pgcrypto, and whether the EQL v3 schemas already exist — and names the statement each gap blocks. Exits 1 when a gap would abort eql install.

Membership of postgres is reported but never blocks: on managed platforms whose role is not a member (e.g. Lovable), eql install skips the optional owner-scoped ALTER DEFAULT PRIVILEGES statements — the install is complete without them, since stash re-grants every object on each install/upgrade.

npx stash eql preflight [flags]

stash eql preflight flags

FlagDescription
--jsonEmit the machine-readable preflight result instead of the table.
--database-url <url>Database URL for this run only — never written to disk. Highest precedence in the resolution order: --database-url flag → DATABASE_URL env → supabase status → interactive prompt. A stash.config.ts is not a separate tier (its default databaseUrl re-runs this same chain); a hand-set literal databaseUrl in the config bypasses the resolver and wins over all of these. (env: DATABASE_URL)

stash eql preflight examples

npx stash eql preflight
npx stash eql preflight --json

eql install

Scaffold stash.config.ts (if missing) and install EQL extensions

npx stash eql install [flags]

stash eql install flags

FlagDescription
--forceReinstall / overwrite even if already installed.
--dry-runShow what would happen without making changes.
--supabaseUse Supabase-compatible mode (auto-detected from DATABASE_URL).
--database-url <url>Database URL for this run only — never written to disk. Highest precedence in the resolution order: --database-url flag → DATABASE_URL env → supabase status → interactive prompt. A stash.config.ts is not a separate tier (its default databaseUrl re-runs this same chain); a hand-set literal databaseUrl in the config bypasses the resolver and wins over all of these. (env: DATABASE_URL)

eql verify

Compare what the database actually has against everything the pinned EQL v3 bundle installs — every domain, function overload, operator, cast, and the ORE operator class — via read-only catalog queries. A partial install (domains present, some comparison functions or operators absent) reports success at install time and fails at query time on a specific predicate; this is the check that catches it.

Expected absences read as such: on managed Postgres the bundle legitimately skips the ORE operator class (creating it requires superuser) and poisons the _ord_ore domains to fail loudly — that is a supported configuration, reported as info.

Exit 0 means exactly one thing: the surface was checked and found complete. Damage, EQL not installed, and a version mismatch with the pinned bundle all exit 1 — on a mismatch the object-level diff is skipped (the pinned bundle is the wrong manifest to compare against) and the command suggests eql upgrade (or a one-shot eql install --force --database-url ... where no stash.config.ts exists — eql upgrade requires one).

Runs automatically at the end of stash eql install, on the fresh-install path and the already-installed early exit alike. There, only damage fails the install — a version mismatch warns and continues, keeping a no-op re-run over an older EQL exit 0 for idempotent provisioning scripts.

npx stash eql verify [flags]

stash eql verify flags

FlagDescription
--jsonEmit the machine-readable verification report instead of the table.
--database-url <url>One-shot, like eql install's: bypasses config loading entirely, so the database you name is the database that gets judged. Also settable via DATABASE_URL. (env: DATABASE_URL)

stash eql verify examples

npx stash eql verify
npx stash eql verify --json

eql migration

Migration-first is the preferred way to install EQL: it lands in your migration history and ships to every environment through the same migrate step as the rest of your schema. On Supabase it is the only durable way — supabase db reset replays the migrations directory, so a direct eql install is wiped by the next reset.

npx stash eql migration [flags]

stash eql migration flags

FlagDescription
--drizzleEmit a Drizzle custom migration containing the EQL v3 install SQL.
--prismaNot needed: Prisma Next installs EQL through its own migration framework — run prisma-next migrate instead.
--supabaseOn its own, write the install into supabase/migrations/ so it survives supabase db reset. With --drizzle, instead append the Supabase role grants (eql_v3 + eql_v3_internal for anon/authenticated/service_role) to the Drizzle migration.
--name <name>Name for the generated migration (Drizzle). Letters, numbers, dashes, underscores only. Defaults to install-eql.
--out <path>Where the migration is written. Drizzle: your drizzle.config.ts out decides that, and stash follows the path drizzle-kit reports — this is only the fallback directory to look in (defaults to drizzle) if it reports none. Supabase: leave it alone. The Supabase CLI replays supabase/migrations and has no setting to move it, so pointing elsewhere means supabase db reset / db push never apply the install; the command warns when you do.
--forceWrite a Supabase install migration even though one already exists. Not needed for --drizzle (drizzle-kit numbers each generated migration).
--dry-runShow what would happen without making changes.

stash eql migration examples

npx stash eql migration --drizzle
npx stash eql migration --drizzle --supabase
npx stash eql migration --supabase
npx stash eql migration --supabase --force

eql repair

Sweep an existing Drizzle output directory for in-place ALTER COLUMN ... SET DATA TYPE <eql domain> statements — which cannot run, because Postgres has no cast from text/numeric to an EQL domain — and rewrite each into an additive encrypted column that preserves the source column.

This is the same sweep eql migration --drizzle runs, without having to generate an EQL install migration you do not want just to trigger it.

Migrations the database has already applied are reported and left alone: rewriting one would leave its .sql describing a shape that database never got from it, so a fresh CI or staging database replaying the file would silently diverge. Pass --database-url so that check can run; without it the repair proceeds and warns that applied state could not be verified. If your drizzle.config.ts overrides migrations.table / migrations.schema, name the ledger with --migrations-table — otherwise the check queries the default relation, finds nothing, and reports applied state as unverified.

npx stash eql repair [flags]

stash eql repair flags

FlagDescription
--drizzleRepair a Drizzle migration directory.
--out <path>Directory holding the migrations to sweep. Defaults to drizzle; set it to match your drizzle.config.ts.
--migrations-table <[schema.]table>Drizzle's migration ledger, when drizzle.config.ts overrides migrations.table / migrations.schema. Defaults to drizzle.__drizzle_migrations. Only read with --database-url.
--dry-runShow what would happen without making changes.
--database-url <url>Database URL for this run only — never written to disk. Highest precedence in the resolution order: --database-url flag → DATABASE_URL env → supabase status → interactive prompt. A stash.config.ts is not a separate tier (its default databaseUrl re-runs this same chain); a hand-set literal databaseUrl in the config bypasses the resolver and wins over all of these. (env: DATABASE_URL)

stash eql repair examples

npx stash eql repair --drizzle
npx stash eql repair --drizzle --dry-run
npx stash eql repair --drizzle --out db/migrations --database-url postgres://…

eql upgrade

Upgrade EQL extensions to the latest version

npx stash eql upgrade [flags]

stash eql upgrade flags

FlagDescription
--dry-runShow what would happen without making changes.
--supabaseUse Supabase-compatible mode.
--database-url <url>Database URL for this run only — never written to disk. Highest precedence in the resolution order: --database-url flag → DATABASE_URL env → supabase status → interactive prompt. A stash.config.ts is not a separate tier (its default databaseUrl re-runs this same chain); a hand-set literal databaseUrl in the config bypasses the resolver and wins over all of these. (env: DATABASE_URL)

eql status

Show EQL installation status

npx stash eql status [flags]

stash eql status flags

FlagDescription
--database-url <url>Database URL for this run only — never written to disk. Highest precedence in the resolution order: --database-url flag → DATABASE_URL env → supabase status → interactive prompt. A stash.config.ts is not a separate tier (its default databaseUrl re-runs this same chain); a hand-set literal databaseUrl in the config bypasses the resolver and wins over all of these. (env: DATABASE_URL)

eql validate

Read the tables passed to Encryption({ schemas }) and check each encrypted column against the EQL v3 domain vocabulary — then, if a database is reachable, against what that database actually has.

Schema checks (no database needed): an _ord_ore domain, whose ORE operator class only a superuser can create; storage-only columns, reported so an unsearchable column is a decision rather than a surprise; and hand-authored configs that ask for free-text match on a non-text domain, encrypted-JSONB search without types.Json, or a searchable boolean.

Database checks (skipped with a notice when no database is reachable): declared columns missing from the database, a column whose domain has drifted from the schema, an _ord_ore column on a database whose EQL install could not create the ORE operator class, and queryable columns with no functional index over their term extractor.

Exits 1 on errors only — warnings and info do not fail the command.

npx stash eql validate [flags]

stash eql validate flags

FlagDescription
--supabaseUse Supabase-compatible mode.
--database-url <url>Database URL for this run only — never written to disk. Highest precedence in the resolution order: --database-url flag → DATABASE_URL env → supabase status → interactive prompt. A stash.config.ts is not a separate tier (its default databaseUrl re-runs this same chain); a hand-set literal databaseUrl in the config bypasses the resolver and wins over all of these. (env: DATABASE_URL)

stash eql validate examples

npx stash eql validate
npx stash eql validate --database-url postgres://…

On this page