Skip to main content

Claim relations

Use the relations endpoints to assert typed edges between two claims. A relation row carries a sourceClaimId, a targetClaimId, a relationTypeId from the persona's relationTypes, and optional confidence, span, and note fields.

Endpoints

POST   /api/summaries/:summaryId/claims/:claimId/relations
GET /api/summaries/:summaryId/claims/:claimId/relations
DELETE /api/summaries/:summaryId/claims/relations/:relationId

Create a relation

curl -X POST \
http://localhost:3001/api/summaries/$SUMMARY_ID/claims/$CLAIM_A_ID/relations \
-H 'Content-Type: application/json' --cookie cookies.txt \
-d '{"targetClaimId":"<claim-b>","relationTypeId":"causes",
"confidence":0.8,"notes":"explicit cue word"}'

The route loads both the source and target claims, returning 404 NotFoundError if either is missing or if the source claim's summaryId does not match the path's summaryId. It then enforces update permission on each claim via CASL (request.ability.can('update', subject('Claim', sourceClaim)) and the same for the target claim), throwing 403 ForbiddenError when the caller lacks the ability. A relation pointing at a foreign user's existing claim returns 403; 404 is only returned when one of the claims does not exist at all.

Spans

sourceSpans and targetSpans are JSON arrays of character offsets into the parent summary text. They are optional; the extractor populates them when it can locate the relevant phrases.

Delete

DELETE /api/summaries/:summaryId/claims/relations/:relationId first verifies the relation's source claim belongs to the given summary, then requires CASL update ability on the Claim subject for both the source and target claims. In practice, only a user who can update both endpoint claims, typically the owner of the source-claim summary, can delete the relation.