@ia-ccun/code-agent-claw 0.0.3 → 0.0.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/bin/cli.js +36 -1
- package/dist/public/index.html +42 -21
- package/ia-ccun-code-agent-claw-0.0.4.tgz +0 -0
- package/package.json +1 -1
- package/public/index.html +55 -22
- package/package/.claude/plan/aicode-ui-npm.md +0 -477
- package/package/README.md +0 -108
- package/package/bin/cli.js +0 -16
- package/package/config/default.json +0 -18
- package/package/package.json +0 -43
- package/package/public/aicode.svg +0 -1
- package/package/public/index-v3.html +0 -1757
- package/package/public/index.html +0 -1818
- package/package/public/index_v3.html +0 -1757
- package/package/public/juejin.css +0 -143
- package/package/src/config.ts +0 -239
- package/package/src/index.ts +0 -40
- package/package/src/server/index.ts +0 -103
- package/package/src/server/routes.ts +0 -342
- package/package/src/server/websocket.ts +0 -82
- package/package/src/services/agent-rpc.ts +0 -397
- package/package/src/types/index.ts +0 -60
- package/package/src/utils/logger.ts +0 -13
- package/package/tsconfig.json +0 -19
package/bin/cli.js
CHANGED
|
@@ -2,13 +2,48 @@
|
|
|
2
2
|
|
|
3
3
|
const { spawn } = require('child_process');
|
|
4
4
|
const path = require('path');
|
|
5
|
+
const fs = require('fs');
|
|
6
|
+
|
|
7
|
+
const args = process.argv.slice(2);
|
|
8
|
+
|
|
9
|
+
// 获取版本号
|
|
10
|
+
if (args.includes('--version') || args.includes('-v')) {
|
|
11
|
+
const packageJson = JSON.parse(fs.readFileSync(path.join(__dirname, '..', 'package.json'), 'utf-8'));
|
|
12
|
+
console.log(packageJson.version);
|
|
13
|
+
process.exit(0);
|
|
14
|
+
}
|
|
15
|
+
|
|
16
|
+
// 显示帮助
|
|
17
|
+
if (args.includes('--help') || args.includes('-h')) {
|
|
18
|
+
console.log('Usage: code-agent-claw [options]');
|
|
19
|
+
console.log('');
|
|
20
|
+
console.log('Options:');
|
|
21
|
+
console.log(' --version, -v Show version number');
|
|
22
|
+
console.log(' --port, -p <port> Specify server port (default: 8081)');
|
|
23
|
+
console.log(' --help, -h Show this help message');
|
|
24
|
+
process.exit(0);
|
|
25
|
+
}
|
|
26
|
+
|
|
27
|
+
// 解析端口参数
|
|
28
|
+
let port = null;
|
|
29
|
+
for (let i = 0; i < args.length; i++) {
|
|
30
|
+
if ((args[i] === '--port' || args[i] === '-p') && args[i + 1]) {
|
|
31
|
+
port = args[i + 1];
|
|
32
|
+
break;
|
|
33
|
+
}
|
|
34
|
+
}
|
|
5
35
|
|
|
6
36
|
const distPath = path.join(__dirname, '..', 'dist', 'index.js');
|
|
7
37
|
|
|
38
|
+
const env = { ...process.env };
|
|
39
|
+
if (port) {
|
|
40
|
+
env.AICODE_UI_PORT = port;
|
|
41
|
+
}
|
|
42
|
+
|
|
8
43
|
const child = spawn('node', [distPath], {
|
|
9
44
|
stdio: 'inherit',
|
|
10
45
|
cwd: process.cwd(),
|
|
11
|
-
env
|
|
46
|
+
env
|
|
12
47
|
});
|
|
13
48
|
|
|
14
49
|
child.on('exit', (code) => {
|
package/dist/public/index.html
CHANGED
|
@@ -382,11 +382,22 @@
|
|
|
382
382
|
animation: pulse 2s ease-in-out infinite;
|
|
383
383
|
}
|
|
384
384
|
|
|
385
|
+
.status-dot.disconnected {
|
|
386
|
+
background: var(--error);
|
|
387
|
+
box-shadow: 0 0 8px rgba(201, 74, 74, 0.5);
|
|
388
|
+
animation: pulse-red 1.5s ease-in-out infinite;
|
|
389
|
+
}
|
|
390
|
+
|
|
385
391
|
@keyframes pulse {
|
|
386
392
|
0%, 100% { opacity: 1; }
|
|
387
393
|
50% { opacity: 0.6; }
|
|
388
394
|
}
|
|
389
395
|
|
|
396
|
+
@keyframes pulse-red {
|
|
397
|
+
0%, 100% { opacity: 1; box-shadow: 0 0 8px rgba(201, 74, 74, 0.5); }
|
|
398
|
+
50% { opacity: 0.5; box-shadow: 0 0 16px rgba(201, 74, 74, 0.8); }
|
|
399
|
+
}
|
|
400
|
+
|
|
390
401
|
/* Action buttons */
|
|
391
402
|
.action-btn {
|
|
392
403
|
width: 36px;
|
|
@@ -855,8 +866,9 @@
|
|
|
855
866
|
/* Quick questions */
|
|
856
867
|
.quick-questions {
|
|
857
868
|
display: flex;
|
|
858
|
-
flex-wrap:
|
|
869
|
+
flex-wrap: nowrap;
|
|
859
870
|
gap: var(--space-sm);
|
|
871
|
+
overflow-x: auto;
|
|
860
872
|
}
|
|
861
873
|
|
|
862
874
|
.quick-question {
|
|
@@ -869,6 +881,8 @@
|
|
|
869
881
|
color: var(--text-secondary);
|
|
870
882
|
cursor: pointer;
|
|
871
883
|
transition: all 0.2s ease;
|
|
884
|
+
white-space: nowrap;
|
|
885
|
+
flex-shrink: 0;
|
|
872
886
|
}
|
|
873
887
|
|
|
874
888
|
.quick-question:hover {
|
|
@@ -1063,7 +1077,7 @@
|
|
|
1063
1077
|
}
|
|
1064
1078
|
</style>
|
|
1065
1079
|
</head>
|
|
1066
|
-
<body class="
|
|
1080
|
+
<body class="dark">
|
|
1067
1081
|
<div class="container">
|
|
1068
1082
|
<!-- Header -->
|
|
1069
1083
|
<header class="header">
|
|
@@ -1184,7 +1198,7 @@
|
|
|
1184
1198
|
<aside class="input-panel">
|
|
1185
1199
|
<!-- Quick Questions Card -->
|
|
1186
1200
|
<div class="card">
|
|
1187
|
-
<div class="card-title"
|
|
1201
|
+
<div class="card-title">快捷命令</div>
|
|
1188
1202
|
<div class="quick-questions">
|
|
1189
1203
|
<span class="quick-question" onclick="setPrompt('你好,请介绍一下你自己')">👋 自我介绍</span>
|
|
1190
1204
|
<span class="quick-question" onclick="setPrompt('帮我写一个 Hello World')">Hello World</span>
|
|
@@ -1195,19 +1209,19 @@
|
|
|
1195
1209
|
|
|
1196
1210
|
<!-- Message Type Card -->
|
|
1197
1211
|
<div class="card">
|
|
1198
|
-
<div class="card-title"
|
|
1212
|
+
<div class="card-title">消息类型</div>
|
|
1199
1213
|
<div class="msg-type-group">
|
|
1200
1214
|
<input type="radio" id="type-prompt" name="msgType" value="prompt" checked onchange="onMsgTypeChange()">
|
|
1201
|
-
<label for="type-prompt"
|
|
1215
|
+
<label for="type-prompt" title="发送新的任务请求,AI 会从头开始处理">对话</label>
|
|
1202
1216
|
|
|
1203
1217
|
<input type="radio" id="type-steer" name="msgType" value="steer" onchange="onMsgTypeChange()">
|
|
1204
|
-
<label for="type-steer"
|
|
1218
|
+
<label for="type-steer" title="引导或干预当前正在执行的任务,AI 会中断并响应你的引导">引导</label>
|
|
1205
1219
|
|
|
1206
1220
|
<input type="radio" id="type-follow" name="msgType" value="follow_up" onchange="onMsgTypeChange()">
|
|
1207
|
-
<label for="type-follow"
|
|
1221
|
+
<label for="type-follow" title="在当前对话基础上继续交流,AI 记得之前的上下文">追问</label>
|
|
1208
1222
|
|
|
1209
1223
|
<input type="radio" id="type-abort" name="msgType" value="abort" onchange="onMsgTypeChange()">
|
|
1210
|
-
<label for="type-abort"
|
|
1224
|
+
<label for="type-abort" title="立即终止当前正在执行的任务">中止</label>
|
|
1211
1225
|
</div>
|
|
1212
1226
|
</div>
|
|
1213
1227
|
|
|
@@ -1246,9 +1260,9 @@
|
|
|
1246
1260
|
|
|
1247
1261
|
// Toggle theme
|
|
1248
1262
|
function toggleTheme() {
|
|
1249
|
-
document.body.classList.toggle('
|
|
1263
|
+
document.body.classList.toggle('dark');
|
|
1250
1264
|
const icon = document.getElementById('themeIcon');
|
|
1251
|
-
icon.textContent = document.body.classList.contains('
|
|
1265
|
+
icon.textContent = document.body.classList.contains('dark') ? '☀' : '☾';
|
|
1252
1266
|
}
|
|
1253
1267
|
|
|
1254
1268
|
// Toggle width
|
|
@@ -1439,11 +1453,12 @@
|
|
|
1439
1453
|
|
|
1440
1454
|
if (data.success && data.data && data.data.running) {
|
|
1441
1455
|
statusDot.classList.add('active');
|
|
1442
|
-
|
|
1456
|
+
statusDot.classList.remove('disconnected');
|
|
1457
|
+
statusText.textContent = '已连接';
|
|
1443
1458
|
} else {
|
|
1444
1459
|
statusDot.classList.remove('active');
|
|
1445
|
-
|
|
1446
|
-
|
|
1460
|
+
statusDot.classList.add('disconnected');
|
|
1461
|
+
statusText.textContent = '未连接';
|
|
1447
1462
|
}
|
|
1448
1463
|
} catch (e) {
|
|
1449
1464
|
console.error('Check status error:', e);
|
|
@@ -1471,13 +1486,19 @@
|
|
|
1471
1486
|
|
|
1472
1487
|
if (data.running) {
|
|
1473
1488
|
statusDot.classList.add('active');
|
|
1474
|
-
|
|
1489
|
+
statusDot.classList.remove('disconnected');
|
|
1490
|
+
statusText.textContent = '已连接';
|
|
1475
1491
|
} else {
|
|
1476
1492
|
statusDot.classList.remove('active');
|
|
1477
|
-
|
|
1493
|
+
statusDot.classList.add('disconnected');
|
|
1494
|
+
statusText.textContent = '未连接';
|
|
1478
1495
|
}
|
|
1479
1496
|
} catch (e) {
|
|
1480
|
-
document.getElementById('
|
|
1497
|
+
const statusDot = document.getElementById('statusDot');
|
|
1498
|
+
const statusText = document.getElementById('statusText');
|
|
1499
|
+
statusDot.classList.remove('active');
|
|
1500
|
+
statusDot.classList.add('disconnected');
|
|
1501
|
+
statusText.textContent = '连接错误';
|
|
1481
1502
|
}
|
|
1482
1503
|
}
|
|
1483
1504
|
|
|
@@ -1491,12 +1512,12 @@
|
|
|
1491
1512
|
const msgType = getMsgType();
|
|
1492
1513
|
const input = document.getElementById('promptInput');
|
|
1493
1514
|
const placeholder = {
|
|
1494
|
-
'prompt': '
|
|
1495
|
-
'steer': '
|
|
1496
|
-
'follow_up': '
|
|
1497
|
-
'abort': '
|
|
1515
|
+
'prompt': '输入你的任务描述,AI 会从头开始处理...',
|
|
1516
|
+
'steer': '输入引导信息,干预当前正在执行的任务...',
|
|
1517
|
+
'follow_up': '输入追问内容,AI 会基于之前的上下文继续...',
|
|
1518
|
+
'abort': '点击发送即可立即终止当前任务'
|
|
1498
1519
|
};
|
|
1499
|
-
input.placeholder = placeholder[msgType] || '
|
|
1520
|
+
input.placeholder = placeholder[msgType] || '输入你的任务描述...';
|
|
1500
1521
|
|
|
1501
1522
|
if (msgType === 'abort') {
|
|
1502
1523
|
input.value = '';
|
|
Binary file
|
package/package.json
CHANGED
package/public/index.html
CHANGED
|
@@ -382,11 +382,22 @@
|
|
|
382
382
|
animation: pulse 2s ease-in-out infinite;
|
|
383
383
|
}
|
|
384
384
|
|
|
385
|
+
.status-dot.disconnected {
|
|
386
|
+
background: var(--error);
|
|
387
|
+
box-shadow: 0 0 8px rgba(201, 74, 74, 0.5);
|
|
388
|
+
animation: pulse-red 1.5s ease-in-out infinite;
|
|
389
|
+
}
|
|
390
|
+
|
|
385
391
|
@keyframes pulse {
|
|
386
392
|
0%, 100% { opacity: 1; }
|
|
387
393
|
50% { opacity: 0.6; }
|
|
388
394
|
}
|
|
389
395
|
|
|
396
|
+
@keyframes pulse-red {
|
|
397
|
+
0%, 100% { opacity: 1; box-shadow: 0 0 8px rgba(201, 74, 74, 0.5); }
|
|
398
|
+
50% { opacity: 0.5; box-shadow: 0 0 16px rgba(201, 74, 74, 0.8); }
|
|
399
|
+
}
|
|
400
|
+
|
|
390
401
|
/* Action buttons */
|
|
391
402
|
.action-btn {
|
|
392
403
|
width: 36px;
|
|
@@ -855,8 +866,9 @@
|
|
|
855
866
|
/* Quick questions */
|
|
856
867
|
.quick-questions {
|
|
857
868
|
display: flex;
|
|
858
|
-
flex-wrap:
|
|
869
|
+
flex-wrap: nowrap;
|
|
859
870
|
gap: var(--space-sm);
|
|
871
|
+
overflow-x: auto;
|
|
860
872
|
}
|
|
861
873
|
|
|
862
874
|
.quick-question {
|
|
@@ -869,6 +881,8 @@
|
|
|
869
881
|
color: var(--text-secondary);
|
|
870
882
|
cursor: pointer;
|
|
871
883
|
transition: all 0.2s ease;
|
|
884
|
+
white-space: nowrap;
|
|
885
|
+
flex-shrink: 0;
|
|
872
886
|
}
|
|
873
887
|
|
|
874
888
|
.quick-question:hover {
|
|
@@ -1063,7 +1077,7 @@
|
|
|
1063
1077
|
}
|
|
1064
1078
|
</style>
|
|
1065
1079
|
</head>
|
|
1066
|
-
<body class="
|
|
1080
|
+
<body class="dark">
|
|
1067
1081
|
<div class="container">
|
|
1068
1082
|
<!-- Header -->
|
|
1069
1083
|
<header class="header">
|
|
@@ -1184,7 +1198,7 @@
|
|
|
1184
1198
|
<aside class="input-panel">
|
|
1185
1199
|
<!-- Quick Questions Card -->
|
|
1186
1200
|
<div class="card">
|
|
1187
|
-
<div class="card-title"
|
|
1201
|
+
<div class="card-title">快捷命令</div>
|
|
1188
1202
|
<div class="quick-questions">
|
|
1189
1203
|
<span class="quick-question" onclick="setPrompt('你好,请介绍一下你自己')">👋 自我介绍</span>
|
|
1190
1204
|
<span class="quick-question" onclick="setPrompt('帮我写一个 Hello World')">Hello World</span>
|
|
@@ -1195,19 +1209,19 @@
|
|
|
1195
1209
|
|
|
1196
1210
|
<!-- Message Type Card -->
|
|
1197
1211
|
<div class="card">
|
|
1198
|
-
<div class="card-title"
|
|
1212
|
+
<div class="card-title">消息类型</div>
|
|
1199
1213
|
<div class="msg-type-group">
|
|
1200
1214
|
<input type="radio" id="type-prompt" name="msgType" value="prompt" checked onchange="onMsgTypeChange()">
|
|
1201
|
-
<label for="type-prompt"
|
|
1215
|
+
<label for="type-prompt" title="发送新的任务请求,AI 会从头开始处理">对话</label>
|
|
1202
1216
|
|
|
1203
1217
|
<input type="radio" id="type-steer" name="msgType" value="steer" onchange="onMsgTypeChange()">
|
|
1204
|
-
<label for="type-steer"
|
|
1218
|
+
<label for="type-steer" title="引导或干预当前正在执行的任务,AI 会中断并响应你的引导">引导</label>
|
|
1205
1219
|
|
|
1206
1220
|
<input type="radio" id="type-follow" name="msgType" value="follow_up" onchange="onMsgTypeChange()">
|
|
1207
|
-
<label for="type-follow"
|
|
1221
|
+
<label for="type-follow" title="在当前对话基础上继续交流,AI 记得之前的上下文">追问</label>
|
|
1208
1222
|
|
|
1209
1223
|
<input type="radio" id="type-abort" name="msgType" value="abort" onchange="onMsgTypeChange()">
|
|
1210
|
-
<label for="type-abort"
|
|
1224
|
+
<label for="type-abort" title="立即终止当前正在执行的任务">中止</label>
|
|
1211
1225
|
</div>
|
|
1212
1226
|
</div>
|
|
1213
1227
|
|
|
@@ -1246,9 +1260,9 @@
|
|
|
1246
1260
|
|
|
1247
1261
|
// Toggle theme
|
|
1248
1262
|
function toggleTheme() {
|
|
1249
|
-
document.body.classList.toggle('
|
|
1263
|
+
document.body.classList.toggle('dark');
|
|
1250
1264
|
const icon = document.getElementById('themeIcon');
|
|
1251
|
-
icon.textContent = document.body.classList.contains('
|
|
1265
|
+
icon.textContent = document.body.classList.contains('dark') ? '☀' : '☾';
|
|
1252
1266
|
}
|
|
1253
1267
|
|
|
1254
1268
|
// Toggle width
|
|
@@ -1439,11 +1453,12 @@
|
|
|
1439
1453
|
|
|
1440
1454
|
if (data.success && data.data && data.data.running) {
|
|
1441
1455
|
statusDot.classList.add('active');
|
|
1442
|
-
|
|
1456
|
+
statusDot.classList.remove('disconnected');
|
|
1457
|
+
statusText.textContent = '已连接';
|
|
1443
1458
|
} else {
|
|
1444
1459
|
statusDot.classList.remove('active');
|
|
1445
|
-
|
|
1446
|
-
|
|
1460
|
+
statusDot.classList.add('disconnected');
|
|
1461
|
+
statusText.textContent = '未连接';
|
|
1447
1462
|
}
|
|
1448
1463
|
} catch (e) {
|
|
1449
1464
|
console.error('Check status error:', e);
|
|
@@ -1471,13 +1486,19 @@
|
|
|
1471
1486
|
|
|
1472
1487
|
if (data.running) {
|
|
1473
1488
|
statusDot.classList.add('active');
|
|
1474
|
-
|
|
1489
|
+
statusDot.classList.remove('disconnected');
|
|
1490
|
+
statusText.textContent = '已连接';
|
|
1475
1491
|
} else {
|
|
1476
1492
|
statusDot.classList.remove('active');
|
|
1477
|
-
|
|
1493
|
+
statusDot.classList.add('disconnected');
|
|
1494
|
+
statusText.textContent = '未连接';
|
|
1478
1495
|
}
|
|
1479
1496
|
} catch (e) {
|
|
1480
|
-
document.getElementById('
|
|
1497
|
+
const statusDot = document.getElementById('statusDot');
|
|
1498
|
+
const statusText = document.getElementById('statusText');
|
|
1499
|
+
statusDot.classList.remove('active');
|
|
1500
|
+
statusDot.classList.add('disconnected');
|
|
1501
|
+
statusText.textContent = '连接错误';
|
|
1481
1502
|
}
|
|
1482
1503
|
}
|
|
1483
1504
|
|
|
@@ -1491,12 +1512,12 @@
|
|
|
1491
1512
|
const msgType = getMsgType();
|
|
1492
1513
|
const input = document.getElementById('promptInput');
|
|
1493
1514
|
const placeholder = {
|
|
1494
|
-
'prompt': '
|
|
1495
|
-
'steer': '
|
|
1496
|
-
'follow_up': '
|
|
1497
|
-
'abort': '
|
|
1515
|
+
'prompt': '输入你的任务描述,AI 会从头开始处理...',
|
|
1516
|
+
'steer': '输入引导信息,干预当前正在执行的任务...',
|
|
1517
|
+
'follow_up': '输入追问内容,AI 会基于之前的上下文继续...',
|
|
1518
|
+
'abort': '点击发送即可立即终止当前任务'
|
|
1498
1519
|
};
|
|
1499
|
-
input.placeholder = placeholder[msgType] || '
|
|
1520
|
+
input.placeholder = placeholder[msgType] || '输入你的任务描述...';
|
|
1500
1521
|
|
|
1501
1522
|
if (msgType === 'abort') {
|
|
1502
1523
|
input.value = '';
|
|
@@ -1750,7 +1771,19 @@
|
|
|
1750
1771
|
|
|
1751
1772
|
// WebSocket
|
|
1752
1773
|
let ws;
|
|
1774
|
+
let reconnectTimer;
|
|
1753
1775
|
function connectWebSocket() {
|
|
1776
|
+
// 清除之前的重连定时器
|
|
1777
|
+
if (reconnectTimer) {
|
|
1778
|
+
clearTimeout(reconnectTimer);
|
|
1779
|
+
reconnectTimer = null;
|
|
1780
|
+
}
|
|
1781
|
+
|
|
1782
|
+
// 关闭旧的连接
|
|
1783
|
+
if (ws && ws.readyState === WebSocket.OPEN) {
|
|
1784
|
+
ws.close();
|
|
1785
|
+
}
|
|
1786
|
+
|
|
1754
1787
|
const protocol = window.location.protocol === 'https:' ? 'wss:' : 'ws:';
|
|
1755
1788
|
const wsUrl = `${protocol}//${window.location.host}/ws/agent`;
|
|
1756
1789
|
|
|
@@ -1771,7 +1804,7 @@
|
|
|
1771
1804
|
};
|
|
1772
1805
|
|
|
1773
1806
|
ws.onclose = () => {
|
|
1774
|
-
setTimeout(connectWebSocket, 3000);
|
|
1807
|
+
reconnectTimer = setTimeout(connectWebSocket, 3000);
|
|
1775
1808
|
};
|
|
1776
1809
|
}
|
|
1777
1810
|
|