fix(trino): support schema-aware table browsing and inserts

This commit is contained in:
t8y2
2026-05-13 20:46:27 +08:00
parent 2ba97869a1
commit 7f19a0376a
7 changed files with 61 additions and 4 deletions
+4 -2
View File
@@ -812,7 +812,9 @@ const tableUsesSyntheticRowId = computed(() =>
usesSyntheticRowIdKey(props.databaseType, props.tableMeta?.primaryKeys ?? []),
);
const hiveTableTransactional = ref<boolean | undefined>(undefined);
const canEditExistingRows = computed(() => canEditExistingTableRows(props.databaseType, hiveTableTransactional.value));
const canEditExistingRows = computed(() =>
canEditExistingTableRows(props.databaseType, hiveTableTransactional.value, props.tableMeta?.primaryKeys ?? []),
);
watch(
() => [props.databaseType, props.connectionId, props.database, props.tableMeta?.schema, props.tableMeta?.tableName],
async () => {
@@ -2033,7 +2035,7 @@ defineExpose({
{{ t("grid.refresh") }}
</Button>
<Button
v-if="useTransaction && editable && (tableMeta || customSave)"
v-if="editable && (tableMeta || customSave)"
variant="ghost"
size="sm"
class="h-5 text-xs px-1.5 shrink-0"
+9 -1
View File
@@ -12,6 +12,7 @@ export const SCHEMA_AWARE_TYPES = new Set<DatabaseType>([
"jdbc",
"h2",
"snowflake",
"trino",
"db2",
"informix",
]);
@@ -109,7 +110,14 @@ export const SINGLE_DATABASE_TYPES = new Set<DatabaseType>(["oracle", "dameng"])
export const FETCH_FIRST_TYPES = new Set<DatabaseType>(["oracle", "dameng"]);
export const TREE_SCHEMA_TYPES = new Set<DatabaseType>(["postgres", "redshift", "sqlserver", "gaussdb", "jdbc"]);
export const TREE_SCHEMA_TYPES = new Set<DatabaseType>([
"postgres",
"redshift",
"sqlserver",
"gaussdb",
"jdbc",
"trino",
]);
export const PG_LIKE_STRUCTURE_TYPES = new Set<DatabaseType>(["postgres", "redshift", "gaussdb"]);
+4 -1
View File
@@ -12,18 +12,21 @@ export function editablePrimaryKeys(databaseType: DatabaseType | undefined, colu
export function isTableDataEditable(databaseType: DatabaseType | undefined, primaryKeys: string[]): boolean {
if (databaseType === "hive") return true;
if (databaseType === "trino") return true;
return primaryKeys.length > 0;
}
export function supportsDataGridTransaction(databaseType: DatabaseType | undefined): boolean {
return databaseType !== "hive";
return databaseType !== "hive" && databaseType !== "trino";
}
export function canEditExistingTableRows(
databaseType: DatabaseType | undefined,
hiveTableTransactional?: boolean,
primaryKeys: string[] = [],
): boolean {
if (databaseType === "hive") return hiveTableTransactional === true;
if (databaseType === "trino") return primaryKeys.length > 0;
return true;
}
+18
View File
@@ -80,6 +80,24 @@ test("builds Hive grid save statements without primary keys using row predicates
]);
});
test("builds Trino insert statements with schema-qualified identifiers", () => {
const statements = buildDataGridSaveStatements({
databaseType: "trino",
tableMeta: {
schema: "tiny",
tableName: "nation",
primaryKeys: [],
},
columns: ["nationkey", "name"],
rows: [],
dirtyRows: [],
deletedRows: [],
newRows: [[100, "Atlantis"]],
});
assert.deepEqual(statements, ['INSERT INTO "tiny"."nation" ("nationkey", "name") VALUES (100, \'Atlantis\');']);
});
test("uses Oracle ROWID as a synthetic key without writing it as a normal column", () => {
const statements = buildDataGridSaveStatements({
databaseType: "oracle",
+11
View File
@@ -0,0 +1,11 @@
import assert from "node:assert/strict";
import test from "node:test";
import { SCHEMA_AWARE_TYPES, TREE_SCHEMA_TYPES } from "../src/lib/databaseCapabilities.ts";
test("treats Trino catalogs as schema tree roots", () => {
assert.equal(TREE_SCHEMA_TYPES.has("trino"), true);
});
test("treats Trino tables as schema-qualified SQL targets", () => {
assert.equal(SCHEMA_AWARE_TYPES.has("trino"), true);
});
+4
View File
@@ -38,12 +38,14 @@ test("does not synthesize ROWID for non-Oracle keyless tables", () => {
test("allows Hive table data editing even without declared primary keys", () => {
assert.equal(isTableDataEditable("hive", []), true);
assert.equal(isTableDataEditable("trino", []), true);
assert.equal(isTableDataEditable("mysql", []), false);
assert.equal(isTableDataEditable("postgres", ["id"]), true);
});
test("does not use transactional grid saves for Hive", () => {
assert.equal(supportsDataGridTransaction("hive"), false);
assert.equal(supportsDataGridTransaction("trino"), false);
assert.equal(supportsDataGridTransaction("postgres"), true);
});
@@ -51,6 +53,8 @@ test("allows existing row edits for Hive only when the table is transactional",
assert.equal(canEditExistingTableRows("hive", true), true);
assert.equal(canEditExistingTableRows("hive", false), false);
assert.equal(canEditExistingTableRows("hive", undefined), false);
assert.equal(canEditExistingTableRows("trino", undefined, []), false);
assert.equal(canEditExistingTableRows("trino", undefined, ["id"]), true);
assert.equal(canEditExistingTableRows("postgres", undefined), true);
});
+11
View File
@@ -28,6 +28,17 @@ test("builds a schema-qualified PostgreSQL table WHERE query", () => {
assert.equal(sql, 'SELECT * FROM "public"."orders" WHERE (amount > 10) LIMIT 50 OFFSET 100;');
});
test("builds schema-qualified Trino table data queries", () => {
const sql = buildTableSelectSql({
databaseType: "trino",
schema: "tiny",
tableName: "nation",
limit: 100,
});
assert.equal(sql, 'SELECT * FROM "tiny"."nation" LIMIT 100;');
});
test("builds Hive table data queries with backtick identifiers", () => {
const sql = buildTableSelectSql({
databaseType: "hive",