River’s had insert-only clients for Ruby and Python for a while, each of which inserts jobs that’ll be worked by a main Go installation with which they share a database.
Today we’re adding TypeScript, which does the same for the JS/TS ecosystem. Like the main River package, it supports single and bulk inserts, unique jobs, scheduled jobs, transactional enqueueing, and a host of River’s other standard features.
The TypeScript client can’t claim the same disproportionate performance gain as when sending work over from Ruby and Python, but it could be useful in primarily TypeScript environments for breaking off select features to leverage Go’s low memory overhead and sharp build toolchain. TypeScript’s so ubiquitous these days that it’s probably already a part of any stack that contains Go.
Multi-driver support
The package comes with two drivers: node-postgres (pg) and Prisma. Each wraps up specific internals and abstracts them away behind a generalized River insertion API.
// node-postgresimport { Pool } from 'pg';import { Client } from 'riverqueue';import { PgDriver } from '@riverqueue/driver-pg';
const pool = new Pool({ connectionString: 'postgres://...' });const client = new Client(new PgDriver(pool));// Prismaimport { PrismaClient } from '@prisma/client';import { Client } from 'riverqueue';import { PrismaDriver } from '@riverqueue/driver-prisma';
const prisma = new PrismaClient();const client = new Client(new PrismaDriver(prisma));After initialization, client.insert and client.insertMany work identically regardless of driver:
const result = await client.insert(new SortArgs(['whale', 'tiger', 'bear']), { queue: 'high_priority',});Transaction support follows each driver’s idioms — a pool client for node-postgres (where by design, transactions are started and committed manually with BEGIN/COMMIT), and $transaction for Prisma passed as an explicit { tx } option to insert functions:
await prisma.$transaction(async (tx) => { await client.insert(new SortArgs(['whale']), { tx }); await client.insert(new SortArgs(['tiger']), { tx });});Minimize dependencies
The project is structured as a monorepo, with the core client and each driver published as separate packages:
| Package | Description |
|---|---|
riverqueue | Core client, types, and insertion logic |
@riverqueue/driver-pg | Driver for node-postgres |
@riverqueue/driver-prisma | Driver for Prisma |
A Prisma project doesn’t pull in pg as a transitive dependency, and vice versa — install what you use, and nothing extra. This keeps install size small, avoids peer dependency conflicts, and avoids bloat in case more drivers are added down the road.
# Only install what you needpnpm add riverqueue @riverqueue/driver-pg pgWe’re not foremost TypeScript developers, so we’re curious to hear more feedback from people who are. If you have strong feelings on our API or design and how it could be potentially improved, let us know.
See also the TypeScript docs for full API detail, or the project on GitHub.