shennian 0.2.89 → 0.2.90
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/dist/assets/wechat-channel/macos/manifest.json +13 -4
- package/dist/assets/wechat-channel/macos/shennian-wechat-channel-helper +0 -0
- package/dist/bin/shennian.js +1 -1
- package/dist/publish-build-manifest.json +548 -0
- package/dist/scripts/wechat-rpa-confirmation.mjs +5 -97
- package/dist/src/agent-env.js +4 -105
- package/dist/src/agents/adapter.js +1 -19
- package/dist/src/agents/claude.js +8 -305
- package/dist/src/agents/codex-control.js +2 -188
- package/dist/src/agents/codex-utils.js +7 -200
- package/dist/src/agents/codex.js +15 -916
- package/dist/src/agents/command-spec.js +2 -413
- package/dist/src/agents/config-status.js +1 -226
- package/dist/src/agents/cursor.js +1 -249
- package/dist/src/agents/custom.js +4 -271
- package/dist/src/agents/detect.js +1 -56
- package/dist/src/agents/external-channel-instructions.js +10 -94
- package/dist/src/agents/gemini.js +1 -173
- package/dist/src/agents/manager.js +13 -157
- package/dist/src/agents/model-registry/cache.js +1 -37
- package/dist/src/agents/model-registry/discovery.js +2 -187
- package/dist/src/agents/model-registry/parsers.js +4 -447
- package/dist/src/agents/model-registry/runner.js +1 -30
- package/dist/src/agents/model-registry/service.js +1 -78
- package/dist/src/agents/model-registry/types.js +1 -8
- package/dist/src/agents/model-registry.js +1 -18
- package/dist/src/agents/openclaw.js +2 -275
- package/dist/src/agents/opencode.js +1 -231
- package/dist/src/agents/pi-context.js +12 -217
- package/dist/src/agents/pi.js +14 -723
- package/dist/src/agents/platform-instructions.js +9 -54
- package/dist/src/channels/base.js +1 -3
- package/dist/src/channels/registry.js +1 -30
- package/dist/src/channels/reply-split.js +10 -89
- package/dist/src/channels/runtime.js +5 -564
- package/dist/src/channels/secret-registry.js +1 -46
- package/dist/src/channels/websocket.js +8 -378
- package/dist/src/channels/wechat-channel/anchor.js +1 -65
- package/dist/src/channels/wechat-channel/client.js +1 -96
- package/dist/src/channels/wechat-channel/cooldown.js +1 -38
- package/dist/src/channels/wechat-channel/fingerprint.js +1 -71
- package/dist/src/channels/wechat-channel/helper-assets.d.ts +10 -1
- package/dist/src/channels/wechat-channel/helper-assets.js +1 -68
- package/dist/src/channels/wechat-channel/helper-client.js +3 -149
- package/dist/src/channels/wechat-channel/helper-protocol.d.ts +1 -1
- package/dist/src/channels/wechat-channel/helper-protocol.js +1 -115
- package/dist/src/channels/wechat-channel/index.d.ts +1 -0
- package/dist/src/channels/wechat-channel/index.js +1 -19
- package/dist/src/channels/wechat-channel/ledger.js +1 -54
- package/dist/src/channels/wechat-channel/media-resolver.js +1 -181
- package/dist/src/channels/wechat-channel/message-key.js +1 -105
- package/dist/src/channels/wechat-channel/observer.js +1 -118
- package/dist/src/channels/wechat-channel/outbound-ledger.d.ts +3 -0
- package/dist/src/channels/wechat-channel/outbound-ledger.js +2 -112
- package/dist/src/channels/wechat-channel/outbound-sender.d.ts +26 -0
- package/dist/src/channels/wechat-channel/outbound-sender.js +1 -0
- package/dist/src/channels/wechat-channel/preflight.js +1 -48
- package/dist/src/channels/wechat-channel/runner.js +1 -84
- package/dist/src/channels/wechat-channel/runtime.js +1 -66
- package/dist/src/channels/wechat-channel/scheduler.d.ts +5 -0
- package/dist/src/channels/wechat-channel/scheduler.js +1 -152
- package/dist/src/channels/wechat-rpa/macos-flow.js +1 -96
- package/dist/src/channels/wechat-rpa/macos.js +6 -48
- package/dist/src/channels/wechat-rpa/normalizer.js +7 -127
- package/dist/src/channels/wechat-rpa.js +6 -1028
- package/dist/src/channels/wecom.js +4 -357
- package/dist/src/commands/agent.js +6 -131
- package/dist/src/commands/daemon-windows.js +8 -48
- package/dist/src/commands/daemon.js +19 -1013
- package/dist/src/commands/external-attachments.js +1 -51
- package/dist/src/commands/external.js +1 -137
- package/dist/src/commands/manager.js +2 -391
- package/dist/src/commands/pair-qr.js +1 -6
- package/dist/src/commands/pair.js +9 -287
- package/dist/src/commands/tools.js +1 -34
- package/dist/src/commands/upgrade.js +1 -198
- package/dist/src/config/index.js +1 -35
- package/dist/src/daemon-log.js +6 -58
- package/dist/src/env-path.js +1 -64
- package/dist/src/fs/boundary.js +1 -126
- package/dist/src/fs/handler.js +1 -130
- package/dist/src/fs/security.js +1 -32
- package/dist/src/fs/text-decoder.js +1 -110
- package/dist/src/index.js +2 -404
- package/dist/src/log-reporter.js +1 -16
- package/dist/src/manager/prompt.js +29 -34
- package/dist/src/manager/registry.js +2 -269
- package/dist/src/manager/runtime.js +19 -1007
- package/dist/src/native-fusion/config.js +1 -5
- package/dist/src/native-fusion/opencode-parser.js +3 -123
- package/dist/src/native-fusion/parser-common.js +8 -264
- package/dist/src/native-fusion/parsers.js +8 -729
- package/dist/src/native-fusion/service.js +2 -225
- package/dist/src/native-fusion/state.js +1 -22
- package/dist/src/native-fusion/types.js +1 -1
- package/dist/src/region.js +1 -88
- package/dist/src/relay/client.js +1 -343
- package/dist/src/session/archive-zip.js +1 -220
- package/dist/src/session/handlers/agent-config.js +1 -150
- package/dist/src/session/handlers/agents.js +1 -55
- package/dist/src/session/handlers/chat.js +2 -751
- package/dist/src/session/handlers/control.js +1 -55
- package/dist/src/session/handlers/fs.js +1 -783
- package/dist/src/session/handlers/session-refresh.js +1 -47
- package/dist/src/session/handlers/skills.js +1 -121
- package/dist/src/session/handlers/title.js +1 -60
- package/dist/src/session/handlers/tool-detail.js +1 -218
- package/dist/src/session/manager.js +1 -319
- package/dist/src/session/projection.js +1 -54
- package/dist/src/session/queue.js +4 -317
- package/dist/src/session/remote-attachments.js +1 -72
- package/dist/src/session/store.js +3 -109
- package/dist/src/session/types.js +1 -4
- package/dist/src/skills/registry.js +15 -148
- package/dist/src/skills/setup.js +1 -101
- package/dist/src/tools/markdown-to-pdf.js +10 -346
- package/dist/src/upgrade/engine.js +3 -347
- package/package.json +3 -2
|
@@ -1,12 +1,4 @@
|
|
|
1
|
-
|
|
2
|
-
// @test src/__tests__/platform-instructions.test.ts
|
|
3
|
-
import fs from 'node:fs';
|
|
4
|
-
import path from 'node:path';
|
|
5
|
-
import { createHash } from 'node:crypto';
|
|
6
|
-
import { resolveShennianPath } from '../config/index.js';
|
|
7
|
-
import { buildExternalChannelInstructions } from './external-channel-instructions.js';
|
|
8
|
-
import { buildInstalledSkillInstructions } from '../skills/registry.js';
|
|
9
|
-
export const PLATFORM_OUTPUT_INSTRUCTIONS = `## Shennian Output Instructions
|
|
1
|
+
import s from"node:fs";import a from"node:path";import{createHash as c}from"node:crypto";import{resolveShennianPath as l}from"../config/index.js";import{buildExternalChannelInstructions as u}from"./external-channel-instructions.js";import{buildInstalledSkillInstructions as f}from"../skills/registry.js";const h=`## Shennian Output Instructions
|
|
10
2
|
|
|
11
3
|
When you mention a local file that the user may want to open in Shennian, format it as a Markdown link using the exact local path:
|
|
12
4
|
|
|
@@ -14,48 +6,11 @@ When you mention a local file that the user may want to open in Shennian, format
|
|
|
14
6
|
- Use [filename.ext](<relative/path/to/filename.ext>) for paths relative to the current working directory.
|
|
15
7
|
- Do not use file:// URLs for local files.
|
|
16
8
|
- Do not put user-openable file paths only inside code blocks.
|
|
17
|
-
- Keep normal http:// and https:// links unchanged.`;
|
|
18
|
-
|
|
19
|
-
|
|
20
|
-
|
|
21
|
-
|
|
22
|
-
|
|
23
|
-
|
|
24
|
-
|
|
25
|
-
}
|
|
26
|
-
}
|
|
27
|
-
export function buildPlatformInstructions(workDir, externalChannel, sessionId) {
|
|
28
|
-
const projectInstructions = readProjectAgentsMd(workDir);
|
|
29
|
-
const channelInstructions = buildExternalChannelInstructions(externalChannel, path.resolve(workDir), sessionId);
|
|
30
|
-
const skillInstructions = buildInstalledSkillInstructions();
|
|
31
|
-
const sections = [
|
|
32
|
-
'# Shennian Agent Instructions',
|
|
33
|
-
projectInstructions
|
|
34
|
-
? `## Project Instructions\n\n${projectInstructions}`
|
|
35
|
-
: '',
|
|
36
|
-
PLATFORM_OUTPUT_INSTRUCTIONS,
|
|
37
|
-
skillInstructions,
|
|
38
|
-
channelInstructions
|
|
39
|
-
? `## External Message Channel Instructions\n\n${channelInstructions}`
|
|
40
|
-
: '',
|
|
41
|
-
].filter(Boolean);
|
|
42
|
-
return `${sections.join('\n\n')}\n`;
|
|
43
|
-
}
|
|
44
|
-
export function ensurePlatformInstructionsFile(workDir, externalChannel, sessionId) {
|
|
45
|
-
const key = createHash('sha256')
|
|
46
|
-
.update(`${path.resolve(workDir)}:${sessionId ?? ''}:${JSON.stringify(externalChannel ?? null)}`)
|
|
47
|
-
.digest('hex')
|
|
48
|
-
.slice(0, 16);
|
|
49
|
-
const filePath = resolveShennianPath('runtime', 'agent-instructions', `${key}.md`);
|
|
50
|
-
const content = buildPlatformInstructions(workDir, externalChannel, sessionId);
|
|
51
|
-
fs.mkdirSync(path.dirname(filePath), { recursive: true });
|
|
52
|
-
try {
|
|
53
|
-
if (fs.readFileSync(filePath, 'utf8') === content)
|
|
54
|
-
return filePath;
|
|
55
|
-
}
|
|
56
|
-
catch {
|
|
57
|
-
// Write the generated instruction file below.
|
|
58
|
-
}
|
|
59
|
-
fs.writeFileSync(filePath, content);
|
|
60
|
-
return filePath;
|
|
61
|
-
}
|
|
9
|
+
- Keep normal http:// and https:// links unchanged.`;function m(n){const e=a.join(n,"AGENTS.md");try{return s.readFileSync(e,"utf8").trim()}catch{return""}}function p(n,e,o){const r=m(n),t=u(e,a.resolve(n),o),i=f();return`${["# Shennian Agent Instructions",r?`## Project Instructions
|
|
10
|
+
|
|
11
|
+
${r}`:"",h,i,t?`## External Message Channel Instructions
|
|
12
|
+
|
|
13
|
+
${t}`:""].filter(Boolean).join(`
|
|
14
|
+
|
|
15
|
+
`)}
|
|
16
|
+
`}function b(n,e,o){const r=c("sha256").update(`${a.resolve(n)}:${o??""}:${JSON.stringify(e??null)}`).digest("hex").slice(0,16),t=l("runtime","agent-instructions",`${r}.md`),i=p(n,e,o);s.mkdirSync(a.dirname(t),{recursive:!0});try{if(s.readFileSync(t,"utf8")===i)return t}catch{}return s.writeFileSync(t,i),t}export{h as PLATFORM_OUTPUT_INSTRUCTIONS,p as buildPlatformInstructions,b as ensurePlatformInstructionsFile};
|
|
@@ -1,30 +1 @@
|
|
|
1
|
-
|
|
2
|
-
// @test src/__tests__/manager-runtime.test.ts
|
|
3
|
-
import fs from 'node:fs';
|
|
4
|
-
import path from 'node:path';
|
|
5
|
-
import { resolveShennianPath } from '../config/index.js';
|
|
6
|
-
const CHANNELS_PATH = resolveShennianPath('channels.json');
|
|
7
|
-
export class ChannelConfigRegistry {
|
|
8
|
-
list() {
|
|
9
|
-
try {
|
|
10
|
-
const parsed = JSON.parse(fs.readFileSync(CHANNELS_PATH, 'utf-8'));
|
|
11
|
-
return parsed.channels ?? [];
|
|
12
|
-
}
|
|
13
|
-
catch {
|
|
14
|
-
return [];
|
|
15
|
-
}
|
|
16
|
-
}
|
|
17
|
-
get(channelId) {
|
|
18
|
-
return this.list().find((channel) => channel.id === channelId);
|
|
19
|
-
}
|
|
20
|
-
upsert(config) {
|
|
21
|
-
const channels = this.list().filter((channel) => channel.id !== config.id);
|
|
22
|
-
channels.push(config);
|
|
23
|
-
fs.mkdirSync(path.dirname(CHANNELS_PATH), { recursive: true });
|
|
24
|
-
fs.writeFileSync(CHANNELS_PATH, JSON.stringify({ channels }, null, 2));
|
|
25
|
-
}
|
|
26
|
-
replaceAll(channels) {
|
|
27
|
-
fs.mkdirSync(path.dirname(CHANNELS_PATH), { recursive: true });
|
|
28
|
-
fs.writeFileSync(CHANNELS_PATH, JSON.stringify({ channels }, null, 2));
|
|
29
|
-
}
|
|
30
|
-
}
|
|
1
|
+
import e from"node:fs";import t from"node:path";import{resolveShennianPath as l}from"../config/index.js";const i=l("channels.json");class d{list(){try{return JSON.parse(e.readFileSync(i,"utf-8")).channels??[]}catch{return[]}}get(r){return this.list().find(n=>n.id===r)}upsert(r){const n=this.list().filter(s=>s.id!==r.id);n.push(r),e.mkdirSync(t.dirname(i),{recursive:!0}),e.writeFileSync(i,JSON.stringify({channels:n},null,2))}replaceAll(r){e.mkdirSync(t.dirname(i),{recursive:!0}),e.writeFileSync(i,JSON.stringify({channels:r},null,2))}}export{d as ChannelConfigRegistry};
|
|
@@ -1,89 +1,10 @@
|
|
|
1
|
-
|
|
2
|
-
|
|
3
|
-
|
|
4
|
-
const
|
|
5
|
-
|
|
6
|
-
function
|
|
7
|
-
|
|
8
|
-
}
|
|
9
|
-
|
|
10
|
-
|
|
11
|
-
}
|
|
12
|
-
function normalizeReplyText(text) {
|
|
13
|
-
return text
|
|
14
|
-
.replace(/\r\n/g, '\n')
|
|
15
|
-
.replace(/[ \t]+\n/g, '\n')
|
|
16
|
-
.replace(/\n[ \t]+/g, '\n')
|
|
17
|
-
.trim();
|
|
18
|
-
}
|
|
19
|
-
function splitLongParagraph(paragraph) {
|
|
20
|
-
const pieces = [];
|
|
21
|
-
const sentences = paragraph
|
|
22
|
-
.split(/(?<=[。!?!?;;])\s*/)
|
|
23
|
-
.map((part) => part.trim())
|
|
24
|
-
.filter(Boolean);
|
|
25
|
-
const units = sentences.length > 1 ? sentences : Array.from(paragraph);
|
|
26
|
-
let current = '';
|
|
27
|
-
for (const unit of units) {
|
|
28
|
-
const next = current ? `${current}${sentences.length > 1 ? '' : ''}${unit}` : unit;
|
|
29
|
-
if (current && visualLength(next) > TARGET_REPLY_CHARS) {
|
|
30
|
-
pieces.push(current);
|
|
31
|
-
current = unit;
|
|
32
|
-
}
|
|
33
|
-
else {
|
|
34
|
-
current = next;
|
|
35
|
-
}
|
|
36
|
-
}
|
|
37
|
-
if (current)
|
|
38
|
-
pieces.push(current);
|
|
39
|
-
return pieces.flatMap((piece) => {
|
|
40
|
-
if (visualLength(piece) <= MAX_REPLY_CHARS)
|
|
41
|
-
return [piece];
|
|
42
|
-
const chars = Array.from(piece);
|
|
43
|
-
const chunks = [];
|
|
44
|
-
for (let i = 0; i < chars.length; i += TARGET_REPLY_CHARS) {
|
|
45
|
-
chunks.push(chars.slice(i, i + TARGET_REPLY_CHARS).join('').trim());
|
|
46
|
-
}
|
|
47
|
-
return chunks.filter(Boolean);
|
|
48
|
-
});
|
|
49
|
-
}
|
|
50
|
-
function capReplyParts(chunks) {
|
|
51
|
-
if (chunks.length <= MAX_REPLY_PARTS)
|
|
52
|
-
return chunks;
|
|
53
|
-
const head = chunks.slice(0, MAX_REPLY_PARTS - 1);
|
|
54
|
-
const tail = chunks.slice(MAX_REPLY_PARTS - 1).join('\n\n');
|
|
55
|
-
const tailText = visualLength(tail) > MAX_REPLY_CHARS
|
|
56
|
-
? `${sliceVisual(tail, MAX_REPLY_CHARS - 1)}…`
|
|
57
|
-
: tail;
|
|
58
|
-
return [...head, tailText].filter(Boolean);
|
|
59
|
-
}
|
|
60
|
-
export function splitExternalReplyText(text) {
|
|
61
|
-
const normalized = normalizeReplyText(text);
|
|
62
|
-
if (!normalized)
|
|
63
|
-
return [];
|
|
64
|
-
if (visualLength(normalized) <= MAX_REPLY_CHARS && !normalized.includes('\n\n'))
|
|
65
|
-
return [normalized];
|
|
66
|
-
const paragraphs = normalized
|
|
67
|
-
.split(/\n{2,}/)
|
|
68
|
-
.map((part) => part.replace(/\n/g, ' ').replace(/\s+/g, ' ').trim())
|
|
69
|
-
.filter(Boolean);
|
|
70
|
-
if (paragraphs.length > 1 && visualLength(normalized) > TARGET_REPLY_CHARS) {
|
|
71
|
-
return capReplyParts(paragraphs.flatMap(splitLongParagraph));
|
|
72
|
-
}
|
|
73
|
-
const sourceParts = paragraphs.length > 1 ? paragraphs : [normalized.replace(/\n/g, ' ').replace(/\s+/g, ' ').trim()];
|
|
74
|
-
const chunks = [];
|
|
75
|
-
let current = '';
|
|
76
|
-
for (const part of sourceParts.flatMap(splitLongParagraph)) {
|
|
77
|
-
const next = current ? `${current}\n\n${part}` : part;
|
|
78
|
-
if (current && visualLength(next) > MAX_REPLY_CHARS) {
|
|
79
|
-
chunks.push(current);
|
|
80
|
-
current = part;
|
|
81
|
-
}
|
|
82
|
-
else {
|
|
83
|
-
current = next;
|
|
84
|
-
}
|
|
85
|
-
}
|
|
86
|
-
if (current)
|
|
87
|
-
chunks.push(current);
|
|
88
|
-
return capReplyParts(chunks);
|
|
89
|
-
}
|
|
1
|
+
const _=500,p=360,P=6;function s(t){return Array.from(t).length}function f(t,e){return Array.from(t).slice(0,e).join("")}function u(t){return t.replace(/\r\n/g,`
|
|
2
|
+
`).replace(/[ \t]+\n/g,`
|
|
3
|
+
`).replace(/\n[ \t]+/g,`
|
|
4
|
+
`).trim()}function R(t){const e=[],r=t.split(/(?<=[。!?!?;;])\s*/).map(n=>n.trim()).filter(Boolean),i=r.length>1?r:Array.from(t);let l="";for(const n of i){const o=l?`${l}${r.length>1,""}${n}`:n;l&&s(o)>360?(e.push(l),l=n):l=o}return l&&e.push(l),e.flatMap(n=>{if(s(n)<=500)return[n];const o=Array.from(n),c=[];for(let a=0;a<o.length;a+=360)c.push(o.slice(a,a+360).join("").trim());return c.filter(Boolean)})}function A(t){if(t.length<=6)return t;const e=t.slice(0,5),r=t.slice(5).join(`
|
|
5
|
+
|
|
6
|
+
`),i=s(r)>500?`${f(r,499)}\u2026`:r;return[...e,i].filter(Boolean)}function E(t){const e=u(t);if(!e)return[];if(s(e)<=500&&!e.includes(`
|
|
7
|
+
|
|
8
|
+
`))return[e];const r=e.split(/\n{2,}/).map(o=>o.replace(/\n/g," ").replace(/\s+/g," ").trim()).filter(Boolean);if(r.length>1&&s(e)>360)return A(r.flatMap(R));const i=r.length>1?r:[e.replace(/\n/g," ").replace(/\s+/g," ").trim()],l=[];let n="";for(const o of i.flatMap(R)){const c=n?`${n}
|
|
9
|
+
|
|
10
|
+
${o}`:o;n&&s(c)>500?(l.push(n),n=o):n=c}return n&&l.push(n),A(l)}export{E as splitExternalReplyText};
|