nexarch 0.1.18 → 0.1.19

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.
@@ -4,7 +4,7 @@ import { join } from "path";
4
4
  import process from "process";
5
5
  import { requireCredentials } from "../lib/credentials.js";
6
6
  import { callMcpTool, mcpInitialize, mcpListTools } from "../lib/mcp.js";
7
- const CLI_VERSION = "0.1.18";
7
+ const CLI_VERSION = "0.1.19";
8
8
  const AGENT_ENTITY_TYPE = "agent";
9
9
  const TECH_COMPONENT_ENTITY_TYPE = "technology_component";
10
10
  function parseFlag(args, flag) {
@@ -437,28 +437,37 @@ STEP 1 — Read the project README / docs and build your understanding of:
437
437
  • What is the high-level architecture?
438
438
  • Any notable technical decisions or constraints?
439
439
 
440
- STEP 2 — Call nexarch_upsert_entities to enrich the project entity:
441
- • externalKey: "${projectExternalKey}"
442
- name: (proper product/project name from the README)
443
- description: (2–4 sentence summary of what it does and why)
444
- Preserve existing attributes, add any business context attributes you find.
445
- entityTypeCode: "${entityTypeOverride}"${entityTypeOverride === "application" ? '\n • entitySubtypeCode: "app_custom_built"' : ""}
440
+ STEP 2 — Enrich the project entity. Run this command with the description you've written:
441
+
442
+ npx nexarch update-entity \\
443
+ --key "${projectExternalKey}" \\
444
+ --entity-type "${entityTypeOverride}"${entityTypeOverride === "application" ? ' \\\n --subtype "app_custom_built"' : ""} \\
445
+ --name "<proper product name from README>" \\
446
+ --description "<2–4 sentence summary of what it does and why>"
446
447
  ${subPackages.length > 0 ? `
447
- STEP 3 — Register each sub-application as its own entity:
448
- The scanner found ${subPackages.length} workspace package(s). For each one, call
449
- nexarch_upsert_entities then nexarch_upsert_relationships to wire it to the parent.
448
+ STEP 3 — Register each sub-application as its own entity.
449
+ The scanner found ${subPackages.length} workspace package(s). For each one, read its
450
+ README / package.json description, then run:
450
451
 
451
452
  Sub-packages detected:
452
453
  ${subPackages.map((sp) => ` • ${sp.name} (${sp.relativePath})`).join("\n")}
453
454
 
454
- For each sub-package:
455
- • Read its own README / package.json description if present
456
- entityTypeCode: "application", entitySubtypeCode: "app_custom_built"
457
- externalKey: "application:<slug>" (slugify the package name)
458
- description: what this specific sub-app does
459
- Relationship: fromEntityExternalKey = "<sub-app key>",
460
- toEntityExternalKey = "${projectExternalKey}",
461
- relationshipTypeCode = "part_of"
462
- ` : ""}
463
- Once enrichment is complete, run \`nexarch graph snapshot\` to capture the updated state.`);
455
+ For each sub-package run:
456
+
457
+ npx nexarch update-entity \\
458
+ --key "application:<slugified-package-name>" \\
459
+ --entity-type "application" \\
460
+ --subtype "app_custom_built" \\
461
+ --name "<sub-app name>" \\
462
+ --description "<what this sub-app does>"
463
+
464
+ Then wire it to the parent project:
465
+
466
+ npx nexarch add-relationship \\
467
+ --from "application:<slugified-package-name>" \\
468
+ --to "${projectExternalKey}" \\
469
+ --type "part_of"
470
+
471
+ (Note: add-relationship is coming soon — skip if not yet available)
472
+ ` : ""}`);
464
473
  }
@@ -0,0 +1,84 @@
1
+ import process from "process";
2
+ import { requireCredentials } from "../lib/credentials.js";
3
+ import { callMcpTool } from "../lib/mcp.js";
4
+ function parseFlag(args, flag) {
5
+ return args.includes(flag);
6
+ }
7
+ function parseOptionValue(args, option) {
8
+ const idx = args.indexOf(option);
9
+ if (idx === -1)
10
+ return null;
11
+ const value = args[idx + 1];
12
+ if (!value || value.startsWith("--"))
13
+ return null;
14
+ return value;
15
+ }
16
+ function parseToolText(result) {
17
+ const text = result.content?.[0]?.text ?? "{}";
18
+ return JSON.parse(text);
19
+ }
20
+ export async function updateEntity(args) {
21
+ const asJson = parseFlag(args, "--json");
22
+ const externalKey = parseOptionValue(args, "--key");
23
+ const name = parseOptionValue(args, "--name");
24
+ const description = parseOptionValue(args, "--description");
25
+ const entityTypeCode = parseOptionValue(args, "--entity-type") ?? "application";
26
+ const entitySubtypeCode = parseOptionValue(args, "--subtype");
27
+ if (!externalKey) {
28
+ console.error("error: --key <externalKey> is required");
29
+ process.exit(1);
30
+ }
31
+ if (!name && !description) {
32
+ console.error("error: at least one of --name or --description is required");
33
+ process.exit(1);
34
+ }
35
+ const creds = requireCredentials();
36
+ const mcpOpts = { companyId: creds.companyId };
37
+ const policiesRaw = await callMcpTool("nexarch_get_applied_policies", {}, mcpOpts);
38
+ const policies = parseToolText(policiesRaw);
39
+ const policyBundleHash = policies.policyBundleHash ?? null;
40
+ const nowIso = new Date().toISOString();
41
+ const agentContext = {
42
+ agentId: "nexarch-cli:update-entity",
43
+ agentRunId: `update-entity-${Date.now()}`,
44
+ observedAt: nowIso,
45
+ source: "nexarch-cli",
46
+ model: "n/a",
47
+ provider: "n/a",
48
+ };
49
+ const policyContext = policyBundleHash
50
+ ? { policyBundleHash, alignmentSummary: { score: 1, violations: [], waivers: [] } }
51
+ : undefined;
52
+ const entity = {
53
+ externalKey,
54
+ entityTypeCode,
55
+ confidence: 1,
56
+ };
57
+ if (name)
58
+ entity.name = name;
59
+ if (description)
60
+ entity.description = description;
61
+ if (entitySubtypeCode)
62
+ entity.entitySubtypeCode = entitySubtypeCode;
63
+ const raw = await callMcpTool("nexarch_upsert_entities", { entities: [entity], agentContext, policyContext }, mcpOpts);
64
+ const result = parseToolText(raw);
65
+ if (asJson) {
66
+ process.stdout.write(`${JSON.stringify(result, null, 2)}\n`);
67
+ if (Number(result.summary?.failed ?? 0) > 0)
68
+ process.exitCode = 1;
69
+ return;
70
+ }
71
+ const succeeded = result.summary?.succeeded ?? 0;
72
+ const failed = result.summary?.failed ?? 0;
73
+ if (failed > 0) {
74
+ console.error(`Failed to update entity: ${externalKey}`);
75
+ for (const err of result.errors ?? []) {
76
+ console.error(` ${err.externalKey}: ${err.error} — ${err.message}`);
77
+ }
78
+ process.exitCode = 1;
79
+ return;
80
+ }
81
+ if (!asJson) {
82
+ console.log(`Updated ${succeeded} entity: ${externalKey}`);
83
+ }
84
+ }
package/dist/index.js CHANGED
@@ -11,6 +11,7 @@ import { mcpProxy } from "./commands/mcp-proxy.js";
11
11
  import { initAgent } from "./commands/init-agent.js";
12
12
  import { agentIdentify } from "./commands/agent-identify.js";
13
13
  import { initProject } from "./commands/init-project.js";
14
+ import { updateEntity } from "./commands/update-entity.js";
14
15
  const [, , command, ...args] = process.argv;
15
16
  const commands = {
16
17
  login,
@@ -22,6 +23,7 @@ const commands = {
22
23
  "init-agent": initAgent,
23
24
  "agent-identify": agentIdentify,
24
25
  "init-project": initProject,
26
+ "update-entity": updateEntity,
25
27
  };
26
28
  async function main() {
27
29
  if (command === "agent") {
@@ -78,9 +80,19 @@ Usage:
78
80
  names as reference candidates.
79
81
  Options: --dir <path> (default: cwd)
80
82
  --name <name> override project name
81
- --entity-type <code> (default: service)
83
+ --entity-type <code> (default: application)
82
84
  --dry-run preview without writing
83
85
  --json
86
+ nexarch update-entity
87
+ Update the name and/or description of an existing graph entity.
88
+ Use this after init-project to enrich the entity with meaningful
89
+ content from the project README or docs.
90
+ Options: --key <externalKey> (required)
91
+ --name <name>
92
+ --description <text>
93
+ --entity-type <code> (default: application)
94
+ --subtype <code>
95
+ --json
84
96
  `);
85
97
  process.exit(command ? 1 : 0);
86
98
  }
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "nexarch",
3
- "version": "0.1.18",
3
+ "version": "0.1.19",
4
4
  "description": "Connect AI coding tools to your Nexarch architecture workspace",
5
5
  "keywords": [
6
6
  "nexarch",