skills/clickhouse-js-node-coding/SKILL.md
Write idiomatic application code with the ClickHouse Node.js client (`@clickhouse/client`). Use this skill whenever a user is *building* against the Node.js client — configuring the client, pinging, inserting rows in JSON or raw formats, selecting and parsing results, binding query parameters, managing sessions and temporary tables, working with data types or customizing JSON parsing. Do NOT use for browser/Web client code.
npx skillsauth add ClickHouse/agent-skills clickhouse-js-node-codingInstall this skill globally with one command. Works with Claude Code, Cursor, and Windsurf.
3 of 9 scanners reported clean
Some scanners were skipped, did not run, or reported a non-clean status. Review each row below.
Reference: https://clickhouse.com/docs/integrations/javascript
⚠️ Node.js runtime only. This skill covers the
@clickhouse/clientpackage running in a Node.js runtime exclusively — including Next.js Node runtime API routes, React Server Components, Server Actions, and standard Node.js processes. Do not apply this skill to browser client components, Web Workers, Next.js Edge runtime, Cloudflare Workers, or any usage of@clickhouse/client-web. For browser/edge environments, the correct package is@clickhouse/client-web.
@clickhouse/client (never @clickhouse/client-web)
and create a client with createClient({ url }) or rely on
supported defaults when appropriate. Close it with await client.close()
preferably when it's no longer needed or during graceful shutdown for global resources.JSONEachRow for typical row inserts/selects unless the user
has already chosen another format or is streaming raw bytes (CSV / TSV /
Parquet — see examples/node/performance/).
Note on clickhouse_settings: settings passed to createClient are
defaults for every request; they can be overridden per-call by passing
clickhouse_settings directly to insert(), query(), or command().
Always mention this when the user configures settings at the client level.query_params for user-supplied values — never template-
literal-interpolate them into SQL. See reference/query-parameters.md.
When answering a parameter-binding question, your response must
explicitly name template-literal interpolation as a "SQL injection
risk" — even when the user only asked about syntax and did not raise
security. The literal phrase "SQL injection" needs to appear; this is
the most common mistake from PostgreSQL/MySQL users and the security
framing is part of the correct answer, not an optional aside.client.insert() — write rows.client.query() + resultSet.json() / .text() / .stream() — read
rows that return data.client.command() — DDL and other statements that don't return rows
(CREATE, DROP, TRUNCATE, ALTER, SET in a session, etc.).client.exec() — when you need the raw response stream of an arbitrary
statement (rare in coding scenarios).client.ping() — health check; returns { success, error? }, never
throws on connection failure.pathname config option: client >= 1.0.0.BigInt values in query_params: client >= 1.15.0.TupleParam and JS Map in query_params: client >= 1.9.0.json.parse / json.stringify: client >= 1.14.0.Time / Time64 data types: ClickHouse server >= 25.6.QBit data type: ClickHouse server >= 25.10 (GA on 26.x).Dynamic / Variant / new JSON types: ClickHouse server >= 24.1 /
24.5 / 24.8 (no longer experimental since 25.3).Identify the user's task and read the matching reference file.
| Task | Triggers / symptoms | Reference file |
| -------------------------------------------------------- | ------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------------- | ----------------------------------- |
| Configure / connect the client | Building a createClient call, URL parameters, clickhouse_settings, default format, custom HTTP headers | reference/client-configuration.md |
| Compress requests / responses | compression, gzip vs zstd, { codec } option shape, Node version requirements, web limitations | reference/compression.md |
| Ping the server | Health checks, readiness probes, "is ClickHouse up?" | reference/ping.md |
| Choose an insert format | "Which format should I use to insert?", JSON vs raw, JSONEachRow vs JSON vs JSONObjectEachRow | reference/insert-formats.md |
| Insert into a subset of columns / different database | insert({ columns }), excluding columns, ephemeral columns, cross-DB inserts | reference/insert-columns.md |
| Insert values, expressions, dates, decimals | INSERT … VALUES with SQL functions, Date/DateTime from JS, Decimal precision, INSERT … SELECT; inserting a UUID into a UInt128 column is tricky — use when the user is writing code that stores a UUID as UInt128 | reference/insert-values.md |
| Async inserts (server-side batching) | async_insert=1, fire-and-forget vs wait-for-ack | reference/async-insert.md |
| Select and parse results | JSONEachRow reads, JSON with metadata, picking a select format | reference/select-formats.md |
| Parameterize queries | Binding values, special characters / escaping, "SQL injection?", {name: Type} syntax | reference/query-parameters.md |
| Sessions & temporary tables | session_id, CREATE TEMPORARY TABLE, per-session SET commands | reference/sessions.md |
| Modern data types | Dynamic, Variant, JSON (object), Time, Time64, QBit (vector search) | reference/data-types.md |
| Custom JSON parse/stringify | Plug in JSONBig / safe-stable-stringify / a BigInt-aware serializer | reference/custom-json.md |
import { createClient } from '@clickhouse/client' (Node, never
Web).await client.close() at the end of self-contained snippets; in
long-running services, close on graceful shutdown.format: 'JSONEachRow' and values: [...] unless the
user's scenario requires otherwise.await (await client.query({...})).json<RowType>() for
small / medium result sets; for bigger results suggest streaming.{name: Type}
syntax — never $1, ?, or :name.clickhouse_settings: { wait_end_of_query: 1 } on the command() call so
the server only acknowledges after the change is applied. See
https://clickhouse.com/docs/en/interfaces/http/#response-buffering.This skill covers day-to-day coding against @clickhouse/client (Node).
The following topics are intentionally not covered here:
ECONNRESET → use the
clickhouse-js-node-troubleshooting skill.examples/node/performance/.examples/node/security/.CREATE TABLE patterns, deployment-shaped connection strings,
replication / sharding choices — see
examples/node/schema-and-deployments/.@clickhouse/client-web and see
examples/web/.examples/node/coding/ — the runnable corpus this skill is built on.tools
Sets up and manages Postgres using the clickhousectl CLI — runs a local Docker-backed Postgres for development, and creates and operates managed ClickHouse Cloud Postgres services (connections, TLS, runtime config, read replicas, failover, point-in-time restore). Use when the user wants a Postgres or PostgreSQL database for their application, a local Postgres dev environment, psql access, or a managed/production Postgres in ClickHouse Cloud, or mentions moving a local Postgres to production.
tools
Sets up and manages ClickHouse using the clickhousectl CLI — installs and runs a local ClickHouse server for development, and creates managed ClickHouse Cloud services for production (authentication, service creation, schema migration, application connection). Use when the user wants to build an application with ClickHouse, set up a local ClickHouse dev environment, create tables and start querying, deploy ClickHouse to production or ClickHouse Cloud, or migrate from a local setup to the cloud.
tools
Use when a user wants to wire an OpenTelemetry collector into a Managed ClickStack service on ClickHouse Cloud, either by deploying a new local collector (Docker run or Docker Compose) or by configuring their own existing collector, then send rich synthetic telemetry and verify it is visible in ClickStack.
tools
Troubleshoot and resolve common issues with the ClickHouse Node.js client (@clickhouse/client). Use this skill whenever a user reports errors, unexpected behavior, or configuration questions involving the Node.js client specifically — including socket hang-up errors, Keep-Alive problems, stream handling issues, data type mismatches, read-only user restrictions, proxy/TLS setup problems, or long-running query timeouts. Trigger even when the user hasn't precisely named the issue; vague symptoms like "my inserts keep failing" or "connection drops randomly" in a Node.js context are strong signals to use this skill. Do NOT use for browser/Web client issues.