@getmarrow/install 0.1.3 → 0.1.5

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 CHANGED
@@ -11,8 +11,9 @@ npx @getmarrow/install --repair
11
11
  npx @getmarrow/install doctor
12
12
  ```
13
13
 
14
- ## What's New in v0.1.3
14
+ ## What's New in v0.1.4
15
15
 
16
+ - Installer self-test now finishes with a first-value summary: Marrow active state, captured surfaces, first useful lesson, value proof, and exact next action.
16
17
  - Generated SDK passive runtime enables one-call agent runtime checks by default with `MARROW_AGENT_RUNTIME=true`.
17
18
  - Self-test now verifies the runtime endpoint in addition to creating a harmless decision and committing its outcome.
18
19
  - `--repair` keeps dry-run behavior safe when `--dry-run` is present and reports whether one-call runtime was verified.
@@ -50,7 +51,7 @@ npx @getmarrow/install --md --dry-run
50
51
 
51
52
  ## Self-Test
52
53
 
53
- When `MARROW_API_KEY` is present, the installer creates a harmless test decision, commits the outcome, and reads `/v1/agent/status`.
54
+ When `MARROW_API_KEY` is present, the installer creates a harmless test decision, commits the outcome, reads `/v1/agent/status`, calls the one-call runtime, and prints the first useful Marrow signal.
54
55
 
55
56
  ```bash
56
57
  MARROW_API_KEY=mrw_live_xxx npx @getmarrow/install --yes
@@ -77,3 +78,12 @@ MARROW_API_KEY=mrw_live_xxx npx @getmarrow/install --repair
77
78
  ## Trust Model
78
79
 
79
80
  This package is intended to be open source and auditable. It prints every file it will touch, requires `--yes` to write, does not store API keys in project files, and supports MCP-only, SDK-only, both, and markdown-only setups.
81
+
82
+ ---
83
+
84
+ ## Related Packages
85
+
86
+ - **[@getmarrow/sdk](https://www.npmjs.com/package/@getmarrow/sdk)** — TypeScript/Node.js SDK for custom agent integrations, passive runtime hooks, guarded actions, and direct API access.
87
+ - **[@getmarrow/mcp](https://www.npmjs.com/package/@getmarrow/mcp)** — MCP server for Claude Code, Claude Desktop, Cursor, and other MCP-compatible clients.
88
+
89
+ **Docs:** [https://getmarrow.ai/docs](https://getmarrow.ai/docs)
@@ -0,0 +1,9 @@
1
+ #!/usr/bin/env node
2
+
3
+ const { runCli } = require('../src/installer');
4
+
5
+ runCli(process.argv.slice(2)).catch((error) => {
6
+ const message = error instanceof Error ? error.message : String(error);
7
+ process.stderr.write(`marrow-install failed: ${message}\n`);
8
+ process.exit(1);
9
+ });
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@getmarrow/install",
3
- "version": "0.1.3",
3
+ "version": "0.1.5",
4
4
  "description": "Universal installer for Marrow passive agent setup.",
5
5
  "bin": {
6
6
  "marrow-install": "bin/marrow-install.js"
package/src/installer.js CHANGED
@@ -453,6 +453,12 @@ async function runSelfTest(options) {
453
453
  ok: false,
454
454
  error: error instanceof Error ? error.message : String(error),
455
455
  }));
456
+ const performance = await requestJson(`${baseUrl}/v1/analytics/agent-performance?period=7`, { headers })
457
+ .catch((error) => ({
458
+ ok: false,
459
+ error: error instanceof Error ? error.message : String(error),
460
+ }));
461
+ const firstValueSignal = buildFirstValueSignal(status, runtime, performance);
456
462
  return {
457
463
  skipped: false,
458
464
  decision_id: decisionId,
@@ -465,6 +471,50 @@ async function runSelfTest(options) {
465
471
  runtime_active: Boolean(runtime && runtime.ok !== false),
466
472
  runtime_exact_next_action: runtime.exact_next_action || null,
467
473
  runtime_before_you_act: runtime.before_you_act || null,
474
+ first_value_signal: firstValueSignal,
475
+ performance_proof: performance && performance.ok !== false ? {
476
+ avoided_mistakes: performance.avoided_mistakes ?? performance.avoided_repeated_mistakes ?? 0,
477
+ reused_winning_decisions: performance.reused_winning_decisions ?? 0,
478
+ prevented_bad_actions: performance.prevented_bad_actions ?? 0,
479
+ estimated_tokens_saved: performance.token_time_saved_estimate?.estimated_tokens_saved ?? 0,
480
+ estimated_minutes_saved: performance.token_time_saved_estimate?.estimated_minutes_saved ?? 0,
481
+ reliability_score: performance.agent_reliability_score ?? null,
482
+ } : null,
483
+ };
484
+ }
485
+
486
+ function buildFirstValueSignal(status, runtime, performance) {
487
+ const capture = status.capture_coverage || {};
488
+ const closure = status.auto_outcome_closure || {};
489
+ const captured = [];
490
+ if (status.enabled || capture.decisions) captured.push('decisions');
491
+ if (capture.tools === 'detected') captured.push('tools');
492
+ if (capture.commands === 'detected') captured.push('commands');
493
+ if (capture.deploys === 'detected') captured.push('deploys');
494
+ if (capture.publishes === 'detected') captured.push('publishes');
495
+ if (closure.state) captured.push(`outcomes:${closure.state}`);
496
+
497
+ const proof = performance && performance.ok !== false ? performance : {};
498
+ const proofBits = [];
499
+ if (Number(proof.avoided_mistakes || proof.avoided_repeated_mistakes || 0) > 0) proofBits.push(`${proof.avoided_mistakes || proof.avoided_repeated_mistakes} avoided mistake(s)`);
500
+ if (Number(proof.reused_winning_decisions || 0) > 0) proofBits.push(`${proof.reused_winning_decisions} reused winning decision(s)`);
501
+ if (Number(proof.prevented_bad_actions || 0) > 0) proofBits.push(`${proof.prevented_bad_actions} prevented risky action(s)`);
502
+ const tokens = proof.token_time_saved_estimate?.estimated_tokens_saved || 0;
503
+ if (tokens > 0) proofBits.push(`~${tokens} tokens saved`);
504
+
505
+ const firstLesson = runtime.before_you_act
506
+ || runtime.before_you_act_injection?.message
507
+ || runtime.exact_next_action
508
+ || status.recommended_fix
509
+ || 'Marrow will surface prior lessons before risky or repeated work.';
510
+
511
+ return {
512
+ active: Boolean(status.enabled ?? status.ok),
513
+ headline: `Marrow active: ${captured.length ? captured.join(', ') : 'decisions'} captured.`,
514
+ captured,
515
+ first_lesson: firstLesson,
516
+ value_proof: proofBits,
517
+ next_action: runtime.exact_next_action || status.next_action || 'Keep working; Marrow will capture outcomes and reuse lessons automatically.',
468
518
  };
469
519
  }
470
520
 
@@ -495,6 +545,15 @@ function printReport(report) {
495
545
  process.stdout.write(`- health: ${report.selfTest.health || 'unknown'}\n`);
496
546
  process.stdout.write(`- one-call runtime: ${report.selfTest.runtime_active ? 'active' : 'not verified'}\n`);
497
547
  if (report.selfTest.next_action) process.stdout.write(`- next action: ${report.selfTest.next_action}\n`);
548
+ if (report.selfTest.first_value_signal) {
549
+ process.stdout.write('\nFirst value:\n');
550
+ process.stdout.write(`- ${report.selfTest.first_value_signal.headline}\n`);
551
+ process.stdout.write(`- First useful lesson: ${report.selfTest.first_value_signal.first_lesson}\n`);
552
+ if (report.selfTest.first_value_signal.value_proof.length) {
553
+ process.stdout.write(`- Proof: ${report.selfTest.first_value_signal.value_proof.join('; ')}\n`);
554
+ }
555
+ process.stdout.write(`- Next: ${report.selfTest.first_value_signal.next_action}\n`);
556
+ }
498
557
  }
499
558
 
500
559
  if (report.remediation) {