Skip to content

Commit 9af2ee7

Browse files
authored
ENG-587 ContentVariant type and input (#284)
1 parent baaf261 commit 9af2ee7

File tree

4 files changed

+195
-27
lines changed

4 files changed

+195
-27
lines changed

packages/database/schema.yaml

Lines changed: 15 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -22,6 +22,12 @@ enums:
2222
quote:
2323
sentence:
2424
phrase:
25+
ContentVariant:
26+
description: Is the text taken as-is, or is it a computed variant?
27+
permissible_values:
28+
direct:
29+
direct_and_children:
30+
direct_and_description:
2531
Validation:
2632
description: Whether a given value was given by a person, or suggested by an automated agent (and then possibly infirmed.)
2733
permissible_values:
@@ -139,15 +145,15 @@ classes:
139145
active:
140146
range: boolean
141147
required: true
142-
ifabsent: 'true'
148+
ifabsent: "true"
143149
agent_type:
144150
required: true
145151
range: AgentType
146152
ifabsent: AgentType(person)
147153
metadata:
148154
range: JSON
149155
description: Additional platform-specific information about the account
150-
ifabsent: '{}'
156+
ifabsent: "{}"
151157
dg_account:
152158
range: Users
153159
unique_keys:
@@ -298,7 +304,7 @@ classes:
298304
obsolete:
299305
description: Whether this embedding is obsolete (becauses the Content was modified)
300306
range: boolean
301-
ifabsent: 'false'
307+
ifabsent: "false"
302308
ContentEmbedding_openai_text_embedding_3_small_1536:
303309
is_a: ContentEmbedding
304310
description: The table for the openai text_embedding_3_small model (1536 dimensions)
@@ -318,7 +324,7 @@ classes:
318324
arity:
319325
range: integer
320326
required: true
321-
ifabsent: '0'
327+
ifabsent: "0"
322328
description: The number of roles in this relation; nodes have zero, binary relations have 2, etc.
323329
schema:
324330
range: ConceptSchema
@@ -327,16 +333,16 @@ classes:
327333
description: "Aspects of the concept that reference other concepts. `{[key: string]: number|number[]}`"
328334
range: JSON
329335
required: true
330-
ifabsent: '{}'
336+
ifabsent: "{}"
331337
literal_content:
332338
range: JSON
333339
required: true
334340
description: "Aspects of the concept that have literal values. `{[key: string]: any}`"
335-
ifabsent: '{}'
341+
ifabsent: "{}"
336342
is_schema:
337343
range: boolean
338344
required: true
339-
ifabsent: 'false'
345+
ifabsent: "false"
340346
represented_by:
341347
description: This concept is explicitly represented by a given content unit
342348
range: Content
@@ -445,13 +451,13 @@ slots:
445451
position:
446452
description: The ordinal position of the content within its parent, wrt other content units of the same scale
447453
range: integer
448-
ifabsent: '0'
454+
ifabsent: "0"
449455
required: true
450456
char_position:
451457
description: The character position of the content within its parent.
452458
# Does not apply to outline sub-elements
453459
range: integer
454-
ifabsent: '0'
460+
ifabsent: "0"
455461
validation:
456462
range: Validation
457463
required: true
Lines changed: 137 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,137 @@
1+
CREATE TYPE public."ContentVariant" AS ENUM (
2+
'direct',
3+
'direct_and_children',
4+
'direct_and_description'
5+
);
6+
7+
ALTER TYPE public."ContentVariant" OWNER TO postgres;
8+
9+
ALTER TABLE public."Content" ADD COLUMN variant public."ContentVariant" NOT NULL DEFAULT 'direct';
10+
11+
DROP INDEX IF EXISTS public."content_space_and_local_id_idx";
12+
13+
CREATE UNIQUE INDEX content_space_local_id_variant_idx ON public."Content" USING btree (space_id, source_local_id, variant);
14+
15+
ALTER TYPE public.content_local_input ADD ATTRIBUTE variant public."ContentVariant";
16+
17+
CREATE OR REPLACE FUNCTION public.upsert_content(v_space_id bigint, data jsonb, v_creator_id BIGINT, content_as_document boolean DEFAULT true)
18+
RETURNS SETOF BIGINT
19+
LANGUAGE plpgsql
20+
AS $$
21+
DECLARE
22+
v_platform public."Platform";
23+
db_document public."Document"%ROWTYPE;
24+
document_id BIGINT;
25+
local_content public.content_local_input;
26+
db_content public."Content"%ROWTYPE;
27+
content_row JSONB;
28+
upsert_id BIGINT;
29+
BEGIN
30+
SELECT platform INTO STRICT v_platform FROM public."Space" WHERE id=v_space_id;
31+
FOR content_row IN SELECT * FROM jsonb_array_elements(data)
32+
LOOP
33+
local_content := jsonb_populate_record(NULL::public.content_local_input, content_row);
34+
local_content.space_id := v_space_id;
35+
db_content := public._local_content_to_db_content(local_content);
36+
IF account_local_id(author_inline(local_content)) IS NOT NULL THEN
37+
SELECT public.create_account_in_space(
38+
v_space_id,
39+
account_local_id(author_inline(local_content)),
40+
name(author_inline(local_content))
41+
) INTO STRICT upsert_id;
42+
local_content.author_id := upsert_id;
43+
END IF;
44+
IF account_local_id(creator_inline(local_content)) IS NOT NULL THEN
45+
SELECT public.create_account_in_space(
46+
v_space_id,
47+
account_local_id(creator_inline(local_content)),
48+
name(creator_inline(local_content))
49+
) INTO STRICT upsert_id;
50+
local_content.creator_id := upsert_id;
51+
END IF;
52+
IF content_as_document THEN
53+
db_content.scale = 'document';
54+
END IF;
55+
IF content_as_document AND document_id(db_content) IS NULL AND source_local_id(document_inline(local_content)) IS NULL THEN
56+
local_content.document_inline.space_id := v_space_id;
57+
local_content.document_inline.source_local_id := db_content.source_local_id;
58+
local_content.document_inline.last_modified := db_content.last_modified;
59+
local_content.document_inline.created := db_content.created;
60+
local_content.document_inline.author_id := db_content.author_id;
61+
END IF;
62+
IF source_local_id(document_inline(local_content)) IS NOT NULL THEN
63+
db_document := _local_document_to_db_document(document_inline(local_content));
64+
INSERT INTO public."Document" (
65+
space_id,
66+
source_local_id,
67+
url,
68+
created,
69+
metadata,
70+
last_modified,
71+
author_id,
72+
contents
73+
) VALUES (
74+
COALESCE(db_document.space_id, v_space_id),
75+
db_document.source_local_id,
76+
db_document.url,
77+
db_document.created,
78+
COALESCE(db_document.metadata, '{}'::jsonb),
79+
db_document.last_modified,
80+
db_document.author_id,
81+
db_document.contents
82+
)
83+
ON CONFLICT (space_id, source_local_id) DO UPDATE SET
84+
url = COALESCE(db_document.url, EXCLUDED.url),
85+
created = COALESCE(db_document.created, EXCLUDED.created),
86+
metadata = COALESCE(db_document.metadata, EXCLUDED.metadata),
87+
last_modified = COALESCE(db_document.last_modified, EXCLUDED.last_modified),
88+
author_id = COALESCE(db_document.author_id, EXCLUDED.author_id),
89+
contents = COALESCE(db_document.contents, EXCLUDED.contents)
90+
RETURNING id INTO STRICT document_id;
91+
db_content.document_id := document_id;
92+
END IF;
93+
INSERT INTO public."Content" (
94+
document_id,
95+
source_local_id,
96+
variant,
97+
author_id,
98+
creator_id,
99+
created,
100+
text,
101+
metadata,
102+
scale,
103+
space_id,
104+
last_modified,
105+
part_of_id
106+
) VALUES (
107+
db_content.document_id,
108+
db_content.source_local_id,
109+
COALESCE(db_content.variant, 'direct'::public."ContentVariant"),
110+
db_content.author_id,
111+
db_content.creator_id,
112+
db_content.created,
113+
db_content.text,
114+
COALESCE(db_content.metadata, '{}'::jsonb),
115+
db_content.scale,
116+
db_content.space_id,
117+
db_content.last_modified,
118+
db_content.part_of_id
119+
)
120+
ON CONFLICT (space_id, source_local_id, variant) DO UPDATE SET
121+
document_id = COALESCE(db_content.document_id, EXCLUDED.document_id),
122+
author_id = COALESCE(db_content.author_id, EXCLUDED.author_id),
123+
creator_id = COALESCE(db_content.creator_id, EXCLUDED.creator_id),
124+
created = COALESCE(db_content.created, EXCLUDED.created),
125+
text = COALESCE(db_content.text, EXCLUDED.text),
126+
metadata = COALESCE(db_content.metadata, EXCLUDED.metadata),
127+
scale = COALESCE(db_content.scale, EXCLUDED.scale),
128+
last_modified = COALESCE(db_content.last_modified, EXCLUDED.last_modified),
129+
part_of_id = COALESCE(db_content.part_of_id, EXCLUDED.part_of_id)
130+
RETURNING id INTO STRICT upsert_id;
131+
IF model(embedding_inline(local_content)) IS NOT NULL THEN
132+
PERFORM public.upsert_content_embedding(upsert_id, model(embedding_inline(local_content)), vector(embedding_inline(local_content)));
133+
END IF;
134+
RETURN NEXT upsert_id;
135+
END LOOP;
136+
END;
137+
$$;

packages/database/supabase/schemas/content.sql

Lines changed: 19 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -13,6 +13,14 @@ CREATE TYPE public."Scale" AS ENUM (
1313

1414
ALTER TYPE public."Scale" OWNER TO postgres;
1515

16+
CREATE TYPE public."ContentVariant" AS ENUM (
17+
'direct',
18+
'direct_and_children',
19+
'direct_and_description'
20+
);
21+
22+
ALTER TYPE public."ContentVariant" OWNER TO postgres;
23+
1624
CREATE TABLE IF NOT EXISTS public."Document" (
1725
id bigint DEFAULT nextval(
1826
'public.entity_id_seq'::regclass
@@ -68,6 +76,7 @@ CREATE TABLE IF NOT EXISTS public."Content" (
6876
) NOT NULL,
6977
document_id bigint NOT NULL,
7078
source_local_id character varying,
79+
variant public."ContentVariant" NOT NULL DEFAULT 'direct',
7180
author_id bigint,
7281
creator_id bigint,
7382
created timestamp without time zone NOT NULL,
@@ -119,8 +128,8 @@ CREATE INDEX "Content_part_of" ON public."Content" USING btree (
119128

120129
CREATE INDEX "Content_space" ON public."Content" USING btree (space_id);
121130

122-
CREATE UNIQUE INDEX content_space_and_local_id_idx ON public."Content" USING btree (
123-
space_id, source_local_id
131+
CREATE UNIQUE INDEX content_space_local_id_variant_idx ON public."Content" USING btree (
132+
space_id, source_local_id, variant
124133
) NULLS DISTINCT;
125134

126135
CREATE INDEX "Content_text" ON public."Content" USING pgroonga (text);
@@ -178,6 +187,7 @@ CREATE TYPE public.content_local_input AS (
178187
-- content columns
179188
document_id bigint,
180189
source_local_id character varying,
190+
variant public."ContentVariant",
181191
author_id bigint,
182192
creator_id bigint,
183193
created timestamp without time zone,
@@ -406,7 +416,6 @@ BEGIN
406416
local_content.document_inline.last_modified := db_content.last_modified;
407417
local_content.document_inline.created := db_content.created;
408418
local_content.document_inline.author_id := db_content.author_id;
409-
local_content.document_inline.metadata := '{}';
410419
END IF;
411420
IF source_local_id(document_inline(local_content)) IS NOT NULL THEN
412421
db_document := _local_document_to_db_document(document_inline(local_content));
@@ -424,7 +433,7 @@ BEGIN
424433
db_document.source_local_id,
425434
db_document.url,
426435
db_document.created,
427-
db_document.metadata,
436+
COALESCE(db_document.metadata, '{}'::jsonb),
428437
db_document.last_modified,
429438
db_document.author_id,
430439
db_document.contents
@@ -442,6 +451,7 @@ BEGIN
442451
INSERT INTO public."Content" (
443452
document_id,
444453
source_local_id,
454+
variant,
445455
author_id,
446456
creator_id,
447457
created,
@@ -454,17 +464,18 @@ BEGIN
454464
) VALUES (
455465
db_content.document_id,
456466
db_content.source_local_id,
467+
COALESCE(db_content.variant, 'direct'::public."ContentVariant"),
457468
db_content.author_id,
458469
db_content.creator_id,
459470
db_content.created,
460471
db_content.text,
461-
db_content.metadata,
472+
COALESCE(db_content.metadata, '{}'::jsonb),
462473
db_content.scale,
463474
db_content.space_id,
464475
db_content.last_modified,
465476
db_content.part_of_id
466477
)
467-
ON CONFLICT (space_id, source_local_id) DO UPDATE SET
478+
ON CONFLICT (space_id, source_local_id, variant) DO UPDATE SET
468479
document_id = COALESCE(db_content.document_id, EXCLUDED.document_id),
469480
author_id = COALESCE(db_content.author_id, EXCLUDED.author_id),
470481
creator_id = COALESCE(db_content.creator_id, EXCLUDED.creator_id),
@@ -508,9 +519,9 @@ COMMENT ON FUNCTION public.document_in_space IS 'security utility: does current
508519
ALTER TABLE public."Document" ENABLE ROW LEVEL SECURITY;
509520

510521
DROP POLICY IF EXISTS document_policy ON public."Document";
511-
CREATE POLICY document_policy ON public."Document" FOR ALL USING (public.in_space (space_id));
522+
CREATE POLICY document_policy ON public."Document" FOR ALL USING (public.in_space(space_id));
512523

513524
ALTER TABLE public."Content" ENABLE ROW LEVEL SECURITY;
514525

515526
DROP POLICY IF EXISTS content_policy ON public."Content";
516-
CREATE POLICY content_policy ON public."Content" FOR ALL USING (public.in_space (space_id));
527+
CREATE POLICY content_policy ON public."Content" FOR ALL USING (public.in_space(space_id));

0 commit comments

Comments
 (0)