@sanqianx/project-knowledge 5.0.16-rc.5 → 5.0.16-rc.6

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.
@@ -9,7 +9,7 @@
9
9
  "plugins": [
10
10
  {
11
11
  "name": "project-knowledge",
12
- "version": "5.0.16-rc.5",
12
+ "version": "5.0.16-rc.6",
13
13
  "source": "./plugins/project-knowledge",
14
14
  "description": "Search durable project decisions and implementation history through MCP."
15
15
  }
package/CHANGELOG.md CHANGED
@@ -1,5 +1,12 @@
1
1
  # Changelog
2
2
 
3
+ ## [5.0.16-rc.6] - 2026-10-15
4
+
5
+ - 修复 Codex 0.137 将 scoped npm 目录中的 `@` 误作 Git ref:本地目录含 `@` 时从该目录执行 `marketplace add .`,更换和回退分别使用自己的工作目录,不复制目录、不访问 GitHub。
6
+ - CLI 子操作日志关联原操作 ID,允许继续处理的失败仍记录安全诊断;本地路径误判保留 `CODEX_LOCAL_SOURCE_REF`,不写入原始 CLI 输出。
7
+ - 保留 rc.5 的已验证四模块版本、索引与知识功能。rc.5 本机保真升级已通过:7 项目、43 历史文件、565 索引文件保留;真实记忆闭环与双 Node 浏览器门禁通过,热查询 P95 为 693ms(1000 文档合成语料)。
8
+ - 本机 Codex 已通过原生本地市场操作恢复,MCP 声明入口 initialize/六工具/resolve/search/get 验证通过;Hook 尚待用户审核,不计自动上下文通过。候选不更新 latest。
9
+
3
10
  ## [5.0.16-rc.5] - 2026-10-15
4
11
 
5
12
  - 精确锁定 Workbench 0.13.2-rc.13:模型目录加载失败不再伪装成空目录;保留上次有效结果,提供明确错误与重试,打开菜单可恢复请求,关闭菜单后的迟到响应不会重开菜单。保存或删除供应商后不复用保存前的旧快照,普通菜单打开仍共享请求。
@@ -0,0 +1,186 @@
1
+ 'use strict';
2
+ // Red-first regression (Q7): Codex CLI 0.137 rejects
3
+ // `plugin marketplace add <SOURCE>` with
4
+ // "Error: --ref is only supported for git marketplace sources"
5
+ // whenever the SOURCE string contains '@', which every scoped npm root
6
+ // (node_modules/@sanqianx/project-knowledge) does. Running the same add from
7
+ // the package directory's own cwd with SOURCE '.' avoids the '@' entirely.
8
+ // ensureCodexMarketplace() must use that form for the target add and for the
9
+ // rollback re-add of a previous scoped root, while non-'@' absolute paths keep
10
+ // the original invocation and third-party same-name sources stay untouched.
11
+ const assert = require('node:assert/strict');
12
+ const fs = require('node:fs');
13
+ const os = require('node:os');
14
+ const path = require('node:path');
15
+ const { IntegrationManager } = require('../lib/integration-installer');
16
+
17
+ const TEMP_BASE = fs.mkdtempSync(path.join(os.tmpdir(), 'codex-marketplace-scoped-path-'));
18
+ const TEST_HOME = path.join(TEMP_BASE, 'home');
19
+ const MARKETPLACE = 'project-knowledge';
20
+ const REF_ERROR = 'Error: --ref is only supported for git marketplace sources';
21
+ const NEW_ROOT = path.join(TEMP_BASE, 'new-root', '@sanqianx', 'project-knowledge');
22
+ const OLD_ROOT = path.join(TEMP_BASE, 'old-root', '@sanqianx-previous', 'project-knowledge');
23
+ const PLAIN_ROOT = path.join(TEMP_BASE, 'plain-root', 'project-knowledge');
24
+ const THIRD_PARTY_ROOT = path.join(TEMP_BASE, 'third-party', 'marketplace');
25
+
26
+ function writePackage(directory, name, version) {
27
+ fs.mkdirSync(directory, { recursive: true });
28
+ fs.writeFileSync(path.join(directory, 'package.json'), JSON.stringify({ name, version }, null, 2));
29
+ }
30
+
31
+ // Native-style in-memory codex CLI mirroring 0.137 marketplace semantics:
32
+ // a marketplace add SOURCE containing '@' is parsed as <repo>@<ref> and
33
+ // rejected; SOURCE '.' resolves against runnerOptions.cwd.
34
+ function createCodexCli() {
35
+ const state = { marketplaces: new Map(), calls: [], addCalls: [], removeCalls: [], failAddDirs: new Set() };
36
+ const runner = (command, args, runnerOptions = {}) => {
37
+ state.calls.push({ command, args: [...args], cwd: runnerOptions.cwd || null });
38
+ if (args[0] !== 'plugin' || args[1] !== 'marketplace') {
39
+ return { status: 1, stdout: '', stderr: `fake codex CLI: unsupported command: ${args.join(' ')}` };
40
+ }
41
+ if (args[2] === 'list') {
42
+ const lines = [...state.marketplaces].map(([name, source]) => `${name} ${source}`);
43
+ return { status: 0, stdout: lines.length ? `${lines.join('\n')}\n` : '', stderr: '' };
44
+ }
45
+ if (args[2] === 'remove') {
46
+ state.marketplaces.delete(args[3]);
47
+ state.removeCalls.push(args[3]);
48
+ return { status: 0, stdout: '', stderr: '' };
49
+ }
50
+ if (args[2] === 'add') {
51
+ const source = String(args[3]);
52
+ const resolved = path.resolve(String(runnerOptions.cwd || process.cwd()), source);
53
+ state.addCalls.push({ source, cwd: runnerOptions.cwd || null, resolved });
54
+ if (source.includes('@')) return { status: 1, stdout: '', stderr: REF_ERROR };
55
+ if (state.failAddDirs.has(resolved)) return { status: 1, stdout: '', stderr: 'forced marketplace add failure (test)' };
56
+ let stat = null;
57
+ try { stat = fs.statSync(resolved); } catch { /* missing source handled below */ }
58
+ if (!stat || !stat.isDirectory()) return { status: 1, stdout: '', stderr: `Error: marketplace source not found: ${source}` };
59
+ state.marketplaces.set(MARKETPLACE, resolved);
60
+ return { status: 0, stdout: '', stderr: '' };
61
+ }
62
+ return { status: 1, stdout: '', stderr: `fake codex CLI: unsupported marketplace command: ${args.join(' ')}` };
63
+ };
64
+ return { runner, state };
65
+ }
66
+
67
+ function createManager(cli, rootDir) {
68
+ return new IntegrationManager({
69
+ rootDir,
70
+ homeDir: TEST_HOME,
71
+ bridgeHomeDir: path.join(TEMP_BASE, 'bridge'),
72
+ env: {},
73
+ commandResolver: name => `fake-${name}`,
74
+ runner: cli.runner,
75
+ });
76
+ }
77
+
78
+ function registeredSource(cli) {
79
+ const line = [...cli.state.marketplaces].map(([name, source]) => `${name} ${source}`)
80
+ .find(item => item.startsWith(`${MARKETPLACE} `));
81
+ return line ? line.slice(MARKETPLACE.length).trim() : null;
82
+ }
83
+
84
+ function lastAdd(cli) {
85
+ assert.ok(cli.state.addCalls.length, 'expected at least one marketplace add call');
86
+ return cli.state.addCalls[cli.state.addCalls.length - 1];
87
+ }
88
+
89
+ function assertDotAdd(add, expectedRoot, label) {
90
+ assert.equal(add.source, '.', `${label}: scoped root must be added via the "." source, not an "@"-containing path`);
91
+ assert.equal(path.resolve(add.cwd || ''), expectedRoot, `${label}: "." must resolve against the package directory's own cwd`);
92
+ }
93
+
94
+ function main() {
95
+ writePackage(NEW_ROOT, '@sanqianx/project-knowledge', '5.0.16');
96
+ writePackage(OLD_ROOT, '@sanqianx/project-knowledge', '5.0.15');
97
+ writePackage(PLAIN_ROOT, '@sanqianx/project-knowledge', '5.0.16');
98
+ writePackage(THIRD_PARTY_ROOT, 'third-party-market', '1.0.0');
99
+
100
+ const results = [];
101
+ const scenario = (name, fn) => {
102
+ try { fn(); results.push({ name, ok: true }); }
103
+ catch (error) { results.push({ name, ok: false, error: String((error && error.message) || error) }); }
104
+ };
105
+
106
+ scenario('fresh: scoped npm root installs via "." from its own cwd', () => {
107
+ const cli = createCodexCli();
108
+ createManager(cli, NEW_ROOT).ensureCodexMarketplace();
109
+ assert.equal(registeredSource(cli), NEW_ROOT, 'fresh install must register the scoped npm root');
110
+ assertDotAdd(lastAdd(cli), NEW_ROOT, 'fresh install');
111
+ assert.equal(cli.state.removeCalls.length, 0, 'fresh install must not remove anything');
112
+ });
113
+
114
+ scenario('switch: replacing a previous scoped root registers the new root', () => {
115
+ const cli = createCodexCli();
116
+ cli.state.marketplaces.set(MARKETPLACE, OLD_ROOT);
117
+ createManager(cli, NEW_ROOT).ensureCodexMarketplace();
118
+ assert.ok(cli.state.removeCalls.includes(MARKETPLACE), 'switch must remove the previous marketplace first');
119
+ assert.equal(registeredSource(cli), NEW_ROOT, 'switch must end registered on the new scoped root');
120
+ assertDotAdd(lastAdd(cli), NEW_ROOT, 'switch');
121
+ assert.ok(cli.state.addCalls.every(add => !add.source.includes('@')), 'no add may pass an "@"-containing source');
122
+ });
123
+
124
+ scenario('rollback: failed switch restores the old scoped root', () => {
125
+ const cli = createCodexCli();
126
+ cli.state.marketplaces.set(MARKETPLACE, OLD_ROOT);
127
+ cli.state.failAddDirs.add(NEW_ROOT);
128
+ assert.throws(() => createManager(cli, NEW_ROOT).ensureCodexMarketplace(), /已恢复原市场来源/);
129
+ assert.equal(registeredSource(cli), OLD_ROOT, 'rollback must restore the previous scoped root');
130
+ assertDotAdd(lastAdd(cli), OLD_ROOT, 'rollback');
131
+ assert.ok(cli.state.addCalls.every(add => !add.source.includes('@')), 'rollback add must also avoid "@" in the source');
132
+ });
133
+
134
+ scenario('plain path: non-"@" absolute source keeps the original invocation', () => {
135
+ const cli = createCodexCli();
136
+ createManager(cli, PLAIN_ROOT).ensureCodexMarketplace();
137
+ assert.equal(registeredSource(cli), PLAIN_ROOT);
138
+ const add = lastAdd(cli);
139
+ assert.equal(add.source, PLAIN_ROOT, 'non-scoped absolute path must keep being passed as the add source');
140
+ assert.notEqual(add.source, '.', 'the "." form is reserved for "@"-containing paths');
141
+ });
142
+
143
+ scenario('third-party: same-name marketplace is never overwritten', () => {
144
+ const cli = createCodexCli();
145
+ cli.state.marketplaces.set(MARKETPLACE, THIRD_PARTY_ROOT);
146
+ assert.throws(() => createManager(cli, NEW_ROOT).ensureCodexMarketplace(), /未覆盖第三方来源/);
147
+ assert.equal(cli.state.addCalls.length, 0, 'third-party source must not be replaced');
148
+ assert.equal(cli.state.removeCalls.length, 0, 'third-party source must not be removed');
149
+ assert.equal(registeredSource(cli), THIRD_PARTY_ROOT, 'third-party registration must be untouched');
150
+ });
151
+
152
+ scenario('allowed failure keeps operation linkage and a safe diagnostic code', () => {
153
+ const cli = createCodexCli();
154
+ const logs = [];
155
+ const manager = createManager(cli, NEW_ROOT);
156
+ manager.operationId = 'op-native-source-test';
157
+ manager.logger = Object.fromEntries(['info', 'warn', 'error'].map(level => [level, (event, message, meta) => logs.push({ event, message, meta })]));
158
+ manager.execute('codex', ['plugin', 'marketplace', 'add', NEW_ROOT], { allowFailure: true });
159
+ const failure = logs.find(log => log.event === 'integration.command_failed');
160
+ assert.ok(failure, 'a tolerated CLI failure must not be logged as success');
161
+ assert.equal(failure.meta.operationId, 'op-native-source-test');
162
+ assert.equal(failure.meta.error.code, 'CODEX_LOCAL_SOURCE_REF');
163
+ assert.equal(failure.meta.context.status, 1);
164
+ assert.ok(!JSON.stringify(logs).includes(REF_ERROR), 'never save raw CLI output');
165
+ });
166
+
167
+ assert.equal(path.dirname(TEMP_BASE), path.resolve(os.tmpdir()));
168
+ assert.equal(fs.lstatSync(TEMP_BASE).isSymbolicLink(), false);
169
+ fs.rmSync(TEMP_BASE, { recursive: true, force: true, maxRetries: 5, retryDelay: 100 });
170
+
171
+ const failed = results.filter(item => !item.ok);
172
+ for (const item of results) console.log(`${item.ok ? 'PASS' : 'FAIL'} ${item.name}${item.ok ? '' : ` :: ${item.error}`}`);
173
+ if (failed.length) {
174
+ console.error(`codex-marketplace-scoped-path-test: ${failed.length} of ${results.length} case(s) failed.`);
175
+ process.exitCode = 1;
176
+ return;
177
+ }
178
+ console.log('codex-marketplace-scoped-path-test passed.');
179
+ }
180
+
181
+ try {
182
+ main();
183
+ } catch (error) {
184
+ console.error(error);
185
+ process.exitCode = 1;
186
+ }
@@ -436,7 +436,7 @@ class IntegrationManager {
436
436
 
437
437
  log(level, event, message, input = {}) {
438
438
  if (!this.logger || typeof this.logger[level] !== 'function') return;
439
- Promise.resolve(this.logger[level](event, message, { component: 'integration-manager', ...input })).catch(() => {
439
+ Promise.resolve(this.logger[level](event, message, { component: 'integration-manager', operationId: this.operationId, ...input })).catch(() => {
440
440
  try { process.stderr.write(`[integration-manager logger fallback] ${event}\n`); } catch {
441
441
  // stderr is the final non-recursive observer fallback.
442
442
  }
@@ -638,19 +638,29 @@ class IntegrationManager {
638
638
  }
639
639
  const result = this.runner(command, args, {
640
640
  env: this.env,
641
- cwd: this.rootDir,
641
+ cwd: options.cwd || this.rootDir,
642
642
  timeout: options.timeout,
643
643
  });
644
644
  if (result.error) {
645
645
  this.log('error', 'integration.command_failed', 'Integration CLI command failed.', { durationMs: Date.now() - startedAt, error: Object.assign(new Error('Integration CLI command failed.'), { code: result.error.code || 'INTEGRATION_COMMAND_FAILED' }), context: { client, argsHash } });
646
646
  throw result.error;
647
647
  }
648
+ const localRefFailure = client === 'codex' && String(result.stderr || '').trim() === 'Error: --ref is only supported for git marketplace sources';
648
649
  if (result.status !== 0 && !options.allowFailure) {
649
650
  const detail = String(result.stderr || result.stdout || '').trim();
650
- this.log('error', 'integration.command_failed', 'Integration CLI command failed.', { durationMs: Date.now() - startedAt, error: Object.assign(new Error('Integration CLI command failed.'), { code: 'INTEGRATION_COMMAND_FAILED' }), context: { client, status: result.status, argsHash, outputHash: `sha256:${crypto.createHash('sha256').update(detail, 'utf8').digest('hex')}` } });
651
+ this.log('error', 'integration.command_failed', 'Integration CLI command failed.', { durationMs: Date.now() - startedAt, error: Object.assign(new Error('Integration CLI command failed.'), { code: localRefFailure ? 'CODEX_LOCAL_SOURCE_REF' : 'INTEGRATION_COMMAND_FAILED' }), context: { client, status: result.status, argsHash, outputHash: `sha256:${crypto.createHash('sha256').update(detail, 'utf8').digest('hex')}` } });
651
652
  throw new Error(detail || `${CLIENT_LABELS[client]} command failed with exit code ${result.status}`);
652
653
  }
653
- this.log('info', 'integration.command_completed', 'Integration CLI command completed.', { durationMs: Date.now() - startedAt, context: { client, status: result.status, argsHash } });
654
+ const completed = result.status === 0;
655
+ const safeError = completed ? undefined : Object.assign(new Error(localRefFailure
656
+ ? 'Codex 把本地目录中的 @ 误当作 Git ref;请使用目录内相对路径重试。'
657
+ : 'Integration CLI command returned a failure.'), {
658
+ code: localRefFailure ? 'CODEX_LOCAL_SOURCE_REF' : 'INTEGRATION_COMMAND_FAILED',
659
+ });
660
+ this.log(completed ? 'info' : 'warn', completed ? 'integration.command_completed' : 'integration.command_failed', completed ? 'Integration CLI command completed.' : 'Integration CLI command returned a failure.', {
661
+ durationMs: Date.now() - startedAt, error: safeError,
662
+ context: { client, status: result.status, argsHash },
663
+ });
654
664
  return result;
655
665
  }
656
666
 
@@ -718,6 +728,16 @@ class IntegrationManager {
718
728
  this.execute('claude', ['plugin', 'marketplace', 'add', this.claudeMarketplaceSource]);
719
729
  }
720
730
 
731
+ addCodexMarketplaceSource(source, options = {}) {
732
+ // Codex 0.137 parses @ in an absolute npm path as a Git ref. Resolve a
733
+ // real local directory via cwd instead; rollback must use its own cwd.
734
+ let local = false;
735
+ if (path.isAbsolute(source) && source.includes('@')) {
736
+ try { local = fs.statSync(source).isDirectory(); } catch {}
737
+ }
738
+ return this.execute('codex', ['plugin', 'marketplace', 'add', local ? '.' : source], local ? { ...options, cwd: source } : options);
739
+ }
740
+
721
741
  ensureCodexMarketplace() {
722
742
  const target = path.resolve(this.codexMarketplaceAddSource);
723
743
  if (!this.dryRun) {
@@ -727,9 +747,9 @@ class IntegrationManager {
727
747
  if (path.resolve(existing).toLowerCase() === target.toLowerCase()) return;
728
748
  if (!this.isOwnCodexMarketplaceSource(existing)) throw new Error('同名 Codex 插件市场来源不是当前安装包,且无法确认属于本产品;未覆盖第三方来源。请检查 Codex 插件市场配置。');
729
749
  this.execute('codex', ['plugin', 'marketplace', 'remove', MARKETPLACE_NAME]);
730
- const added = this.execute('codex', ['plugin', 'marketplace', 'add', target], { allowFailure: true });
750
+ const added = this.addCodexMarketplaceSource(target, { allowFailure: true });
731
751
  if (added.status !== 0) {
732
- const restored = this.execute('codex', ['plugin', 'marketplace', 'add', existing], { allowFailure: true });
752
+ const restored = this.addCodexMarketplaceSource(existing, { allowFailure: true });
733
753
  throw new Error(restored.status === 0
734
754
  ? 'Codex 插件市场更换为当前安装包失败,已恢复原市场来源;请重试接入。'
735
755
  : 'Codex 插件市场更换为当前安装包失败,恢复原市场来源也未成功;请手动检查 codex 插件市场。');
@@ -737,7 +757,7 @@ class IntegrationManager {
737
757
  return;
738
758
  }
739
759
  }
740
- this.execute('codex', ['plugin', 'marketplace', 'add', target]);
760
+ this.addCodexMarketplaceSource(target);
741
761
  }
742
762
 
743
763
  installClaude(options = {}) {
@@ -2,6 +2,14 @@
2
2
 
3
3
  ## 当前结论
4
4
 
5
+ 最新候选收敛到 `5.0.16-rc.6`,四模块仍锁定 Workbench rc.13、引擎 rc.7、vector-hub rc.8、bridge 0.7.2。修复限于 Codex 本地市场路径与关联日志;发布和安装版验收尚待执行,latest 仍为 5.0.14。
6
+
7
+ rc.5 官方安装收据 `kb-registry-product-2PqRja/registry-installation.json` 已验证。五仓库冻结回归在 Node 22/24 均通过:外壳 138、Workbench 365、vector-hub 73、bridge 30;引擎 169 通过、1 项 Windows 符号链接权限跳过。安装版正常页面、一次 503 恢复、故障和生命周期八项均通过。真实 MiniMax 记忆、流式、单/并发提交、1536 维索引及重启 10 项通过;固定留出集 Recall@5=1、MRR=0.9667,单独热查询 P95=692.9615ms。
8
+
9
+ 已通过保护备份与 npm 全局升级把本机安装为 rc.5,7 个现有项目、43 个历史文件、565 个 D 盘索引文件及配置保持不变,运行字节与官方下载包一致。首次本机客户端修复的 Codex 失败操作 `op-29b0bc154aa94f43aa2dc759cf898697` 保留:隔离原生 CLI 复现绝对路径中的 `@` 被当作 ref,目录内 `add .` 成功;随后仅通过原生命令恢复本产品市场,正常修复操作 `op-d6d22efd9e534b1f9d06cd0ba06680cb` 成功。未修改信任记录。
10
+
11
+ Codex 声明入口的真实 MCP initialize/六工具/resolve/search/get 已通过;该结果不等于 Codex 原生模型任务自动收到知识。当前 Hook 为 modified,尚未运行此模型门禁。Claude、ZCode、OpenCode 接线已完成,实际原生送达、二次开发及正式包验收仍需完成。用于实际 Codex 路径回归的 GLM 测试文件经 Leader 修正为跨平台唯一临时目录,避免共享目录清理;首次红测试保留。
12
+
5
13
  2026-10-14 开始执行本轮计划。状态:**实施中,未完成系统验收,不更新 latest**。
6
14
 
7
15
  2026-10-15 收敛到候选 `5.0.16-rc.5`,精确锁定 Workbench `0.13.2-rc.13`,其余模块保留 rc.4 的已验收运行文件。Leader 负责关键开发与交付,GLM 独立并行故障测试、回归和审查;不新增产品功能。
@@ -9,9 +9,9 @@
9
9
  "plugins/project-knowledge/hooks/codex.json": "216e03c07295606ef6ebb2c4f669ad0d790b5e7c4f3f34600488033db75e4239",
10
10
  "plugins/project-knowledge/scripts/context-hook.cjs": "da666153ad5723592cce42d25337ae649f7d93e43fab76b3c6d1263933de063f",
11
11
  "plugins/project-knowledge/scripts/mcp-launcher.cjs": "7c68830b5c73eb53ef030756a4de33987f7eab6b1a6cc15602835aac3f954893",
12
- "plugins/project-knowledge/.claude-plugin/plugin.json": "c23181cb440688eedd0a6e307ceda43a5e5553d847d4589ad14780d548b57bd3",
13
- "plugins/project-knowledge/.codex-plugin/plugin.json": "991b0a4ae85318968e96b511508cae6a359c3d936b5d5bc99105570e95b171f0",
14
- "plugins/project-knowledge/.mcp.json": "488fba785e30d53071b433bbf6339c8b4bd7733a7838c3d1e925cc4d1a86af45"
12
+ "plugins/project-knowledge/.claude-plugin/plugin.json": "3fcae0e4c576273eb1b92d6e5445a63c70e4c7a47d3f39e5c4d2cd7b9f8fa54c",
13
+ "plugins/project-knowledge/.codex-plugin/plugin.json": "f310840f564417ea12a1d510fce4ab672a6679aa30a0eb5b767b830cfc9995df",
14
+ "plugins/project-knowledge/.mcp.json": "807e061ce4bf14353ae35a95a282f01384828f36832b93c65513643b133669aa"
15
15
  },
16
16
  "modules": {
17
17
  "terminal": {
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@sanqianx/project-knowledge",
3
- "version": "5.0.16-rc.5",
3
+ "version": "5.0.16-rc.6",
4
4
  "description": "Knowledge base manager with Git integration, AI-driven analysis, and bilingual (zh-CN/en-US) knowledge output",
5
5
  "main": "_site/server.js",
6
6
  "scripts": {
@@ -2,7 +2,7 @@
2
2
  "$schema": "https://json.schemastore.org/claude-code-plugin-manifest.json",
3
3
  "name": "project-knowledge",
4
4
  "hooks": "./hooks/claude.json",
5
- "version": "5.0.16-rc.5",
5
+ "version": "5.0.16-rc.6",
6
6
  "description": "Read durable project decisions and implementation history from Project Knowledge.",
7
7
  "author": {
8
8
  "name": "SanQianX",
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "project-knowledge",
3
- "version": "5.0.16-rc.5",
3
+ "version": "5.0.16-rc.6",
4
4
  "description": "Read durable project decisions and implementation history from Project Knowledge.",
5
5
  "author": {
6
6
  "name": "SanQianX",
@@ -8,7 +8,7 @@
8
8
  "const fs=require('fs'),path=require('path'),os=require('os');const PKG='@sanqianx/project-knowledge',SC='project-knowledge/integration-runtime/v1';let f='';const root=process.env.CLAUDE_PLUGIN_ROOT||process.env.PLUGIN_ROOT;if(root){f=path.join(root,'scripts','mcp-launcher.cjs');if(!fs.existsSync(f))f=''}if(!f){const dd=process.env.KB_DATA_DIR||path.join(os.homedir(),'.project-knowledge-v5');try{const bp=path.join(dd,'integration-runtime.json');const st=fs.statSync(bp);if(st.isFile()&&st.size<=32768){const b=JSON.parse(fs.readFileSync(bp,'utf8'));if(b&&b.schema===SC&&b.packageName===PKG&&typeof b.packageRoot==='string'&&path.isAbsolute(b.packageRoot)){const c=path.join(b.packageRoot,'plugins','project-knowledge','scripts','mcp-launcher.cjs');const rr=fs.realpathSync(b.packageRoot),cr=fs.realpathSync(c);const rel=path.relative(rr,cr);if(rel&&rel!=='..'&&!rel.startsWith('..'+path.sep)&&!path.isAbsolute(rel)&&fs.statSync(cr).isFile())f=cr}}}catch(e){}}if(!f){console.error('[project-knowledge-mcp] 未能通过受信任插件根或已验证的安装绑定定位启动器,已停止;不访问网络,也不加载工作目录源码。');process.exit(127)}require(f);"
9
9
  ],
10
10
  "env": {
11
- "KB_PLUGIN_VERSION": "5.0.16-rc.5"
11
+ "KB_PLUGIN_VERSION": "5.0.16-rc.6"
12
12
  }
13
13
  }
14
14
  }