mirror of
https://github.com/DeusData/codebase-memory-mcp.git
synced 2026-11-06 17:49:47 +00:00
v0.12.0 could not be installed through npm, pnpm, pip or the Go wrapper on any platform (#2657): each wrapper refused an archive member above 256 MiB, and every v0.12.0 binary is 331-335 MB. The v0.11.0 binaries were already about 300 MB, so the Go wrapper, which has had the cap since v0.10.0, was broken before; npm and PyPI gained it in v0.12.0. The archive is verified against the release's checksums.txt before it is unpacked, so a byte cap only ever refused what we ship. - npm, PyPI, Go: delete every byte-size cap (compressed archive, per member, aggregate, checksum manifest, download size). The checksum, the exact member set, path and link refusal, the member count, HTTPS and the --version check stay. - All three honour CBM_DOWNLOAD_URL like install.sh, for testing: https, or plain http to an exact loopback authority with no proxy and no redirect. - Smoke: scripts/smoke-wrappers.sh installs the three wrappers from the checkout against the release fixture and runs the binary each one installed. smoke-test.sh Phase 13w runs it; SMOKE_REQUIRE_WRAPPERS=1 makes it required on the PR smoke lanes and in the release smoke, which gates publishing. Other install paths found broken while checking every channel: - Homebrew: the formula was still at 0.10.3 and installed the dynamic Linux build, which needs glibc 2.38 (Ubuntu 22.04, Debian 12 and RHEL 9 lack it). It now installs 0.12.0 with the static -portable Linux assets and tracks the newest release in the version contract like the other surfaces. - Go: `go install .../pkg/go/cmd/codebase-memory-mcp@vX.Y.Z` never worked (no pkg/go/v* tags, so Go fetched the whole repository, over its 500 MB module limit), and @latest built main's wrapper, whose version constant lags each release. The release now also tags pkg/go/vX.Y.Z, and the wrapper installs its own module version (the constant only for local and untagged builds). - npm: a stable release also moves the `next` dist-tag to itself; `next` still pointed to 0.9.1-rc.1. - Docs: winget and Chocolatey were listed as install channels but are not published; they are removed until they are. Windows arm64 ships and is now listed. Fixes #2657. Signed-off-by: Martin Vogel <martin.vogel.tech@gmail.com>
110 lines
3.6 KiB
JavaScript
110 lines
3.6 KiB
JavaScript
'use strict';
|
|
|
|
const assert = require('node:assert/strict');
|
|
const fs = require('node:fs');
|
|
const os = require('node:os');
|
|
const path = require('node:path');
|
|
const test = require('node:test');
|
|
const vm = require('node:vm');
|
|
|
|
test('postinstall exits nonzero when installation fails', async () => {
|
|
const installPath = path.join(__dirname, '..', 'install.js');
|
|
const source = fs.readFileSync(installPath, 'utf8');
|
|
const output = { stdout: '', stderr: '' };
|
|
const observed = { exitCode: undefined };
|
|
const fakeProcess = {
|
|
// Force a deterministic failure before any filesystem or network access.
|
|
platform: 'unsupported-test-platform',
|
|
arch: 'x64',
|
|
env: {},
|
|
pid: 12345,
|
|
stdout: { write: (text) => { output.stdout += String(text); } },
|
|
stderr: { write: (text) => { output.stderr += String(text); } },
|
|
exit: (code) => { observed.exitCode = code; },
|
|
exitCode: undefined,
|
|
};
|
|
|
|
const sandbox = {
|
|
Buffer,
|
|
URL,
|
|
__dirname: path.dirname(installPath),
|
|
__filename: installPath,
|
|
clearTimeout,
|
|
console,
|
|
exports: {},
|
|
module: { exports: {} },
|
|
process: fakeProcess,
|
|
require: (specifier) => {
|
|
if (specifier === './package.json') return { version: '0.0.0-test' };
|
|
return require(specifier);
|
|
},
|
|
setTimeout,
|
|
};
|
|
|
|
vm.runInNewContext(source, sandbox, { filename: installPath });
|
|
await new Promise((resolve) => setImmediate(resolve));
|
|
|
|
const exitCode = observed.exitCode ?? fakeProcess.exitCode ?? 0;
|
|
assert.match(output.stderr, /install failed/);
|
|
assert.notEqual(
|
|
exitCode,
|
|
0,
|
|
'npm postinstall reported success after a deterministic installation failure',
|
|
);
|
|
});
|
|
|
|
test('postinstall refuses a non-loopback http CBM_DOWNLOAD_URL before any download', async () => {
|
|
const installPath = path.join(__dirname, '..', 'install.js');
|
|
const source = fs.readFileSync(installPath, 'utf8');
|
|
// A fresh package directory: no cached binary, and nothing may be created.
|
|
const packageDir = fs.mkdtempSync(path.join(os.tmpdir(), 'cbm-npm-override-test-'));
|
|
const output = { stdout: '', stderr: '' };
|
|
const observed = { exitCode: undefined };
|
|
const fakeProcess = {
|
|
platform: 'linux',
|
|
arch: 'x64',
|
|
env: { CBM_DOWNLOAD_URL: 'http://example.com/releases' },
|
|
pid: 12345,
|
|
stdout: { write: (text) => { output.stdout += String(text); } },
|
|
stderr: { write: (text) => { output.stderr += String(text); } },
|
|
exit: (code) => { observed.exitCode = code; },
|
|
exitCode: undefined,
|
|
};
|
|
const refusingTransport = {
|
|
get(url) { throw new Error(`unexpected request to ${url}`); },
|
|
};
|
|
|
|
try {
|
|
const sandbox = {
|
|
Buffer,
|
|
URL,
|
|
__dirname: packageDir,
|
|
__filename: path.join(packageDir, 'install.js'),
|
|
clearTimeout,
|
|
console,
|
|
exports: {},
|
|
module: { exports: {} },
|
|
process: fakeProcess,
|
|
require: (specifier) => {
|
|
if (specifier === './package.json') return { version: '0.0.0-test' };
|
|
if (specifier === 'https' || specifier === 'http') return refusingTransport;
|
|
return require(specifier);
|
|
},
|
|
setTimeout,
|
|
};
|
|
|
|
vm.runInNewContext(source, sandbox, { filename: installPath });
|
|
await new Promise((resolve) => setImmediate(resolve));
|
|
|
|
assert.match(
|
|
output.stderr,
|
|
/install failed .*Refusing non-HTTPS download URL \(CBM_DOWNLOAD_URL\): http:\/\/example\.com\/releases/,
|
|
);
|
|
assert.equal(observed.exitCode, 1);
|
|
assert.doesNotMatch(output.stdout, /downloading/);
|
|
assert.deepEqual(fs.readdirSync(packageDir), []);
|
|
} finally {
|
|
fs.rmSync(packageDir, { recursive: true, force: true });
|
|
}
|
|
});
|