@querypanel/node-sdk 1.3.0 → 1.3.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
package/dist/index.d.cts CHANGED
@@ -731,12 +731,11 @@ interface AskOptions {
731
731
  */
732
732
  querypanelSessionId?: string;
733
733
  /**
734
- * Pipeline version for query generation.
735
- * Defaults to `"v2"` (`POST /v2/query`).
736
- * - `"v2"` (default): intent planning, hybrid retrieval, schema linking, SQL reflection
737
- * - `"v1"` (**deprecated**): legacy `POST /query` pipeline — prefer omitting or `"v2"`
734
+ * Query pipeline. Only `"v2"` is accepted (`POST /v2/query`).
735
+ * `"v1"` was removed: passing it fails typecheck and throws at runtime.
736
+ * Omit this field; asks always use v2.
738
737
  */
739
- pipeline?: "v1" | "v2";
738
+ pipeline?: "v2";
740
739
  /**
741
740
  * Optional model id for SQL generation (e.g. OpenAI or `gemini-*` when the API uses Gemini). Omit for server default.
742
741
  */
@@ -750,7 +749,7 @@ interface AskOptions {
750
749
  * Use this for tenant-specific policies (e.g. retention windows) that must
751
750
  * be enforced on every query.
752
751
  *
753
- * Sent when the resolved pipeline is `"v2"` (the default).
752
+ * Sent on every ask (`POST /v2/query`).
754
753
  */
755
754
  systemPrompt?: string;
756
755
  /**
@@ -828,9 +827,10 @@ interface AskResponse {
828
827
  trace?: PipelineTrace;
829
828
  }
830
829
  /**
831
- * Resolve ask/modify pipeline. Defaults to v2; `"v1"` remains available but deprecated.
830
+ * Resolve ask/modify pipeline. Always `"v2"` (`POST /v2/query`).
831
+ * Throws if a removed pipeline such as `"v1"` is passed.
832
832
  */
833
- declare function resolveQueryPipeline(pipeline?: "v1" | "v2"): "v1" | "v2";
833
+ declare function resolveQueryPipeline(pipeline?: "v2"): "v2";
834
834
  declare function anonymizeResults(rows: Array<Record<string, unknown>>): Array<Record<string, string>>;
835
835
 
836
836
  /**
@@ -985,12 +985,11 @@ interface ChartModifyOptions {
985
985
  /** Chart generation method: 'vega-lite' or 'vizspec' */
986
986
  chartType?: "vega-lite" | "vizspec";
987
987
  /**
988
- * Pipeline version for SQL regeneration.
989
- * Defaults to `"v2"` (`POST /v2/query`).
990
- * - `"v2"` (default): intent planning, hybrid retrieval, schema linking, SQL reflection
991
- * - `"v1"` (**deprecated**): legacy `POST /query` pipeline — prefer omitting or `"v2"`
988
+ * Query pipeline. Only `"v2"` is accepted (`POST /v2/query`).
989
+ * `"v1"` was removed: passing it fails typecheck and throws at runtime.
990
+ * Omit this field; chart modifications always use v2.
992
991
  */
993
- pipeline?: "v1" | "v2";
992
+ pipeline?: "v2";
994
993
  /**
995
994
  * QueryPanel session ID for context-aware follow-ups.
996
995
  * Pass the querypanelSessionId from a previous ask() response
package/dist/index.d.ts CHANGED
@@ -731,12 +731,11 @@ interface AskOptions {
731
731
  */
732
732
  querypanelSessionId?: string;
733
733
  /**
734
- * Pipeline version for query generation.
735
- * Defaults to `"v2"` (`POST /v2/query`).
736
- * - `"v2"` (default): intent planning, hybrid retrieval, schema linking, SQL reflection
737
- * - `"v1"` (**deprecated**): legacy `POST /query` pipeline — prefer omitting or `"v2"`
734
+ * Query pipeline. Only `"v2"` is accepted (`POST /v2/query`).
735
+ * `"v1"` was removed: passing it fails typecheck and throws at runtime.
736
+ * Omit this field; asks always use v2.
738
737
  */
739
- pipeline?: "v1" | "v2";
738
+ pipeline?: "v2";
740
739
  /**
741
740
  * Optional model id for SQL generation (e.g. OpenAI or `gemini-*` when the API uses Gemini). Omit for server default.
742
741
  */
@@ -750,7 +749,7 @@ interface AskOptions {
750
749
  * Use this for tenant-specific policies (e.g. retention windows) that must
751
750
  * be enforced on every query.
752
751
  *
753
- * Sent when the resolved pipeline is `"v2"` (the default).
752
+ * Sent on every ask (`POST /v2/query`).
754
753
  */
755
754
  systemPrompt?: string;
756
755
  /**
@@ -828,9 +827,10 @@ interface AskResponse {
828
827
  trace?: PipelineTrace;
829
828
  }
830
829
  /**
831
- * Resolve ask/modify pipeline. Defaults to v2; `"v1"` remains available but deprecated.
830
+ * Resolve ask/modify pipeline. Always `"v2"` (`POST /v2/query`).
831
+ * Throws if a removed pipeline such as `"v1"` is passed.
832
832
  */
833
- declare function resolveQueryPipeline(pipeline?: "v1" | "v2"): "v1" | "v2";
833
+ declare function resolveQueryPipeline(pipeline?: "v2"): "v2";
834
834
  declare function anonymizeResults(rows: Array<Record<string, unknown>>): Array<Record<string, string>>;
835
835
 
836
836
  /**
@@ -985,12 +985,11 @@ interface ChartModifyOptions {
985
985
  /** Chart generation method: 'vega-lite' or 'vizspec' */
986
986
  chartType?: "vega-lite" | "vizspec";
987
987
  /**
988
- * Pipeline version for SQL regeneration.
989
- * Defaults to `"v2"` (`POST /v2/query`).
990
- * - `"v2"` (default): intent planning, hybrid retrieval, schema linking, SQL reflection
991
- * - `"v1"` (**deprecated**): legacy `POST /query` pipeline — prefer omitting or `"v2"`
988
+ * Query pipeline. Only `"v2"` is accepted (`POST /v2/query`).
989
+ * `"v1"` was removed: passing it fails typecheck and throws at runtime.
990
+ * Omit this field; chart modifications always use v2.
992
991
  */
993
- pipeline?: "v1" | "v2";
992
+ pipeline?: "v2";
994
993
  /**
995
994
  * QueryPanel session ID for context-aware follow-ups.
996
995
  * Pass the querypanelSessionId from a previous ask() response
package/dist/index.js CHANGED
@@ -14,6 +14,13 @@ var BigQueryAdapter = class {
14
14
  );
15
15
  }
16
16
  }
17
+ clientFn;
18
+ projectId;
19
+ datasetProjectId;
20
+ defaultDataset;
21
+ databaseName;
22
+ kind;
23
+ allowedTables;
17
24
  async execute(sql, params) {
18
25
  if (this.allowedTables) {
19
26
  this.validateQueryTables(sql);
@@ -244,6 +251,11 @@ var ClickHouseAdapter = class {
244
251
  this.allowedTables = normalizeTableFilter2(options.allowedTables);
245
252
  }
246
253
  }
254
+ clientFn;
255
+ databaseName;
256
+ defaultFormat;
257
+ kind;
258
+ allowedTables;
247
259
  async execute(sql, params) {
248
260
  if (this.allowedTables) {
249
261
  this.validateQueryTables(sql);
@@ -497,6 +509,11 @@ var PostgresAdapter = class {
497
509
  );
498
510
  }
499
511
  }
512
+ clientFn;
513
+ databaseName;
514
+ defaultSchema;
515
+ kind;
516
+ allowedTables;
500
517
  async execute(sql, params) {
501
518
  if (this.allowedTables) {
502
519
  this.validateQueryTables(sql);
@@ -805,6 +822,9 @@ var QueryPipelineError = class extends Error {
805
822
  this.status = status;
806
823
  this.name = "QueryPipelineError";
807
824
  }
825
+ code;
826
+ details;
827
+ status;
808
828
  /**
809
829
  * Check if this is a moderation error
810
830
  */
@@ -857,8 +877,14 @@ var QueryPipelineError = class extends Error {
857
877
 
858
878
  // src/core/client.ts
859
879
  var ApiClient = class {
880
+ baseUrl;
881
+ privateKey;
882
+ organizationId;
883
+ defaultTenantId;
884
+ additionalHeaders;
885
+ fetchImpl;
886
+ cryptoKey = null;
860
887
  constructor(baseUrl, privateKey, organizationId, options) {
861
- this.cryptoKey = null;
862
888
  if (!baseUrl) {
863
889
  throw new Error("Base URL is required");
864
890
  }
@@ -1112,6 +1138,8 @@ var ApiClient = class {
1112
1138
 
1113
1139
  // src/core/callback-client.ts
1114
1140
  var CallbackApiClient = class {
1141
+ requestHandler;
1142
+ defaultTenantId;
1115
1143
  constructor(requestHandler, options) {
1116
1144
  this.requestHandler = requestHandler;
1117
1145
  this.defaultTenantId = options?.defaultTenantId;
@@ -1254,10 +1282,9 @@ function normalizeSqlParamsInput(params) {
1254
1282
 
1255
1283
  // src/core/query-engine.ts
1256
1284
  var QueryEngine = class {
1257
- constructor() {
1258
- this.databases = /* @__PURE__ */ new Map();
1259
- this.databaseMetadata = /* @__PURE__ */ new Map();
1260
- }
1285
+ databases = /* @__PURE__ */ new Map();
1286
+ databaseMetadata = /* @__PURE__ */ new Map();
1287
+ defaultDatabase;
1261
1288
  attachDatabase(name, adapter, metadata) {
1262
1289
  this.databases.set(name, adapter);
1263
1290
  this.databaseMetadata.set(name, metadata);
@@ -1943,7 +1970,13 @@ import crypto4 from "crypto";
1943
1970
  // src/routes/query.ts
1944
1971
  import crypto3 from "crypto";
1945
1972
  function resolveQueryPipeline(pipeline) {
1946
- return pipeline ?? "v2";
1973
+ const requested = pipeline;
1974
+ if (requested != null && requested !== "v2") {
1975
+ throw new Error(
1976
+ `Query pipeline "${requested}" was removed. ask() and modifyChart() always use POST /v2/query.`
1977
+ );
1978
+ }
1979
+ return "v2";
1947
1980
  }
1948
1981
  async function ask(client, queryEngine, question, options, signal) {
1949
1982
  const tenantId = resolveTenantId5(client, options.tenantId);
@@ -1953,8 +1986,9 @@ async function ask(client, queryEngine, question, options, signal) {
1953
1986
  let attempt = 0;
1954
1987
  let lastError = options.lastError;
1955
1988
  let previousSql = options.previousSql;
1956
- const pipeline = resolveQueryPipeline(options.pipeline);
1957
- const queryEndpoint = pipeline === "v2" ? "/v2/query" : "/query";
1989
+ let parentQueryId;
1990
+ resolveQueryPipeline(options.pipeline);
1991
+ const queryEndpoint = "/v2/query";
1958
1992
  while (attempt <= maxRetry) {
1959
1993
  const databaseName = options.database ?? queryEngine.getDefaultDatabase();
1960
1994
  const metadata = databaseName ? queryEngine.getDatabaseMetadata(databaseName) : void 0;
@@ -1984,7 +2018,8 @@ async function ask(client, queryEngine, question, options, signal) {
1984
2018
  ...databaseName ? { database: databaseName } : {},
1985
2019
  ...metadata?.dialect ? { dialect: metadata.dialect } : {},
1986
2020
  ...options.model?.trim() ? { model: options.model.trim() } : {},
1987
- ...pipeline === "v2" && options.systemPrompt?.trim() ? { system_prompt: options.systemPrompt.trim() } : {},
2021
+ ...options.systemPrompt?.trim() ? { system_prompt: options.systemPrompt.trim() } : {},
2022
+ ...parentQueryId ? { parent_query_id: parentQueryId } : {},
1988
2023
  debug: options.debug ?? false
1989
2024
  },
1990
2025
  tenantId,
@@ -2006,6 +2041,9 @@ async function ask(client, queryEngine, question, options, signal) {
2006
2041
  if (!sql || !dialect) {
2007
2042
  throw new Error("Query response missing required SQL or dialect");
2008
2043
  }
2044
+ if (queryResponse.data.queryId) {
2045
+ parentQueryId = queryResponse.data.queryId;
2046
+ }
2009
2047
  const dbName = queryResponse.data.database ?? options.database ?? queryEngine.getDefaultDatabase();
2010
2048
  if (!dbName) {
2011
2049
  throw new Error(
@@ -2165,35 +2203,35 @@ async function resolveQuery(client, queryEngine, queryId, options, signal) {
2165
2203
  dialect: response.dialect
2166
2204
  };
2167
2205
  }
2206
+ async function markQueryExecuted(client, queryId, options, signal) {
2207
+ try {
2208
+ await client.post(
2209
+ `/v2/queries/${encodeURIComponent(queryId)}/executed`,
2210
+ {},
2211
+ options.tenantId,
2212
+ options.userId,
2213
+ options.scopes,
2214
+ signal
2215
+ );
2216
+ } catch {
2217
+ }
2218
+ }
2168
2219
 
2169
2220
  // src/routes/modify.ts
2170
- function buildModifiedQuestion(originalQuestion, modifications, pipeline, hasSessionContext = false) {
2221
+ function buildModifiedQuestion(originalQuestion, modifications, hasSessionContext = false) {
2171
2222
  const hints = [];
2172
2223
  if (modifications.timeGranularity) {
2173
2224
  hints.push(`group results by ${modifications.timeGranularity}`);
2174
2225
  }
2175
2226
  if (modifications.dateRange) {
2176
- if (pipeline === "v2") {
2177
- const from = normalizeDateInput(modifications.dateRange.from);
2178
- const to = normalizeDateInput(modifications.dateRange.to);
2179
- if (from && to) {
2180
- hints.push(`change date range to ${from} through ${to}`);
2181
- } else if (from) {
2182
- hints.push(`change start date to ${from}`);
2183
- } else if (to) {
2184
- hints.push(`change end date to ${to}`);
2185
- }
2186
- } else {
2187
- const parts = [];
2188
- if (modifications.dateRange.from) {
2189
- parts.push(`from ${modifications.dateRange.from}`);
2190
- }
2191
- if (modifications.dateRange.to) {
2192
- parts.push(`to ${modifications.dateRange.to}`);
2193
- }
2194
- if (parts.length > 0) {
2195
- hints.push(`filter date range ${parts.join(" ")}`);
2196
- }
2227
+ const from = normalizeDateInput(modifications.dateRange.from);
2228
+ const to = normalizeDateInput(modifications.dateRange.to);
2229
+ if (from && to) {
2230
+ hints.push(`change date range to ${from} through ${to}`);
2231
+ } else if (from) {
2232
+ hints.push(`change start date to ${from}`);
2233
+ } else if (to) {
2234
+ hints.push(`change end date to ${to}`);
2197
2235
  }
2198
2236
  }
2199
2237
  if (modifications.additionalInstructions) {
@@ -2202,7 +2240,7 @@ function buildModifiedQuestion(originalQuestion, modifications, pipeline, hasSes
2202
2240
  if (hints.length === 0) {
2203
2241
  return originalQuestion;
2204
2242
  }
2205
- if (pipeline === "v2" && hasSessionContext) {
2243
+ if (hasSessionContext) {
2206
2244
  return hints.join(", ");
2207
2245
  }
2208
2246
  return `${originalQuestion} (${hints.join(", ")})`;
@@ -2318,8 +2356,8 @@ async function modifyChart(client, queryEngine, input, options, signal) {
2318
2356
  const hasSqlMods = !!input.sqlModifications;
2319
2357
  const hasVizMods = !!input.vizModifications;
2320
2358
  const hasCustomSql = !!input.sqlModifications?.customSql;
2321
- const pipeline = resolveQueryPipeline(options?.pipeline);
2322
- const queryEndpoint = pipeline === "v2" ? "/v2/query" : "/query";
2359
+ resolveQueryPipeline(options?.pipeline);
2360
+ const queryEndpoint = "/v2/query";
2323
2361
  let currentSql = input.sql;
2324
2362
  let finalParams = input.params ?? {};
2325
2363
  let paramMetadata = [];
@@ -2375,12 +2413,9 @@ async function modifyChart(client, queryEngine, input, options, signal) {
2375
2413
  const modifiedQuestion = buildModifiedQuestion(
2376
2414
  input.question,
2377
2415
  input.sqlModifications,
2378
- pipeline,
2379
2416
  hasQuerypanelSessionContext
2380
2417
  );
2381
- if (pipeline === "v2") {
2382
- finalQuestion = modifiedQuestion;
2383
- }
2418
+ finalQuestion = modifiedQuestion;
2384
2419
  const queryResponse = await client.post(
2385
2420
  queryEndpoint,
2386
2421
  {
@@ -2402,13 +2437,11 @@ async function modifyChart(client, queryEngine, input, options, signal) {
2402
2437
  finalSql = queryResponse.sql;
2403
2438
  paramMetadata = Array.isArray(queryResponse.params) ? queryResponse.params : [];
2404
2439
  finalParams = queryEngine.mapGeneratedParams(paramMetadata);
2405
- if (pipeline === "v2") {
2406
- applyDateRangeOverrides(
2407
- input.sqlModifications?.dateRange,
2408
- finalParams,
2409
- paramMetadata
2410
- );
2411
- }
2440
+ applyDateRangeOverrides(
2441
+ input.sqlModifications?.dateRange,
2442
+ finalParams,
2443
+ paramMetadata
2444
+ );
2412
2445
  rationale = queryResponse.rationale;
2413
2446
  queryId = queryResponse.queryId;
2414
2447
  sqlChanged = finalSql !== currentSql;
@@ -2626,6 +2659,9 @@ function resolveAttachEnforceTenantIsolation(tenantFieldName, enforceTenantIsola
2626
2659
  return tenantFieldName ? true : void 0;
2627
2660
  }
2628
2661
  var QueryPanelSdkAPI = class _QueryPanelSdkAPI {
2662
+ client;
2663
+ queryEngine;
2664
+ supportedChartTypes;
2629
2665
  /**
2630
2666
  * @param workspaceId - Workspace UUID (same value as your org in the dashboard). Passed to the API as JWT claim `organizationId`.
2631
2667
  */
@@ -2877,6 +2913,11 @@ var QueryPanelSdkAPI = class _QueryPanelSdkAPI {
2877
2913
  databaseName,
2878
2914
  tenantId
2879
2915
  );
2916
+ if (input.queryId) {
2917
+ await markQueryExecuted(this.client, input.queryId, {
2918
+ tenantId
2919
+ });
2920
+ }
2880
2921
  return { rows: result.rows, fields: result.fields };
2881
2922
  }
2882
2923
  // VizSpec generation