@venturekit/data
Installation
Section titled “Installation”npm install @venturekit/dataWhat It Provides
Section titled “What It Provides”RDS Configuration
Section titled “RDS Configuration”import { createRdsConfig, DEFAULT_RDS_CONFIG, buildRdsConfig } from '@venturekit/data';
const config = createRdsConfig({ engine: 'postgres', instanceSize: 'small', databaseName: 'mydb' });Query Utilities
Section titled “Query Utilities”import { query, getPool, mapResults, mapRow } from '@venturekit/data';
const result = await query('SELECT * FROM tasks WHERE id = $1', [taskId]);const tasks = mapResults(result, row => ({ id: row.id, title: row.title }));Transactions
Section titled “Transactions”import { beginTransaction, withTransaction, buildTransaction } from '@venturekit/data';
// Automatic commit/rollbackconst result = await withTransaction(async (tx) => { await tx.query('INSERT INTO tasks (title) VALUES ($1)', ['New']); return { created: true };});Migration Utilities
Section titled “Migration Utilities”Config helpers and the tool-agnostic dispatcher used by vk migrate:
import { createMigrationConfig, DEFAULT_MIGRATION_CONFIG, getFlywayEnv,} from '@venturekit/data';Built-in Migration Runner
Section titled “Built-in Migration Runner”@venturekit/data ships a pure-SQL migration runner that the CLI uses by
default — files in db/migrations/ are applied in lexical order, one per
transaction, tracked in the __vk_migrations table along with a content hash:
import { runMigrations, getMigrationStatus, runSeeds, getSeedStatus, MIGRATIONS_TRACKING_TABLE, // '__vk_migrations' SEEDS_TRACKING_TABLE, // '__vk_seeds'} from '@venturekit/data';
await runMigrations({ config: createMigrationConfig(), onApply: (entry) => console.log('applied', entry.filename),});Error Classes
Section titled “Error Classes”Thrown by the migration runner — catch these in CI to fail loudly:
import { MigrationToolNotImplementedError, // unsupported runner selected MigrationHashMismatchError, // applied file was edited after the fact MigrationCollisionError, // duplicate version across dirs} from '@venturekit/data';Env-Var Bridges
Section titled “Env-Var Bridges”Hydrate DATABASE_URL from a Secrets Manager secret or an existing connection
string at Lambda cold start:
import { applyDatabaseUrlToEnv, applyDbSecretToEnv,} from '@venturekit/data';Mapper Customisation
Section titled “Mapper Customisation”The default row mapper converts snake_case columns to camelCase properties.
Override globally if your schema uses a different convention:
import { configureMapper, getMapperConfig } from '@venturekit/data';
configureMapper({ rename: (col) => col }); // identity (no rename)Tenant Context (RLS)
Section titled “Tenant Context (RLS)”Wrap a request in runWithTenant() and every query inside it runs with the app.tenant_id / app.tenant_ids GUCs set, so Postgres row-level-security policies filter the rows your SQL forgot to — fail-closed:
import { runWithTenant, runWithTenantScope, runWithoutTenant } from '@venturekit/data';
await runWithTenant(tenantId, () => query('SELECT * FROM posts')); // only this tenant's rowsawait runWithTenantScope([parentId, ...childIds], () => listReports()); // hierarchical read scopeawait runWithoutTenant(() => listAllTenants()); // platform-level jobSet DB_TENANT_ROLE=app_user so scoped statements SET ROLE to a non-owner role — RLS does not apply to table owners or postgres (vk dev). @venturekit-pro/tenancy’s createTenantRlsMiddleware does the wrapping per request.
Subpath Exports
Section titled “Subpath Exports”| Subpath | Description |
|---|---|
@venturekit/data/idempotency | createPostgresIdempotencyStore() for the runtime’s idempotencyMiddleware + purgeExpiredIdempotencyRecords() |
@venturekit/data/outbox | appendToOutbox(), createPostgresOutboxStore() — the transactional-outbox store for relayOnce() |
@venturekit/data/jobs | Queryable Postgres job queue — enqueueJob, claimJobs, runJobsOnce, listJobs, reclaimStuckJobs |
@venturekit/data/files | Upload metadata — recordFileObject, findFileObjectByChecksum, archiveFileObject, sweepArchivedFiles |
@venturekit/data/flags | Feature flags with per-tenant / per-user pins and stable %-rollouts (createFlags, upsertFlag, setFlagOverride) + one JSONB settings document per tenant (getTenantSettings, setTenantSettings) |
@venturekit/data/search | Pure SQL builders — escaped ILIKE patterns, generated tsvector columns and websearch_to_tsquery fragments, keyset cursors. Nothing here runs a query |
Each ships its migration (vk_data_00N_*.sql) in the package’s vk.migrations directory, which vk migrate auto-discovers (search has none). See the API reference.
import { createFlags } from '@venturekit/data/flags';import { query } from '@venturekit/data';
const flags = createFlags({ querier: query }); // module scope — one snapshot per container, refreshed every 30 s
if (await flags.isEnabled('new-editor', { tenantId: ctx.tenant?.id, userId: ctx.user?.id })) { /* … */ }RdsOutputs,RdsInfraConfig— RDS infrastructure typesTransaction,ResultsMapper— query and transaction typesRunOptions,RunResult,StatusEntry,SeedRunOptions— runner typesQuerier,MapperOptions— mapper customisation typesJob,JobStatus,JobHandler,FileObject,OutboxRow,PostgresOutboxStore— subpath typesFeatureFlag,FeatureFlagOverride,FlagSubject,Flags,TenantSettingsOptions,KeysetCursor,FtsColumnOptions— flags and search types
Dependencies
Section titled “Dependencies”@venturekit/core— requiredpg— PostgreSQL client
Related
Section titled “Related”- Database Guide — setup walkthrough
- Handlers — transactional handlers
- CLI: migrate — migration commands
- API Reference — full type documentation