{"record":{"id":"b8c3e7608460ca54","repo":"cube-js/cube","slug":"this-constructor-driver-supports-only-rows-uplo-b8c3e7","errorCode":null,"errorMessage":"${this.constructor} driver supports only rows upload","messagePattern":"(.+?) driver supports only rows upload","errorType":"exception","errorClass":"Error","httpStatus":null,"severity":"error","filePath":"packages/cubejs-questdb-driver/src/QuestDriver.ts","lineNumber":232,"sourceCode":"\n  // eslint-disable-next-line camelcase\n  public async getTablesQuery(_schemaName: string): Promise<({ table_name?: string, TABLE_NAME?: string })[]> {\n    return this.query('SHOW TABLES', []);\n  }\n\n  public async tableColumnTypes(table: string): Promise<TableStructure> {\n    const response: any[] = await this.query(`SHOW COLUMNS FROM ${escapeStringLiteral(table)}`, []);\n\n    return response.map((row) => ({ name: row.column, type: this.toGenericType(row.type) }));\n  }\n\n  public async uploadTableWithIndexes(\n    table: string,\n    columns: TableStructure,\n    tableData: DownloadTableMemoryData,\n    indexesSql: IndexesSQL\n  ) {\n    if (!tableData.rows) {\n      throw new Error(`${this.constructor} driver supports only rows upload`);\n    }\n\n    await this.createTable(table, columns);\n\n    try {\n      for (let i = 0; i < tableData.rows.length; i++) {\n        await this.query(\n          `INSERT INTO ${escapeStringLiteral(table)}\n        (${columns.map(c => this.quoteIdentifier(c.name)).join(', ')})\n        VALUES (${columns.map((c, paramIndex) => this.param(paramIndex)).join(', ')})`,\n          columns.map(c => this.toColumnValue(tableData.rows[i][c.name] as string, c.type))\n        );\n      }\n      // Make sure to commit the data to make it visible for later queries.\n      await this.query('COMMIT', []);\n\n      for (let i = 0; i < indexesSql.length; i++) {","sourceCodeStart":214,"sourceCodeEnd":250,"githubUrl":"https://github.com/cube-js/cube/blob/7d981676b36392fec34088b9afab6bdcad40207c/packages/cubejs-questdb-driver/src/QuestDriver.ts#L214-L250","documentation":"uploadTableWithIndexes requires the source data to be row-form (tableData.rows). If tableData contains only columnar data (columns) — typically because the source driver returned results in column format — the QuestDB driver cannot convert it and throws. QuestDB ingestion in this driver is implemented only for row arrays.","triggerScenarios":"Calling uploadTableWithIndexes (via loadTable / export queries / pre-aggregation upload) with a DownloadTableMemoryData built from a driver that sets `columns` but not `rows`.","commonSituations":"Cross-database pre-aggregation exports where the source driver downloads results column-wise; combining a column-oriented source driver with QuestDB as target without a rows conversion step.","solutions":["Ensure the source download uses downloadQueryResults with row format so tableData.rows is populated","Convert columnar data to rows before calling: rows = columnNames.map((_, i) => Object.fromEntries(names.map(n => [n, cols[n][i]])))","Upload without the column-only data path, or use a driver version that converts columns to rows automatically"],"exampleFix":"// before\nawait questDriver.uploadTableWithIndexes(table, structure, { columns: colData }, indexes);\n// after\nconst rows = colData.ids.map((_, i) => ({ id: colData.ids[i], ts: colData.ts[i] }));\nawait questDriver.uploadTableWithIndexes(table, structure, { rows }, indexes);","handlingStrategy":"validation","validationCode":"if (!tableData.rows || tableData.rows.length === 0) throw new Error('QuestDB upload requires row-form tableData.rows');","typeGuard":"function hasRows(d) { return Array.isArray(d?.rows) && d.rows.length > 0; }","tryCatchPattern":"try { await driver.uploadTableWithIndexes(table, columns, tableData, indexes); } catch (e) { if (e.message.includes('supports only rows upload')) { return uploadConvertedToRows(table, columns, tableData, indexes); } throw e; }","preventionTips":["Always source uploads from drivers/configurations that return row data","Convert columnar results to rows before upload","Write a unit test around uploadTable with both data shapes"],"tags":["data-upload","questdb","driver"],"backgroundTag":"unsupported-upload-format","analyzedSha":"7d981676b36392fec34088b9afab6bdcad40207c","analyzedAt":"2026-09-02T03:45:10.400Z","contentChangedAt":null,"schemaVersion":2},"datasetVersion":"2026-09-08T15:18:49.778Z"}