@ai-matrx/records 0.57.2 → 0.58.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +126 -0
- package/dist/core/index.cjs +643 -168
- package/dist/core/index.cjs.map +1 -1
- package/dist/core/index.d.cts +305 -7
- package/dist/core/index.d.ts +305 -7
- package/dist/core/index.js +643 -168
- package/dist/core/index.js.map +1 -1
- package/dist/index.cjs +329 -2
- package/dist/index.cjs.map +1 -1
- package/dist/index.d.cts +825 -195
- package/dist/index.d.ts +825 -195
- package/dist/index.js +329 -2
- package/dist/index.js.map +1 -1
- package/dist/react/index.cjs +432 -47
- package/dist/react/index.cjs.map +1 -1
- package/dist/react/index.d.cts +1054 -205
- package/dist/react/index.d.ts +1054 -205
- package/dist/react/index.js +432 -47
- package/dist/react/index.js.map +1 -1
- package/dist/{types-BpBSMhYq.d.cts → types-NKSc_jZq.d.cts} +31 -3
- package/dist/{types-BpBSMhYq.d.ts → types-NKSc_jZq.d.ts} +31 -3
- package/dist/use-cases/index.cjs.map +1 -1
- package/dist/use-cases/index.d.cts +2 -2
- package/dist/use-cases/index.d.ts +2 -2
- package/dist/use-cases/index.js.map +1 -1
- package/package.json +1 -1
package/dist/react/index.js
CHANGED
|
@@ -2219,6 +2219,31 @@ function sameDocument(a, b) {
|
|
|
2219
2219
|
return JSON.stringify(a) === JSON.stringify(b);
|
|
2220
2220
|
}
|
|
2221
2221
|
|
|
2222
|
+
// src/aggregate.ts
|
|
2223
|
+
function isRuleFilter(filter) {
|
|
2224
|
+
if (!filter || typeof filter !== "object" || Array.isArray(filter)) return false;
|
|
2225
|
+
const node = filter;
|
|
2226
|
+
return typeof node.op === "string" && Array.isArray(node.args);
|
|
2227
|
+
}
|
|
2228
|
+
function measureKey(measure) {
|
|
2229
|
+
return measure.op === "count" ? "count" : `${measure.op}_${measure.key ?? ""}`;
|
|
2230
|
+
}
|
|
2231
|
+
function stableFilterKey(filter) {
|
|
2232
|
+
if (!filter) return "{}";
|
|
2233
|
+
if (isRuleFilter(filter)) return JSON.stringify(filter);
|
|
2234
|
+
const keys = Object.keys(filter).sort();
|
|
2235
|
+
if (keys.length === 0) return "{}";
|
|
2236
|
+
const parts = keys.map((key) => {
|
|
2237
|
+
const value = filter[key];
|
|
2238
|
+
if (value !== null && typeof value === "object") {
|
|
2239
|
+
const window2 = value;
|
|
2240
|
+
return `${JSON.stringify(key)}:{"from":${JSON.stringify(window2.from ?? null)},"to":${JSON.stringify(window2.to ?? null)}}`;
|
|
2241
|
+
}
|
|
2242
|
+
return `${JSON.stringify(key)}:${JSON.stringify(value ?? null)}`;
|
|
2243
|
+
});
|
|
2244
|
+
return `{${parts.join(",")}}`;
|
|
2245
|
+
}
|
|
2246
|
+
|
|
2222
2247
|
// src/ops.ts
|
|
2223
2248
|
var REMEMBER_MS = 3e4;
|
|
2224
2249
|
var REMEMBER_MAX = 500;
|
|
@@ -2374,6 +2399,51 @@ function recordChangeTrigger(tableId, options = {}) {
|
|
|
2374
2399
|
...options.changedFields && options.changedFields.length > 0 ? { changed_fields: options.changedFields } : {}
|
|
2375
2400
|
};
|
|
2376
2401
|
}
|
|
2402
|
+
function sheetSyncSpec(args) {
|
|
2403
|
+
const [header = [], ...body] = args.cells;
|
|
2404
|
+
const columns = header.map((c, i) => {
|
|
2405
|
+
const name = c == null ? "" : String(c).trim();
|
|
2406
|
+
return name === "" ? `Column ${i + 1}` : name;
|
|
2407
|
+
});
|
|
2408
|
+
if (columns.length === 0) {
|
|
2409
|
+
throw new Error("The sheet has no header row, so there are no columns to sync. Nothing was sent.");
|
|
2410
|
+
}
|
|
2411
|
+
const seenCol = /* @__PURE__ */ new Set();
|
|
2412
|
+
for (const c of columns) {
|
|
2413
|
+
if (seenCol.has(c)) throw new Error(`The sheet has two columns named "${c}". Rename one and sync again.`);
|
|
2414
|
+
seenCol.add(c);
|
|
2415
|
+
}
|
|
2416
|
+
const refIdx = args.refColumn == null ? -1 : columns.indexOf(args.refColumn);
|
|
2417
|
+
if (args.refColumn != null && refIdx < 0) {
|
|
2418
|
+
throw new Error(`The id column "${args.refColumn}" is not in the sheet's header. Nothing was sent.`);
|
|
2419
|
+
}
|
|
2420
|
+
const seen = /* @__PURE__ */ new Set();
|
|
2421
|
+
const rows = [];
|
|
2422
|
+
body.forEach((cells, i) => {
|
|
2423
|
+
if (cells.every((v) => v == null || String(v).trim() === "")) return;
|
|
2424
|
+
const ref = refIdx >= 0 ? String(cells[refIdx] ?? "").trim() : `row-${i + 2}`;
|
|
2425
|
+
if (ref === "") throw new Error(`Sheet row ${i + 2} has no value in the id column "${args.refColumn}".`);
|
|
2426
|
+
if (seen.has(ref)) throw new Error(`Two sheet rows share the id "${ref}"; each row needs its own.`);
|
|
2427
|
+
seen.add(ref);
|
|
2428
|
+
const values = {};
|
|
2429
|
+
columns.forEach((c, j) => {
|
|
2430
|
+
const v = cells[j];
|
|
2431
|
+
values[c] = v === void 0 || v === "" ? null : v;
|
|
2432
|
+
});
|
|
2433
|
+
rows.push({ ref, values });
|
|
2434
|
+
});
|
|
2435
|
+
return { source: args.source, table_name: args.tableName, columns, rows };
|
|
2436
|
+
}
|
|
2437
|
+
function withRowCounts(tables, counts) {
|
|
2438
|
+
if (!counts) return [...tables];
|
|
2439
|
+
const byId = new Map(counts.map((c) => [c.table_id, Number(c.visible_rows)]));
|
|
2440
|
+
return tables.map((t) => byId.has(t.id) ? { ...t, row_count: byId.get(t.id) } : t);
|
|
2441
|
+
}
|
|
2442
|
+
function moveInOrder(order, moved, toIndex) {
|
|
2443
|
+
const rest = order.filter((id) => id !== moved);
|
|
2444
|
+
const at = Math.max(0, Math.min(Math.trunc(toIndex), rest.length));
|
|
2445
|
+
return [...rest.slice(0, at), moved, ...rest.slice(at)];
|
|
2446
|
+
}
|
|
2377
2447
|
|
|
2378
2448
|
// src/store.generated.ts
|
|
2379
2449
|
var ACTOR_VOCABULARY = ["user", "agent", "system"];
|
|
@@ -3049,6 +3119,7 @@ var STORE_DOORS = [
|
|
|
3049
3119
|
{ name: "table_work_kind", args: "p_organization_id uuid, p_table_id uuid", returns: "text", security: "invoker" },
|
|
3050
3120
|
{ name: "tables_at_home", args: "p_organization_id uuid, p_home_ids uuid[]", returns: "TABLE(table_id uuid, home_record_id uuid, kind text)", security: "definer" },
|
|
3051
3121
|
{ name: "tables_described_without_asking", args: "", returns: "TABLE(function_name text, identity_args text, why text)", security: "invoker" },
|
|
3122
|
+
{ name: "tables_i_can_open", args: "", returns: "TABLE(table_id uuid, table_name text, organization_id uuid, organization_name text, member boolean, visibility text, updated_at timestamp with time zone)", security: "definer" },
|
|
3052
3123
|
{ name: "tables_shared_with_me", args: "", returns: "TABLE(table_id uuid, organization_id uuid, organization text, table_name text, level text, level_label text, shared_at timestamp with time zone, opens boolean, say text)", security: "definer" },
|
|
3053
3124
|
{ name: "trg_associations_bump_visibility", args: "", returns: "trigger", security: "definer" },
|
|
3054
3125
|
{ name: "undeclared_keys", args: "p_organization_id uuid, p_table_id uuid, p_data jsonb", returns: "text[]", security: "invoker" },
|
|
@@ -3073,6 +3144,7 @@ var STORE_DOORS = [
|
|
|
3073
3144
|
{ name: "visible_predicate_sql", args: "p_user uuid, p_organization_id uuid, p_table_id uuid, p_required permission_level DEFAULT 'viewer'::permission_level, p_alias text DEFAULT 'r'::text", returns: "text", security: "definer" },
|
|
3074
3145
|
{ name: "visible_record_ids", args: "p_user_id uuid, p_required permission_level DEFAULT 'viewer'::permission_level", returns: "TABLE(id uuid)", security: "definer" },
|
|
3075
3146
|
{ name: "visible_set", args: "p_user uuid, p_organization_id uuid, p_table_id uuid, p_required permission_level DEFAULT 'viewer'::permission_level, OUT o_all_visible boolean, OUT o_true_visibility platform.visibility[], OUT o_granted_all uuid[], OUT o_granted_visible uuid[], OUT o_carried_visible uuid[], OUT o_ladder_calls integer, OUT o_fallback boolean, OUT o_note text", returns: "record", security: "definer" },
|
|
3147
|
+
{ name: "where_id_opens", args: "p_id uuid", returns: "jsonb", security: "definer" },
|
|
3076
3148
|
{ name: "widget_kernel_id", args: "", returns: "uuid", security: "invoker" },
|
|
3077
3149
|
{ name: "withheld_marker", args: "p_mask jsonb, p_key text", returns: "jsonb", security: "invoker" },
|
|
3078
3150
|
{ name: "withheld_sentence", args: "p_mask jsonb, p_key text", returns: "text", security: "invoker" },
|
|
@@ -3179,7 +3251,7 @@ var STORE_REFUSAL_CODES = [
|
|
|
3179
3251
|
{ code: "23505", raised_by: "_share_write_person,_unique_rule_holds,doc_sign,doc_signature_write,entity_field_declare,field_declare,home_add,inbound_declare,io_proposal_accept,relation_carry,relation_own,sign_request_cancel,sign_request_create,table_share_outside_resend,work_approval_decide,work_slot_hold" },
|
|
3180
3252
|
{ code: "23514", raised_by: "_checklist_instantiate,_checklist_step_guard,_containment_guard,_dated_values_guard,_derived_fields,_display_format_check,_display_spec_for,_entity_custom_fields_guard,_field_class_guard,_field_document_for,_field_shape_guard,_field_type_parity_guard,_merge_field_shape_guard,_merge_field_temporal_guard,_promoted_field_cap_guard,_record_rule_uses,_relation_halves_agree,_relation_kernel_targets,_resolve_choice_words,_rule_shape_guard,_rule_topology_guard,_store_relation_edge_names_its_field,_table_columns_word_guard,_table_shape_guard,_undeclared_key_guard,_value_envelope,_with_display,_work_shape_guard,_workdoors_approval_guard,action_run,assert_columns_are_defined,assert_entity_is_organization_scoped,booking_declare,capture_publish,capture_sheet_declare,checklist_declare,checklist_step_complete,doc_sign,doc_signature_write,doc_template_save,entity_field_declare,entity_field_retire,entity_field_update,entity_records_find,entity_table,field_declare,field_retire,field_update,home_add,io_comment_write,io_import_rows,migrate_merge,migrate_purge_hard,portal_archive,portal_restore,record_write_graph,relation_carry,relation_halves_repair,relation_own,sign_request_create,sign_request_sign,table_declare,table_from_example,validate_value_envelope,validate_values,work_set_state,work_slots_declare,work_take_assignment,work_template_instantiate" },
|
|
3181
3253
|
{ code: "40001", raised_by: "has_visibility_at" },
|
|
3182
|
-
{ code: "42501", raised_by: "_doc_render_immutable,_doc_signature_immutable,_field_definition_write,_field_write_door,_rule_definition_write,_store_door,agent_table_claim,anon_capture,anon_inbound_land,anon_publish,anon_token_issue,anon_token_verify,anon_write,assert_client_may_change,assert_client_may_open,assert_client_may_reach,assert_may_know_table,assert_organization_admin,assert_store_door,booking_confirm,booking_declare,booking_hold,capture_submit,checklist_run,comment_write,conversation_scope_bind,conversation_scope_unbind,doc_sign,enrich_declare,enrich_due,enrich_land,enrich_normalize,entity_field_declare,entity_field_retire,entity_field_update,entity_value_write,external_write_through,form_declare,form_submit,inbound_mail_land,io_comment_resolve,io_comment_write,io_import_begin,io_import_finish,io_restore,migrate_purge,migrate_purge_hard,migrate_purge_hard_request,migrate_reclass,my_levels,organization_clear,portal_declare,portal_invitation,portal_invite,portal_invite_accept,portal_principal_bind,promote_table,query_visibility_parity,read_record,read_records,read_records_archived,read_records_by_ids,read_records_matching,record_table,record_write_graph,relation_halves_disagreements,relation_halves_repair,share_grant,subscription_mute,subscription_preview,table_share_outside_accept,table_share_outside_invite,table_share_outside_resend,table_webhook_declare,visibility_as_of,work_approval_decide,work_approval_read,work_approval_request,work_person" },
|
|
3254
|
+
{ code: "42501", raised_by: "_doc_render_immutable,_doc_signature_immutable,_field_definition_write,_field_write_door,_rule_definition_write,_store_door,agent_table_claim,anon_capture,anon_inbound_land,anon_publish,anon_token_issue,anon_token_verify,anon_write,assert_client_may_change,assert_client_may_open,assert_client_may_reach,assert_may_know_table,assert_organization_admin,assert_store_door,booking_confirm,booking_declare,booking_hold,capture_submit,checklist_run,comment_write,conversation_scope_bind,conversation_scope_unbind,doc_sign,enrich_declare,enrich_due,enrich_land,enrich_normalize,entity_field_declare,entity_field_retire,entity_field_update,entity_value_write,external_write_through,form_declare,form_submit,inbound_mail_land,io_comment_resolve,io_comment_write,io_import_begin,io_import_finish,io_restore,migrate_purge,migrate_purge_hard,migrate_purge_hard_request,migrate_reclass,my_levels,organization_clear,organization_contents,portal_declare,portal_invitation,portal_invite,portal_invite_accept,portal_principal_bind,promote_table,query_visibility_parity,read_record,read_records,read_records_archived,read_records_by_ids,read_records_matching,record_table,record_write_graph,relation_halves_disagreements,relation_halves_repair,share_grant,subscription_mute,subscription_preview,table_share_outside_accept,table_share_outside_invite,table_share_outside_resend,table_webhook_declare,visibility_as_of,work_approval_decide,work_approval_read,work_approval_request,work_person" },
|
|
3183
3255
|
{ code: "42703", raised_by: "entity_table,portal_declare" },
|
|
3184
3256
|
{ code: "53400", raised_by: "anon_rate_take,delete_cascade_closure,enrich_due,enrich_land,promote_field" },
|
|
3185
3257
|
{ code: "54000", raised_by: "action_run,hub_changed_by,table_decorate,table_from_example,table_webhook_declare" },
|
|
@@ -4240,6 +4312,20 @@ var OWED_BY = {
|
|
|
4240
4312
|
table_webhook_archive: "GRID-PRIMITIVES G4 \u2014 gridprim_every_row_change_reaches_the_webhook.sql (chair's production apply)",
|
|
4241
4313
|
table_from_example: "GRID-PRIMITIVES G5 \u2014 gridprim_a_table_can_start_from_a_real_example.sql (chair's production apply)",
|
|
4242
4314
|
autonumber_backfill: "GRID-PRIMITIVES G5 \u2014 gridprim_a_table_can_start_from_a_real_example.sql (chair's production apply)",
|
|
4315
|
+
table_list_everywhere: "GRID-PRIMITIVES G9 \u2014 gridprim_every_picker_lists_both_stores.sql (chair's production apply)",
|
|
4316
|
+
table_sync: "GRID-PRIMITIVES G10 \u2014 gridprim_a_synced_sheet_is_one_table_that_refreshes.sql (chair's production apply)",
|
|
4317
|
+
scope_table_provision: "GRID-PRIMITIVES G11 \u2014 gridprim_a_scope_provisions_its_table_in_the_store.sql (chair's production apply)",
|
|
4318
|
+
table_row_counts: "GRID-PRIMITIVES G12 \u2014 gridprim_every_table_counts_its_rows_and_every_row_shows_its_header.sql + its grant file (chair's production apply)",
|
|
4319
|
+
view_record_order_set: "GRID-PRIMITIVES G13 \u2014 gridprim_a_view_keeps_the_order_a_person_dragged.sql + its grant file (chair's production apply)",
|
|
4320
|
+
table_share_outside_grant: "GRID-PRIMITIVES G14 \u2014 gridprim_a_known_outsider_is_granted_at_once.sql + gridprim_a_signed_in_person_may_share_with_a_known_outsider.sql (chair's production apply)",
|
|
4321
|
+
read_records_in_view_order: "GRID-PRIMITIVES G13 \u2014 gridprim_a_view_keeps_the_order_a_person_dragged.sql + its grant file (chair's production apply)",
|
|
4322
|
+
rule_members_visible: "S2-PRIME FILTER-GROUPS \u2014 filtergroups_a_views_nested_question_is_one_where_clause.sql + its grant file (chair's production apply)",
|
|
4323
|
+
record_headers: "GRID-PRIMITIVES G12 \u2014 gridprim_every_table_counts_its_rows_and_every_row_shows_its_header.sql + its grant file (chair's production apply)",
|
|
4324
|
+
pipeline_move_many: "UI-CHAMPIONS S4 \u2014 uichamp_s4_a_selection_moves_and_decides_in_one_call.sql + its grant file (chair's production apply)",
|
|
4325
|
+
work_decide_many: "UI-CHAMPIONS S4 \u2014 uichamp_s4_a_selection_moves_and_decides_in_one_call.sql + its grant file (chair's production apply)",
|
|
4326
|
+
portal_form: "UI-CHAMPIONS S6 \u2014 uichamp_s6_a_portal_carries_its_look_and_its_forms.sql + uichamp_s6_a_signed_in_person_may_open_a_portals_look_and_forms.sql (chair's production apply)",
|
|
4327
|
+
portal_form_submit: "UI-CHAMPIONS S6 \u2014 uichamp_s6_a_portal_carries_its_look_and_its_forms.sql + uichamp_s6_a_signed_in_person_may_open_a_portals_look_and_forms.sql (chair's production apply)",
|
|
4328
|
+
form_preview_asks: "FORMS-FIX-1 \u2014 formsfix1_the_owners_preview_asks_the_store_the_same_question.sql + its grant file (chair's production apply)",
|
|
4243
4329
|
rule_declare: "W1-RULE \u2014 `custom.record_write` writes `data_class = 'record'`, so the ONE write door cannot make a Rule record; declaring a Rule (and therefore a DOOR-18 subscription) needs a door of its own"
|
|
4244
4330
|
};
|
|
4245
4331
|
var TRUST_SCHEMA = "iam";
|
|
@@ -4443,6 +4529,8 @@ var DOORS = {
|
|
|
4443
4529
|
pipelineBoard: "pipeline_board",
|
|
4444
4530
|
pipelineTransitionRefusal: "pipeline_transition_refusal",
|
|
4445
4531
|
pipelineMove: "pipeline_move",
|
|
4532
|
+
/** Lane S4: many cards, one call, a verdict and a version per card. */
|
|
4533
|
+
pipelineMoveMany: "pipeline_move_many",
|
|
4446
4534
|
tableStageField: "table_stage_field",
|
|
4447
4535
|
// STAGE-RULES. A gate can refuse or it can hand the change to the approvals queue; the
|
|
4448
4536
|
// closed list is the store's, the knob is the organization's, and what is WAITING on a
|
|
@@ -4453,6 +4541,7 @@ var DOORS = {
|
|
|
4453
4541
|
pipelinePending: "pipeline_pending",
|
|
4454
4542
|
pipelineGatePreview: "pipeline_gate_preview",
|
|
4455
4543
|
ruleMembers: "rule_members",
|
|
4544
|
+
ruleMembersVisible: "rule_members_visible",
|
|
4456
4545
|
ruleMembership: "rule_membership",
|
|
4457
4546
|
ruleRun: "rule_run",
|
|
4458
4547
|
ruleEval: "rule_eval",
|
|
@@ -4467,6 +4556,12 @@ var DOORS = {
|
|
|
4467
4556
|
// are server-lane doors and a browser never calls them.
|
|
4468
4557
|
forms: "forms",
|
|
4469
4558
|
formDeclare: "form_declare",
|
|
4559
|
+
/**
|
|
4560
|
+
* WHICH QUESTIONS THE OWNER'S PREVIEW ASKS NEXT (lane FORMS-FIX-1). The same store answer a
|
|
4561
|
+
* stranger's form gets (`custom._form_questions_asked` → `custom.rule_eval`), behind the
|
|
4562
|
+
* organization wall and the caller's own rung on the Table — never `rule_eval` from a browser.
|
|
4563
|
+
*/
|
|
4564
|
+
formPreviewAsks: "form_preview_asks",
|
|
4470
4565
|
// PRODUCTS row 14 — "let clients book a 30-minute consult". A booking page IS an
|
|
4471
4566
|
// `anon_form`, so it is opened and closed by `anonPublish` like any other; this is
|
|
4472
4567
|
// the owner's list of them with the numbers that make it worth opening. The
|
|
@@ -4526,6 +4621,11 @@ var DOORS = {
|
|
|
4526
4621
|
portalInvite: "portal_invite",
|
|
4527
4622
|
portalRevoke: "portal_revoke",
|
|
4528
4623
|
portalPreview: "portal_preview",
|
|
4624
|
+
// S6 — the CLIENT's two form doors. They are store doors (schema `custom`), called by a
|
|
4625
|
+
// signed-in portal principal, and each refuses anybody who is not a live principal of that
|
|
4626
|
+
// live portal — so, unlike the sign-in pair above, they belong in this table.
|
|
4627
|
+
portalForm: "portal_form",
|
|
4628
|
+
portalFormSubmit: "portal_form_submit",
|
|
4529
4629
|
// ORG-CLEANUP, 2026-09-22 — A PORTAL IS ARCHIVED, NEVER DELETED.
|
|
4530
4630
|
// `portals` keeps its signature and HIDES archived portals (the law's default
|
|
4531
4631
|
// is to hide); `list_portals(org, 'active'|'archived'|'all')` is the
|
|
@@ -4721,6 +4821,8 @@ var DOORS = {
|
|
|
4721
4821
|
workApprovalRequest: "work_approval_request",
|
|
4722
4822
|
workApprovalMayDecide: "work_approval_may_decide",
|
|
4723
4823
|
workApprovalDecide: "work_approval_decide",
|
|
4824
|
+
/** Lane S4: many inbox decisions, one call, a verdict per item. */
|
|
4825
|
+
workDecideMany: "work_decide_many",
|
|
4724
4826
|
workApprovalRead: "work_approval_read",
|
|
4725
4827
|
// PRODUCTS row 13 — checklists and SOP runs.
|
|
4726
4828
|
checklistRefusal: "checklist_refusal",
|
|
@@ -4746,6 +4848,14 @@ var DOORS = {
|
|
|
4746
4848
|
tableFromExample: "table_from_example",
|
|
4747
4849
|
autonumberBackfill: "autonumber_backfill",
|
|
4748
4850
|
ioExport: "io_export",
|
|
4851
|
+
tableListEverywhere: "table_list_everywhere",
|
|
4852
|
+
tableSync: "table_sync",
|
|
4853
|
+
scopeTableProvision: "scope_table_provision",
|
|
4854
|
+
tableRowCounts: "table_row_counts",
|
|
4855
|
+
recordHeaders: "record_headers",
|
|
4856
|
+
viewRecordOrderSet: "view_record_order_set",
|
|
4857
|
+
readRecordsInViewOrder: "read_records_in_view_order",
|
|
4858
|
+
tableShareOutsideGrant: "table_share_outside_grant",
|
|
4749
4859
|
// Declared here BECAUSE they do not exist yet: naming them is what makes the
|
|
4750
4860
|
// absence visible to `pnpm check:store-registry` and to the suite.
|
|
4751
4861
|
metadataSearch: "metadata_search",
|
|
@@ -5145,6 +5255,10 @@ function createRecordsClient(config) {
|
|
|
5145
5255
|
})
|
|
5146
5256
|
);
|
|
5147
5257
|
},
|
|
5258
|
+
async tableFacts() {
|
|
5259
|
+
if (!doorExists(DOORS.tableFacts)) return ok(null);
|
|
5260
|
+
return callDoor(DOORS.tableFacts, { p_organization_id: org }, "tableFacts");
|
|
5261
|
+
},
|
|
5148
5262
|
async tableArchived({ table_id }) {
|
|
5149
5263
|
const kernel = await callDoor(DOORS.tableKernelId, {}, "tableArchived.kernel");
|
|
5150
5264
|
if (!kernel.ok) return err(kernel.error);
|
|
@@ -5328,23 +5442,6 @@ function createRecordsClient(config) {
|
|
|
5328
5442
|
const { document } = unfold(row.document);
|
|
5329
5443
|
return { ...document, id: row.id, organization_id: org };
|
|
5330
5444
|
});
|
|
5331
|
-
if (doorExists(DOORS.tableFacts)) {
|
|
5332
|
-
const facts = await callDoor(
|
|
5333
|
-
DOORS.tableFacts,
|
|
5334
|
-
{ p_organization_id: org },
|
|
5335
|
-
"tableList.facts"
|
|
5336
|
-
);
|
|
5337
|
-
if (facts.ok) {
|
|
5338
|
-
const byId = new Map((facts.data ?? []).map((f) => [f.table_id, f]));
|
|
5339
|
-
const me = config.actor.user_id ?? null;
|
|
5340
|
-
for (const table of tables) {
|
|
5341
|
-
const fact = byId.get(table.id);
|
|
5342
|
-
if (!fact) continue;
|
|
5343
|
-
table.visibility = fact.visibility;
|
|
5344
|
-
if (fact.mine && me) table.created_by = me;
|
|
5345
|
-
}
|
|
5346
|
-
}
|
|
5347
|
-
}
|
|
5348
5445
|
tables.sort((a, b) => (a.name ?? "").localeCompare(b.name ?? ""));
|
|
5349
5446
|
return ok(tables);
|
|
5350
5447
|
},
|
|
@@ -5538,10 +5635,11 @@ function createRecordsClient(config) {
|
|
|
5538
5635
|
"pipelineRead"
|
|
5539
5636
|
);
|
|
5540
5637
|
},
|
|
5541
|
-
async pipelineBoard({ table_id, measure }) {
|
|
5638
|
+
async pipelineBoard({ table_id, measure, filter }) {
|
|
5639
|
+
const asked = filter && stableFilterKey(filter) !== "{}";
|
|
5542
5640
|
return callDoor(
|
|
5543
5641
|
DOORS.pipelineBoard,
|
|
5544
|
-
{ p_organization_id: org, p_table_id: table_id, p_measure: measure ?? null },
|
|
5642
|
+
asked ? { p_organization_id: org, p_table_id: table_id, p_measure: measure ?? null, p_filter: filter } : { p_organization_id: org, p_table_id: table_id, p_measure: measure ?? null },
|
|
5545
5643
|
"pipelineBoard"
|
|
5546
5644
|
);
|
|
5547
5645
|
},
|
|
@@ -5565,6 +5663,13 @@ function createRecordsClient(config) {
|
|
|
5565
5663
|
"pipelineMove"
|
|
5566
5664
|
);
|
|
5567
5665
|
},
|
|
5666
|
+
async pipelineMoveMany({ moves }) {
|
|
5667
|
+
return callDoor(
|
|
5668
|
+
DOORS.pipelineMoveMany,
|
|
5669
|
+
{ p_organization_id: org, p_moves: moves },
|
|
5670
|
+
"pipelineMoveMany"
|
|
5671
|
+
);
|
|
5672
|
+
},
|
|
5568
5673
|
async pipelineDeclare({ table_id, spec }) {
|
|
5569
5674
|
return callDoor(
|
|
5570
5675
|
DOORS.pipelineDeclare,
|
|
@@ -5614,6 +5719,18 @@ function createRecordsClient(config) {
|
|
|
5614
5719
|
"pipelineGatePreview"
|
|
5615
5720
|
);
|
|
5616
5721
|
},
|
|
5722
|
+
async ruleMembersVisible({ rule_id, limit = 200, offset = 0 }) {
|
|
5723
|
+
const door = await callDoor(
|
|
5724
|
+
DOORS.ruleMembersVisible,
|
|
5725
|
+
{ p_organization_id: org, p_rule_id: rule_id, p_limit: limit, p_offset: offset },
|
|
5726
|
+
"ruleMembersVisible"
|
|
5727
|
+
);
|
|
5728
|
+
if (!door.ok) return err(door.error);
|
|
5729
|
+
return ok((door.data ?? []).map((row) => {
|
|
5730
|
+
const { document, hidden } = unfold(row.document);
|
|
5731
|
+
return { id: row.id, document, level: row.level, hidden };
|
|
5732
|
+
}));
|
|
5733
|
+
},
|
|
5617
5734
|
async ruleMembers({ rule_id }) {
|
|
5618
5735
|
return callDoor(
|
|
5619
5736
|
DOORS.ruleMembers,
|
|
@@ -5666,6 +5783,13 @@ function createRecordsClient(config) {
|
|
|
5666
5783
|
"bookingDeclare"
|
|
5667
5784
|
);
|
|
5668
5785
|
},
|
|
5786
|
+
async formPreviewAsks({ table_id, questions, values }) {
|
|
5787
|
+
return callDoor(
|
|
5788
|
+
DOORS.formPreviewAsks,
|
|
5789
|
+
{ p_organization_id: org, p_table_id: table_id, p_questions: questions, p_values: values },
|
|
5790
|
+
"formPreviewAsks"
|
|
5791
|
+
);
|
|
5792
|
+
},
|
|
5669
5793
|
async formDeclare(args) {
|
|
5670
5794
|
return callDoor(
|
|
5671
5795
|
DOORS.formDeclare,
|
|
@@ -5841,11 +5965,33 @@ function createRecordsClient(config) {
|
|
|
5841
5965
|
p_tables: args.tables,
|
|
5842
5966
|
p_portal_id: args.portal_id ?? null,
|
|
5843
5967
|
p_slug: args.slug ?? null,
|
|
5844
|
-
p_sign_in_method: args.sign_in_method ?? "magic_link"
|
|
5968
|
+
p_sign_in_method: args.sign_in_method ?? "magic_link",
|
|
5969
|
+
// S6: sent only when given, so a caller that says nothing about the look keeps it.
|
|
5970
|
+
...args.config !== void 0 ? { p_config: args.config } : {}
|
|
5845
5971
|
},
|
|
5846
5972
|
"portalDeclare"
|
|
5847
5973
|
);
|
|
5848
5974
|
},
|
|
5975
|
+
async portalForm({ portal_id, form_id }) {
|
|
5976
|
+
return callDoor(
|
|
5977
|
+
DOORS.portalForm,
|
|
5978
|
+
{ p_organization_id: org, p_portal_id: portal_id, p_form_id: form_id },
|
|
5979
|
+
"portalForm"
|
|
5980
|
+
);
|
|
5981
|
+
},
|
|
5982
|
+
async portalFormSubmit({ portal_id, form_id, answers, client_key }) {
|
|
5983
|
+
return callDoor(
|
|
5984
|
+
DOORS.portalFormSubmit,
|
|
5985
|
+
{
|
|
5986
|
+
p_organization_id: org,
|
|
5987
|
+
p_portal_id: portal_id,
|
|
5988
|
+
p_form_id: form_id,
|
|
5989
|
+
p_payload: answers,
|
|
5990
|
+
p_client_key: client_key ?? null
|
|
5991
|
+
},
|
|
5992
|
+
"portalFormSubmit"
|
|
5993
|
+
);
|
|
5994
|
+
},
|
|
5849
5995
|
async portalInvite(args) {
|
|
5850
5996
|
return callDoor(
|
|
5851
5997
|
DOORS.portalInvite,
|
|
@@ -6044,10 +6190,17 @@ function createRecordsClient(config) {
|
|
|
6044
6190
|
"dashboardDeclare"
|
|
6045
6191
|
);
|
|
6046
6192
|
},
|
|
6047
|
-
async dashboardRun({ dashboard_id, filter }) {
|
|
6193
|
+
async dashboardRun({ dashboard_id, filter, compare, grain }) {
|
|
6048
6194
|
return callDoor(
|
|
6049
6195
|
DOORS.dashboardRun,
|
|
6050
|
-
{
|
|
6196
|
+
{
|
|
6197
|
+
p_organization_id: org,
|
|
6198
|
+
p_dashboard_id: dashboard_id,
|
|
6199
|
+
p_filter: filter ?? {},
|
|
6200
|
+
// Sent only when asked, so a caller that never compares calls exactly what it did.
|
|
6201
|
+
...compare ? { p_compare: compare } : {},
|
|
6202
|
+
...grain ? { p_grain: grain } : {}
|
|
6203
|
+
},
|
|
6051
6204
|
"dashboardRun"
|
|
6052
6205
|
);
|
|
6053
6206
|
},
|
|
@@ -6072,7 +6225,7 @@ function createRecordsClient(config) {
|
|
|
6072
6225
|
"dashboardDelete"
|
|
6073
6226
|
);
|
|
6074
6227
|
},
|
|
6075
|
-
async recordAggregate({ table_id, groupBy, measures, bucket, filter, limit }) {
|
|
6228
|
+
async recordAggregate({ table_id, groupBy, measures, bucket, filter, limit, compare }) {
|
|
6076
6229
|
return callDoor(
|
|
6077
6230
|
DOORS.recordAggregate,
|
|
6078
6231
|
{
|
|
@@ -6082,7 +6235,8 @@ function createRecordsClient(config) {
|
|
|
6082
6235
|
p_measures: measures ?? [],
|
|
6083
6236
|
p_bucket: bucket ?? null,
|
|
6084
6237
|
p_filter: filter ?? {},
|
|
6085
|
-
p_limit: limit ?? 200
|
|
6238
|
+
p_limit: limit ?? 200,
|
|
6239
|
+
...compare ? { p_compare: compare } : {}
|
|
6086
6240
|
},
|
|
6087
6241
|
"recordAggregate"
|
|
6088
6242
|
);
|
|
@@ -6810,6 +6964,13 @@ function createRecordsClient(config) {
|
|
|
6810
6964
|
"workApprovalDecide"
|
|
6811
6965
|
);
|
|
6812
6966
|
},
|
|
6967
|
+
async workDecideMany({ decisions }) {
|
|
6968
|
+
return callDoor(
|
|
6969
|
+
DOORS.workDecideMany,
|
|
6970
|
+
{ p_organization_id: org, p_decisions: decisions },
|
|
6971
|
+
"workDecideMany"
|
|
6972
|
+
);
|
|
6973
|
+
},
|
|
6813
6974
|
async workApprovalRead({ approval_id }) {
|
|
6814
6975
|
return callDoor(
|
|
6815
6976
|
DOORS.workApprovalRead,
|
|
@@ -7013,6 +7174,69 @@ function createRecordsClient(config) {
|
|
|
7013
7174
|
"tableFromExample"
|
|
7014
7175
|
);
|
|
7015
7176
|
},
|
|
7177
|
+
async tableListEverywhere() {
|
|
7178
|
+
return callDoor(
|
|
7179
|
+
DOORS.tableListEverywhere,
|
|
7180
|
+
{ p_organization_id: org },
|
|
7181
|
+
"tableListEverywhere"
|
|
7182
|
+
);
|
|
7183
|
+
},
|
|
7184
|
+
async tableSync({ home_id, spec }) {
|
|
7185
|
+
return callDoor(
|
|
7186
|
+
DOORS.tableSync,
|
|
7187
|
+
{ p_organization_id: org, p_home_id: home_id, p_spec: spec },
|
|
7188
|
+
"tableSync"
|
|
7189
|
+
);
|
|
7190
|
+
},
|
|
7191
|
+
async scopeTableProvision({ home_id, item_id, scope_id }) {
|
|
7192
|
+
return callDoor(
|
|
7193
|
+
DOORS.scopeTableProvision,
|
|
7194
|
+
{ p_organization_id: org, p_item_id: item_id, p_scope_id: scope_id, p_home_id: home_id ?? null },
|
|
7195
|
+
"scopeTableProvision"
|
|
7196
|
+
);
|
|
7197
|
+
},
|
|
7198
|
+
async tableRowCounts({ table_ids }) {
|
|
7199
|
+
return callDoor(
|
|
7200
|
+
DOORS.tableRowCounts,
|
|
7201
|
+
{ p_organization_id: org, p_table_ids: table_ids },
|
|
7202
|
+
"tableRowCounts"
|
|
7203
|
+
);
|
|
7204
|
+
},
|
|
7205
|
+
async recordHeaders({ ids }) {
|
|
7206
|
+
return callDoor(
|
|
7207
|
+
DOORS.recordHeaders,
|
|
7208
|
+
{ p_organization_id: org, p_ids: ids },
|
|
7209
|
+
"recordHeaders"
|
|
7210
|
+
);
|
|
7211
|
+
},
|
|
7212
|
+
async tableShareOutsideGrant({ table_id, person, level }) {
|
|
7213
|
+
return callDoor(
|
|
7214
|
+
DOORS.tableShareOutsideGrant,
|
|
7215
|
+
{ p_organization_id: org, p_table_id: table_id, p_person: person, p_level: level ?? "viewer" },
|
|
7216
|
+
"tableShareOutsideGrant"
|
|
7217
|
+
);
|
|
7218
|
+
},
|
|
7219
|
+
async viewRecordOrderSet({ view_id, record_ids }) {
|
|
7220
|
+
return callDoor(
|
|
7221
|
+
DOORS.viewRecordOrderSet,
|
|
7222
|
+
{ p_organization_id: org, p_view_id: view_id, p_record_ids: record_ids },
|
|
7223
|
+
"viewRecordOrderSet"
|
|
7224
|
+
);
|
|
7225
|
+
},
|
|
7226
|
+
async readInViewOrder({ view_id, limit, offset }) {
|
|
7227
|
+
const door = await callDoor(
|
|
7228
|
+
DOORS.readRecordsInViewOrder,
|
|
7229
|
+
{ p_organization_id: org, p_view_id: view_id, p_by_id: false, p_limit: limit ?? 200, p_offset: offset ?? 0 },
|
|
7230
|
+
"readInViewOrder"
|
|
7231
|
+
);
|
|
7232
|
+
if (!door.ok) return err(door.error);
|
|
7233
|
+
return ok(
|
|
7234
|
+
(door.data ?? []).map((row) => {
|
|
7235
|
+
const { document, hidden } = unfold(row.document);
|
|
7236
|
+
return { id: row.id, document, level: row.level, hidden, position: row.position ?? null };
|
|
7237
|
+
})
|
|
7238
|
+
);
|
|
7239
|
+
},
|
|
7016
7240
|
async autonumberBackfill({ field_id }) {
|
|
7017
7241
|
return callDoor(
|
|
7018
7242
|
DOORS.autonumberBackfill,
|
|
@@ -7107,27 +7331,6 @@ function useRecordsActor() {
|
|
|
7107
7331
|
|
|
7108
7332
|
// src/react/hooks.ts
|
|
7109
7333
|
import { useCallback, useEffect, useMemo as useMemo2, useRef, useState, useSyncExternalStore } from "react";
|
|
7110
|
-
|
|
7111
|
-
// src/aggregate.ts
|
|
7112
|
-
function measureKey(measure) {
|
|
7113
|
-
return measure.op === "count" ? "count" : `${measure.op}_${measure.key ?? ""}`;
|
|
7114
|
-
}
|
|
7115
|
-
function stableFilterKey(filter) {
|
|
7116
|
-
if (!filter) return "{}";
|
|
7117
|
-
const keys = Object.keys(filter).sort();
|
|
7118
|
-
if (keys.length === 0) return "{}";
|
|
7119
|
-
const parts = keys.map((key) => {
|
|
7120
|
-
const value = filter[key];
|
|
7121
|
-
if (value !== null && typeof value === "object") {
|
|
7122
|
-
const window2 = value;
|
|
7123
|
-
return `${JSON.stringify(key)}:{"from":${JSON.stringify(window2.from ?? null)},"to":${JSON.stringify(window2.to ?? null)}}`;
|
|
7124
|
-
}
|
|
7125
|
-
return `${JSON.stringify(key)}:${JSON.stringify(value ?? null)}`;
|
|
7126
|
-
});
|
|
7127
|
-
return `{${parts.join(",")}}`;
|
|
7128
|
-
}
|
|
7129
|
-
|
|
7130
|
-
// src/react/hooks.ts
|
|
7131
7334
|
function useAsync(run, deps) {
|
|
7132
7335
|
const client = useRecordsClient();
|
|
7133
7336
|
const [state, setState] = useState(
|
|
@@ -7607,6 +7810,88 @@ function useMergeField(key, state) {
|
|
|
7607
7810
|
return resolution;
|
|
7608
7811
|
}
|
|
7609
7812
|
|
|
7813
|
+
// src/react/entity-reference.ts
|
|
7814
|
+
import { useEffect as useEffect2, useState as useState2 } from "react";
|
|
7815
|
+
|
|
7816
|
+
// src/relation.ts
|
|
7817
|
+
var ENTITY_REF_ID = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
7818
|
+
function isRefLike(value) {
|
|
7819
|
+
return typeof value === "object" && value !== null && "token" in value && "id" in value;
|
|
7820
|
+
}
|
|
7821
|
+
function entityRefsOf(value) {
|
|
7822
|
+
const items = Array.isArray(value) ? value : value == null ? [] : [value];
|
|
7823
|
+
const out = [];
|
|
7824
|
+
for (const item of items) {
|
|
7825
|
+
if (!isRefLike(item)) continue;
|
|
7826
|
+
const token = String(item.token ?? "").trim().toLowerCase();
|
|
7827
|
+
const id = String(item.id ?? "").trim();
|
|
7828
|
+
if (!token || !ENTITY_REF_ID.test(id)) continue;
|
|
7829
|
+
const label = item.label;
|
|
7830
|
+
out.push({ token, id: id.toLowerCase(), label: typeof label === "string" ? label : null });
|
|
7831
|
+
}
|
|
7832
|
+
return out;
|
|
7833
|
+
}
|
|
7834
|
+
function entityRefsToWrite(value, multi) {
|
|
7835
|
+
const seen = /* @__PURE__ */ new Set();
|
|
7836
|
+
const refs = [];
|
|
7837
|
+
for (const ref of entityRefsOf(value)) {
|
|
7838
|
+
const k = `${ref.token}:${ref.id}`;
|
|
7839
|
+
if (seen.has(k)) continue;
|
|
7840
|
+
seen.add(k);
|
|
7841
|
+
refs.push({ token: ref.token, id: ref.id });
|
|
7842
|
+
}
|
|
7843
|
+
if (multi) return refs;
|
|
7844
|
+
return refs[0] ?? null;
|
|
7845
|
+
}
|
|
7846
|
+
async function entityReferenceKinds(source) {
|
|
7847
|
+
const { data, error } = await source.rpc("entity_reference_kinds", {}, { schema: "custom" });
|
|
7848
|
+
if (error) return err(mapPgError(error, "entityReferenceKinds"));
|
|
7849
|
+
return ok(Array.isArray(data) ? data : []);
|
|
7850
|
+
}
|
|
7851
|
+
async function entityReferenceWords(source, organizationId, refs) {
|
|
7852
|
+
if (refs.length === 0) return ok([]);
|
|
7853
|
+
const { data, error } = await source.rpc(
|
|
7854
|
+
"entity_reference_words",
|
|
7855
|
+
{ p_organization_id: organizationId, p_refs: refs.map((r) => ({ token: r.token, id: r.id })) },
|
|
7856
|
+
{ schema: "custom" }
|
|
7857
|
+
);
|
|
7858
|
+
if (error) return err(mapPgError(error, "entityReferenceWords"));
|
|
7859
|
+
return ok(entityRefsOf(data));
|
|
7860
|
+
}
|
|
7861
|
+
|
|
7862
|
+
// src/react/entity-reference.ts
|
|
7863
|
+
function useEntityReferenceKinds() {
|
|
7864
|
+
const client = useRecordsClient();
|
|
7865
|
+
const [state, setState] = useState2({ data: null, loading: true, error: null });
|
|
7866
|
+
useEffect2(() => {
|
|
7867
|
+
let live = true;
|
|
7868
|
+
void entityReferenceKinds(client.config.dataSource).then((res) => {
|
|
7869
|
+
if (!live) return;
|
|
7870
|
+
setState(res.ok ? { data: res.data, loading: false, error: null } : { data: null, loading: false, error: res.error });
|
|
7871
|
+
});
|
|
7872
|
+
return () => {
|
|
7873
|
+
live = false;
|
|
7874
|
+
};
|
|
7875
|
+
}, [client]);
|
|
7876
|
+
return state;
|
|
7877
|
+
}
|
|
7878
|
+
function useEntityReferenceWords(refs) {
|
|
7879
|
+
const client = useRecordsClient();
|
|
7880
|
+
const key = refs.map((r) => `${r.token}:${r.id}`).join(",");
|
|
7881
|
+
const [state, setState] = useState2({ data: null, loading: refs.length > 0, error: null });
|
|
7882
|
+
useEffect2(() => {
|
|
7883
|
+
let live = true;
|
|
7884
|
+
void entityReferenceWords(client.config.dataSource, client.config.organizationId, refs).then((res) => {
|
|
7885
|
+
if (!live) return;
|
|
7886
|
+
setState(res.ok ? { data: res.data, loading: false, error: null } : { data: null, loading: false, error: res.error });
|
|
7887
|
+
});
|
|
7888
|
+
return () => {
|
|
7889
|
+
live = false;
|
|
7890
|
+
};
|
|
7891
|
+
}, [client, key]);
|
|
7892
|
+
return state;
|
|
7893
|
+
}
|
|
7894
|
+
|
|
7610
7895
|
// src/vocabulary.ts
|
|
7611
7896
|
var TABLE_TYPES = [
|
|
7612
7897
|
"entity",
|
|
@@ -7718,6 +8003,7 @@ var FIELD_KINDS = [
|
|
|
7718
8003
|
"currency",
|
|
7719
8004
|
"datetime",
|
|
7720
8005
|
"email",
|
|
8006
|
+
"entity_reference",
|
|
7721
8007
|
"formula",
|
|
7722
8008
|
"json",
|
|
7723
8009
|
"long_text",
|
|
@@ -7756,6 +8042,7 @@ function fieldKindFor(field, kernel) {
|
|
|
7756
8042
|
case "list":
|
|
7757
8043
|
return field.multi ? "multi_select" : "select";
|
|
7758
8044
|
case "relation": {
|
|
8045
|
+
if (isEntityReferenceConfig(config)) return "entity_reference";
|
|
7759
8046
|
const parity = String(config["parity"] ?? "");
|
|
7760
8047
|
if (parity === "attachment" || parity === "member") return parity;
|
|
7761
8048
|
if (kernel?.file && field.relation_target === kernel.file) return "attachment";
|
|
@@ -7773,6 +8060,14 @@ function fieldKindFor(field, kernel) {
|
|
|
7773
8060
|
}
|
|
7774
8061
|
}
|
|
7775
8062
|
var UUID_TEXT = /^[0-9a-f]{8}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{4}-[0-9a-f]{12}$/i;
|
|
8063
|
+
function isEntityReferenceConfig(config) {
|
|
8064
|
+
const allowed = config?.["allowed_types"];
|
|
8065
|
+
return Array.isArray(allowed) && allowed.length > 0;
|
|
8066
|
+
}
|
|
8067
|
+
function entityReferenceKindsOf(field) {
|
|
8068
|
+
const allowed = field.config?.["allowed_types"];
|
|
8069
|
+
return Array.isArray(allowed) ? allowed.map((k) => String(k).trim().toLowerCase()).filter(Boolean) : [];
|
|
8070
|
+
}
|
|
7776
8071
|
var TRUE_WORDS = /* @__PURE__ */ new Set(["true", "yes", "y", "1", "\u2713", "x", "checked", "on"]);
|
|
7777
8072
|
var FALSE_WORDS = /* @__PURE__ */ new Set(["false", "no", "n", "0", "", "unchecked", "off"]);
|
|
7778
8073
|
function coercionLabel(field) {
|
|
@@ -7888,6 +8183,23 @@ function coerceTypedAnswer(field, raw, opts = {}) {
|
|
|
7888
8183
|
return {
|
|
7889
8184
|
refusal: `${label} points at another record, so it is chosen rather than typed. Open it and pick the record.`
|
|
7890
8185
|
};
|
|
8186
|
+
// SC-R / P12. An entity reference names a platform thing by kind and id.
|
|
8187
|
+
// An import or an agent may hand over `note:<id>` — or a bare id when the
|
|
8188
|
+
// column allows exactly one kind; the store then decides whether the thing
|
|
8189
|
+
// is there and whether the writer may open it. Words are chosen, not typed.
|
|
8190
|
+
case "entity_reference": {
|
|
8191
|
+
const allowed = entityReferenceKindsOf(field);
|
|
8192
|
+
const [maybeToken, maybeId] = text.includes(":") ? text.split(/:(.*)/s, 2) : ["", text];
|
|
8193
|
+
const token = (maybeToken ?? "").trim().toLowerCase() || (allowed.length === 1 ? allowed[0] : "");
|
|
8194
|
+
const id = (maybeId ?? "").trim();
|
|
8195
|
+
if (token && UUID_TEXT.test(id)) {
|
|
8196
|
+
const ref = { token, id: id.toLowerCase() };
|
|
8197
|
+
return { value: field.multi ? [ref] : ref };
|
|
8198
|
+
}
|
|
8199
|
+
return {
|
|
8200
|
+
refusal: `${label} points at something on the platform, so it is chosen rather than typed. Open it and pick it.`
|
|
8201
|
+
};
|
|
8202
|
+
}
|
|
7891
8203
|
case "formula":
|
|
7892
8204
|
case "lookup":
|
|
7893
8205
|
case "rollup":
|
|
@@ -7944,6 +8256,10 @@ function publicFormPath(formId) {
|
|
|
7944
8256
|
}
|
|
7945
8257
|
|
|
7946
8258
|
// src/portal.ts
|
|
8259
|
+
var PORTAL_ACCENTS = ["slate", "green", "amber", "red", "blue", "violet", "teal"];
|
|
8260
|
+
function isPortalAccent(word) {
|
|
8261
|
+
return typeof word === "string" && PORTAL_ACCENTS.includes(word);
|
|
8262
|
+
}
|
|
7947
8263
|
function portalPath(slug) {
|
|
7948
8264
|
return `/portal/c/${slug}`;
|
|
7949
8265
|
}
|
|
@@ -7966,6 +8282,56 @@ function emptyPortalArchiveLine() {
|
|
|
7966
8282
|
return "No portal of this organization has been archived. A portal you put away waits here until somebody restores it, and nothing is ever destroyed.";
|
|
7967
8283
|
}
|
|
7968
8284
|
|
|
8285
|
+
// src/placement.ts
|
|
8286
|
+
function keptOutOfSight(placement) {
|
|
8287
|
+
return placement?.kept_by_the_app === true;
|
|
8288
|
+
}
|
|
8289
|
+
function offeredAsContext(placement) {
|
|
8290
|
+
return placement?.offered_as_context === true;
|
|
8291
|
+
}
|
|
8292
|
+
function withTablePlacement(tables, facts) {
|
|
8293
|
+
if (!facts) return [...tables];
|
|
8294
|
+
const byId = new Map(facts.map((f) => [f.table_id, f]));
|
|
8295
|
+
return tables.map((table) => {
|
|
8296
|
+
const fact = byId.get(table.id);
|
|
8297
|
+
if (!fact || fact.kept_by_the_app === void 0) return table;
|
|
8298
|
+
return {
|
|
8299
|
+
...table,
|
|
8300
|
+
kept_by_the_app: fact.kept_by_the_app,
|
|
8301
|
+
kept_for: fact.kept_for ?? null,
|
|
8302
|
+
offered_as_context: fact.offered_as_context ?? false,
|
|
8303
|
+
keeper_group: fact.keeper_group ?? null,
|
|
8304
|
+
keeper_says: fact.keeper_says ?? null,
|
|
8305
|
+
used_in_kind: fact.used_in_kind ?? null,
|
|
8306
|
+
used_in_id: fact.used_in_id ?? null,
|
|
8307
|
+
used_in_table_id: fact.used_in_table_id ?? null
|
|
8308
|
+
};
|
|
8309
|
+
});
|
|
8310
|
+
}
|
|
8311
|
+
function keptGroups(tables) {
|
|
8312
|
+
const out = [];
|
|
8313
|
+
const at = /* @__PURE__ */ new Map();
|
|
8314
|
+
for (const table of tables) {
|
|
8315
|
+
if (!keptOutOfSight(table)) continue;
|
|
8316
|
+
const group = table.keeper_group?.trim() || "Kept by the app";
|
|
8317
|
+
let i = at.get(group);
|
|
8318
|
+
if (i === void 0) {
|
|
8319
|
+
i = out.length;
|
|
8320
|
+
at.set(group, i);
|
|
8321
|
+
out.push({ group, tables: [] });
|
|
8322
|
+
}
|
|
8323
|
+
out[i].tables.push(table);
|
|
8324
|
+
}
|
|
8325
|
+
return out;
|
|
8326
|
+
}
|
|
8327
|
+
function keptTableHref(fact, hrefs) {
|
|
8328
|
+
if (fact.used_in_kind === "scope" && fact.used_in_id) return hrefs.scope(fact.used_in_id);
|
|
8329
|
+
if (fact.used_in_kind === "table" && (fact.used_in_table_id || fact.used_in_id)) {
|
|
8330
|
+
return hrefs.table(fact.used_in_table_id || fact.used_in_id);
|
|
8331
|
+
}
|
|
8332
|
+
return hrefs.table(fact.table_id);
|
|
8333
|
+
}
|
|
8334
|
+
|
|
7969
8335
|
// src/capture-queue.ts
|
|
7970
8336
|
var DB_NAME = "matrx-capture";
|
|
7971
8337
|
var DB_VERSION = 1;
|
|
@@ -8276,6 +8642,7 @@ export {
|
|
|
8276
8642
|
PERMISSION_LEVELS,
|
|
8277
8643
|
PER_VALUE_ACCESS_WORDS,
|
|
8278
8644
|
PIPELINE_RULE_KINDS,
|
|
8645
|
+
PORTAL_ACCENTS,
|
|
8279
8646
|
PORTAL_ARCHIVE_FILTERS,
|
|
8280
8647
|
REFUSALS_WORTH_REPEATING,
|
|
8281
8648
|
RELATION_BINDINGS,
|
|
@@ -8311,6 +8678,11 @@ export {
|
|
|
8311
8678
|
coercionLabel,
|
|
8312
8679
|
emptyArchiveLine,
|
|
8313
8680
|
emptyPortalArchiveLine,
|
|
8681
|
+
entityReferenceKinds,
|
|
8682
|
+
entityReferenceKindsOf,
|
|
8683
|
+
entityReferenceWords,
|
|
8684
|
+
entityRefsOf,
|
|
8685
|
+
entityRefsToWrite,
|
|
8314
8686
|
err,
|
|
8315
8687
|
exampleSpec,
|
|
8316
8688
|
exportPageXlsx,
|
|
@@ -8321,16 +8693,24 @@ export {
|
|
|
8321
8693
|
indexedDbStore,
|
|
8322
8694
|
isArchiveLane,
|
|
8323
8695
|
isDecided,
|
|
8696
|
+
isEntityReferenceConfig,
|
|
8324
8697
|
isOwnOp,
|
|
8698
|
+
isPortalAccent,
|
|
8325
8699
|
isPortalArchiveFilter,
|
|
8326
8700
|
isRecordsErr,
|
|
8701
|
+
isRuleFilter,
|
|
8327
8702
|
isTheChosen,
|
|
8703
|
+
keptGroups,
|
|
8704
|
+
keptOutOfSight,
|
|
8705
|
+
keptTableHref,
|
|
8328
8706
|
looksLikeAnId,
|
|
8329
8707
|
mayDrag,
|
|
8330
8708
|
measureKey,
|
|
8331
8709
|
memoryStore,
|
|
8332
8710
|
mintClientKey,
|
|
8333
8711
|
mintOpId,
|
|
8712
|
+
moveInOrder,
|
|
8713
|
+
offeredAsContext,
|
|
8334
8714
|
ok,
|
|
8335
8715
|
openCaptureQueue,
|
|
8336
8716
|
optionKey,
|
|
@@ -8344,12 +8724,15 @@ export {
|
|
|
8344
8724
|
rememberedOpCount,
|
|
8345
8725
|
sameDocument,
|
|
8346
8726
|
scopeChip,
|
|
8727
|
+
sheetSyncSpec,
|
|
8347
8728
|
stableFilterKey,
|
|
8348
8729
|
tableShapeChanged,
|
|
8349
8730
|
useEntityFieldMutation,
|
|
8350
8731
|
useEntityFieldRights,
|
|
8351
8732
|
useEntityFields,
|
|
8352
8733
|
useEntityRecord,
|
|
8734
|
+
useEntityReferenceKinds,
|
|
8735
|
+
useEntityReferenceWords,
|
|
8353
8736
|
useEntityTable,
|
|
8354
8737
|
useFieldMutation,
|
|
8355
8738
|
useFields,
|
|
@@ -8365,6 +8748,8 @@ export {
|
|
|
8365
8748
|
useRecordsClient,
|
|
8366
8749
|
useTable,
|
|
8367
8750
|
useTableArchive,
|
|
8368
|
-
useTables
|
|
8751
|
+
useTables,
|
|
8752
|
+
withRowCounts,
|
|
8753
|
+
withTablePlacement
|
|
8369
8754
|
};
|
|
8370
8755
|
//# sourceMappingURL=index.js.map
|