@medicine-wheel/relational-query 0.2.2

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/README.md ADDED
@@ -0,0 +1,60 @@
1
+ # @medicine-wheel/relational-query
2
+
3
+ Query builder, graph traversal, and accountability audit for the Medicine Wheel relational web. Protocol-aware: respects ceremony boundaries and OCAP® compliance during traversal.
4
+
5
+ ## Install
6
+
7
+ ```bash
8
+ npm install @medicine-wheel/relational-query
9
+ ```
10
+
11
+ ## Modules
12
+
13
+ ### Query Builder
14
+ Filter, sort, and paginate nodes and edges.
15
+
16
+ ```ts
17
+ import { filterNodes, sortNodes, paginate } from '@medicine-wheel/relational-query';
18
+
19
+ const elders = filterNodes(nodes, { type: 'human', direction: 'north' });
20
+ const sorted = sortNodes(elders, { field: 'name', order: 'asc' });
21
+ const page = paginate(sorted, { offset: 0, limit: 10 });
22
+ ```
23
+
24
+ ### Traversal
25
+ Context-aware graph traversal with ceremony and OCAP boundaries.
26
+
27
+ ```ts
28
+ import { traverse, shortestPath, neighborhood } from '@medicine-wheel/relational-query';
29
+
30
+ const result = traverse('node-id', nodes, edges, relations, {
31
+ maxDepth: 3,
32
+ respectCeremonyBoundaries: true,
33
+ ocapOnly: true,
34
+ });
35
+
36
+ const path = shortestPath('from-id', 'to-id', nodes, edges);
37
+ const neighbors = neighborhood('node-id', nodes, edges, 2);
38
+ ```
39
+
40
+ ### Accountability Audit
41
+ Relational health metrics and OCAP® compliance reports.
42
+
43
+ ```ts
44
+ import { auditAccountability, relationsNeedingAttention } from '@medicine-wheel/relational-query';
45
+
46
+ const report = auditAccountability(nodes, edges, relations);
47
+ console.log(report.averageWilsonAlignment);
48
+ console.log(report.recommendations);
49
+
50
+ const needsWork = relationsNeedingAttention(relations, 0.5);
51
+ ```
52
+
53
+ ## Peer dependency
54
+
55
+ Requires `@medicine-wheel/ontology-core` ^0.1.0.
56
+
57
+ ## License
58
+
59
+ MIT
60
+
@@ -0,0 +1,12 @@
1
+ /**
2
+ * Accountability Audit — relational health metrics and OCAP® compliance.
3
+ */
4
+ import type { Relation, RelationalNode, RelationalEdge } from '@medicine-wheel/ontology-core';
5
+ import type { AccountabilityReport } from './types.js';
6
+ /** Generate an accountability report for a relational web */
7
+ export declare function auditAccountability(nodes: RelationalNode[], edges: RelationalEdge[], relations: Relation[]): AccountabilityReport;
8
+ /** Quick OCAP compliance check for a single relation */
9
+ export declare function isOcapCompliant(relation: Relation): boolean;
10
+ /** Identify relations that need attention (low alignment or non-compliant) */
11
+ export declare function relationsNeedingAttention(relations: Relation[], wilsonThreshold?: number): Relation[];
12
+ //# sourceMappingURL=audit.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit.d.ts","sourceRoot":"","sources":["../src/audit.ts"],"names":[],"mappings":"AAAA;;GAEG;AACH,OAAO,KAAK,EAEV,QAAQ,EACR,cAAc,EACd,cAAc,EACf,MAAM,+BAA+B,CAAC;AAKvC,OAAO,KAAK,EAAE,oBAAoB,EAAE,MAAM,YAAY,CAAC;AAEvD,6DAA6D;AAC7D,wBAAgB,mBAAmB,CACjC,KAAK,EAAE,cAAc,EAAE,EACvB,KAAK,EAAE,cAAc,EAAE,EACvB,SAAS,EAAE,QAAQ,EAAE,GACpB,oBAAoB,CAwEtB;AAED,wDAAwD;AACxD,wBAAgB,eAAe,CAAC,QAAQ,EAAE,QAAQ,GAAG,OAAO,CAE3D;AAED,8EAA8E;AAC9E,wBAAgB,yBAAyB,CACvC,SAAS,EAAE,QAAQ,EAAE,EACrB,eAAe,GAAE,MAAY,GAC5B,QAAQ,EAAE,CAMZ"}
package/dist/audit.js ADDED
@@ -0,0 +1,85 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.auditAccountability = auditAccountability;
4
+ exports.isOcapCompliant = isOcapCompliant;
5
+ exports.relationsNeedingAttention = relationsNeedingAttention;
6
+ const ontology_core_1 = require("@medicine-wheel/ontology-core");
7
+ /** Generate an accountability report for a relational web */
8
+ function auditAccountability(nodes, edges, relations) {
9
+ const recommendations = [];
10
+ // OCAP compliance
11
+ let ocapCompliant = 0;
12
+ let ocapNonCompliant = 0;
13
+ for (const relation of relations) {
14
+ if (relation.ocap && (0, ontology_core_1.checkOcapCompliance)(relation.ocap).compliant) {
15
+ ocapCompliant++;
16
+ }
17
+ else {
18
+ ocapNonCompliant++;
19
+ }
20
+ }
21
+ // Wilson alignment
22
+ const averageWilsonAlignment = (0, ontology_core_1.aggregateWilsonAlignment)(relations);
23
+ // Direction coverage
24
+ const directionCoverage = { east: 0, south: 0, west: 0, north: 0 };
25
+ for (const node of nodes) {
26
+ if (node.direction) {
27
+ directionCoverage[node.direction]++;
28
+ }
29
+ }
30
+ // Ceremony honoring
31
+ const ceremoniedRelations = edges.filter(e => e.ceremony_honored).length;
32
+ const unceremoniedRelations = edges.filter(e => !e.ceremony_honored).length;
33
+ // Outstanding obligations (count total obligations across relations)
34
+ let obligationsOutstanding = 0;
35
+ for (const relation of relations) {
36
+ if (relation.obligations) {
37
+ obligationsOutstanding += relation.obligations.reduce((sum, o) => sum + o.obligations.length, 0);
38
+ }
39
+ }
40
+ // Recommendations
41
+ if (ocapNonCompliant > 0) {
42
+ recommendations.push(`${ocapNonCompliant} relation(s) lack full OCAP® compliance — review ownership, control, access, and possession flags`);
43
+ }
44
+ if (averageWilsonAlignment < 0.5) {
45
+ recommendations.push(`Wilson alignment is ${(averageWilsonAlignment * 100).toFixed(0)}% — strengthen respect, reciprocity, and responsibility`);
46
+ }
47
+ const emptyDirections = Object.entries(directionCoverage)
48
+ .filter(([, count]) => count === 0)
49
+ .map(([dir]) => dir);
50
+ if (emptyDirections.length > 0) {
51
+ recommendations.push(`No nodes in ${emptyDirections.join(', ')} direction(s) — consider expanding relational awareness`);
52
+ }
53
+ if (unceremoniedRelations > ceremoniedRelations && edges.length > 0) {
54
+ recommendations.push(`${unceremoniedRelations} of ${edges.length} relations lack ceremony — consider honoring these connections`);
55
+ }
56
+ if (obligationsOutstanding > 0) {
57
+ recommendations.push(`${obligationsOutstanding} obligation(s) outstanding — attend to relational responsibilities`);
58
+ }
59
+ return {
60
+ totalRelations: relations.length,
61
+ ocapCompliant,
62
+ ocapNonCompliant,
63
+ averageWilsonAlignment: Math.round(averageWilsonAlignment * 100) / 100,
64
+ directionCoverage,
65
+ ceremoniedRelations,
66
+ unceremoniedRelations,
67
+ obligationsOutstanding,
68
+ recommendations,
69
+ };
70
+ }
71
+ /** Quick OCAP compliance check for a single relation */
72
+ function isOcapCompliant(relation) {
73
+ return !!relation.ocap && (0, ontology_core_1.checkOcapCompliance)(relation.ocap).compliant;
74
+ }
75
+ /** Identify relations that need attention (low alignment or non-compliant) */
76
+ function relationsNeedingAttention(relations, wilsonThreshold = 0.5) {
77
+ return relations.filter(r => {
78
+ if (r.ocap && !(0, ontology_core_1.checkOcapCompliance)(r.ocap).compliant)
79
+ return true;
80
+ if (r.accountability && r.accountability.wilson_alignment < wilsonThreshold)
81
+ return true;
82
+ return false;
83
+ });
84
+ }
85
+ //# sourceMappingURL=audit.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"audit.js","sourceRoot":"","sources":["../src/audit.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,40 @@
1
+ /**
2
+ * @medicine-wheel/relational-query — Cypher Query Builders
3
+ *
4
+ * Generates Cypher queries for RSIS relational science dimensions.
5
+ * Used by rsis-gitnexus tool handlers to query the KuzuDB graph.
6
+ */
7
+ import type { DirectionName, SunName } from '@medicine-wheel/ontology-core';
8
+ /** Build a Cypher query to find stewards of a symbol */
9
+ export declare function queryStewards(symbolId: string): string;
10
+ /** Build a Cypher query to find ceremony provenance */
11
+ export declare function queryCeremonyProvenance(symbolId: string): string;
12
+ /** Build a Cypher query to find inquiries a symbol serves */
13
+ export declare function queryInquiries(symbolId: string): string;
14
+ /** Build a Cypher query to find kinship hubs */
15
+ export declare function queryKinshipHubs(): string;
16
+ /** Build a Cypher query to find kinship relations */
17
+ export declare function queryKinshipRelations(): string;
18
+ /** Build a Cypher query to find direction alignment */
19
+ export declare function queryDirectionAlignment(symbolId: string): string;
20
+ /** Build a Cypher query to find reciprocity flows */
21
+ export declare function queryReciprocityFlows(): string;
22
+ /** Build a Cypher query for all inquiries in a Sun */
23
+ export declare function queryInquiriesBySun(sun: SunName): string;
24
+ /** Build a Cypher query for all ceremonies */
25
+ export declare function queryCeremonies(): string;
26
+ /** Build a Cypher query for all inquiries */
27
+ export declare function queryAllInquiries(): string;
28
+ /**
29
+ * Format a reciprocity observation — always framed as invitation, never performance
30
+ */
31
+ export declare function formatReciprocityObservation(flows: Array<{
32
+ from: string;
33
+ to: string;
34
+ type: string;
35
+ }>): string;
36
+ /**
37
+ * Format a direction distribution observation
38
+ */
39
+ export declare function formatDirectionObservation(distribution: Record<DirectionName, number>): string;
40
+ //# sourceMappingURL=cypher.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cypher.d.ts","sourceRoot":"","sources":["../src/cypher.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAEH,OAAO,KAAK,EAAE,aAAa,EAAE,OAAO,EAAE,MAAM,+BAA+B,CAAC;AAO5E,wDAAwD;AACxD,wBAAgB,aAAa,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAItD;AAED,uDAAuD;AACvD,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAKhE;AAED,6DAA6D;AAC7D,wBAAgB,cAAc,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAIvD;AAED,gDAAgD;AAChD,wBAAgB,gBAAgB,IAAI,MAAM,CAKzC;AAED,qDAAqD;AACrD,wBAAgB,qBAAqB,IAAI,MAAM,CAG9C;AAED,uDAAuD;AACvD,wBAAgB,uBAAuB,CAAC,QAAQ,EAAE,MAAM,GAAG,MAAM,CAIhE;AAED,qDAAqD;AACrD,wBAAgB,qBAAqB,IAAI,MAAM,CAI9C;AAED,sDAAsD;AACtD,wBAAgB,mBAAmB,CAAC,GAAG,EAAE,OAAO,GAAG,MAAM,CAGxD;AAED,8CAA8C;AAC9C,wBAAgB,eAAe,IAAI,MAAM,CAExC;AAED,6CAA6C;AAC7C,wBAAgB,iBAAiB,IAAI,MAAM,CAE1C;AAED;;GAEG;AACH,wBAAgB,4BAA4B,CAC1C,KAAK,EAAE,KAAK,CAAC;IAAE,IAAI,EAAE,MAAM,CAAC;IAAC,EAAE,EAAE,MAAM,CAAC;IAAC,IAAI,EAAE,MAAM,CAAA;CAAE,CAAC,GACvD,MAAM,CAKR;AAED;;GAEG;AACH,wBAAgB,0BAA0B,CACxC,YAAY,EAAE,MAAM,CAAC,aAAa,EAAE,MAAM,CAAC,GAC1C,MAAM,CAOR"}
package/dist/cypher.js ADDED
@@ -0,0 +1,101 @@
1
+ "use strict";
2
+ /**
3
+ * @medicine-wheel/relational-query — Cypher Query Builders
4
+ *
5
+ * Generates Cypher queries for RSIS relational science dimensions.
6
+ * Used by rsis-gitnexus tool handlers to query the KuzuDB graph.
7
+ */
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.queryStewards = queryStewards;
10
+ exports.queryCeremonyProvenance = queryCeremonyProvenance;
11
+ exports.queryInquiries = queryInquiries;
12
+ exports.queryKinshipHubs = queryKinshipHubs;
13
+ exports.queryKinshipRelations = queryKinshipRelations;
14
+ exports.queryDirectionAlignment = queryDirectionAlignment;
15
+ exports.queryReciprocityFlows = queryReciprocityFlows;
16
+ exports.queryInquiriesBySun = queryInquiriesBySun;
17
+ exports.queryCeremonies = queryCeremonies;
18
+ exports.queryAllInquiries = queryAllInquiries;
19
+ exports.formatReciprocityObservation = formatReciprocityObservation;
20
+ exports.formatDirectionObservation = formatDirectionObservation;
21
+ /** Escape a string for safe use in Cypher string literals */
22
+ function escapeCypher(value) {
23
+ return value.replace(/\\/g, '\\\\').replace(/'/g, "\\'");
24
+ }
25
+ /** Build a Cypher query to find stewards of a symbol */
26
+ function queryStewards(symbolId) {
27
+ const escaped = escapeCypher(symbolId);
28
+ return `MATCH (p:Person)-[:RSISRelation {type: 'STEWARDS'}]->(n {id: '${escaped}'})
29
+ RETURN p.id AS id, p.name AS name, p.email AS email, p.roles AS roles`;
30
+ }
31
+ /** Build a Cypher query to find ceremony provenance */
32
+ function queryCeremonyProvenance(symbolId) {
33
+ const escaped = escapeCypher(symbolId);
34
+ return `MATCH (n {id: '${escaped}'})-[:RSISRelation {type: 'BORN_FROM'}]->(c:Ceremony)
35
+ RETURN c.id AS id, c.name AS name, c.hostSun AS hostSun, c.cycle AS cycle, c.phase AS phase, c.intention AS intention
36
+ ORDER BY c.cycle`;
37
+ }
38
+ /** Build a Cypher query to find inquiries a symbol serves */
39
+ function queryInquiries(symbolId) {
40
+ const escaped = escapeCypher(symbolId);
41
+ return `MATCH (n {id: '${escaped}'})-[:RSISRelation {type: 'SERVES'}]->(i:Inquiry)
42
+ RETURN i.id AS id, i.name AS name, i.sun AS sun, i.coreQuestion AS coreQuestion`;
43
+ }
44
+ /** Build a Cypher query to find kinship hubs */
45
+ function queryKinshipHubs() {
46
+ return `MATCH (k:KinshipHub)
47
+ RETURN k.id AS id, k.name AS name, k.filePath AS filePath, k.identity AS identity,
48
+ k.lineage AS lineage, k.humanAccountabilities AS humanAccountabilities,
49
+ k.moreThanHumanAccountabilities AS moreThanHumanAccountabilities, k.boundaries AS boundaries`;
50
+ }
51
+ /** Build a Cypher query to find kinship relations */
52
+ function queryKinshipRelations() {
53
+ return `MATCH (a:KinshipHub)-[r:RSISRelation {type: 'KINSHIP_OF'}]->(b:KinshipHub)
54
+ RETURN a.name AS from_name, b.name AS to_name, r.reason AS reason`;
55
+ }
56
+ /** Build a Cypher query to find direction alignment */
57
+ function queryDirectionAlignment(symbolId) {
58
+ const escaped = escapeCypher(symbolId);
59
+ return `MATCH (n {id: '${escaped}'})-[:RSISRelation {type: 'ALIGNED_WITH'}]->(d:Direction)
60
+ RETURN d.name AS name, d.focus AS focus`;
61
+ }
62
+ /** Build a Cypher query to find reciprocity flows */
63
+ function queryReciprocityFlows() {
64
+ return `MATCH (p:Person)-[r:RSISRelation {type: 'GIVES_BACK_TO'}]->(target)
65
+ RETURN p.name AS from_name, labels(target)[0] AS target_type, target.name AS to_name, r.reason AS reason
66
+ LIMIT 50`;
67
+ }
68
+ /** Build a Cypher query for all inquiries in a Sun */
69
+ function queryInquiriesBySun(sun) {
70
+ return `MATCH (i:Inquiry {sun: '${sun}'})
71
+ RETURN i.id AS id, i.name AS name, i.coreQuestion AS coreQuestion, i.status AS status`;
72
+ }
73
+ /** Build a Cypher query for all ceremonies */
74
+ function queryCeremonies() {
75
+ return `MATCH (c:Ceremony) RETURN c.id AS id, c.name AS name, c.hostSun AS hostSun, c.cycle AS cycle, c.phase AS phase`;
76
+ }
77
+ /** Build a Cypher query for all inquiries */
78
+ function queryAllInquiries() {
79
+ return `MATCH (i:Inquiry) RETURN i.id AS id, i.name AS name, i.sun AS sun, i.coreQuestion AS coreQuestion, i.status AS status`;
80
+ }
81
+ /**
82
+ * Format a reciprocity observation — always framed as invitation, never performance
83
+ */
84
+ function formatReciprocityObservation(flows) {
85
+ if (flows.length === 0) {
86
+ return 'No reciprocity data has been populated yet. Consider running rsis-gitnexus analyze with RSIS mode enabled.';
87
+ }
88
+ return `${flows.length} reciprocity flow(s) identified. This area invites reflection on how contributions move through the ecosystem.`;
89
+ }
90
+ /**
91
+ * Format a direction distribution observation
92
+ */
93
+ function formatDirectionObservation(distribution) {
94
+ const sorted = Object.entries(distribution).sort((a, b) => b[1] - a[1]);
95
+ const dominant = sorted[0][0];
96
+ const weakest = sorted[sorted.length - 1][0];
97
+ const emoji = { east: '🌸', south: '🧠', west: '⚡', north: '🕸️' };
98
+ return `Recent work is concentrated in ${dominant} ${emoji[dominant]} (${distribution[dominant]}%). ` +
99
+ `The ecosystem may benefit from a ${weakest} ${emoji[weakest]} ceremony.`;
100
+ }
101
+ //# sourceMappingURL=cypher.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"cypher.js","sourceRoot":"","sources":["../src/cypher.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;AAUH,sCAIC;AAGD,0DAKC;AAGD,wCAIC;AAGD,4CAKC;AAGD,sDAGC;AAGD,0DAIC;AAGD,sDAIC;AAGD,kDAGC;AAGD,0CAEC;AAGD,8CAEC;AAKD,oEAOC;AAKD,gEASC;AA/FD,6DAA6D;AAC7D,SAAS,YAAY,CAAC,KAAa;IACjC,OAAO,KAAK,CAAC,OAAO,CAAC,KAAK,EAAE,MAAM,CAAC,CAAC,OAAO,CAAC,IAAI,EAAE,KAAK,CAAC,CAAC;AAC3D,CAAC;AAED,wDAAwD;AACxD,SAAgB,aAAa,CAAC,QAAgB;IAC5C,MAAM,OAAO,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;IACvC,OAAO,iEAAiE,OAAO;sEACX,CAAC;AACvE,CAAC;AAED,uDAAuD;AACvD,SAAgB,uBAAuB,CAAC,QAAgB;IACtD,MAAM,OAAO,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;IACvC,OAAO,kBAAkB,OAAO;;iBAEjB,CAAC;AAClB,CAAC;AAED,6DAA6D;AAC7D,SAAgB,cAAc,CAAC,QAAgB;IAC7C,MAAM,OAAO,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;IACvC,OAAO,kBAAkB,OAAO;gFAC8C,CAAC;AACjF,CAAC;AAED,gDAAgD;AAChD,SAAgB,gBAAgB;IAC9B,OAAO;;;oGAG2F,CAAC;AACrG,CAAC;AAED,qDAAqD;AACrD,SAAgB,qBAAqB;IACnC,OAAO;kEACyD,CAAC;AACnE,CAAC;AAED,uDAAuD;AACvD,SAAgB,uBAAuB,CAAC,QAAgB;IACtD,MAAM,OAAO,GAAG,YAAY,CAAC,QAAQ,CAAC,CAAC;IACvC,OAAO,kBAAkB,OAAO;wCACM,CAAC;AACzC,CAAC;AAED,qDAAqD;AACrD,SAAgB,qBAAqB;IACnC,OAAO;;SAEA,CAAC;AACV,CAAC;AAED,sDAAsD;AACtD,SAAgB,mBAAmB,CAAC,GAAY;IAC9C,OAAO,2BAA2B,GAAG;sFAC+C,CAAC;AACvF,CAAC;AAED,8CAA8C;AAC9C,SAAgB,eAAe;IAC7B,OAAO,gHAAgH,CAAC;AAC1H,CAAC;AAED,6CAA6C;AAC7C,SAAgB,iBAAiB;IAC/B,OAAO,uHAAuH,CAAC;AACjI,CAAC;AAED;;GAEG;AACH,SAAgB,4BAA4B,CAC1C,KAAwD;IAExD,IAAI,KAAK,CAAC,MAAM,KAAK,CAAC,EAAE,CAAC;QACvB,OAAO,4GAA4G,CAAC;IACtH,CAAC;IACD,OAAO,GAAG,KAAK,CAAC,MAAM,gHAAgH,CAAC;AACzI,CAAC;AAED;;GAEG;AACH,SAAgB,0BAA0B,CACxC,YAA2C;IAE3C,MAAM,MAAM,GAAG,MAAM,CAAC,OAAO,CAAC,YAAY,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IACxE,MAAM,QAAQ,GAAG,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC9B,MAAM,OAAO,GAAG,MAAM,CAAC,MAAM,CAAC,MAAM,GAAG,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAC7C,MAAM,KAAK,GAA2B,EAAE,IAAI,EAAE,IAAI,EAAE,KAAK,EAAE,IAAI,EAAE,IAAI,EAAE,GAAG,EAAE,KAAK,EAAE,KAAK,EAAE,CAAC;IAC3F,OAAO,kCAAkC,QAAQ,IAAI,KAAK,CAAC,QAAQ,CAAC,KAAK,YAAY,CAAC,QAAyB,CAAC,MAAM;QACpH,oCAAoC,OAAO,IAAI,KAAK,CAAC,OAAO,CAAC,YAAY,CAAC;AAC9E,CAAC"}
@@ -0,0 +1,12 @@
1
+ /**
2
+ * @medicine-wheel/relational-query
3
+ *
4
+ * Query builder, graph traversal, and accountability audit
5
+ * for the Medicine Wheel relational web.
6
+ */
7
+ export type { NodeFilter, EdgeFilter, RelationFilter, SortField, SortOrder, QuerySort, QueryPagination, QueryOptions, QueryResult, TraversalDirection, TraversalOptions, TraversalPath, TraversalResult, AccountabilityReport, } from './types.js';
8
+ export { filterNodes, filterEdges, filterRelations, sortNodes, paginate, filterByRelation, relationCounts, filterByMinRelations, } from './query.js';
9
+ export { traverse, shortestPath, neighborhood, } from './traversal.js';
10
+ export { auditAccountability, isOcapCompliant, relationsNeedingAttention, } from './audit.js';
11
+ export { queryStewards, queryCeremonyProvenance, queryInquiries, queryKinshipHubs, queryKinshipRelations, queryDirectionAlignment, queryReciprocityFlows, queryInquiriesBySun, queryCeremonies, queryAllInquiries, formatReciprocityObservation, formatDirectionObservation, } from './cypher.js';
12
+ //# sourceMappingURL=index.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.d.ts","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AAGH,YAAY,EACV,UAAU,EACV,UAAU,EACV,cAAc,EACd,SAAS,EACT,SAAS,EACT,SAAS,EACT,eAAe,EACf,YAAY,EACZ,WAAW,EACX,kBAAkB,EAClB,gBAAgB,EAChB,aAAa,EACb,eAAe,EACf,oBAAoB,GACrB,MAAM,YAAY,CAAC;AAGpB,OAAO,EACL,WAAW,EACX,WAAW,EACX,eAAe,EACf,SAAS,EACT,QAAQ,EACR,gBAAgB,EAChB,cAAc,EACd,oBAAoB,GACrB,MAAM,YAAY,CAAC;AAGpB,OAAO,EACL,QAAQ,EACR,YAAY,EACZ,YAAY,GACb,MAAM,gBAAgB,CAAC;AAGxB,OAAO,EACL,mBAAmB,EACnB,eAAe,EACf,yBAAyB,GAC1B,MAAM,YAAY,CAAC;AAGpB,OAAO,EACL,aAAa,EACb,uBAAuB,EACvB,cAAc,EACd,gBAAgB,EAChB,qBAAqB,EACrB,uBAAuB,EACvB,qBAAqB,EACrB,mBAAmB,EACnB,eAAe,EACf,iBAAiB,EACjB,4BAA4B,EAC5B,0BAA0B,GAC3B,MAAM,aAAa,CAAC"}
package/dist/index.js ADDED
@@ -0,0 +1,44 @@
1
+ "use strict";
2
+ /**
3
+ * @medicine-wheel/relational-query
4
+ *
5
+ * Query builder, graph traversal, and accountability audit
6
+ * for the Medicine Wheel relational web.
7
+ */
8
+ Object.defineProperty(exports, "__esModule", { value: true });
9
+ exports.formatDirectionObservation = exports.formatReciprocityObservation = exports.queryAllInquiries = exports.queryCeremonies = exports.queryInquiriesBySun = exports.queryReciprocityFlows = exports.queryDirectionAlignment = exports.queryKinshipRelations = exports.queryKinshipHubs = exports.queryInquiries = exports.queryCeremonyProvenance = exports.queryStewards = exports.relationsNeedingAttention = exports.isOcapCompliant = exports.auditAccountability = exports.neighborhood = exports.shortestPath = exports.traverse = exports.filterByMinRelations = exports.relationCounts = exports.filterByRelation = exports.paginate = exports.sortNodes = exports.filterRelations = exports.filterEdges = exports.filterNodes = void 0;
10
+ // Query builder
11
+ var query_js_1 = require("./query.js");
12
+ Object.defineProperty(exports, "filterNodes", { enumerable: true, get: function () { return query_js_1.filterNodes; } });
13
+ Object.defineProperty(exports, "filterEdges", { enumerable: true, get: function () { return query_js_1.filterEdges; } });
14
+ Object.defineProperty(exports, "filterRelations", { enumerable: true, get: function () { return query_js_1.filterRelations; } });
15
+ Object.defineProperty(exports, "sortNodes", { enumerable: true, get: function () { return query_js_1.sortNodes; } });
16
+ Object.defineProperty(exports, "paginate", { enumerable: true, get: function () { return query_js_1.paginate; } });
17
+ Object.defineProperty(exports, "filterByRelation", { enumerable: true, get: function () { return query_js_1.filterByRelation; } });
18
+ Object.defineProperty(exports, "relationCounts", { enumerable: true, get: function () { return query_js_1.relationCounts; } });
19
+ Object.defineProperty(exports, "filterByMinRelations", { enumerable: true, get: function () { return query_js_1.filterByMinRelations; } });
20
+ // Traversal
21
+ var traversal_js_1 = require("./traversal.js");
22
+ Object.defineProperty(exports, "traverse", { enumerable: true, get: function () { return traversal_js_1.traverse; } });
23
+ Object.defineProperty(exports, "shortestPath", { enumerable: true, get: function () { return traversal_js_1.shortestPath; } });
24
+ Object.defineProperty(exports, "neighborhood", { enumerable: true, get: function () { return traversal_js_1.neighborhood; } });
25
+ // Audit
26
+ var audit_js_1 = require("./audit.js");
27
+ Object.defineProperty(exports, "auditAccountability", { enumerable: true, get: function () { return audit_js_1.auditAccountability; } });
28
+ Object.defineProperty(exports, "isOcapCompliant", { enumerable: true, get: function () { return audit_js_1.isOcapCompliant; } });
29
+ Object.defineProperty(exports, "relationsNeedingAttention", { enumerable: true, get: function () { return audit_js_1.relationsNeedingAttention; } });
30
+ // Cypher query builders (for RSIS-GitNexus KuzuDB queries)
31
+ var cypher_js_1 = require("./cypher.js");
32
+ Object.defineProperty(exports, "queryStewards", { enumerable: true, get: function () { return cypher_js_1.queryStewards; } });
33
+ Object.defineProperty(exports, "queryCeremonyProvenance", { enumerable: true, get: function () { return cypher_js_1.queryCeremonyProvenance; } });
34
+ Object.defineProperty(exports, "queryInquiries", { enumerable: true, get: function () { return cypher_js_1.queryInquiries; } });
35
+ Object.defineProperty(exports, "queryKinshipHubs", { enumerable: true, get: function () { return cypher_js_1.queryKinshipHubs; } });
36
+ Object.defineProperty(exports, "queryKinshipRelations", { enumerable: true, get: function () { return cypher_js_1.queryKinshipRelations; } });
37
+ Object.defineProperty(exports, "queryDirectionAlignment", { enumerable: true, get: function () { return cypher_js_1.queryDirectionAlignment; } });
38
+ Object.defineProperty(exports, "queryReciprocityFlows", { enumerable: true, get: function () { return cypher_js_1.queryReciprocityFlows; } });
39
+ Object.defineProperty(exports, "queryInquiriesBySun", { enumerable: true, get: function () { return cypher_js_1.queryInquiriesBySun; } });
40
+ Object.defineProperty(exports, "queryCeremonies", { enumerable: true, get: function () { return cypher_js_1.queryCeremonies; } });
41
+ Object.defineProperty(exports, "queryAllInquiries", { enumerable: true, get: function () { return cypher_js_1.queryAllInquiries; } });
42
+ Object.defineProperty(exports, "formatReciprocityObservation", { enumerable: true, get: function () { return cypher_js_1.formatReciprocityObservation; } });
43
+ Object.defineProperty(exports, "formatDirectionObservation", { enumerable: true, get: function () { return cypher_js_1.formatDirectionObservation; } });
44
+ //# sourceMappingURL=index.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"index.js","sourceRoot":"","sources":["../src/index.ts"],"names":[],"mappings":";AAAA;;;;;GAKG;;;AAoBH,gBAAgB;AAChB,uCASoB;AARlB,uGAAA,WAAW,OAAA;AACX,uGAAA,WAAW,OAAA;AACX,2GAAA,eAAe,OAAA;AACf,qGAAA,SAAS,OAAA;AACT,oGAAA,QAAQ,OAAA;AACR,4GAAA,gBAAgB,OAAA;AAChB,0GAAA,cAAc,OAAA;AACd,gHAAA,oBAAoB,OAAA;AAGtB,YAAY;AACZ,+CAIwB;AAHtB,wGAAA,QAAQ,OAAA;AACR,4GAAA,YAAY,OAAA;AACZ,4GAAA,YAAY,OAAA;AAGd,QAAQ;AACR,uCAIoB;AAHlB,+GAAA,mBAAmB,OAAA;AACnB,2GAAA,eAAe,OAAA;AACf,qHAAA,yBAAyB,OAAA;AAG3B,2DAA2D;AAC3D,yCAaqB;AAZnB,0GAAA,aAAa,OAAA;AACb,oHAAA,uBAAuB,OAAA;AACvB,2GAAA,cAAc,OAAA;AACd,6GAAA,gBAAgB,OAAA;AAChB,kHAAA,qBAAqB,OAAA;AACrB,oHAAA,uBAAuB,OAAA;AACvB,kHAAA,qBAAqB,OAAA;AACrB,gHAAA,mBAAmB,OAAA;AACnB,4GAAA,eAAe,OAAA;AACf,8GAAA,iBAAiB,OAAA;AACjB,yHAAA,4BAA4B,OAAA;AAC5B,uHAAA,0BAA0B,OAAA"}
@@ -0,0 +1,23 @@
1
+ /**
2
+ * Query Builder — fluent API for querying relational nodes and edges
3
+ * with Indigenous protocol awareness.
4
+ */
5
+ import type { RelationalNode, RelationalEdge, Relation } from '@medicine-wheel/ontology-core';
6
+ import type { NodeFilter, EdgeFilter, RelationFilter, QuerySort, QueryPagination, QueryResult } from './types.js';
7
+ /** Apply a NodeFilter to an array of nodes */
8
+ export declare function filterNodes(nodes: RelationalNode[], filter: NodeFilter): RelationalNode[];
9
+ /** Apply an EdgeFilter to an array of edges */
10
+ export declare function filterEdges(edges: RelationalEdge[], filter: EdgeFilter): RelationalEdge[];
11
+ /** Apply sorting to nodes */
12
+ export declare function sortNodes(nodes: RelationalNode[], sort: QuerySort): RelationalNode[];
13
+ /** Apply pagination */
14
+ export declare function paginate<T>(items: T[], pagination: QueryPagination): QueryResult<T>;
15
+ /** Filter nodes that have relations to a specific node */
16
+ export declare function filterByRelation(nodes: RelationalNode[], edges: RelationalEdge[], targetNodeId: string): RelationalNode[];
17
+ /** Count relations per node */
18
+ export declare function relationCounts(nodes: RelationalNode[], edges: RelationalEdge[]): Map<string, number>;
19
+ /** Filter nodes with minimum relation count */
20
+ export declare function filterByMinRelations(nodes: RelationalNode[], edges: RelationalEdge[], minRelations: number): RelationalNode[];
21
+ /** Apply a RelationFilter to first-class Relation objects */
22
+ export declare function filterRelations(relations: Relation[], filter: RelationFilter): Relation[];
23
+ //# sourceMappingURL=query.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"query.d.ts","sourceRoot":"","sources":["../src/query.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,KAAK,EAAE,cAAc,EAAE,cAAc,EAAE,QAAQ,EAAE,MAAM,+BAA+B,CAAC;AAC9F,OAAO,KAAK,EACV,UAAU,EACV,UAAU,EACV,cAAc,EACd,SAAS,EACT,eAAe,EACf,WAAW,EACZ,MAAM,YAAY,CAAC;AAEpB,8CAA8C;AAC9C,wBAAgB,WAAW,CACzB,KAAK,EAAE,cAAc,EAAE,EACvB,MAAM,EAAE,UAAU,GACjB,cAAc,EAAE,CA2BlB;AAED,+CAA+C;AAC/C,wBAAgB,WAAW,CACzB,KAAK,EAAE,cAAc,EAAE,EACvB,MAAM,EAAE,UAAU,GACjB,cAAc,EAAE,CAyBlB;AAED,6BAA6B;AAC7B,wBAAgB,SAAS,CACvB,KAAK,EAAE,cAAc,EAAE,EACvB,IAAI,EAAE,SAAS,GACd,cAAc,EAAE,CAsBlB;AAED,uBAAuB;AACvB,wBAAgB,QAAQ,CAAC,CAAC,EACxB,KAAK,EAAE,CAAC,EAAE,EACV,UAAU,EAAE,eAAe,GAC1B,WAAW,CAAC,CAAC,CAAC,CAWhB;AAED,0DAA0D;AAC1D,wBAAgB,gBAAgB,CAC9B,KAAK,EAAE,cAAc,EAAE,EACvB,KAAK,EAAE,cAAc,EAAE,EACvB,YAAY,EAAE,MAAM,GACnB,cAAc,EAAE,CAOlB;AAED,+BAA+B;AAC/B,wBAAgB,cAAc,CAC5B,KAAK,EAAE,cAAc,EAAE,EACvB,KAAK,EAAE,cAAc,EAAE,GACtB,GAAG,CAAC,MAAM,EAAE,MAAM,CAAC,CAUrB;AAED,+CAA+C;AAC/C,wBAAgB,oBAAoB,CAClC,KAAK,EAAE,cAAc,EAAE,EACvB,KAAK,EAAE,cAAc,EAAE,EACvB,YAAY,EAAE,MAAM,GACnB,cAAc,EAAE,CAGlB;AAED,6DAA6D;AAC7D,wBAAgB,eAAe,CAC7B,SAAS,EAAE,QAAQ,EAAE,EACrB,MAAM,EAAE,cAAc,GACrB,QAAQ,EAAE,CA+BZ"}
package/dist/query.js ADDED
@@ -0,0 +1,148 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.filterNodes = filterNodes;
4
+ exports.filterEdges = filterEdges;
5
+ exports.sortNodes = sortNodes;
6
+ exports.paginate = paginate;
7
+ exports.filterByRelation = filterByRelation;
8
+ exports.relationCounts = relationCounts;
9
+ exports.filterByMinRelations = filterByMinRelations;
10
+ exports.filterRelations = filterRelations;
11
+ /** Apply a NodeFilter to an array of nodes */
12
+ function filterNodes(nodes, filter) {
13
+ let result = [...nodes];
14
+ if (filter.type) {
15
+ const types = Array.isArray(filter.type) ? filter.type : [filter.type];
16
+ result = result.filter(n => types.includes(n.type));
17
+ }
18
+ if (filter.direction) {
19
+ const dirs = Array.isArray(filter.direction) ? filter.direction : [filter.direction];
20
+ result = result.filter(n => n.direction && dirs.includes(n.direction));
21
+ }
22
+ if (filter.nameContains) {
23
+ const term = filter.nameContains.toLowerCase();
24
+ result = result.filter(n => n.name.toLowerCase().includes(term));
25
+ }
26
+ if (filter.createdAfter) {
27
+ result = result.filter(n => n.created_at >= filter.createdAfter);
28
+ }
29
+ if (filter.createdBefore) {
30
+ result = result.filter(n => n.created_at <= filter.createdBefore);
31
+ }
32
+ return result;
33
+ }
34
+ /** Apply an EdgeFilter to an array of edges */
35
+ function filterEdges(edges, filter) {
36
+ let result = [...edges];
37
+ if (filter.relationshipType) {
38
+ const types = Array.isArray(filter.relationshipType) ? filter.relationshipType : [filter.relationshipType];
39
+ result = result.filter(e => types.includes(e.relationship_type));
40
+ }
41
+ if (filter.minStrength !== undefined) {
42
+ result = result.filter(e => e.strength >= filter.minStrength);
43
+ }
44
+ if (filter.ceremonyHonored !== undefined) {
45
+ result = result.filter(e => e.ceremony_honored === filter.ceremonyHonored);
46
+ }
47
+ if (filter.fromNode) {
48
+ result = result.filter(e => e.from_id === filter.fromNode);
49
+ }
50
+ if (filter.toNode) {
51
+ result = result.filter(e => e.to_id === filter.toNode);
52
+ }
53
+ return result;
54
+ }
55
+ /** Apply sorting to nodes */
56
+ function sortNodes(nodes, sort) {
57
+ const sorted = [...nodes];
58
+ const multiplier = sort.order === 'desc' ? -1 : 1;
59
+ sorted.sort((a, b) => {
60
+ let aVal, bVal;
61
+ switch (sort.field) {
62
+ case 'name':
63
+ aVal = a.name;
64
+ bVal = b.name;
65
+ break;
66
+ case 'type':
67
+ aVal = a.type;
68
+ bVal = b.type;
69
+ break;
70
+ case 'direction':
71
+ aVal = a.direction ?? '';
72
+ bVal = b.direction ?? '';
73
+ break;
74
+ case 'updated_at':
75
+ aVal = a.updated_at;
76
+ bVal = b.updated_at;
77
+ break;
78
+ default:
79
+ aVal = a.created_at;
80
+ bVal = b.created_at;
81
+ }
82
+ return aVal.localeCompare(bVal) * multiplier;
83
+ });
84
+ return sorted;
85
+ }
86
+ /** Apply pagination */
87
+ function paginate(items, pagination) {
88
+ const total = items.length;
89
+ const paged = items.slice(pagination.offset, pagination.offset + pagination.limit);
90
+ return {
91
+ items: paged,
92
+ total,
93
+ offset: pagination.offset,
94
+ limit: pagination.limit,
95
+ hasMore: pagination.offset + pagination.limit < total,
96
+ };
97
+ }
98
+ /** Filter nodes that have relations to a specific node */
99
+ function filterByRelation(nodes, edges, targetNodeId) {
100
+ const connectedIds = new Set();
101
+ for (const edge of edges) {
102
+ if (edge.from_id === targetNodeId)
103
+ connectedIds.add(edge.to_id);
104
+ if (edge.to_id === targetNodeId)
105
+ connectedIds.add(edge.from_id);
106
+ }
107
+ return nodes.filter(n => connectedIds.has(n.id));
108
+ }
109
+ /** Count relations per node */
110
+ function relationCounts(nodes, edges) {
111
+ const counts = new Map();
112
+ for (const node of nodes)
113
+ counts.set(node.id, 0);
114
+ for (const edge of edges) {
115
+ counts.set(edge.from_id, (counts.get(edge.from_id) ?? 0) + 1);
116
+ counts.set(edge.to_id, (counts.get(edge.to_id) ?? 0) + 1);
117
+ }
118
+ return counts;
119
+ }
120
+ /** Filter nodes with minimum relation count */
121
+ function filterByMinRelations(nodes, edges, minRelations) {
122
+ const counts = relationCounts(nodes, edges);
123
+ return nodes.filter(n => (counts.get(n.id) ?? 0) >= minRelations);
124
+ }
125
+ /** Apply a RelationFilter to first-class Relation objects */
126
+ function filterRelations(relations, filter) {
127
+ let result = [...relations];
128
+ if (filter.direction) {
129
+ result = result.filter(r => r.direction === filter.direction);
130
+ }
131
+ if (filter.ceremonied !== undefined) {
132
+ result = result.filter(r => r.ceremony_context?.ceremony_honored === filter.ceremonied);
133
+ }
134
+ if (filter.ocapCompliant !== undefined) {
135
+ result = result.filter(r => r.ocap.compliant === filter.ocapCompliant);
136
+ }
137
+ if (filter.minWilsonAlignment !== undefined) {
138
+ result = result.filter(r => r.accountability.wilson_alignment >= filter.minWilsonAlignment);
139
+ }
140
+ if (filter.hasObligations !== undefined) {
141
+ result = result.filter(r => {
142
+ const has = r.obligations.length > 0;
143
+ return has === filter.hasObligations;
144
+ });
145
+ }
146
+ return result;
147
+ }
148
+ //# sourceMappingURL=query.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"query.js","sourceRoot":"","sources":["../src/query.ts"],"names":[],"mappings":";;AAeA,kCA8BC;AAGD,kCA4BC;AAGD,8BAyBC;AAGD,4BAcC;AAGD,4CAWC;AAGD,wCAaC;AAGD,oDAOC;AAGD,0CAkCC;AAxLD,8CAA8C;AAC9C,SAAgB,WAAW,CACzB,KAAuB,EACvB,MAAkB;IAElB,IAAI,MAAM,GAAG,CAAC,GAAG,KAAK,CAAC,CAAC;IAExB,IAAI,MAAM,CAAC,IAAI,EAAE,CAAC;QAChB,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,IAAI,CAAC,CAAC;QACvE,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,IAAI,CAAC,CAAC,CAAC;IACtD,CAAC;IAED,IAAI,MAAM,CAAC,SAAS,EAAE,CAAC;QACrB,MAAM,IAAI,GAAG,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,SAAS,CAAC,CAAC;QACrF,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,SAAS,IAAI,IAAI,CAAC,QAAQ,CAAC,CAAC,CAAC,SAAS,CAAC,CAAC,CAAC;IACzE,CAAC;IAED,IAAI,MAAM,CAAC,YAAY,EAAE,CAAC;QACxB,MAAM,IAAI,GAAG,MAAM,CAAC,YAAY,CAAC,WAAW,EAAE,CAAC;QAC/C,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,WAAW,EAAE,CAAC,QAAQ,CAAC,IAAI,CAAC,CAAC,CAAC;IACnE,CAAC;IAED,IAAI,MAAM,CAAC,YAAY,EAAE,CAAC;QACxB,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,IAAI,MAAM,CAAC,YAAa,CAAC,CAAC;IACpE,CAAC;IAED,IAAI,MAAM,CAAC,aAAa,EAAE,CAAC;QACzB,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,UAAU,IAAI,MAAM,CAAC,aAAc,CAAC,CAAC;IACrE,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,+CAA+C;AAC/C,SAAgB,WAAW,CACzB,KAAuB,EACvB,MAAkB;IAElB,IAAI,MAAM,GAAG,CAAC,GAAG,KAAK,CAAC,CAAC;IAExB,IAAI,MAAM,CAAC,gBAAgB,EAAE,CAAC;QAC5B,MAAM,KAAK,GAAG,KAAK,CAAC,OAAO,CAAC,MAAM,CAAC,gBAAgB,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,gBAAgB,CAAC,CAAC,CAAC,CAAC,MAAM,CAAC,gBAAgB,CAAC,CAAC;QAC3G,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,KAAK,CAAC,QAAQ,CAAC,CAAC,CAAC,iBAAiB,CAAC,CAAC,CAAC;IACnE,CAAC;IAED,IAAI,MAAM,CAAC,WAAW,KAAK,SAAS,EAAE,CAAC;QACrC,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,QAAQ,IAAI,MAAM,CAAC,WAAY,CAAC,CAAC;IACjE,CAAC;IAED,IAAI,MAAM,CAAC,eAAe,KAAK,SAAS,EAAE,CAAC;QACzC,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,gBAAgB,KAAK,MAAM,CAAC,eAAe,CAAC,CAAC;IAC7E,CAAC;IAED,IAAI,MAAM,CAAC,QAAQ,EAAE,CAAC;QACpB,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,OAAO,KAAK,MAAM,CAAC,QAAQ,CAAC,CAAC;IAC7D,CAAC;IAED,IAAI,MAAM,CAAC,MAAM,EAAE,CAAC;QAClB,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,KAAK,KAAK,MAAM,CAAC,MAAM,CAAC,CAAC;IACzD,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,6BAA6B;AAC7B,SAAgB,SAAS,CACvB,KAAuB,EACvB,IAAe;IAEf,MAAM,MAAM,GAAG,CAAC,GAAG,KAAK,CAAC,CAAC;IAC1B,MAAM,UAAU,GAAG,IAAI,CAAC,KAAK,KAAK,MAAM,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC,CAAC;IAElD,MAAM,CAAC,IAAI,CAAC,CAAC,CAAC,EAAE,CAAC,EAAE,EAAE;QACnB,IAAI,IAAY,EAAE,IAAY,CAAC;QAC/B,QAAQ,IAAI,CAAC,KAAK,EAAE,CAAC;YACnB,KAAK,MAAM;gBACT,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC;gBAAC,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC;gBAAC,MAAM;YACtC,KAAK,MAAM;gBACT,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC;gBAAC,IAAI,GAAG,CAAC,CAAC,IAAI,CAAC;gBAAC,MAAM;YACtC,KAAK,WAAW;gBACd,IAAI,GAAG,CAAC,CAAC,SAAS,IAAI,EAAE,CAAC;gBAAC,IAAI,GAAG,CAAC,CAAC,SAAS,IAAI,EAAE,CAAC;gBAAC,MAAM;YAC5D,KAAK,YAAY;gBACf,IAAI,GAAG,CAAC,CAAC,UAAU,CAAC;gBAAC,IAAI,GAAG,CAAC,CAAC,UAAU,CAAC;gBAAC,MAAM;YAClD;gBACE,IAAI,GAAG,CAAC,CAAC,UAAU,CAAC;gBAAC,IAAI,GAAG,CAAC,CAAC,UAAU,CAAC;QAC7C,CAAC;QACD,OAAO,IAAI,CAAC,aAAa,CAAC,IAAI,CAAC,GAAG,UAAU,CAAC;IAC/C,CAAC,CAAC,CAAC;IAEH,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,uBAAuB;AACvB,SAAgB,QAAQ,CACtB,KAAU,EACV,UAA2B;IAE3B,MAAM,KAAK,GAAG,KAAK,CAAC,MAAM,CAAC;IAC3B,MAAM,KAAK,GAAG,KAAK,CAAC,KAAK,CAAC,UAAU,CAAC,MAAM,EAAE,UAAU,CAAC,MAAM,GAAG,UAAU,CAAC,KAAK,CAAC,CAAC;IAEnF,OAAO;QACL,KAAK,EAAE,KAAK;QACZ,KAAK;QACL,MAAM,EAAE,UAAU,CAAC,MAAM;QACzB,KAAK,EAAE,UAAU,CAAC,KAAK;QACvB,OAAO,EAAE,UAAU,CAAC,MAAM,GAAG,UAAU,CAAC,KAAK,GAAG,KAAK;KACtD,CAAC;AACJ,CAAC;AAED,0DAA0D;AAC1D,SAAgB,gBAAgB,CAC9B,KAAuB,EACvB,KAAuB,EACvB,YAAoB;IAEpB,MAAM,YAAY,GAAG,IAAI,GAAG,EAAU,CAAC;IACvC,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,IAAI,IAAI,CAAC,OAAO,KAAK,YAAY;YAAE,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,CAAC;QAChE,IAAI,IAAI,CAAC,KAAK,KAAK,YAAY;YAAE,YAAY,CAAC,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,CAAC;IAClE,CAAC;IACD,OAAO,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,YAAY,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC;AACnD,CAAC;AAED,+BAA+B;AAC/B,SAAgB,cAAc,CAC5B,KAAuB,EACvB,KAAuB;IAEvB,MAAM,MAAM,GAAG,IAAI,GAAG,EAAkB,CAAC;IACzC,KAAK,MAAM,IAAI,IAAI,KAAK;QAAE,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,EAAE,EAAE,CAAC,CAAC,CAAC;IAEjD,KAAK,MAAM,IAAI,IAAI,KAAK,EAAE,CAAC;QACzB,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,OAAO,EAAE,CAAC,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,OAAO,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;QAC9D,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,EAAE,CAAC,MAAM,CAAC,GAAG,CAAC,IAAI,CAAC,KAAK,CAAC,IAAI,CAAC,CAAC,GAAG,CAAC,CAAC,CAAC;IAC5D,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC;AAED,+CAA+C;AAC/C,SAAgB,oBAAoB,CAClC,KAAuB,EACvB,KAAuB,EACvB,YAAoB;IAEpB,MAAM,MAAM,GAAG,cAAc,CAAC,KAAK,EAAE,KAAK,CAAC,CAAC;IAC5C,OAAO,KAAK,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,MAAM,CAAC,GAAG,CAAC,CAAC,CAAC,EAAE,CAAC,IAAI,CAAC,CAAC,IAAI,YAAY,CAAC,CAAC;AACpE,CAAC;AAED,6DAA6D;AAC7D,SAAgB,eAAe,CAC7B,SAAqB,EACrB,MAAsB;IAEtB,IAAI,MAAM,GAAG,CAAC,GAAG,SAAS,CAAC,CAAC;IAE5B,IAAI,MAAM,CAAC,SAAS,EAAE,CAAC;QACrB,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,SAAS,KAAK,MAAM,CAAC,SAAS,CAAC,CAAC;IAChE,CAAC;IAED,IAAI,MAAM,CAAC,UAAU,KAAK,SAAS,EAAE,CAAC;QACpC,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CACzB,CAAC,CAAC,gBAAgB,EAAE,gBAAgB,KAAK,MAAM,CAAC,UAAU,CAC3D,CAAC;IACJ,CAAC;IAED,IAAI,MAAM,CAAC,aAAa,KAAK,SAAS,EAAE,CAAC;QACvC,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CAAC,CAAC,CAAC,IAAI,CAAC,SAAS,KAAK,MAAM,CAAC,aAAa,CAAC,CAAC;IACzE,CAAC;IAED,IAAI,MAAM,CAAC,kBAAkB,KAAK,SAAS,EAAE,CAAC;QAC5C,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE,CACzB,CAAC,CAAC,cAAc,CAAC,gBAAgB,IAAI,MAAM,CAAC,kBAAmB,CAChE,CAAC;IACJ,CAAC;IAED,IAAI,MAAM,CAAC,cAAc,KAAK,SAAS,EAAE,CAAC;QACxC,MAAM,GAAG,MAAM,CAAC,MAAM,CAAC,CAAC,CAAC,EAAE;YACzB,MAAM,GAAG,GAAG,CAAC,CAAC,WAAW,CAAC,MAAM,GAAG,CAAC,CAAC;YACrC,OAAO,GAAG,KAAK,MAAM,CAAC,cAAc,CAAC;QACvC,CAAC,CAAC,CAAC;IACL,CAAC;IAED,OAAO,MAAM,CAAC;AAChB,CAAC"}
@@ -0,0 +1,13 @@
1
+ /**
2
+ * Graph Traversal — context-aware relationship traversal
3
+ * with ceremony boundary and OCAP® awareness.
4
+ */
5
+ import type { RelationalNode, RelationalEdge, Relation } from '@medicine-wheel/ontology-core';
6
+ import type { TraversalOptions, TraversalPath, TraversalResult } from './types.js';
7
+ /** Traverse the relational web from a root node */
8
+ export declare function traverse(rootId: string, nodes: RelationalNode[], edges: RelationalEdge[], relations: Relation[], opts?: Partial<TraversalOptions>): TraversalResult;
9
+ /** Find shortest path between two nodes */
10
+ export declare function shortestPath(fromId: string, toId: string, nodes: RelationalNode[], edges: RelationalEdge[]): TraversalPath | null;
11
+ /** Find all nodes reachable within N hops */
12
+ export declare function neighborhood(nodeId: string, nodes: RelationalNode[], edges: RelationalEdge[], maxDepth?: number): RelationalNode[];
13
+ //# sourceMappingURL=traversal.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"traversal.d.ts","sourceRoot":"","sources":["../src/traversal.ts"],"names":[],"mappings":"AAAA;;;GAGG;AACH,OAAO,KAAK,EAAE,cAAc,EAAE,cAAc,EAAE,QAAQ,EAAE,MAAM,+BAA+B,CAAC;AAE9F,OAAO,KAAK,EACV,gBAAgB,EAChB,aAAa,EACb,eAAe,EAGhB,MAAM,YAAY,CAAC;AAiCpB,mDAAmD;AACnD,wBAAgB,QAAQ,CACtB,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,cAAc,EAAE,EACvB,KAAK,EAAE,cAAc,EAAE,EACvB,SAAS,EAAE,QAAQ,EAAE,EACrB,IAAI,GAAE,OAAO,CAAC,gBAAgB,CAAM,GACnC,eAAe,CA+FjB;AAED,2CAA2C;AAC3C,wBAAgB,YAAY,CAC1B,MAAM,EAAE,MAAM,EACd,IAAI,EAAE,MAAM,EACZ,KAAK,EAAE,cAAc,EAAE,EACvB,KAAK,EAAE,cAAc,EAAE,GACtB,aAAa,GAAG,IAAI,CA4CtB;AAED,6CAA6C;AAC7C,wBAAgB,YAAY,CAC1B,MAAM,EAAE,MAAM,EACd,KAAK,EAAE,cAAc,EAAE,EACvB,KAAK,EAAE,cAAc,EAAE,EACvB,QAAQ,GAAE,MAAU,GACnB,cAAc,EAAE,CAMlB"}
@@ -0,0 +1,148 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ exports.traverse = traverse;
4
+ exports.shortestPath = shortestPath;
5
+ exports.neighborhood = neighborhood;
6
+ const ontology_core_1 = require("@medicine-wheel/ontology-core");
7
+ const query_js_1 = require("./query.js");
8
+ const DEFAULT_OPTIONS = {
9
+ maxDepth: 3,
10
+ direction: 'both',
11
+ respectCeremonyBoundaries: false,
12
+ ocapOnly: false,
13
+ };
14
+ /** Build an adjacency map from edges */
15
+ function buildAdjacency(edges, direction) {
16
+ const adj = new Map();
17
+ for (const edge of edges) {
18
+ if (direction === 'outgoing' || direction === 'both') {
19
+ const list = adj.get(edge.from_id) ?? [];
20
+ list.push({ nodeId: edge.to_id, edge });
21
+ adj.set(edge.from_id, list);
22
+ }
23
+ if (direction === 'incoming' || direction === 'both') {
24
+ const list = adj.get(edge.to_id) ?? [];
25
+ list.push({ nodeId: edge.from_id, edge });
26
+ adj.set(edge.to_id, list);
27
+ }
28
+ }
29
+ return adj;
30
+ }
31
+ /** Traverse the relational web from a root node */
32
+ function traverse(rootId, nodes, edges, relations, opts = {}) {
33
+ const options = { ...DEFAULT_OPTIONS, ...opts };
34
+ // Pre-filter edges
35
+ let filteredEdges = edges;
36
+ if (options.edgeFilter) {
37
+ filteredEdges = (0, query_js_1.filterEdges)(edges, options.edgeFilter);
38
+ }
39
+ // OCAP filter: only follow edges whose relations are compliant
40
+ if (options.ocapOnly) {
41
+ const compliantRelIds = new Set(relations
42
+ .filter(r => r.ocap && (0, ontology_core_1.checkOcapCompliance)(r.ocap).compliant)
43
+ .map(r => r.id));
44
+ // Keep edges that match compliant relation IDs or have no relation mapping
45
+ filteredEdges = filteredEdges.filter(e => {
46
+ const relId = `${e.from_id}-${e.to_id}`;
47
+ const reverseId = `${e.to_id}-${e.from_id}`;
48
+ return compliantRelIds.has(relId) || compliantRelIds.has(reverseId) || !relations.some(r => r.id === relId || r.id === reverseId);
49
+ });
50
+ }
51
+ // Build adjacency
52
+ const adj = buildAdjacency(filteredEdges, options.direction);
53
+ // Node lookup
54
+ const nodeMap = new Map(nodes.map(n => [n.id, n]));
55
+ const rootNode = nodeMap.get(rootId);
56
+ if (!rootNode) {
57
+ throw new Error(`Traversal root node not found: "${rootId}"`);
58
+ }
59
+ // BFS traversal
60
+ const paths = [];
61
+ const visited = new Set([rootId]);
62
+ let maxDepthReached = false;
63
+ const queue = [{ nodeId: rootId, path: [rootNode], edgePath: [], depth: 0 }];
64
+ while (queue.length > 0) {
65
+ const current = queue.shift();
66
+ if (current.depth >= options.maxDepth) {
67
+ maxDepthReached = true;
68
+ continue;
69
+ }
70
+ const neighbors = adj.get(current.nodeId) ?? [];
71
+ for (const { nodeId, edge } of neighbors) {
72
+ if (visited.has(nodeId))
73
+ continue;
74
+ // Ceremony boundary check
75
+ if (options.respectCeremonyBoundaries && !edge.ceremony_honored) {
76
+ continue;
77
+ }
78
+ const node = nodeMap.get(nodeId);
79
+ if (!node)
80
+ continue;
81
+ // Node filter
82
+ if (options.nodeFilter) {
83
+ const filtered = (0, query_js_1.filterNodes)([node], options.nodeFilter);
84
+ if (filtered.length === 0)
85
+ continue;
86
+ }
87
+ visited.add(nodeId);
88
+ const newPath = [...current.path, node];
89
+ const newEdgePath = [...current.edgePath, edge];
90
+ paths.push({
91
+ nodes: newPath,
92
+ edges: newEdgePath,
93
+ depth: current.depth + 1,
94
+ });
95
+ queue.push({
96
+ nodeId,
97
+ path: newPath,
98
+ edgePath: newEdgePath,
99
+ depth: current.depth + 1,
100
+ });
101
+ }
102
+ }
103
+ return { root: rootNode, paths, visitedNodes: visited, maxDepthReached };
104
+ }
105
+ /** Find shortest path between two nodes */
106
+ function shortestPath(fromId, toId, nodes, edges) {
107
+ const adj = buildAdjacency(edges, 'both');
108
+ const nodeMap = new Map(nodes.map(n => [n.id, n]));
109
+ const visited = new Set([fromId]);
110
+ const fromNode = nodeMap.get(fromId);
111
+ if (!fromNode)
112
+ return null;
113
+ const queue = [{ nodeId: fromId, path: [fromNode], edgePath: [] }];
114
+ while (queue.length > 0) {
115
+ const current = queue.shift();
116
+ if (current.nodeId === toId) {
117
+ return {
118
+ nodes: current.path,
119
+ edges: current.edgePath,
120
+ depth: current.path.length - 1,
121
+ };
122
+ }
123
+ const neighbors = adj.get(current.nodeId) ?? [];
124
+ for (const { nodeId, edge } of neighbors) {
125
+ if (visited.has(nodeId))
126
+ continue;
127
+ visited.add(nodeId);
128
+ const node = nodeMap.get(nodeId);
129
+ if (!node)
130
+ continue;
131
+ queue.push({
132
+ nodeId,
133
+ path: [...current.path, node],
134
+ edgePath: [...current.edgePath, edge],
135
+ });
136
+ }
137
+ }
138
+ return null;
139
+ }
140
+ /** Find all nodes reachable within N hops */
141
+ function neighborhood(nodeId, nodes, edges, maxDepth = 2) {
142
+ const result = traverse(nodeId, nodes, edges, [], { maxDepth, direction: 'both' });
143
+ const nodeMap = new Map(nodes.map(n => [n.id, n]));
144
+ return [...result.visitedNodes]
145
+ .map(id => nodeMap.get(id))
146
+ .filter((n) => n !== undefined);
147
+ }
148
+ //# sourceMappingURL=traversal.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"traversal.js","sourceRoot":"","sources":["../src/traversal.ts"],"names":[],"mappings":"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"}
@@ -0,0 +1,88 @@
1
+ /**
2
+ * @medicine-wheel/relational-query — types
3
+ *
4
+ * Query builder types for context-aware relational traversal
5
+ * with Indigenous protocol awareness.
6
+ */
7
+ import type { DirectionName, NodeType, RelationalNode, RelationalEdge } from '@medicine-wheel/ontology-core';
8
+ export interface NodeFilter {
9
+ type?: NodeType | NodeType[];
10
+ direction?: DirectionName | DirectionName[];
11
+ nameContains?: string;
12
+ hasRelationsTo?: string;
13
+ minRelations?: number;
14
+ createdAfter?: string;
15
+ createdBefore?: string;
16
+ }
17
+ export interface EdgeFilter {
18
+ relationshipType?: string | string[];
19
+ minStrength?: number;
20
+ ceremonyHonored?: boolean;
21
+ fromNode?: string;
22
+ toNode?: string;
23
+ }
24
+ export interface RelationFilter {
25
+ direction?: DirectionName;
26
+ ceremonied?: boolean;
27
+ ocapCompliant?: boolean;
28
+ minWilsonAlignment?: number;
29
+ hasObligations?: boolean;
30
+ }
31
+ export type SortField = 'name' | 'created_at' | 'updated_at' | 'type' | 'direction';
32
+ export type SortOrder = 'asc' | 'desc';
33
+ export interface QuerySort {
34
+ field: SortField;
35
+ order: SortOrder;
36
+ }
37
+ export interface QueryPagination {
38
+ offset: number;
39
+ limit: number;
40
+ }
41
+ export interface QueryOptions {
42
+ filter?: NodeFilter;
43
+ sort?: QuerySort;
44
+ pagination?: QueryPagination;
45
+ includeEdges?: boolean;
46
+ includeRelations?: boolean;
47
+ }
48
+ export interface QueryResult<T> {
49
+ items: T[];
50
+ total: number;
51
+ offset: number;
52
+ limit: number;
53
+ hasMore: boolean;
54
+ }
55
+ export type TraversalDirection = 'outgoing' | 'incoming' | 'both';
56
+ export interface TraversalOptions {
57
+ maxDepth: number;
58
+ direction: TraversalDirection;
59
+ edgeFilter?: EdgeFilter;
60
+ nodeFilter?: NodeFilter;
61
+ /** Stop traversal at nodes without ceremony-honored edges */
62
+ respectCeremonyBoundaries?: boolean;
63
+ /** Only follow OCAP-compliant relations */
64
+ ocapOnly?: boolean;
65
+ }
66
+ export interface TraversalPath {
67
+ nodes: RelationalNode[];
68
+ edges: RelationalEdge[];
69
+ depth: number;
70
+ }
71
+ export interface TraversalResult {
72
+ root: RelationalNode;
73
+ paths: TraversalPath[];
74
+ visitedNodes: Set<string>;
75
+ maxDepthReached: boolean;
76
+ }
77
+ export interface AccountabilityReport {
78
+ totalRelations: number;
79
+ ocapCompliant: number;
80
+ ocapNonCompliant: number;
81
+ averageWilsonAlignment: number;
82
+ directionCoverage: Record<DirectionName, number>;
83
+ ceremoniedRelations: number;
84
+ unceremoniedRelations: number;
85
+ obligationsOutstanding: number;
86
+ recommendations: string[];
87
+ }
88
+ //# sourceMappingURL=types.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.d.ts","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":"AAAA;;;;;GAKG;AACH,OAAO,KAAK,EACV,aAAa,EACb,QAAQ,EAER,cAAc,EACd,cAAc,EAEf,MAAM,+BAA+B,CAAC;AAIvC,MAAM,WAAW,UAAU;IACzB,IAAI,CAAC,EAAE,QAAQ,GAAG,QAAQ,EAAE,CAAC;IAC7B,SAAS,CAAC,EAAE,aAAa,GAAG,aAAa,EAAE,CAAC;IAC5C,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,cAAc,CAAC,EAAE,MAAM,CAAC;IACxB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,YAAY,CAAC,EAAE,MAAM,CAAC;IACtB,aAAa,CAAC,EAAE,MAAM,CAAC;CACxB;AAED,MAAM,WAAW,UAAU;IACzB,gBAAgB,CAAC,EAAE,MAAM,GAAG,MAAM,EAAE,CAAC;IACrC,WAAW,CAAC,EAAE,MAAM,CAAC;IACrB,eAAe,CAAC,EAAE,OAAO,CAAC;IAC1B,QAAQ,CAAC,EAAE,MAAM,CAAC;IAClB,MAAM,CAAC,EAAE,MAAM,CAAC;CACjB;AAED,MAAM,WAAW,cAAc;IAC7B,SAAS,CAAC,EAAE,aAAa,CAAC;IAC1B,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,aAAa,CAAC,EAAE,OAAO,CAAC;IACxB,kBAAkB,CAAC,EAAE,MAAM,CAAC;IAC5B,cAAc,CAAC,EAAE,OAAO,CAAC;CAC1B;AAID,MAAM,MAAM,SAAS,GAAG,MAAM,GAAG,YAAY,GAAG,YAAY,GAAG,MAAM,GAAG,WAAW,CAAC;AACpF,MAAM,MAAM,SAAS,GAAG,KAAK,GAAG,MAAM,CAAC;AAEvC,MAAM,WAAW,SAAS;IACxB,KAAK,EAAE,SAAS,CAAC;IACjB,KAAK,EAAE,SAAS,CAAC;CAClB;AAED,MAAM,WAAW,eAAe;IAC9B,MAAM,EAAE,MAAM,CAAC;IACf,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,YAAY;IAC3B,MAAM,CAAC,EAAE,UAAU,CAAC;IACpB,IAAI,CAAC,EAAE,SAAS,CAAC;IACjB,UAAU,CAAC,EAAE,eAAe,CAAC;IAC7B,YAAY,CAAC,EAAE,OAAO,CAAC;IACvB,gBAAgB,CAAC,EAAE,OAAO,CAAC;CAC5B;AAED,MAAM,WAAW,WAAW,CAAC,CAAC;IAC5B,KAAK,EAAE,CAAC,EAAE,CAAC;IACX,KAAK,EAAE,MAAM,CAAC;IACd,MAAM,EAAE,MAAM,CAAC;IACf,KAAK,EAAE,MAAM,CAAC;IACd,OAAO,EAAE,OAAO,CAAC;CAClB;AAID,MAAM,MAAM,kBAAkB,GAAG,UAAU,GAAG,UAAU,GAAG,MAAM,CAAC;AAElE,MAAM,WAAW,gBAAgB;IAC/B,QAAQ,EAAE,MAAM,CAAC;IACjB,SAAS,EAAE,kBAAkB,CAAC;IAC9B,UAAU,CAAC,EAAE,UAAU,CAAC;IACxB,UAAU,CAAC,EAAE,UAAU,CAAC;IACxB,6DAA6D;IAC7D,yBAAyB,CAAC,EAAE,OAAO,CAAC;IACpC,2CAA2C;IAC3C,QAAQ,CAAC,EAAE,OAAO,CAAC;CACpB;AAED,MAAM,WAAW,aAAa;IAC5B,KAAK,EAAE,cAAc,EAAE,CAAC;IACxB,KAAK,EAAE,cAAc,EAAE,CAAC;IACxB,KAAK,EAAE,MAAM,CAAC;CACf;AAED,MAAM,WAAW,eAAe;IAC9B,IAAI,EAAE,cAAc,CAAC;IACrB,KAAK,EAAE,aAAa,EAAE,CAAC;IACvB,YAAY,EAAE,GAAG,CAAC,MAAM,CAAC,CAAC;IAC1B,eAAe,EAAE,OAAO,CAAC;CAC1B;AAID,MAAM,WAAW,oBAAoB;IACnC,cAAc,EAAE,MAAM,CAAC;IACvB,aAAa,EAAE,MAAM,CAAC;IACtB,gBAAgB,EAAE,MAAM,CAAC;IACzB,sBAAsB,EAAE,MAAM,CAAC;IAC/B,iBAAiB,EAAE,MAAM,CAAC,aAAa,EAAE,MAAM,CAAC,CAAC;IACjD,mBAAmB,EAAE,MAAM,CAAC;IAC5B,qBAAqB,EAAE,MAAM,CAAC;IAC9B,sBAAsB,EAAE,MAAM,CAAC;IAC/B,eAAe,EAAE,MAAM,EAAE,CAAC;CAC3B"}
package/dist/types.js ADDED
@@ -0,0 +1,3 @@
1
+ "use strict";
2
+ Object.defineProperty(exports, "__esModule", { value: true });
3
+ //# sourceMappingURL=types.js.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"types.js","sourceRoot":"","sources":["../src/types.ts"],"names":[],"mappings":""}
package/package.json ADDED
@@ -0,0 +1,41 @@
1
+ {
2
+ "name": "@medicine-wheel/relational-query",
3
+ "version": "0.2.2",
4
+ "description": "Query builder for relational webs with Indigenous protocol awareness — traversal, accountability, OCAP® compliance",
5
+ "main": "dist/index.js",
6
+ "types": "dist/index.d.ts",
7
+ "exports": {
8
+ ".": {
9
+ "types": "./dist/index.d.ts",
10
+ "import": "./dist/index.js",
11
+ "require": "./dist/index.js",
12
+ "default": "./dist/index.js"
13
+ }
14
+ },
15
+ "sideEffects": false,
16
+ "files": [
17
+ "dist",
18
+ "README.md"
19
+ ],
20
+ "scripts": {
21
+ "build": "tsc",
22
+ "clean": "rm -rf dist",
23
+ "prepublishOnly": "npm run clean && npm run build"
24
+ },
25
+ "keywords": [
26
+ "medicine-wheel",
27
+ "relational",
28
+ "query",
29
+ "indigenous",
30
+ "ocap",
31
+ "graph-traversal"
32
+ ],
33
+ "author": "jgwill",
34
+ "license": "MIT",
35
+ "dependencies": {
36
+ "@medicine-wheel/ontology-core": "^0.2.2"
37
+ },
38
+ "devDependencies": {
39
+ "typescript": "^5.7.0"
40
+ }
41
+ }