Skip to content

[schemas] CRM core: editable contacts + field-proposal truth layer#393

Open
alanshurafa wants to merge 1 commit into
NateBJones-Projects:mainfrom
alanshurafa:upstream/crm-core
Open

[schemas] CRM core: editable contacts + field-proposal truth layer#393
alanshurafa wants to merge 1 commit into
NateBJones-Projects:mainfrom
alanshurafa:upstream/crm-core

Conversation

@alanshurafa

Copy link
Copy Markdown
Collaborator

Adds schemas/crm-core: an editable contact book on top of Open Brain with a human-in-the-loop truth layer.

Six tables (crm_contacts, crm_contact_methods, crm_contact_aliases, crm_contact_change_log, crm_field_proposals, crm_field_evidence) plus RPCs give each contact field per-field provenance and a propose/accept/reject flow: a human writes canonical fields directly, while a machine or agent must propose a change instead of overwriting one. A human then accepts (apply + log) or rejects (discard + log). A pending proposal never mutates the live field. Field locks let a human freeze a field against all writers. Contact-method values are redacted in the audit log.

Every primary key is UUID and every memory reference is UUID REFERENCES public.thoughts(id).

Self-contained under schemas/crm-core/; idempotent (IF NOT EXISTS throughout). Includes README + metadata.json.

Testing: applied on an ephemeral Postgres alongside the full schema stack; composes cleanly.

@github-actions

github-actions Bot commented Jul 6, 2026

Copy link
Copy Markdown

OB1 PR Gate

Folder structure — All files are in allowed directories
Required files — README.md and metadata.json found in all contribution folders
Metadata valid — All metadata.json files passed JSON Schema validation
No credentials — No API keys, tokens, or secrets detected
SQL safety — No destructive SQL or core table modifications
Category artifacts — Required file types present for each category
PR format — Title follows [category] Description format
No binary blobs — No oversized or binary files
README completeness — All READMEs include Prerequisites, Steps, and Expected Outcome
Contribution dependencies — All declared skill and primitive dependencies exist and are linked in README
LLM clarity review — Covered by Claude PR Review workflow
Remote MCP pattern — No local MCP server patterns detected — uses remote MCP correctly
Tool audit link — Extensions/integrations link to the MCP Tool Audit guide
Scope check — All changes are within the contribution folder(s)
Internal links — All relative links in READMEs resolve to existing files

Result: All 15 checks passed! Ready for human review.


Post-Merge Tasks

These don't block merge — they're reminders for admins after this PR lands.

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: 5d69eafb0b

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".

Comment on lines +503 to +507
c_known_keys CONSTANT TEXT[] := ARRAY[
'display_name', 'preferred_name', 'given_name', 'family_name', 'pronouns',
'job_title', 'organization_name', 'location', 'relationship_note',
'lifecycle_status', 'privacy_tier', 'owner_label'
];

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Allow canonical email updates through the truth layer

Because crm_create_contact accepts and stores p_canonical_email, but this allowlist omits canonical_email, any later crm_patch_contact_record call for that field—also the path used when accepting a contact_field proposal—raises unknown contact field before reaching the update. That leaves a created canonical email impossible to correct through the advertised editable/proposal RPC layer unless callers bypass it with direct table writes.

Useful? React with 👍 / 👎.

ELSE
UPDATE public.crm_contact_methods
SET label = NULLIF(trim(COALESCE(p_label, '')), ''),
is_primary = COALESCE(p_is_primary, is_primary),

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Preserve primary status when re-upserting a method

When an existing contact method is re-added without explicitly setting p_is_primary (the default is false), this assignment overwrites a previously primary method to false; the accept path for contact_method proposals also passes false, so accepting a duplicate proposal for the current primary email/phone silently leaves the contact with no primary method. Preserve is_primary on existing rows unless the caller explicitly promotes another method.

Useful? React with 👍 / 👎.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

schema Contribution: database extension

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant