@createsomething/ground-mcp 0.3.2 → 0.3.4

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
@@ -48,27 +48,64 @@ safe to run from a package inside a monorepo.
48
48
 
49
49
  ### Diff coverage
50
50
 
51
- `ground diff` determines analyzability from the requested checks. Its current
52
- duplicate and orphan checks cover TypeScript, JavaScript, and `.mjs` source
53
- paths. The legacy `changed_files` and `changed_file_list` fields continue to
54
- describe only analyzable source files. Use the added
55
- `discovered_changed_files`, `analyzable_changed_files`, and
56
- `excluded_changed_files` fields to see the full Git change scope and why a path
57
- was not analyzed, including `unsupported_by_requested_checks`. If no changed
58
- source is eligible, the result explicitly says so; it does not describe
59
- excluded files as clean.
60
-
61
- For promotion evidence, inspect `check_coverage.<check>.status`,
62
- `analyzed_changed_files`, and `excluded_changed_files`. Ground 0.3.2 removes
63
- `ground diff`'s silent 500-file truncation and makes source traversal
64
- deterministic and cycle-safe. Diff mode parses the complete corpus but only
65
- compares pairs involving changed files. A changed file is only listed as
66
- analyzed for a check after that check completed for the file; partial or failed
67
- analysis stays explicit in the per-check exclusions. Standalone broad duplicate
68
- scans retain their safety bound and report `scan_complete: false` when it is hit.
69
-
70
- The release package includes the native Apple Silicon binaries directly; other
71
- supported platforms download the matching verified release asset during install.
51
+ Every batch, diff, and duplicate-function response has a
52
+ `verification_status`; `ground diff` also returns the same status per requested
53
+ check in `check_coverage.<check>.status`. The contract is explicit:
54
+
55
+ - `PASS`: the check completed for the relevant supported files and found no issue.
56
+ - `FAIL`: the check found an issue or could not complete because of a read/parse failure.
57
+ - `NOT_APPLICABLE`: no changed file needs that check.
58
+ - `UNSUPPORTED`: relevant source exists, but the requested check cannot analyze its language (including Svelte duplicate-function scans).
59
+ - `TIMEOUT`: duplicate analysis reached its deadline before a complete result was available.
60
+
61
+ `ground analyze` and `ground diff` accept `--timeout-ms` (120000 by default).
62
+ The MCP equivalents accept `timeout_ms`; a deadline returns `TIMEOUT`, never a
63
+ clean result. `ground diff` includes `.mjs` with JavaScript source analysis.
64
+ Its `changed_files` and `changed_file_list` fields remain the analyzable-file
65
+ view; read `discovered_changed_files`, `analyzable_changed_files`, and
66
+ `excluded_changed_files` for the full Git scope. Per-check coverage also names
67
+ `unsupported_changed_files` and `excluded_changed_files`, so a clean claim is
68
+ valid only with `PASS`.
69
+
70
+ Ground 0.3.4 adds source-bearing entry-point evidence to orphan analysis, so
71
+ declarative Promptfoo and manual Ground configurations are recognized alongside
72
+ package scripts. It keeps `ground diff`'s complete changed-file coverage and
73
+ deterministic, cycle-safe source traversal. Diff mode parses the complete corpus
74
+ but only compares pairs involving changed files. Standalone broad duplicate scans
75
+ retain their safety bound and report a non-pass status with `scan_complete: false`
76
+ when the bound is hit.
77
+
78
+ The release package ships thin command wrappers for every platform. Install
79
+ downloads the matching versioned release asset and verifies its SHA-256 against
80
+ that release's `SHA256SUMS` manifest before extracting it. Record the artifact
81
+ that produced a receipt with:
82
+
83
+ ```bash
84
+ ground build-info --json
85
+ ```
86
+
87
+ ### Maintainers: trusted publishing
88
+
89
+ Ground tags publish through npm Trusted Publishing rather than a local
90
+ one-time-password or a long-lived write token. Configure the package's
91
+ **Trusted Publisher** in npm with:
92
+
93
+ - Provider: **GitHub Actions**
94
+ - Organization or user: `createsomethingtoday`
95
+ - Repository: `create-something-monorepo`
96
+ - Workflow filename: `ground-release.yml`
97
+ - Allowed action: **npm publish**
98
+
99
+ Do not configure an environment unless the release workflow adds one. The
100
+ workflow publishes only after its matching GitHub Release and `SHA256SUMS`
101
+ manifest have completed successfully.
102
+
103
+ If a release was built successfully but npm publication was blocked (for
104
+ example, during Trusted Publishing setup), rerun **Ground Release** manually
105
+ with its exact `ground-v<version>` tag and **publish only** enabled. That path
106
+ checks out the tag, requires it to match `package.json`, and verifies the
107
+ existing release checksum manifest before publishing; it does not rebuild or
108
+ replace GitHub Release assets.
72
109
 
73
110
  ## The Problem
74
111
 
@@ -217,7 +254,7 @@ The npm package downloads a platform-specific binary on install. If that failed:
217
254
 
218
255
  ```bash
219
256
  # Check if the binary exists
220
- ls node_modules/@createsomething/ground-mcp/bin/
257
+ ls node_modules/@createsomething/ground-mcp/bin/native/
221
258
 
222
259
  # Re-install
223
260
  npm install @createsomething/ground-mcp
@@ -363,8 +400,28 @@ Ground loads `.ground.yml` from your project root for:
363
400
  - Ignore patterns (functions, files, directories)
364
401
  - Known drift exceptions with documented reasons
365
402
  - Context declarations for intentional exclusions
403
+ - Explicit manual CLI entry points for orphan review
366
404
  - Similarity thresholds
367
405
 
406
+ Declare a documented operator CLI by exact path relative to the directory you
407
+ pass to `ground diff`. Ground keeps it in duplicate coverage, excludes it only
408
+ from orphan findings, and records `manual_entry_point` in check coverage:
409
+
410
+ ```yaml
411
+ entry_points:
412
+ manual:
413
+ - "scripts/rebuild-search-index.mjs"
414
+ ```
415
+
416
+ For `ground_find_orphans` and `ground_analyze`, orphan coverage includes
417
+ `entry_point_evidence`: the exact path, entry-point type, and source Ground used
418
+ to protect it. Alongside package, framework, test, and script entry points,
419
+ Ground recognizes exact `entry_points.manual` declarations and local
420
+ `providers[].id`, `prompts[].id`, and assertion-value `file://…` references in
421
+ `promptfooconfig*.yaml`. The Promptfoo adapter accepts only existing source
422
+ files beneath that configuration file; it does not scan arbitrary YAML or
423
+ follow parent/absolute paths.
424
+
368
425
  See [Full Documentation](https://github.com/createsomethingtoday/create-something-monorepo/tree/main/packages/ground) for configuration reference.
369
426
 
370
427
  ## Native service pilot
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+
3
+ require('./run-native').runNative('ground-mcp');
package/bin/ground.js ADDED
@@ -0,0 +1,3 @@
1
+ #!/usr/bin/env node
2
+
3
+ require('./run-native').runNative('ground');
@@ -0,0 +1 @@
1
+
@@ -0,0 +1,27 @@
1
+ const { spawnSync } = require('child_process');
2
+ const fs = require('fs');
3
+ const path = require('path');
4
+
5
+ function runNative(binaryName) {
6
+ const extension = process.platform === 'win32' ? '.exe' : '';
7
+ const binary = path.join(__dirname, 'native', `${binaryName}${extension}`);
8
+
9
+ if (!fs.existsSync(binary)) {
10
+ console.error(
11
+ `Ground MCP native binary is unavailable at ${binary}. Reinstall @createsomething/ground-mcp to complete the verified release-asset download.`
12
+ );
13
+ process.exitCode = 1;
14
+ return;
15
+ }
16
+
17
+ const result = spawnSync(binary, process.argv.slice(2), { stdio: 'inherit' });
18
+ if (result.error) {
19
+ console.error(`Ground MCP could not start ${binaryName}: ${result.error.message}`);
20
+ process.exitCode = 1;
21
+ return;
22
+ }
23
+
24
+ process.exitCode = result.status ?? 1;
25
+ }
26
+
27
+ module.exports = { runNative };
package/install.js CHANGED
@@ -7,10 +7,10 @@
7
7
  */
8
8
 
9
9
  const { execSync } = require('child_process');
10
+ const { createHash } = require('crypto');
10
11
  const fs = require('fs');
11
12
  const https = require('https');
12
13
  const path = require('path');
13
- const zlib = require('zlib');
14
14
 
15
15
  const REPO = 'createsomethingtoday/create-something-monorepo';
16
16
  const VERSION = require('./package.json').version;
@@ -51,20 +51,24 @@ function getDownloadUrl(binaryName, platform = process.platform) {
51
51
  return `https://github.com/${REPO}/releases/download/ground-v${VERSION}/ground-${binaryName}.${ext}`;
52
52
  }
53
53
 
54
- function hasBundledNativeBinaries() {
55
- // The npm artifact includes a release-built Apple Silicon bootstrap pair.
56
- // Other platforms continue through the release-asset downloader below.
57
- if (getPlatformKey() !== 'darwin-arm64') return false;
58
-
59
- const binDir = path.join(__dirname, 'bin');
60
- return ['ground', 'ground-mcp'].every((name) => {
61
- const binary = path.join(binDir, name);
62
- try {
63
- return fs.statSync(binary).isFile() && (fs.statSync(binary).mode & 0o111) !== 0;
64
- } catch {
65
- return false;
66
- }
67
- });
54
+ function getChecksumsUrl() {
55
+ return `https://github.com/${REPO}/releases/download/ground-v${VERSION}/SHA256SUMS`;
56
+ }
57
+
58
+ function verifyArchiveIntegrity(archive, assetName, checksums) {
59
+ const expected = checksums
60
+ .split(/\r?\n/)
61
+ .map((line) => line.trim().match(/^([a-f0-9]{64})\s+\*?(.+)$/i))
62
+ .find((match) => match?.[2] === assetName)?.[1];
63
+
64
+ if (!expected) {
65
+ throw new Error(`Release checksum manifest does not contain a checksum for ${assetName}`);
66
+ }
67
+
68
+ const actual = createHash('sha256').update(archive).digest('hex');
69
+ if (actual !== expected.toLowerCase()) {
70
+ throw new Error(`Release checksum mismatch for ${assetName}`);
71
+ }
68
72
  }
69
73
 
70
74
  async function download(url) {
@@ -119,16 +123,11 @@ async function install() {
119
123
  return;
120
124
  }
121
125
 
122
- if (hasBundledNativeBinaries()) {
123
- console.log('Ground MCP: Using bundled darwin-arm64 binaries');
124
- return;
125
- }
126
-
127
126
  console.log('Ground MCP: Installing binary...');
128
127
 
129
128
  const binaryName = getBinaryName();
130
129
  const url = getDownloadUrl(binaryName);
131
- const binDir = path.join(__dirname, 'bin');
130
+ const binDir = path.join(__dirname, 'bin', 'native');
132
131
 
133
132
  console.log(`Platform: ${getPlatformKey()}`);
134
133
  console.log(`Downloading: ${url}`);
@@ -141,6 +140,8 @@ async function install() {
141
140
 
142
141
  // Download archive
143
142
  const buffer = await download(url);
143
+ const checksums = await download(getChecksumsUrl());
144
+ verifyArchiveIntegrity(buffer, path.basename(url), checksums.toString('utf8'));
144
145
  console.log(`Downloaded ${(buffer.length / 1024 / 1024).toFixed(2)} MB`);
145
146
 
146
147
  // Extract based on platform
@@ -203,5 +204,8 @@ if (require.main === module) {
203
204
  }
204
205
 
205
206
  module.exports = {
207
+ download,
206
208
  getDownloadUrl,
209
+ getChecksumsUrl,
210
+ verifyArchiveIntegrity,
207
211
  };
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@createsomething/ground-mcp",
3
- "version": "0.3.2",
3
+ "version": "0.3.4",
4
4
  "description": "Grounded claims for code. MCP server that prevents AI hallucination in code analysis.",
5
5
  "author": "CREATE SOMETHING <hello@createsomething.io>",
6
6
  "license": "MIT",
@@ -48,11 +48,12 @@
48
48
  "css-analysis"
49
49
  ],
50
50
  "bin": {
51
- "ground": "bin/ground",
52
- "ground-mcp": "bin/ground-mcp"
51
+ "ground": "bin/ground.js",
52
+ "ground-mcp": "bin/ground-mcp.js"
53
53
  },
54
54
  "scripts": {
55
55
  "postinstall": "node install.js",
56
+ "prepublishOnly": "node release-verify.js",
56
57
  "pilot:build": "cargo build --release --manifest-path ../Cargo.toml --bin ground --bin ground-mcp",
57
58
  "pilot:benchmark": "tsx pilot/benchmark.ts",
58
59
  "pilot:check": "tsc --noEmit -p pilot/tsconfig.json",
@@ -61,7 +62,7 @@
61
62
  "pilot:verify": "pnpm run pilot:check && pnpm run pilot:test && pnpm run pilot:benchmark && pnpm run pilot:receipt:validate -- pilot/evidence/ground-native-benchmark-receipt.v1.json"
62
63
  },
63
64
  "devDependencies": {
64
- "@modelcontextprotocol/sdk": "^1.25.3",
65
+ "@modelcontextprotocol/sdk": "^1.26.0",
65
66
  "@types/node": "^24.10.9",
66
67
  "ajv": "^8.17.1",
67
68
  "tsx": "^4.21.0",
package/bin/.gitkeep DELETED
@@ -1,4 +0,0 @@
1
- # Binary files are downloaded during npm install
2
- # This directory will contain:
3
- # - ground-mcp (or ground-mcp.exe on Windows)
4
- # - ground (or ground.exe on Windows)
package/bin/ground DELETED
Binary file
package/bin/ground-mcp DELETED
Binary file