豆豆友情提示:这是一个非官方 GitHub 代理镜像,主要用于网络测试或访问加速。请勿在此进行登录、注册或处理任何敏感信息。进行这些操作请务必访问官方网站 github.com。 Raw 内容也通过此代理提供。
Skip to content

Commit 5bddae3

Browse files
authored
Merge pull request #1303 from ruvnet/fix/adr-061-security-correctness
fix: ADR-061/062 security fixes + cross-platform Windows hooks (v3.5.14)
2 parents 15664e0 + 413e646 commit 5bddae3

36 files changed

+9914
-153
lines changed

.claude/settings.json

Lines changed: 15 additions & 15 deletions
Original file line numberDiff line numberDiff line change
@@ -47,7 +47,7 @@
4747
"hooks": [
4848
{
4949
"type": "command",
50-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" pre-bash",
50+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" pre-bash",
5151
"timeout": 5000
5252
}
5353
]
@@ -59,7 +59,7 @@
5959
"hooks": [
6060
{
6161
"type": "command",
62-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" post-edit",
62+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" post-edit",
6363
"timeout": 10000
6464
}
6565
]
@@ -70,7 +70,7 @@
7070
"hooks": [
7171
{
7272
"type": "command",
73-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" route",
73+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" route",
7474
"timeout": 10000
7575
}
7676
]
@@ -81,12 +81,12 @@
8181
"hooks": [
8282
{
8383
"type": "command",
84-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" session-restore",
84+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" session-restore",
8585
"timeout": 15000
8686
},
8787
{
8888
"type": "command",
89-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/auto-memory-hook.mjs\" import",
89+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/auto-memory-hook.mjs\" import",
9090
"timeout": 8000
9191
}
9292
]
@@ -97,7 +97,7 @@
9797
"hooks": [
9898
{
9999
"type": "command",
100-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" session-end",
100+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" session-end",
101101
"timeout": 10000
102102
}
103103
]
@@ -108,7 +108,7 @@
108108
"hooks": [
109109
{
110110
"type": "command",
111-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/auto-memory-hook.mjs\" sync",
111+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/auto-memory-hook.mjs\" sync",
112112
"timeout": 10000
113113
}
114114
]
@@ -120,11 +120,11 @@
120120
"hooks": [
121121
{
122122
"type": "command",
123-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" compact-manual"
123+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" compact-manual"
124124
},
125125
{
126126
"type": "command",
127-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" session-end",
127+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" session-end",
128128
"timeout": 5000
129129
}
130130
]
@@ -134,11 +134,11 @@
134134
"hooks": [
135135
{
136136
"type": "command",
137-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" compact-auto"
137+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" compact-auto"
138138
},
139139
{
140140
"type": "command",
141-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" session-end",
141+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" session-end",
142142
"timeout": 6000
143143
}
144144
]
@@ -149,7 +149,7 @@
149149
"hooks": [
150150
{
151151
"type": "command",
152-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" status",
152+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" status",
153153
"timeout": 3000
154154
}
155155
]
@@ -160,7 +160,7 @@
160160
"hooks": [
161161
{
162162
"type": "command",
163-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" post-task",
163+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" post-task",
164164
"timeout": 5000
165165
}
166166
]
@@ -171,7 +171,7 @@
171171
"hooks": [
172172
{
173173
"type": "command",
174-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/hook-handler.cjs\" post-task",
174+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs\" post-task",
175175
"timeout": 5000
176176
}
177177
]
@@ -286,7 +286,7 @@
286286
},
287287
"statusLine": {
288288
"type": "command",
289-
"command": "node \"$(git rev-parse --show-toplevel)/.claude/helpers/statusline.cjs\""
289+
"command": "node \"$CLAUDE_PROJECT_DIR/.claude/helpers/statusline.cjs\""
290290
},
291291
"mcpServers": {
292292
"claude-flow": {

package-lock.json

Lines changed: 2 additions & 2 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "claude-flow",
3-
"version": "3.5.7",
3+
"version": "3.5.15",
44
"description": "Ruflo - Enterprise AI agent orchestration for Claude Code. Deploy 60+ specialized agents in coordinated swarms with self-learning, fault-tolerant consensus, vector memory, and MCP integration",
55
"main": "dist/index.js",
66
"type": "module",

ruflo/package.json

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,6 +1,6 @@
11
{
22
"name": "ruflo",
3-
"version": "3.5.7",
3+
"version": "3.5.15",
44
"description": "Ruflo - Enterprise AI agent orchestration platform. Deploy 60+ specialized agents in coordinated swarms with self-learning, fault-tolerant consensus, vector memory, and MCP integration",
55
"main": "bin/ruflo.js",
66
"type": "module",

ruflo/src/ruvocal/Dockerfile

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -30,6 +30,9 @@ USER user
3030

3131

3232
COPY --chown=1000 .env /app/.env
33+
# Remove empty placeholder values that block .env.local overrides via dotenv-cli -c
34+
RUN sed -i 's/^MODELS=$/# MODELS=/' /app/.env && \
35+
sed -i 's/^TASK_MODEL=$/# TASK_MODEL=/' /app/.env
3336
COPY --chown=1000 entrypoint.sh /app/entrypoint.sh
3437
COPY --chown=1000 package.json /app/package.json
3538
COPY --chown=1000 package-lock.json /app/package-lock.json

ruflo/src/ruvocal/src/lib/server/urlSafety.ts

Lines changed: 7 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -38,8 +38,13 @@ export function isValidUrl(urlString: string): boolean {
3838
try {
3939
const url = new URL(urlString.trim());
4040
const hostname = url.hostname.toLowerCase();
41-
// Allow HTTP for localhost/loopback (dev & local MCP bridge)
42-
if (hostname === "localhost" || hostname === "127.0.0.1" || hostname === "::1") {
41+
// Allow HTTP for localhost/loopback/Docker-internal (dev & local MCP bridge)
42+
if (
43+
hostname === "localhost" ||
44+
hostname === "127.0.0.1" ||
45+
hostname === "::1" ||
46+
hostname === "host.docker.internal"
47+
) {
4348
return url.protocol === "http:" || url.protocol === "https:";
4449
}
4550
// Allow HTTP for Docker-internal service names (no dots = private network)

v3/@claude-flow/cli/.claude/helpers/auto-memory-hook.mjs

Lines changed: 4 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -355,9 +355,11 @@ try {
355355
case 'status': await doStatus(); break;
356356
default:
357357
console.log('Usage: auto-memory-hook.mjs <import|sync|status>');
358-
process.exit(1);
358+
break;
359359
}
360360
} catch (err) {
361361
// Hooks must never crash Claude Code - fail silently
362-
dim(`Error (non-critical): ${err.message}`);
362+
try { dim(`Error (non-critical): ${err.message}`); } catch (_) {}
363363
}
364+
// Hooks must ALWAYS exit 0
365+
process.exitCode = 0;

v3/@claude-flow/cli/.claude/helpers/hook-handler.cjs

Lines changed: 20 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -50,15 +50,23 @@ const intelligence = safeRequire(path.join(helpersDir, 'intelligence.cjs'));
5050
// Get the command from argv
5151
const [,, command, ...args] = process.argv;
5252

53-
// Read stdin — Claude Code sends hook data as JSON via stdin
53+
// Read stdin with timeout — Claude Code sends hook data as JSON via stdin.
54+
// Timeout prevents hanging when stdin is not properly closed (common on Windows).
5455
async function readStdin() {
5556
if (process.stdin.isTTY) return '';
56-
let data = '';
57-
process.stdin.setEncoding('utf8');
58-
for await (const chunk of process.stdin) {
59-
data += chunk;
60-
}
61-
return data;
57+
return new Promise((resolve) => {
58+
let data = '';
59+
const timer = setTimeout(() => {
60+
process.stdin.removeAllListeners();
61+
process.stdin.pause();
62+
resolve(data);
63+
}, 500);
64+
process.stdin.setEncoding('utf8');
65+
process.stdin.on('data', (chunk) => { data += chunk; });
66+
process.stdin.on('end', () => { clearTimeout(timer); resolve(data); });
67+
process.stdin.on('error', () => { clearTimeout(timer); resolve(data); });
68+
process.stdin.resume();
69+
});
6270
}
6371

6472
async function main() {
@@ -254,6 +262,10 @@ const handlers = {
254262
}
255263
}
256264

265+
// Hooks must ALWAYS exit 0 — Claude Code treats non-zero as "hook error"
266+
// and skips all subsequent hooks for the event.
267+
process.exitCode = 0;
257268
main().catch((e) => {
258-
console.log(`[WARN] Hook handler error: ${e.message}`);
269+
try { console.log(`[WARN] Hook handler error: ${e.message}`); } catch (_) {}
270+
process.exitCode = 0;
259271
});

v3/@claude-flow/cli/.claude/settings.json

Lines changed: 9 additions & 9 deletions
Original file line numberDiff line numberDiff line change
@@ -11,7 +11,7 @@
1111
"hooks": [
1212
{
1313
"type": "command",
14-
"command": "node .claude/helpers/hook-handler.cjs pre-bash",
14+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs" pre-bash",
1515
"timeout": 5000
1616
}
1717
]
@@ -23,7 +23,7 @@
2323
"hooks": [
2424
{
2525
"type": "command",
26-
"command": "node .claude/helpers/hook-handler.cjs post-edit",
26+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs" post-edit",
2727
"timeout": 10000
2828
}
2929
]
@@ -34,7 +34,7 @@
3434
"hooks": [
3535
{
3636
"type": "command",
37-
"command": "node .claude/helpers/hook-handler.cjs route",
37+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs" route",
3838
"timeout": 10000
3939
}
4040
]
@@ -46,13 +46,13 @@
4646
"hooks": [
4747
{
4848
"type": "command",
49-
"command": "node .claude/helpers/hook-handler.cjs session-restore",
49+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs" session-restore",
5050
"timeout": 15000,
5151
"continueOnError": true
5252
},
5353
{
5454
"type": "command",
55-
"command": "node .claude/helpers/auto-memory-hook.mjs import",
55+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/auto-memory-hook.mjs" import",
5656
"timeout": 8000,
5757
"continueOnError": true
5858
}
@@ -64,7 +64,7 @@
6464
"hooks": [
6565
{
6666
"type": "command",
67-
"command": "node .claude/helpers/hook-handler.cjs session-end",
67+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs" session-end",
6868
"timeout": 10000,
6969
"continueOnError": true
7070
}
@@ -76,7 +76,7 @@
7676
"hooks": [
7777
{
7878
"type": "command",
79-
"command": "node .claude/helpers/hook-handler.cjs status",
79+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/hook-handler.cjs" status",
8080
"timeout": 3000,
8181
"continueOnError": true
8282
}
@@ -88,7 +88,7 @@
8888
"hooks": [
8989
{
9090
"type": "command",
91-
"command": "node .claude/helpers/auto-memory-hook.mjs sync",
91+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/auto-memory-hook.mjs" sync",
9292
"timeout": 10000,
9393
"continueOnError": true
9494
}
@@ -98,7 +98,7 @@
9898
},
9999
"statusLine": {
100100
"type": "command",
101-
"command": "node .claude/helpers/statusline.cjs",
101+
"command": "node "$CLAUDE_PROJECT_DIR/.claude/helpers/statusline.cjs"",
102102
"refreshMs": 5000,
103103
"enabled": true
104104
},

v3/@claude-flow/cli/__tests__/cli.test.ts

Lines changed: 1 addition & 3 deletions
Original file line numberDiff line numberDiff line change
@@ -46,23 +46,21 @@ describe('CLI', () => {
4646
await cli.run(['--version']);
4747

4848
const output = consoleOutput.join('');
49-
expect(output).toContain('claude-flow');
5049
expect(output).toContain(VERSION);
5150
});
5251

5352
it('should show version with -V flag', async () => {
5453
await cli.run(['-V']);
5554

5655
const output = consoleOutput.join('');
57-
expect(output).toContain('claude-flow');
5856
expect(output).toContain(VERSION);
5957
});
6058

6159
it('should show version with correct format', async () => {
6260
await cli.run(['--version']);
6361

6462
const output = consoleOutput.join('');
65-
expect(output).toMatch(/claude-flow v\d+\.\d+\.\d+/);
63+
expect(output).toMatch(/v\d+\.\d+\.\d+/);
6664
});
6765
});
6866

0 commit comments

Comments
 (0)