From 9da10c790e827cb6b8976ad6cc8d3f3f08c2b513 Mon Sep 17 00:00:00 2001 From: Sam Rose Date: Fri, 5 Apr 2024 17:47:55 +0100 Subject: [PATCH] One failure left for MSSQL --- .../src/api/controllers/table/external.ts | 1 + .../server/src/api/routes/tests/table.spec.ts | 26 ++++++------------- .../server/src/integrations/base/sqlTable.ts | 22 ++++++++++++++++ 3 files changed, 31 insertions(+), 18 deletions(-) diff --git a/packages/server/src/api/controllers/table/external.ts b/packages/server/src/api/controllers/table/external.ts index 7c036bec9d..0a6cf58bce 100644 --- a/packages/server/src/api/controllers/table/external.ts +++ b/packages/server/src/api/controllers/table/external.ts @@ -49,6 +49,7 @@ export async function save( builderSocket?.emitDatasourceUpdate(ctx, datasource) return table } catch (err: any) { + throw err if (err instanceof Error) { ctx.throw(400, err.message) } else { diff --git a/packages/server/src/api/routes/tests/table.spec.ts b/packages/server/src/api/routes/tests/table.spec.ts index b8528487ec..8162e08eb6 100644 --- a/packages/server/src/api/routes/tests/table.spec.ts +++ b/packages/server/src/api/routes/tests/table.spec.ts @@ -28,11 +28,11 @@ const { basicTable } = setup.structures const ISO_REGEX_PATTERN = /^\d{4}-\d{2}-\d{2}T\d{2}:\d{2}:\d{2}\.\d{3}Z$/ describe.each([ - ["internal", undefined], - [DatabaseName.POSTGRES, getDatasource(DatabaseName.POSTGRES)], - [DatabaseName.MYSQL, getDatasource(DatabaseName.MYSQL)], - // [DatabaseName.SQL_SERVER, getDatasource(DatabaseName.SQL_SERVER)], - [DatabaseName.MARIADB, getDatasource(DatabaseName.MARIADB)], + // ["internal", undefined], + // [DatabaseName.POSTGRES, getDatasource(DatabaseName.POSTGRES)], + // [DatabaseName.MYSQL, getDatasource(DatabaseName.MYSQL)], + [DatabaseName.SQL_SERVER, getDatasource(DatabaseName.SQL_SERVER)], + // [DatabaseName.MARIADB, getDatasource(DatabaseName.MARIADB)], ])("/tables (%s)", (_, dsProvider) => { let isInternal: boolean let datasource: Datasource | undefined @@ -114,7 +114,7 @@ describe.each([ expect(events.table.updated).toHaveBeenCalledWith(updatedTable) }) - it("updates all the row fields for a table when a schema key is renamed", async () => { + it.only("updates all the row fields for a table when a schema key is renamed", async () => { const testTable = await config.api.table.save(basicTable(datasource)) await config.createLegacyView({ name: "TestView", @@ -130,24 +130,14 @@ describe.each([ }) const updatedTable = await config.api.table.save({ - _id: testTable._id, - _rev: testTable._rev, - type: "table", - sourceId: datasource ? datasource._id! : INTERNAL_TABLE_SOURCE_ID, - sourceType: isInternal - ? TableSourceType.INTERNAL - : TableSourceType.EXTERNAL, - name: "TestTable", + ...testTable, _rename: { old: "name", updated: "updatedName", }, - schema: { - updatedName: { type: FieldType.STRING, name: "updatedName" }, - }, }) - expect(updatedTable.name).toEqual("TestTable") + expect(updatedTable.name).toEqual(testTable.name) const res = await config.api.row.get(testTable._id!, testRow._id!) expect(res.updatedName).toEqual("test") diff --git a/packages/server/src/integrations/base/sqlTable.ts b/packages/server/src/integrations/base/sqlTable.ts index 9718da0ad2..32d0c38599 100644 --- a/packages/server/src/integrations/base/sqlTable.ts +++ b/packages/server/src/integrations/base/sqlTable.ts @@ -229,6 +229,7 @@ class SqlTableQueryBuilder { bindings: [], } } + query = buildUpdateTable( client, json.table, @@ -236,6 +237,27 @@ class SqlTableQueryBuilder { json.meta.table, json.meta.renamed! ) + + // renameColumn for SQL Server returns a parameterised `sp_rename` query, + // which is not supported by SQL Server and gives a syntax error. + if (this.sqlClient === SqlClient.MS_SQL && json.meta.renamed) { + const oldColumn = json.meta.renamed.old + const updatedColumn = json.meta.renamed.updated + const tableName = schemaName + ? `${schemaName}.${json.table.name}` + : `${json.table.name}` + const sql = query.toSQL() + if (Array.isArray(sql)) { + for (const query of sql) { + if (query.sql.startsWith("exec sp_rename")) { + query.sql = `exec sp_rename '${tableName}.${oldColumn}', '${updatedColumn}', 'COLUMN'` + query.bindings = [] + } + } + } + + return sql + } break case Operation.DELETE_TABLE: query = buildDeleteTable(client, json.table)