@c4a/context 0.6.1 → 0.6.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/index.js CHANGED
@@ -6916,6 +6916,10 @@ var require_public_api = __commonJS((exports) => {
6916
6916
  });
6917
6917
 
6918
6918
  // src/contracts.ts
6919
+ var DEFAULT_PACKAGE_NAVIGATION = {
6920
+ foldDirectoryIndexes: true,
6921
+ maxInlineEntries: 50
6922
+ };
6919
6923
  var DOC_MAINLINE_COLLECTIONS = [
6920
6924
  "business",
6921
6925
  "product",
@@ -7084,9 +7088,9 @@ var sourceSnapshotResource = (sourceDefinition, sourceType) => ({
7084
7088
  sourceType,
7085
7089
  path: `sources/${sourceType}/${getSourceName(sourceDefinition)}/manifest.json`
7086
7090
  });
7087
- var unapprovedStructureResource = (collection, status) => ({
7088
- kind: "unapproved.structure",
7089
- path: "unapproved/structure.yaml",
7091
+ var lifecycleStructureResource = (collection, status) => ({
7092
+ kind: "lifecycle.structure",
7093
+ path: ".tmp/context-runtime/lifecycle/structure.yaml",
7090
7094
  profileCollection: collection,
7091
7095
  ...status === undefined ? {} : { status }
7092
7096
  });
@@ -7146,7 +7150,7 @@ var alignProse = (definition) => {
7146
7150
  kind: "source",
7147
7151
  source: definition.source
7148
7152
  }],
7149
- writes: [unapprovedStructureResource(definition.collection, "draft")],
7153
+ writes: [lifecycleStructureResource(definition.collection, "draft")],
7150
7154
  source: definition.source,
7151
7155
  collection: definition.collection
7152
7156
  };
@@ -7156,7 +7160,7 @@ var alignProse = (definition) => {
7156
7160
  kind: "phase.align.prose",
7157
7161
  id: `align:${sourceType}:${sourceId}:${definition.collection}`,
7158
7162
  reads: [sourceSnapshotResource(definition.source, sourceType)],
7159
- writes: [unapprovedStructureResource(definition.collection, "draft")],
7163
+ writes: [lifecycleStructureResource(definition.collection, "draft")],
7160
7164
  source: definition.source,
7161
7165
  sourceType,
7162
7166
  collection: definition.collection
@@ -7172,12 +7176,12 @@ var compileProse = (definition) => {
7172
7176
  reads: [{
7173
7177
  kind: "source",
7174
7178
  source: definition.source
7175
- }, unapprovedStructureResource(definition.collection, "confirmed")],
7179
+ }, lifecycleStructureResource(definition.collection, "confirmed")],
7176
7180
  writes: [
7177
- unapprovedStructureResource(definition.collection, "frozen"),
7181
+ lifecycleStructureResource(definition.collection, "frozen"),
7178
7182
  {
7179
- kind: "unapproved.entities",
7180
- path: "unapproved/entities.jsonl",
7183
+ kind: "lifecycle.candidates",
7184
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7181
7185
  status: "draft"
7182
7186
  }
7183
7187
  ],
@@ -7192,13 +7196,13 @@ var compileProse = (definition) => {
7192
7196
  id: `compile:${sourceType}:${sourceId}:${definition.collection}`,
7193
7197
  reads: [
7194
7198
  sourceSnapshotResource(definition.source, sourceType),
7195
- unapprovedStructureResource(definition.collection, "confirmed")
7199
+ lifecycleStructureResource(definition.collection, "confirmed")
7196
7200
  ],
7197
7201
  writes: [
7198
- unapprovedStructureResource(definition.collection, "frozen"),
7202
+ lifecycleStructureResource(definition.collection, "frozen"),
7199
7203
  {
7200
- kind: "unapproved.entities",
7201
- path: "unapproved/entities.jsonl",
7204
+ kind: "lifecycle.candidates",
7205
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7202
7206
  status: "draft"
7203
7207
  }
7204
7208
  ],
@@ -7230,8 +7234,8 @@ var extractTs = (definition) => {
7230
7234
  source: sourceDefinition
7231
7235
  }],
7232
7236
  writes: [{
7233
- kind: "unapproved.entities",
7234
- path: "unapproved/entities.jsonl",
7237
+ kind: "lifecycle.candidates",
7238
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7235
7239
  collection: definition.collection,
7236
7240
  status: "draft"
7237
7241
  }],
@@ -7243,7 +7247,7 @@ var extractTs = (definition) => {
7243
7247
  exportedOnly: definition.exportedOnly ?? mode === "exports",
7244
7248
  out: {
7245
7249
  kind: "codegraph-entities",
7246
- candidateFile: "unapproved/entities.jsonl",
7250
+ candidateFile: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7247
7251
  approvedPagesDir: `knowledge/${definition.collection}`,
7248
7252
  initialStatus: "draft"
7249
7253
  }
@@ -7253,6 +7257,31 @@ var extractTs = (definition) => {
7253
7257
  }
7254
7258
  return phase;
7255
7259
  };
7260
+ var extractCustom = (definition) => {
7261
+ const id = definition.id.trim();
7262
+ if (id.length === 0)
7263
+ throw new TypeError("extractCustom id must be a non-empty phase id");
7264
+ if (definition.sources.length === 0)
7265
+ throw new TypeError("extractCustom sources must contain at least one repo source");
7266
+ if (definition.collection !== "codegraph") {
7267
+ throw new TypeError(`extractCustom collection must be codegraph: ${definition.collection}`);
7268
+ }
7269
+ const sources = definition.sources.map((sourceDefinition) => bindSourceType(sourceDefinition, "repo", "extractCustom source"));
7270
+ return {
7271
+ kind: "phase.extract.custom",
7272
+ id,
7273
+ reads: sources.map((sourceDefinition) => ({ kind: "source", source: sourceDefinition })),
7274
+ writes: [{
7275
+ kind: "lifecycle.candidates",
7276
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7277
+ collection: definition.collection,
7278
+ status: "draft"
7279
+ }],
7280
+ sources,
7281
+ collection: definition.collection,
7282
+ extract: definition.extract
7283
+ };
7284
+ };
7256
7285
  var reviewValidity = (definition) => {
7257
7286
  const payload = definition.payload ?? "review-payload.json";
7258
7287
  if ("scope" in definition) {
@@ -7263,8 +7292,8 @@ var reviewValidity = (definition) => {
7263
7292
  kind: "phase.review.validity",
7264
7293
  id: "review:all:validity",
7265
7294
  reads: [{
7266
- kind: "unapproved.entities",
7267
- path: "unapproved/entities.jsonl",
7295
+ kind: "lifecycle.candidates",
7296
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7268
7297
  status: "draft"
7269
7298
  }],
7270
7299
  writes: [
@@ -7277,8 +7306,12 @@ var reviewValidity = (definition) => {
7277
7306
  path: "knowledge"
7278
7307
  },
7279
7308
  {
7280
- kind: "unapproved.entities",
7281
- path: "unapproved/entities.jsonl",
7309
+ kind: "knowledge.decisions",
7310
+ path: "knowledge/decisions.json"
7311
+ },
7312
+ {
7313
+ kind: "lifecycle.candidates",
7314
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7282
7315
  status: "rejected"
7283
7316
  }
7284
7317
  ],
@@ -7293,8 +7326,8 @@ var reviewValidity = (definition) => {
7293
7326
  kind: "phase.review.validity",
7294
7327
  id: `review:${definition.collection}:validity`,
7295
7328
  reads: [{
7296
- kind: "unapproved.entities",
7297
- path: "unapproved/entities.jsonl",
7329
+ kind: "lifecycle.candidates",
7330
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7298
7331
  collection: definition.collection,
7299
7332
  status: "draft"
7300
7333
  }],
@@ -7310,8 +7343,12 @@ var reviewValidity = (definition) => {
7310
7343
  status: "approved"
7311
7344
  },
7312
7345
  {
7313
- kind: "unapproved.entities",
7314
- path: "unapproved/entities.jsonl",
7346
+ kind: "knowledge.decisions",
7347
+ path: "knowledge/decisions.json"
7348
+ },
7349
+ {
7350
+ kind: "lifecycle.candidates",
7351
+ path: ".tmp/context-runtime/lifecycle/candidates.jsonl",
7315
7352
  collection: definition.collection,
7316
7353
  status: "rejected"
7317
7354
  }
@@ -11818,7 +11855,20 @@ var normalizeSelect = (select) => {
11818
11855
  }
11819
11856
  return Object.keys(normalized).length > 0 ? normalized : undefined;
11820
11857
  };
11858
+ var normalizePackageNavigation = (navigation) => {
11859
+ const maxInlineEntries = navigation?.maxInlineEntries ?? DEFAULT_PACKAGE_NAVIGATION.maxInlineEntries;
11860
+ if (!Number.isSafeInteger(maxInlineEntries) || maxInlineEntries < 1) {
11861
+ throw new TypeError(`Package navigation.maxInlineEntries must be a positive safe integer: ${maxInlineEntries}`);
11862
+ }
11863
+ return {
11864
+ foldDirectoryIndexes: navigation?.foldDirectoryIndexes ?? DEFAULT_PACKAGE_NAVIGATION.foldDirectoryIndexes,
11865
+ maxInlineEntries
11866
+ };
11867
+ };
11821
11868
  var PACKAGE_NAME_PATTERN = /^[a-z0-9][a-z0-9._-]*$/u;
11869
+ var PACKAGE_KNOWLEDGE_NAMESPACE_SEGMENT_PATTERN = /^[a-z0-9]+(?:[.-][a-z0-9]+)*$/u;
11870
+ var PACKAGE_KNOWLEDGE_NAMESPACE_SEGMENT_MAX_LENGTH = 48;
11871
+ var PACKAGE_KNOWLEDGE_NAMESPACE_MAX_LENGTH = 128;
11822
11872
  var isSafeProjectRelativePath = (value) => {
11823
11873
  if (value.length === 0)
11824
11874
  return false;
@@ -11838,6 +11888,19 @@ var assertSelectCollections = (collections) => {
11838
11888
  assertKnowledgeCollection(collection, "Package select.collections");
11839
11889
  }
11840
11890
  };
11891
+ var normalizePackageDistribution = (distribution) => {
11892
+ if (distribution === undefined)
11893
+ return;
11894
+ if (typeof distribution.knowledgeNamespace !== "string") {
11895
+ throw new TypeError("Package distribution.knowledgeNamespace must be a string.");
11896
+ }
11897
+ const knowledgeNamespace = distribution.knowledgeNamespace.trim();
11898
+ const segments = knowledgeNamespace.split("/");
11899
+ if (knowledgeNamespace.length > PACKAGE_KNOWLEDGE_NAMESPACE_MAX_LENGTH || segments.length === 0 || segments.some((segment) => segment.length > PACKAGE_KNOWLEDGE_NAMESPACE_SEGMENT_MAX_LENGTH || !PACKAGE_KNOWLEDGE_NAMESPACE_SEGMENT_PATTERN.test(segment))) {
11900
+ throw new TypeError(`Package distribution.knowledgeNamespace must contain safe lowercase path segments using letters, numbers, hyphens, or dots, separated by "/", and be at most ${PACKAGE_KNOWLEDGE_NAMESPACE_MAX_LENGTH} characters: ${distribution.knowledgeNamespace}`);
11901
+ }
11902
+ return { knowledgeNamespace };
11903
+ };
11841
11904
  var assertSelectOkfRoots = (roots) => {
11842
11905
  for (const root of roots) {
11843
11906
  assertOkfRoot(root, "Package select.okfRoots");
@@ -11880,10 +11943,16 @@ var createPackageDefinitionBase = (kind, definition) => {
11880
11943
  }
11881
11944
  return packageDefinition;
11882
11945
  };
11883
- var kbPackage = (definition) => ({
11884
- kind: "package.kb",
11885
- ...createPackageDefinitionBase("kb", definition)
11886
- });
11946
+ var kbPackage = (definition) => {
11947
+ const base = createPackageDefinitionBase("kb", definition);
11948
+ const distribution = normalizePackageDistribution(definition.distribution);
11949
+ return {
11950
+ kind: "package.kb",
11951
+ ...base,
11952
+ navigation: normalizePackageNavigation(definition.navigation),
11953
+ ...distribution === undefined ? {} : { distribution }
11954
+ };
11955
+ };
11887
11956
  var llmsPackage = (definition) => ({
11888
11957
  kind: "package.llms",
11889
11958
  ...createPackageDefinitionBase("llms", definition)
@@ -11897,6 +11966,7 @@ export {
11897
11966
  llmsPackage,
11898
11967
  kbPackage,
11899
11968
  extractTs,
11969
+ extractCustom,
11900
11970
  defineProject,
11901
11971
  customPhase,
11902
11972
  compileProse,
@@ -11922,6 +11992,7 @@ export {
11922
11992
  DOCUMENT_EVIDENCE_SECTION_VALIDATION_STAGES,
11923
11993
  DOCUMENT_COMPILE_ACTION_SCHEMA_VERSION,
11924
11994
  DEFAULT_REPO_SOURCES_REGISTRY_PATH,
11995
+ DEFAULT_PACKAGE_NAVIGATION,
11925
11996
  DEFAULT_LARK_SOURCES_REGISTRY_PATH,
11926
11997
  DEFAULT_FILE_SOURCES_REGISTRY_PATH
11927
11998
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@c4a/context",
3
- "version": "0.6.1",
3
+ "version": "0.6.2",
4
4
  "type": "module",
5
5
  "description": "Context SDK — project-local configuration and workspace primitives",
6
6
  "license": "MIT",
package/phases.d.ts CHANGED
@@ -1,4 +1,4 @@
1
- import { type EntityStatus, type FileCaptureProcessorDefinition, type KnowledgeCollection, type MarkdownTransform, type PackageKind, type PackageSelectDefinition, type DocumentMainlineCollection } from "./contracts.js";
1
+ import { type FileCaptureProcessorDefinition, type KnowledgeCollection, type MarkdownTransform, type PackageKind, type PackageSelectDefinition, type DocumentMainlineCollection } from "./contracts.js";
2
2
  import { DOCUMENT_COMPILE_ACTION_SCHEMA_VERSION } from "./documentEvidence.js";
3
3
  import type { DocumentSourceDefinition, DocumentSourceType, FileSourceDefinition, FileSourceReference, LarkSourceDefinition, LarkSourceReference, RepoProjectSourceDefinition, SourceCollectionReference, SourceDefinition } from "./sources.js";
4
4
  export type PhaseResourceReference = {
@@ -10,13 +10,13 @@ export type PhaseResourceReference = {
10
10
  sourceType: DocumentSourceType;
11
11
  path: string;
12
12
  } | {
13
- kind: "unapproved.entities";
13
+ kind: "lifecycle.candidates";
14
14
  path: string;
15
15
  collection?: KnowledgeCollection;
16
- status?: EntityStatus;
16
+ status?: "draft" | "rejected";
17
17
  } | {
18
- kind: "unapproved.structure";
19
- path: "unapproved/structure.yaml";
18
+ kind: "lifecycle.structure";
19
+ path: ".tmp/context-runtime/lifecycle/structure.yaml";
20
20
  profileCollection?: DocumentMainlineCollection;
21
21
  status?: "draft" | "confirmed" | "frozen";
22
22
  } | {
@@ -28,6 +28,9 @@ export type PhaseResourceReference = {
28
28
  kind: "knowledge.approved";
29
29
  path: "knowledge";
30
30
  select?: PackageSelectDefinition;
31
+ } | {
32
+ kind: "knowledge.decisions";
33
+ path: "knowledge/decisions.json";
31
34
  } | {
32
35
  kind: "package.template";
33
36
  path: string;
@@ -71,6 +74,56 @@ export type ExtractTsPhaseDefinition = {
71
74
  initialStatus: "draft";
72
75
  };
73
76
  };
77
+ export interface CustomCodeEvidence {
78
+ source: string;
79
+ file: string;
80
+ symbol: string;
81
+ kind: string;
82
+ digest: string;
83
+ line?: number;
84
+ }
85
+ export interface CustomCodeCandidateReview {
86
+ title: string;
87
+ summary: string;
88
+ behaviorSummary?: string;
89
+ edgeSummary?: string;
90
+ signals: readonly string[];
91
+ reason: string;
92
+ }
93
+ export interface CustomCodeCandidateEdge {
94
+ type: "contains" | "depends_on";
95
+ from: string;
96
+ to: string;
97
+ relationType: string;
98
+ evidence: readonly CustomCodeEvidence[];
99
+ }
100
+ export interface CustomCodeCandidateDraft {
101
+ nodeRef: string;
102
+ kind: string;
103
+ visibility: string;
104
+ module: string;
105
+ markdown: string;
106
+ evidence: readonly CustomCodeEvidence[];
107
+ review: CustomCodeCandidateReview;
108
+ edges?: readonly CustomCodeCandidateEdge[];
109
+ }
110
+ export interface CustomCodeExtractionResult {
111
+ candidates: readonly CustomCodeCandidateDraft[];
112
+ }
113
+ export interface CustomCodeExtractionContext {
114
+ projectRoot: string;
115
+ runId: string;
116
+ }
117
+ export type CustomCodeExtractor = (context: CustomCodeExtractionContext) => CustomCodeExtractionResult | Promise<CustomCodeExtractionResult>;
118
+ export type ExtractCustomPhaseDefinition = {
119
+ kind: "phase.extract.custom";
120
+ id: string;
121
+ reads: readonly PhaseResourceReference[];
122
+ writes: readonly PhaseResourceReference[];
123
+ sources: readonly RepoProjectSourceDefinition[];
124
+ collection: "codegraph";
125
+ extract: CustomCodeExtractor;
126
+ };
74
127
  export declare const NO_ENTRY_DETECTED: "NO_ENTRY_DETECTED";
75
128
  export declare class ExtractTsConfigurationError extends TypeError {
76
129
  readonly code: "NO_ENTRY_DETECTED";
@@ -134,7 +187,7 @@ export type CustomPhaseDefinition = {
134
187
  writes: readonly PhaseResourceReference[];
135
188
  run: ContextPhase;
136
189
  };
137
- export type PhaseDefinition = ExtractTsPhaseDefinition | CaptureFilePhaseDefinition | CaptureLarkPhaseDefinition | AlignProsePhaseDefinition | CompileProsePhaseDefinition | ReviewValidityPhaseDefinition | CustomPhaseDefinition;
190
+ export type PhaseDefinition = ExtractTsPhaseDefinition | ExtractCustomPhaseDefinition | CaptureFilePhaseDefinition | CaptureLarkPhaseDefinition | AlignProsePhaseDefinition | CompileProsePhaseDefinition | ReviewValidityPhaseDefinition | CustomPhaseDefinition;
138
191
  export declare function mdxJsonDocs(options?: {
139
192
  include?: readonly string[];
140
193
  documentExtensions?: readonly string[];
@@ -165,6 +218,12 @@ export declare const extractTs: (definition: {
165
218
  exportedOnly?: boolean;
166
219
  transform?: MarkdownTransform | readonly MarkdownTransform[];
167
220
  }) => ExtractTsPhaseDefinition;
221
+ export declare const extractCustom: (definition: {
222
+ id: string;
223
+ sources: readonly RepoProjectSourceDefinition[];
224
+ collection: "codegraph";
225
+ extract: CustomCodeExtractor;
226
+ }) => ExtractCustomPhaseDefinition;
168
227
  export declare const reviewValidity: (definition: {
169
228
  collection: KnowledgeCollection;
170
229
  payload?: string;
@@ -11,22 +11,19 @@ Approved knowledge files: `{{knowledgeCount}}`
11
11
  Use the Markdown files in this package as source-linked product and code
12
12
  knowledge. Prefer cited facts from the included knowledge pages over memory.
13
13
 
14
- The `skills/knowledge-query/SKILL.md` entry teaches agents how to navigate OKF
15
- indexes and cite copied OKF root directories, starting with
16
- `wikis/`. Customize template files before build when the package needs
17
- product-specific skills or routing rules.
18
-
19
- Selected OKF root directories such as `wikis/`, `guides/`, `rules/`, and
20
- `feats/` follow the C4A OKF Profile: OKF fields and C4A extension fields stay
21
- at the top level, and no `context` or `schema` field is emitted. Root mapping:
22
- `wikis/` maps from structured `codegraph`, `business`, and `product` knowledge;
23
- `guides/` maps from `architecture`, `sop`, `faq`, `decision`, and `incident`;
24
- `rules/` maps from `standards` and `test`; `feats/` maps from `feats`. Treat
25
- `wikis/` as the entity-and-relationship layer; guides and rules may explain or
26
- constrain that layer. Customize
27
- `wikis/index.md` before build to describe the package scope and query guidance;
28
- other selected OKF root indexes are generated unless this template supplies
29
- them.
14
+ The bundled knowledge-query Skill teaches agents how to navigate OKF indexes
15
+ and cite copied OKF root directories, starting with `{{wikisRoot}}/`.
16
+
17
+ Selected OKF root directories such as `{{wikisRoot}}/`, `{{guidesRoot}}/`,
18
+ `{{rulesRoot}}/`, and `{{featsRoot}}/` follow an OKF-compatible Context profile:
19
+ OKF fields and Context extension fields stay at the top level, and no `context`
20
+ or `schema` field is emitted. Root mapping:
21
+ `{{wikisRoot}}/` maps from structured `codegraph`, `business`, and `product` knowledge;
22
+ `{{guidesRoot}}/` maps from `architecture`, `sop`, `faq`, `decision`, and `incident`;
23
+ `{{rulesRoot}}/` maps from `standards` and `test`; `{{featsRoot}}/` maps from `feats`. Treat
24
+ `{{wikisRoot}}/` as the entity-and-relationship layer; guides and rules may
25
+ explain or constrain that layer. Other selected OKF root indexes are generated
26
+ unless the template supplies them.
30
27
 
31
28
  ## Included Knowledge
32
29