Skip to content

Commit 612f9d3

Browse files
authored
Merge pull request #15 from fljdin/deparse-CreateForeignTableStmt
Adds deparser.create_foreign_table_stmt
2 parents ed91175 + 643c615 commit 612f9d3

File tree

4 files changed

+138
-8
lines changed

4 files changed

+138
-8
lines changed

packages/ast/deploy/schemas/deparser/procedures/deparse.sql

Lines changed: 40 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -2166,7 +2166,7 @@ BEGIN
21662166
ELSIF (node->'arg' IS NOT NULL) THEN
21672167
RETURN defname || ' ' || deparser.expression(node->'arg', jsonb_set(context, '{simple}', to_jsonb(TRUE)));
21682168
END IF;
2169-
ELSIF ((context->'foreignSchema')::bool IS TRUE) THEN
2169+
ELSIF ((context->'foreignOptions')::bool IS TRUE) THEN
21702170
RETURN format('%s ''%s''', defname, deparser.expression(node->'arg', jsonb_set(context, '{simple}', to_jsonb(TRUE))));
21712171

21722172
ELSE
@@ -3860,7 +3860,8 @@ LANGUAGE 'plpgsql' IMMUTABLE;
38603860

38613861
CREATE FUNCTION deparser.create_stmt(
38623862
node jsonb,
3863-
context jsonb default '{}'::jsonb
3863+
context jsonb default '{}'::jsonb,
3864+
is_foreign_table bool default false
38643865
) returns text as $$
38653866
DECLARE
38663867
output text[];
@@ -3885,7 +3886,10 @@ BEGIN
38853886
relpersistence = node#>>'{relation, relpersistence}';
38863887
END IF;
38873888

3888-
IF (relpersistence = 't') THEN
3889+
IF (is_foreign_table) THEN
3890+
-- foreign tables cannot be created as temporary
3891+
output = array_append(output, 'CREATE FOREIGN TABLE');
3892+
ELSEIF (relpersistence = 't') THEN
38893893
output = array_append(output, 'CREATE');
38903894
ELSE
38913895
output = array_append(output, 'CREATE TABLE');
@@ -5215,7 +5219,7 @@ BEGIN
52155219
IF (node->'options') IS NOT NULL THEN
52165220
output = array_append(output, 'OPTIONS');
52175221
output = array_append(output, deparser.parens(
5218-
deparser.list(node->'options', ', ', jsonb_set(context, '{foreignSchema}', to_jsonb(TRUE)))
5222+
deparser.list(node->'options', ', ', jsonb_set(context, '{foreignOptions}', to_jsonb(TRUE)))
52195223
));
52205224
END IF;
52215225

@@ -5224,6 +5228,36 @@ END;
52245228
$$
52255229
LANGUAGE 'plpgsql' IMMUTABLE;
52265230

5231+
CREATE FUNCTION deparser.create_foreign_table_stmt(
5232+
node jsonb,
5233+
context jsonb default '{}'::jsonb
5234+
) RETURNS text AS $$
5235+
DECLARE
5236+
output text[];
5237+
BEGIN
5238+
IF (node->'CreateForeignTableStmt') IS NULL THEN
5239+
RAISE EXCEPTION 'BAD_EXPRESSION %', 'CreateForeignTableStmt';
5240+
END IF;
5241+
5242+
node = node->'CreateForeignTableStmt';
5243+
5244+
output = array_append(output, deparser.create_stmt(node->'base', context, is_foreign_table := true));
5245+
output = array_append(output, 'SERVER');
5246+
output = array_append(output, quote_ident(node->>'servername'));
5247+
5248+
-- options
5249+
IF (node->'options') IS NOT NULL THEN
5250+
output = array_append(output, 'OPTIONS');
5251+
output = array_append(output, deparser.parens(
5252+
deparser.list(node->'options', ', ', jsonb_set(context, '{foreignOptions}', to_jsonb(TRUE)))
5253+
));
5254+
END IF;
5255+
5256+
RETURN array_to_string(output, ' ');
5257+
END;
5258+
$$
5259+
LANGUAGE 'plpgsql' IMMUTABLE;
5260+
52275261
CREATE FUNCTION deparser.function_parameter(
52285262
node jsonb,
52295263
context jsonb default '{}'::jsonb
@@ -5378,6 +5412,8 @@ BEGIN
53785412
RETURN deparser.create_enum_stmt(expr, context);
53795413
ELSEIF (expr->>'CreateExtensionStmt') IS NOT NULL THEN
53805414
RETURN deparser.create_extension_stmt(expr, context);
5415+
ELSEIF (expr->>'CreateForeignTableStmt') IS NOT NULL THEN
5416+
RETURN deparser.create_foreign_table_stmt(expr, context);
53815417
ELSEIF (expr->>'CreateFunctionStmt') IS NOT NULL THEN
53825418
RETURN deparser.create_function_stmt(expr, context);
53835419
ELSEIF (expr->>'CreatePolicyStmt') IS NOT NULL THEN

packages/ast/sql/ast--13.0.4.sql

Lines changed: 35 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7355,7 +7355,7 @@ BEGIN
73557355
ELSIF (node->'arg' IS NOT NULL) THEN
73567356
RETURN defname || ' ' || deparser.expression(node->'arg', jsonb_set(context, '{simple}', to_jsonb(TRUE)));
73577357
END IF;
7358-
ELSIF ((context->'foreignSchema')::bool IS TRUE) THEN
7358+
ELSIF ((context->'foreignOptions')::bool IS TRUE) THEN
73597359
RETURN format('%s ''%s''', defname, deparser.expression(node->'arg', jsonb_set(context, '{simple}', to_jsonb(TRUE))));
73607360

73617361
ELSE
@@ -8906,7 +8906,7 @@ BEGIN
89068906
END;
89078907
$EOFCODE$ LANGUAGE plpgsql IMMUTABLE;
89088908

8909-
CREATE FUNCTION deparser.create_stmt ( node jsonb, context jsonb DEFAULT '{}'::jsonb ) RETURNS text AS $EOFCODE$
8909+
CREATE FUNCTION deparser.create_stmt ( node jsonb, context jsonb DEFAULT '{}'::jsonb, is_foreign_table bool DEFAULT FALSE ) RETURNS text AS $EOFCODE$
89108910
DECLARE
89118911
output text[];
89128912
relpersistence text;
@@ -8930,7 +8930,10 @@ BEGIN
89308930
relpersistence = node#>>'{relation, relpersistence}';
89318931
END IF;
89328932

8933-
IF (relpersistence = 't') THEN
8933+
IF (is_foreign_table) THEN
8934+
-- foreign tables cannot be created as temporary
8935+
output = array_append(output, 'CREATE FOREIGN TABLE');
8936+
ELSEIF (relpersistence = 't') THEN
89348937
output = array_append(output, 'CREATE');
89358938
ELSE
89368939
output = array_append(output, 'CREATE TABLE');
@@ -10150,14 +10153,40 @@ BEGIN
1015010153
IF (node->'options') IS NOT NULL THEN
1015110154
output = array_append(output, 'OPTIONS');
1015210155
output = array_append(output, deparser.parens(
10153-
deparser.list(node->'options', ', ', jsonb_set(context, '{foreignSchema}', to_jsonb(TRUE)))
10156+
deparser.list(node->'options', ', ', jsonb_set(context, '{foreignOptions}', to_jsonb(TRUE)))
1015410157
));
1015510158
END IF;
1015610159

1015710160
RETURN array_to_string(output, ' ');
1015810161
END;
1015910162
$EOFCODE$ LANGUAGE plpgsql IMMUTABLE;
1016010163

10164+
CREATE FUNCTION deparser.create_foreign_table_stmt ( node jsonb, context jsonb DEFAULT '{}'::jsonb ) RETURNS text AS $EOFCODE$
10165+
DECLARE
10166+
output text[];
10167+
BEGIN
10168+
IF (node->'CreateForeignTableStmt') IS NULL THEN
10169+
RAISE EXCEPTION 'BAD_EXPRESSION %', 'CreateForeignTableStmt';
10170+
END IF;
10171+
10172+
node = node->'CreateForeignTableStmt';
10173+
10174+
output = array_append(output, deparser.create_stmt(node->'base', context, is_foreign_table := true));
10175+
output = array_append(output, 'SERVER');
10176+
output = array_append(output, quote_ident(node->>'servername'));
10177+
10178+
-- options
10179+
IF (node->'options') IS NOT NULL THEN
10180+
output = array_append(output, 'OPTIONS');
10181+
output = array_append(output, deparser.parens(
10182+
deparser.list(node->'options', ', ', jsonb_set(context, '{foreignOptions}', to_jsonb(TRUE)))
10183+
));
10184+
END IF;
10185+
10186+
RETURN array_to_string(output, ' ');
10187+
END;
10188+
$EOFCODE$ LANGUAGE plpgsql IMMUTABLE;
10189+
1016110190
CREATE FUNCTION deparser.function_parameter ( node jsonb, context jsonb DEFAULT '{}'::jsonb ) RETURNS text AS $EOFCODE$
1016210191
DECLARE
1016310192
output text[];
@@ -10266,6 +10295,8 @@ BEGIN
1026610295
RETURN deparser.create_enum_stmt(expr, context);
1026710296
ELSEIF (expr->>'CreateExtensionStmt') IS NOT NULL THEN
1026810297
RETURN deparser.create_extension_stmt(expr, context);
10298+
ELSEIF (expr->>'CreateForeignTableStmt') IS NOT NULL THEN
10299+
RETURN deparser.create_foreign_table_stmt(expr, context);
1026910300
ELSEIF (expr->>'CreateFunctionStmt') IS NOT NULL THEN
1027010301
RETURN deparser.create_function_stmt(expr, context);
1027110302
ELSEIF (expr->>'CreatePolicyStmt') IS NOT NULL THEN
Lines changed: 7 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,7 @@
1+
// Jest Snapshot v1, https://goo.gl/fbAQLP
2+
3+
exports[`create foreign table stmt 1`] = `
4+
"CREATE FOREIGN TABLE public.foo (
5+
bar pg_catalog.varchar(50)
6+
) SERVER dummy OPTIONS (schema_name 'public', table_name 'foo')"
7+
`;
Lines changed: 56 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,56 @@
1+
import { getConnections } from '../../utils';
2+
3+
let db, teardown;
4+
const objs = {
5+
tables: {}
6+
};
7+
8+
beforeAll(async () => {
9+
({ db, teardown } = await getConnections());
10+
await db.begin();
11+
await db.savepoint();
12+
});
13+
afterAll(async () => {
14+
try {
15+
//try catch here allows us to see the sql parsing issues!
16+
await db.rollback();
17+
await db.commit();
18+
await teardown();
19+
} catch (e) {}
20+
});
21+
22+
it('create foreign table stmt', async () => {
23+
const [{ deparse: result }] = await db.any(
24+
`
25+
select deparser.deparse(
26+
ast.create_foreign_table_stmt(
27+
v_base := ast.create_stmt(
28+
v_relation := ast.range_var(
29+
v_schemaname := 'public',
30+
v_relname := 'foo',
31+
v_inh := true,
32+
v_relpersistence := 'p'
33+
),
34+
v_tableElts := to_jsonb(ARRAY[
35+
ast.column_def(
36+
v_colname := 'bar',
37+
v_typeName := ast.type_name(
38+
v_names := ast_helpers.array_of_strings(
39+
'pg_catalog', 'varchar(50)'
40+
)
41+
)
42+
)
43+
])
44+
),
45+
v_servername := 'dummy',
46+
v_options := to_jsonb(ARRAY[
47+
ast.def_elem(v_defname := 'schema_name', v_arg := ast.string('public')),
48+
ast.def_elem(v_defname := 'table_name', v_arg := ast.string('foo'))
49+
])
50+
)
51+
);`,
52+
[]
53+
);
54+
55+
expect(result).toMatchSnapshot();
56+
});

0 commit comments

Comments
 (0)