{"id":43806,"library":"selectstar","title":"selectstar","description":"Selectstar is a JavaScript/TypeScript library for generating safe, parameterized SQL queries for PostgreSQL using tagged template literals. Current stable version is 1.1.11, maintained since 2018. It provides primitives for constructing dynamic queries without SQL injection risks: parameterized values, query fragments (template), dynamic identifiers, and lists. Unlike alternatives like squel or knex, selectstar stays close to raw SQL syntax while enforcing parameterization — it is ignorant of query semantics, making it ideal for complex or raw SQL generation. It is fully typed (TypeScript declarations included) and integrates directly with node-postgres (pg) via query objects containing text and values. The package has no runtime dependencies.","status":"active","version":"1.1.11","language":"javascript","source_language":"en","source_url":"https://github.com/faradayio/selectstar","tags":["javascript","sql","postgres","postgresql","node-postgres","typescript"],"install":[{"cmd":"npm install selectstar","lang":"bash","label":"npm"},{"cmd":"yarn add selectstar","lang":"bash","label":"yarn"},{"cmd":"pnpm add selectstar","lang":"bash","label":"pnpm"}],"dependencies":[],"imports":[{"note":"sql is a named export, not a default export. Common mistake when migrating from CJS to ESM.","wrong":"import sql from 'selectstar'","symbol":"sql","correct":"import { sql } from 'selectstar'"},{"note":"template is a named export. CJS require() is also valid but the wrong example shows destructuring from require — actually that's fine. The common mistake is trying to use template as a default import or not importing it at all.","wrong":"const { template } = require('selectstar')","symbol":"template","correct":"import { template } from 'selectstar'"},{"note":"identifier is a named export. The CJS pattern using dot notation is valid, but the ESM named import is preferred for TypeScript.","wrong":"const identifier = require('selectstar').identifier","symbol":"identifier","correct":"import { identifier } from 'selectstar'"},{"note":"List is a named export. Ensure you import it correctly to generate comma-separated SQL lists.","wrong":"const list = require('selectstar').list","symbol":"list","correct":"import { list } from 'selectstar'"},{"note":"Use 'import type' for TypeScript type-only imports to avoid runtime bloat. Query is the type of objects returned by sql``.","wrong":"import { Query } from 'selectstar'","symbol":"types","correct":"import type { Query } from 'selectstar'"}],"quickstart":{"code":"import { sql, template, identifier, list } from 'selectstar';\nimport { Pool } from 'pg';\n\nconst pool = new Pool();\n\nasync function runQuery() {\n  const id = 42;\n  const tableName = 'users';\n  const columns = ['id', 'name'];\n  const rows = [{ name: 'Alice' }, { name: 'Bob' }];\n\n  const query = sql`SELECT ${identifier(columns[0])} FROM ${identifier(tableName)} WHERE id = ${id}`;\n  // => { text: 'SELECT \"id\" FROM \"users\" WHERE id = $1', values: [42] }\n\n  const result = await pool.query(query);\n  console.log(result.rows);\n}\n\nrunQuery().catch(console.error);","lang":"typescript","description":"Demonstrates basic parameterized query, dynamic identifier, and integration with node-postgres pool.query."},"warnings":[{"fix":"Cache static queries outside hot loops if needed; e.g., const query = sql`SELECT 1`;","message":"Template literals are not compiled: they generate Query objects at runtime. Performance overhead is minimal but be aware that each call to sql`` creates a new object.","severity":"gotcha","affected_versions":">=0.0.0"},{"fix":"Validate or whitelist identifiers (e.g., column names) before passing to identifier().","message":"identifier does not escape user input enough: it only quotes identifiers using node-postgres's escapeIdentifier. Do not use with untrusted strings that might contain quotes or backslashes without additional validation.","severity":"gotcha","affected_versions":">=0.0.0"},{"fix":"Check array length before constructing list: if (items.length === 0) throw new Error('Need at least one item');","message":"List with no elements: calling list([]) or list with an empty array results in an empty string, which can cause syntax errors if inserted into a query expecting at least one item (e.g., IN ()).","severity":"gotcha","affected_versions":">=0.0.0"},{"fix":"Wrap template usage in ${} within sql``: sql`SELECT * FROM ${template`users`}` — though in this simple case identifier is safer.","message":"If you use template inside sql literal but pass it directly (not as a placeholder), the result might be incorrect. Always use ${template`...`} interpolation.","severity":"gotcha","affected_versions":">=0.0.0"},{"fix":"Upgrade to >=1.0.0 and use { text, values } object. Old call sites: { sql: '...', params: [...] } should be changed.","message":"Before v1.0.0, the library returned a different object shape with keys 'sql' and 'params'. In v1.0.0+, it returns { text, values }. Upgrading from pre-1.0 breaks pg integration.","severity":"breaking","affected_versions":"<1.0.0"}],"env_vars":null,"search_vec":"'1.1.11':23 '2018':26 'altern':48 'close':55 'complex':73 'construct':31 'contain':96 'current':19 'declar':83 'depend':105 'direct':87 'dynam':32,43 'enforc':61 'fragment':41 'fulli':80 'generat':8,77 'ideal':71 'identifi':44 'ignor':65 'includ':84 'inject':36 'integr':86 'javascript':106 'javascript/typescript':5 'knex':52 'librari':6 'like':49 'list':46 'liter':18 'maintain':24 'make':69 'node':90,111 'node-postgr':89,110 'object':95 'packag':101 'parameter':10,38,62 'pg':92 'postgr':91,108,112 'postgresql':14,109 'primit':29 'provid':28 'queri':12,33,40,67,94 'raw':57,75 'risk':37 'runtim':104 'safe':9 'selectstar':1,2,53 'semant':68 'sinc':25 'sql':11,35,58,76,107 'squel':50 'stabl':20 'stay':54 'syntax':59 'tag':16 'templat':17,42 'text':97 'type':81 'typescript':82,113 'unlik':47 'use':15 'valu':39,99 'version':21 'via':93 'without':34","created_at":"2026-06-05T17:01:33.766125+00:00","updated_at":"2026-06-05T17:01:33.766125+00:00","problems":[{"fix":"Change import to: import { sql } from 'selectstar';","cause":"Default import used when only named exports exist: import sql from 'selectstar' instead of import { sql } from 'selectstar'.","error":"TypeError: (0 , selectstar.sql) is not a function"},{"fix":"Run 'npm install selectstar' and ensure tsconfig.json includes 'node_modules/@types' or 'moduleResolution': 'node'.","cause":"Missing npm install or TypeScript cannot find package types. Package ships .d.ts files, so no @types/selectstar needed.","error":"Cannot find module 'selectstar' or its corresponding type declarations."},{"fix":"Add: import { identifier } from 'selectstar';","cause":"Using identifier as a global function without importing it.","error":"ERROR: 'identifier' is not defined"},{"fix":"Use query.text to get the SQL string, or JSON.stringify(query) to inspect both text and values.","cause":"Attempting to pass a sql`` result directly to a function expecting a string (e.g., console.log(query)). The Query object is not a string; use query.text for debugging.","error":"Type 'Query' is not assignable to parameter of type 'string'"}],"ecosystem":"npm","meta_description":null,"install_score":null,"quickstart_score":null,"quickstart_tag":null,"pypi_latest":null,"cli_name":null,"cli_version":null,"type":"library","homepage":"https://github.com/faradayio/selectstar#readme","github":"https://github.com/faradayio/selectstar","docs":null,"changelog":null,"pypi":null,"npm":"selectstar","openapi_spec":null,"status_page":null,"smithery":null,"categories":["database"],"base_url":null,"auth_type":null,"provenance":{"verified_status":null,"verified_at":null,"last_verified":"2026-06-05","next_check":"2026-09-03","install_tag":null}}