
Security News
AI Has Taken Over Open Source
Vibe coding at scale is reshaping how packages are created, contributed, and selected across the software supply chain
@syncagent/js
Advanced tools
Core JavaScript/TypeScript SDK for SyncAgent — add an AI database agent to any app.
npm install @syncagent/js
import { SyncAgentClient } from "@syncagent/js";
const agent = new SyncAgentClient({
apiKey: "sa_your_api_key",
connectionString: process.env.DATABASE_URL,
// baseUrl: "http://localhost:3100", // dev only — defaults to https://syncagent.dev
});
const result = await agent.chat([
{ role: "user", content: "How many users do we have?" }
]);
console.log(result.text);
new SyncAgentClient(config: SyncAgentConfig)
| Option | Type | Required | Description |
|---|---|---|---|
apiKey | string | ✅ | Your SyncAgent API key (sa_...) |
connectionString | string | ✅ | Your database URL — sent at runtime, never stored |
tools | Record<string, ToolDefinition> | — | Custom tools the agent can call client-side |
baseUrl | string | — | Override API URL. Defaults to https://syncagent.dev |
filter | Record<string, any> | — | Mandatory query filter — scopes ALL operations to matching records. Use for multi-tenant SaaS. |
operations | ("read"|"create"|"update"|"delete")[] | — | Restrict which operations are allowed for this session. Must be a subset of the project's configured operations. |
client.chat(messages, options?)const result = await agent.chat(messages, options);
messages — Message[]
{ role: "user" | "assistant"; content: string }
options — ChatOptions
| Option | Type | Description |
|---|---|---|
onToken | (token: string) => void | Called for each streamed text chunk |
onComplete | (text: string) => void | Called with the full response text |
onError | (error: Error) => void | Called on error |
onStatus | (step: string, label: string) => void | Called with live status updates while working |
onData | (data: ToolData) => void | Called when a DB tool returns structured data |
onToolCall | (name: string, args: any, result: any) => void | Called when a custom tool executes |
signal | AbortSignal | Cancel the request |
context | Record<string, any> | Extra context injected into every message |
Returns Promise<ChatResult> → { text: string }
onStatus fires with these step values:
"connecting" — connecting to the database"schema" — discovering schema"thinking" — AI is reasoning"querying" — executing a DB tool"done" — completeclient.getSchema()const schema = await agent.getSchema();
// CollectionSchema[]
Pass per-message context so the agent knows what the user is looking at:
await agent.chat(messages, {
context: {
userId: "user_123",
currentPage: "orders",
selectedOrderId: "ord_456",
}
});
onData callbackReact to structured query results in your own UI:
const agent = new SyncAgentClient({
apiKey: "sa_your_key",
connectionString: process.env.DATABASE_URL,
});
await agent.chat(messages, {
onData: (data) => {
// data.tool — "query_documents" | "aggregate_documents"
// data.collection — e.g. "orders"
// data.data — array of result rows
// data.count — number of results
console.log(`Got ${data.count} rows from ${data.collection}`);
setTableData(data.data); // update your own table component
}
});
const agent = new SyncAgentClient({
apiKey: "sa_your_key",
connectionString: process.env.DATABASE_URL,
tools: {
sendEmail: {
description: "Send an email to a user",
inputSchema: {
to: { type: "string", description: "Recipient email" },
subject: { type: "string", description: "Subject line" },
body: { type: "string", description: "Email body" },
},
execute: async ({ to, subject, body }) => {
await mailer.send({ to, subject, text: body });
return { sent: true };
},
},
},
});
When building a SaaS app, multiple organizations share the same database. Pass filter to scope every agent operation to the current user's organization. The agent cannot query, insert, update, or delete outside this scope — it's enforced server-side.
import { SyncAgentClient } from "@syncagent/js";
// Scope to the current user's organization
const agent = new SyncAgentClient({
apiKey: "sa_your_key",
connectionString: process.env.DATABASE_URL,
filter: { organizationId: currentUser.orgId },
});
// Every query is now automatically scoped:
// "Show all orders" → db.orders.find({ organizationId: "org_123" })
// "Count users" → db.users.countDocuments({ organizationId: "org_123" })
// "Add a product" → db.products.insertOne({ ...doc, organizationId: "org_123" })
Without filter — agent queries everything (suitable for single-tenant apps or admin tools).
With filter — every read, write, update, and delete is strictly scoped. The agent is told about the scope in its system prompt and cannot override it.
Common patterns:
// By organization ID
filter: { organizationId: org.id }
// By tenant slug
filter: { tenant: "acme-corp" }
// By user ID (personal data)
filter: { userId: currentUser.id }
// Multiple fields
filter: { orgId: org.id, deleted: false }
// SQL databases (same syntax)
filter: { tenant_id: tenant.id }
const history: Message[] = [];
history.push({ role: "user", content: "Show top 5 customers" });
const r1 = await agent.chat(history);
history.push({ role: "assistant", content: r1.text });
history.push({ role: "user", content: "Now email all of them" });
const r2 = await agent.chat(history);
const controller = new AbortController();
agent.chat(messages, { signal: controller.signal });
controller.abort(); // cancel at any time
import type {
SyncAgentConfig, Message, ChatOptions, ChatResult,
CollectionSchema, SchemaField, ToolDefinition, ToolParameter, ToolData,
} from "@syncagent/js";
MIT
Use operations to give different users different levels of access within the same project. The client can only restrict further — it can never grant more than what the project dashboard allows.
// Read-only for regular users
const agent = new SyncAgentClient({
apiKey: "sa_your_key",
connectionString: process.env.DATABASE_URL,
filter: { organizationId: currentUser.orgId },
operations: ["read"],
});
// Full access for admins
const adminAgent = new SyncAgentClient({
apiKey: "sa_your_key",
connectionString: process.env.DATABASE_URL,
filter: { organizationId: currentUser.orgId },
operations: ["read", "create", "update", "delete"],
});
FAQs
SyncAgent JavaScript SDK — AI database agent for any app
The npm package @syncagent/js receives a total of 19 weekly downloads. As such, @syncagent/js popularity was classified as not popular.
We found that @syncagent/js demonstrated a healthy version release cadence and project activity because the last version was released less than a year ago. It has 1 open source maintainer collaborating on the project.
Did you know?

Socket for GitHub automatically highlights issues in each pull request and monitors the health of all your open source dependencies. Discover the contents of your packages and block harmful activity before you install or update your dependencies.

Security News
Vibe coding at scale is reshaping how packages are created, contributed, and selected across the software supply chain

Security News
npm invalidated all granular access tokens that bypass 2FA after a fresh Mini Shai-Hulud wave compromised 323 npm packages. Staged publishing also entered public preview.

Research
/Security News
Compromised npm package art-template delivered a Coruna-like iOS Safari exploit framework through a watering-hole attack.