SDKs
Node.js SDK
TypeScript-first client for servers, workers, CLIs, and serverless functions.
orbitnest-node is the official Node.js client. Fully typed, ESM-first, and compatible with both the anon key (for user-scoped apps with RLS) and the service_role key (for trusted backend workers).
Installation
bash
npm install orbitnest-node
# or
pnpm add orbitnest-node
# or
yarn add orbitnest-nodeInitialize
typescript
import { createClient } from 'orbitnest-node';
// For user-scoped apps (respects RLS)
const client = createClient({
projectUrl: process.env.ORBITNEST_URL!,
anonKey: process.env.ORBITNEST_ANON_KEY!,
});
// For trusted backend work (bypasses RLS)
const admin = createClient({
projectUrl: process.env.ORBITNEST_URL!,
serviceRoleKey: process.env.ORBITNEST_SERVICE_ROLE_KEY!,
});Database queries
typescript
// Select with filters
const { data: posts, error } = await client.from('posts')
.select('id, title, author:users(name)')
.eq('published', true)
.order('created_at', { ascending: false })
.limit(20);
// Insert
const { data: created } = await client.from('posts').insert({
title: 'Hello',
body: 'World',
}).select().single();
// Update
await client.from('posts')
.update({ published: true })
.eq('id', postId);
// Raw SQL (service_role only)
const { rows } = await admin.rpc('execute_sql', {
sql: 'SELECT count(*) FROM posts WHERE published = true',
});Authentication
typescript
// Create a user (server-side, service_role)
const { user } = await admin.auth.createUser({
email: 'user@example.com',
password: 'secret',
user_metadata: { name: 'Jane' },
});
// Verify a user JWT from a request header
const { user } = await client.auth.verifyJwt(req.headers.authorization);
// Use user context for RLS-aware queries
const userClient = client.withAuth(accessToken);
const { data: ownPosts } = await userClient.from('posts').select('*');Storage
typescript
import { readFileSync } from 'node:fs';
const buffer = readFileSync('./avatar.png');
const { path } = await client.storage
.from('avatars')
.upload(`${userId}/avatar.png`, buffer, { contentType: 'image/png' });
// Signed URL for a private file (expires in 1 hour)
const { url } = await client.storage
.from('documents')
.createSignedUrl('report.pdf', 3600);Edge functions
typescript
const { data, error } = await client.functions.invoke('process-webhook', {
body: { event: 'payment.succeeded', amount: 5000 },
headers: { 'x-idempotency-key': 'inv_123' },
});Common patterns
Next.js API route
typescript
// app/api/posts/route.ts
import { createClient } from 'orbitnest-node';
import { cookies } from 'next/headers';
export async function GET() {
const token = cookies().get('on-access-token')?.value;
const client = createClient({
projectUrl: process.env.ORBITNEST_URL!,
anonKey: process.env.ORBITNEST_ANON_KEY!,
}).withAuth(token);
const { data, error } = await client.from('posts').select('*');
if (error) return Response.json({ error }, { status: 500 });
return Response.json(data);
}Serverless-friendly
The SDK uses
fetch (no Node-specific deps) and has zero boot-time overhead. Great for Lambda, Vercel, Cloudflare Workers, Deno, Bun.Error handling
All methods return a { data, error } tuple. Errors include a typed code, message, and optional details with PostgreSQL-specific info when relevant.
typescript
const { data, error } = await client.from('posts').insert({...});
if (error) {
if (error.code === 'UNIQUE_VIOLATION') { /* handle */ }
if (error.code === 'RLS_DENIED') { /* handle */ }
console.error(error.message, error.details);
}Runtime support
- Node 18+
- Deno 1.38+
- Bun 1.0+
- Cloudflare Workers, Vercel Edge, AWS Lambda