@fishwithcat/dsh-tui 0.0.0-stage → 0.2.2-alpha.3.fork.1
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/README.i18n.yaml +7 -0
- package/README.md +23 -2
- package/README.zh.md +19 -0
- package/lib/bin.js +123 -0
- package/lib/types/bin.d.ts +3 -0
- package/lib/types/launch.d.ts +45 -0
- package/package.json +34 -4
package/README.i18n.yaml
ADDED
|
@@ -0,0 +1,7 @@
|
|
|
1
|
+
# Bilingual-pair consistency record for README.md (docs/i18n/README.md): per heading
|
|
2
|
+
# section, a hash of its English and Chinese blocks outside code blocks and generated regions.
|
|
3
|
+
# After editing either side, bring the other along and re-record with:
|
|
4
|
+
# pnpm run verify-translation-pairing --write apps/tui-launcher/README.md
|
|
5
|
+
/deepseek-ai-dsh-tui-launcher:
|
|
6
|
+
en: d2af509f44c7c023
|
|
7
|
+
zh: 964f6eade419ff50
|
package/README.md
CHANGED
|
@@ -1,3 +1,24 @@
|
|
|
1
|
-
#
|
|
1
|
+
# `@deepseek-ai/dsh-tui-launcher`
|
|
2
2
|
|
|
3
|
-
|
|
3
|
+
English | [中文](README.zh.md)
|
|
4
|
+
|
|
5
|
+
The terminal entry for npm installs and source checkouts. `dsh-tui` creates
|
|
6
|
+
the `tui` profile when it is missing, resolves the installed
|
|
7
|
+
`@deepseek-ai/dsh` CLI, and runs it with `--profile tui`, forwarding every
|
|
8
|
+
application argument. The packed manifest aliases that CLI dependency to this
|
|
9
|
+
fork's build, so the resolved command is the fork's launcher rather than the
|
|
10
|
+
upstream package. The launcher owns the profile choice: `--profile`,
|
|
11
|
+
`--from-default-profile`, and `dsh plugin` are rejected. A source checkout
|
|
12
|
+
installs the same command with `pnpm run link:dsh-tui` and runs it from source
|
|
13
|
+
with `pnpm dsh-tui`.
|
|
14
|
+
|
|
15
|
+
The published package is `@fishwithcat/dsh-tui`. Its packed manifest aliases
|
|
16
|
+
the TUI layer (`@fishwithcat/dsh` and `@fishwithcat/dsh-tui-app`) at the fork
|
|
17
|
+
version and the eight core-overlay packages at the upstream version, so the
|
|
18
|
+
upstream CLI resolves every name to the fork's builds while upstream exact
|
|
19
|
+
ranges and required peers keep one copy. A fork version has the form
|
|
20
|
+
`<upstream>.fork.<n>`.
|
|
21
|
+
|
|
22
|
+
`dsh-tui watch <session-id>` is translated to `--watch <session-id>`, and
|
|
23
|
+
`dsh-tui --version` prints the launcher's fork version without creating a
|
|
24
|
+
profile or resolving the installed CLI.
|
package/README.zh.md
ADDED
|
@@ -0,0 +1,19 @@
|
|
|
1
|
+
# `@deepseek-ai/dsh-tui-launcher`
|
|
2
|
+
|
|
3
|
+
[English](README.md) | 中文
|
|
4
|
+
|
|
5
|
+
npm 安装与源码 checkout 共用的终端入口。`dsh-tui` 在 `tui` profile 不存在时创建
|
|
6
|
+
它,解析已安装的 `@deepseek-ai/dsh` CLI,并以 `--profile tui` 启动,原样转发应用
|
|
7
|
+
参数。打包后的 manifest 把这个 CLI 依赖别名到本 fork 的构建,因此实际解析到的是
|
|
8
|
+
fork 的启动器,而不是上游包。profile 由启动器固定:`--profile`、
|
|
9
|
+
`--from-default-profile` 和 `dsh plugin` 会被拒绝。源码 checkout 用
|
|
10
|
+
`pnpm run link:dsh-tui` 安装同一个命令,并用 `pnpm dsh-tui` 从源码运行。
|
|
11
|
+
|
|
12
|
+
实际发布的包名是 `@fishwithcat/dsh-tui`。打包后的 manifest 把 TUI 层
|
|
13
|
+
(`@fishwithcat/dsh` 与 `@fishwithcat/dsh-tui-app`)别名到 fork 版本,把 8 个
|
|
14
|
+
核心覆盖包别名到上游版本,让上游 CLI 按同一批依赖名解析到 fork 的构建,同时让
|
|
15
|
+
上游的精确范围与 required peer 只保留一份副本。fork 版本的形式为
|
|
16
|
+
`<upstream>.fork.<n>`。
|
|
17
|
+
|
|
18
|
+
`dsh-tui watch <session-id>` 会转换成 `--watch <session-id>`,`dsh-tui --version`
|
|
19
|
+
会打印启动器的 fork 版本,不创建 profile,也不解析已安装的 CLI。
|
package/lib/bin.js
ADDED
|
@@ -0,0 +1,123 @@
|
|
|
1
|
+
#!/usr/bin/env node
|
|
2
|
+
import { createRequire } from "node:module";
|
|
3
|
+
import { spawn } from "node:child_process";
|
|
4
|
+
import { constants } from "node:os";
|
|
5
|
+
import { existsSync } from "node:fs";
|
|
6
|
+
import { join } from "node:path";
|
|
7
|
+
import { initProfile, resolveProfileDir } from "@deepseek-ai/dsh-app-boot";
|
|
8
|
+
/** Bundle layers a launcher-created `tui` profile starts from. */
|
|
9
|
+
const TUI_PROFILE_BUNDLES = ["@deepseek-ai/dsh-base", "@deepseek-ai/dsh-tui-app"];
|
|
10
|
+
/** Launcher flags that would select a different profile. */
|
|
11
|
+
const PROFILE_FLAGS = new Set(["--profile", "--from-default-profile"]);
|
|
12
|
+
/**
|
|
13
|
+
* Turn the launcher arguments into the dsh CLI arguments.
|
|
14
|
+
*
|
|
15
|
+
* The launcher owns the profile, so profile-selection flags and plugin
|
|
16
|
+
* management are rejected. `watch <id>` becomes the equivalent `--watch <id>`
|
|
17
|
+
* application flag, which the CLI routes to the tui profile on its own.
|
|
18
|
+
* @param argv - arguments after the `dsh-tui` command.
|
|
19
|
+
* @returns the arguments for the dsh CLI.
|
|
20
|
+
* @throws when a caller selects a profile or asks for plugin management.
|
|
21
|
+
*/
|
|
22
|
+
function launcherCliArgs(argv) {
|
|
23
|
+
for (const argument of argv) {
|
|
24
|
+
const flag = argument.split("=", 1)[0];
|
|
25
|
+
if (flag !== void 0 && PROFILE_FLAGS.has(flag)) throw new Error(`dsh-tui: ${flag} is fixed to "tui"; run dsh directly to select another profile`);
|
|
26
|
+
}
|
|
27
|
+
if (argv[0] === "plugin") throw new Error("dsh-tui: plugin management runs through dsh plugin --profile tui <pnpm arguments>");
|
|
28
|
+
if (argv[0] === "watch") {
|
|
29
|
+
const sessionId = argv[1];
|
|
30
|
+
if (sessionId === void 0) throw new Error("dsh-tui: watch needs a session id");
|
|
31
|
+
return [
|
|
32
|
+
"--profile",
|
|
33
|
+
"tui",
|
|
34
|
+
"--watch",
|
|
35
|
+
sessionId,
|
|
36
|
+
...argv.slice(2)
|
|
37
|
+
];
|
|
38
|
+
}
|
|
39
|
+
return [
|
|
40
|
+
"--profile",
|
|
41
|
+
"tui",
|
|
42
|
+
...argv
|
|
43
|
+
];
|
|
44
|
+
}
|
|
45
|
+
/**
|
|
46
|
+
* Create the `tui` profile when the directory has no manifest yet.
|
|
47
|
+
*
|
|
48
|
+
* An existing profile is left untouched: it may carry the user's own patch
|
|
49
|
+
* layer and plugin list, and the bundle names resolve from the launcher's
|
|
50
|
+
* installation before the profile anyway.
|
|
51
|
+
* @param dir - profile directory; defaults to `$DSH_HOME/profiles/tui`.
|
|
52
|
+
* @returns the profile directory.
|
|
53
|
+
*/
|
|
54
|
+
function ensureTuiProfile(dir = resolveProfileDir("tui")) {
|
|
55
|
+
if (!existsSync(join(dir, "package.json"))) initProfile(dir, TUI_PROFILE_BUNDLES);
|
|
56
|
+
return dir;
|
|
57
|
+
}
|
|
58
|
+
/**
|
|
59
|
+
* Resolve the installed CLI entry from the launcher's own installation.
|
|
60
|
+
* @param resolve - Node resolution function anchored at this launcher.
|
|
61
|
+
* @returns the absolute path of the dsh bin script.
|
|
62
|
+
*/
|
|
63
|
+
function resolveCliEntry(resolve) {
|
|
64
|
+
return resolve("@deepseek-ai/dsh/lib/bin.js");
|
|
65
|
+
}
|
|
66
|
+
/**
|
|
67
|
+
* Whether the invocation only asks for the launcher version. The launcher
|
|
68
|
+
* answers it from its own manifest, without creating a profile or resolving
|
|
69
|
+
* the installed CLI.
|
|
70
|
+
* @param argv - normalized CLI arguments.
|
|
71
|
+
* @returns true when the invocation carries a version flag.
|
|
72
|
+
*/
|
|
73
|
+
function isVersionRequest(argv) {
|
|
74
|
+
return argv.some((argument) => argument === "--version" || argument === "-V");
|
|
75
|
+
}
|
|
76
|
+
//#endregion
|
|
77
|
+
//#region lib/types/bin.js
|
|
78
|
+
/* v8 ignore file -- self-executing entry; launch.ts owns the tested decisions. */
|
|
79
|
+
/**
|
|
80
|
+
* Stop the launcher with one stderr line.
|
|
81
|
+
* @param message - diagnostic text.
|
|
82
|
+
* @param code - process exit status.
|
|
83
|
+
* @returns never.
|
|
84
|
+
*/
|
|
85
|
+
function fail(message, code) {
|
|
86
|
+
process.stderr.write(`${message}\n`);
|
|
87
|
+
process.exit(code);
|
|
88
|
+
}
|
|
89
|
+
const require = createRequire(import.meta.url);
|
|
90
|
+
const { version } = require("../package.json");
|
|
91
|
+
const invocation = (() => {
|
|
92
|
+
try {
|
|
93
|
+
const args = launcherCliArgs(process.argv.slice(2));
|
|
94
|
+
if (isVersionRequest(args)) {
|
|
95
|
+
process.stdout.write(`${version}\n`);
|
|
96
|
+
process.exit(0);
|
|
97
|
+
}
|
|
98
|
+
ensureTuiProfile();
|
|
99
|
+
return {
|
|
100
|
+
args,
|
|
101
|
+
entry: resolveCliEntry(require.resolve)
|
|
102
|
+
};
|
|
103
|
+
} catch (error) {
|
|
104
|
+
fail(error instanceof Error ? error.message : String(error), 1);
|
|
105
|
+
}
|
|
106
|
+
})();
|
|
107
|
+
const child = spawn(process.execPath, [invocation.entry, ...invocation.args], {
|
|
108
|
+
stdio: "inherit",
|
|
109
|
+
env: process.env
|
|
110
|
+
});
|
|
111
|
+
process.on("SIGINT", () => {});
|
|
112
|
+
process.on("SIGTERM", () => {
|
|
113
|
+
child.kill("SIGTERM");
|
|
114
|
+
});
|
|
115
|
+
child.on("error", (error) => {
|
|
116
|
+
fail(`dsh-tui: ${error.message}`, 1);
|
|
117
|
+
});
|
|
118
|
+
child.on("exit", (code, signal) => {
|
|
119
|
+
if (signal !== null) process.exit(128 + constants.signals[signal]);
|
|
120
|
+
process.exit(code ?? 1);
|
|
121
|
+
});
|
|
122
|
+
//#endregion
|
|
123
|
+
export {};
|
|
@@ -0,0 +1,45 @@
|
|
|
1
|
+
/**
|
|
2
|
+
* Launcher decisions for the npm-installed terminal entry: argument
|
|
3
|
+
* normalization, the fresh `tui` profile, and the CLI entry lookup.
|
|
4
|
+
* @module @deepseek-ai/dsh-tui-launcher/launch
|
|
5
|
+
*/
|
|
6
|
+
/** Profile this launcher always boots. */
|
|
7
|
+
export declare const TUI_PROFILE = "tui";
|
|
8
|
+
/** Bundle layers a launcher-created `tui` profile starts from. */
|
|
9
|
+
export declare const TUI_PROFILE_BUNDLES: readonly string[];
|
|
10
|
+
/**
|
|
11
|
+
* Turn the launcher arguments into the dsh CLI arguments.
|
|
12
|
+
*
|
|
13
|
+
* The launcher owns the profile, so profile-selection flags and plugin
|
|
14
|
+
* management are rejected. `watch <id>` becomes the equivalent `--watch <id>`
|
|
15
|
+
* application flag, which the CLI routes to the tui profile on its own.
|
|
16
|
+
* @param argv - arguments after the `dsh-tui` command.
|
|
17
|
+
* @returns the arguments for the dsh CLI.
|
|
18
|
+
* @throws when a caller selects a profile or asks for plugin management.
|
|
19
|
+
*/
|
|
20
|
+
export declare function launcherCliArgs(argv: readonly string[]): string[];
|
|
21
|
+
/**
|
|
22
|
+
* Create the `tui` profile when the directory has no manifest yet.
|
|
23
|
+
*
|
|
24
|
+
* An existing profile is left untouched: it may carry the user's own patch
|
|
25
|
+
* layer and plugin list, and the bundle names resolve from the launcher's
|
|
26
|
+
* installation before the profile anyway.
|
|
27
|
+
* @param dir - profile directory; defaults to `$DSH_HOME/profiles/tui`.
|
|
28
|
+
* @returns the profile directory.
|
|
29
|
+
*/
|
|
30
|
+
export declare function ensureTuiProfile(dir?: string): string;
|
|
31
|
+
/**
|
|
32
|
+
* Resolve the installed CLI entry from the launcher's own installation.
|
|
33
|
+
* @param resolve - Node resolution function anchored at this launcher.
|
|
34
|
+
* @returns the absolute path of the dsh bin script.
|
|
35
|
+
*/
|
|
36
|
+
export declare function resolveCliEntry(resolve: (specifier: string) => string): string;
|
|
37
|
+
/**
|
|
38
|
+
* Whether the invocation only asks for the launcher version. The launcher
|
|
39
|
+
* answers it from its own manifest, without creating a profile or resolving
|
|
40
|
+
* the installed CLI.
|
|
41
|
+
* @param argv - normalized CLI arguments.
|
|
42
|
+
* @returns true when the invocation carries a version flag.
|
|
43
|
+
*/
|
|
44
|
+
export declare function isVersionRequest(argv: readonly string[]): boolean;
|
|
45
|
+
//# sourceMappingURL=launch.d.ts.map
|
package/package.json
CHANGED
|
@@ -1,6 +1,36 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@fishwithcat/dsh-tui",
|
|
3
|
-
"
|
|
4
|
-
"
|
|
5
|
-
"
|
|
6
|
-
|
|
3
|
+
"description": "The npm-installable terminal entry: creates the tui profile and launches the installed dsh CLI",
|
|
4
|
+
"version": "0.2.2-alpha.3.fork.1",
|
|
5
|
+
"type": "module",
|
|
6
|
+
"bin": {
|
|
7
|
+
"dsh-tui": "lib/bin.js"
|
|
8
|
+
},
|
|
9
|
+
"files": [
|
|
10
|
+
"lib/*.js",
|
|
11
|
+
"lib/types/*.d.ts"
|
|
12
|
+
],
|
|
13
|
+
"license": "MIT",
|
|
14
|
+
"repository": {
|
|
15
|
+
"type": "git",
|
|
16
|
+
"url": "https://github.com/FishwithCat/deepseek-harness-tui",
|
|
17
|
+
"directory": "apps/tui-launcher"
|
|
18
|
+
},
|
|
19
|
+
"engines": {
|
|
20
|
+
"node": ">=24.9.0"
|
|
21
|
+
},
|
|
22
|
+
"dependencies": {
|
|
23
|
+
"@deepseek-ai/dsh": "npm:@fishwithcat/dsh@0.2.2-alpha.3.fork.1",
|
|
24
|
+
"@deepseek-ai/dsh-app-boot": "0.2.2-alpha.3",
|
|
25
|
+
"@deepseek-ai/dsh-base": "0.2.2-alpha.3",
|
|
26
|
+
"@deepseek-ai/dsh-agent": "npm:@fishwithcat/dsh-agent@0.2.2-alpha.3",
|
|
27
|
+
"@deepseek-ai/dsh-session": "npm:@fishwithcat/dsh-session@0.2.2-alpha.3",
|
|
28
|
+
"@deepseek-ai/dsh-user-approval": "npm:@fishwithcat/dsh-user-approval@0.2.2-alpha.3",
|
|
29
|
+
"@deepseek-ai/dsh-tool-ask-user": "npm:@fishwithcat/dsh-tool-ask-user@0.2.2-alpha.3",
|
|
30
|
+
"@deepseek-ai/dsh-compaction": "npm:@fishwithcat/dsh-compaction@0.2.2-alpha.3",
|
|
31
|
+
"@deepseek-ai/dsh-compaction-basic": "npm:@fishwithcat/dsh-compaction-basic@0.2.2-alpha.3",
|
|
32
|
+
"@deepseek-ai/dsh-subagent": "npm:@fishwithcat/dsh-subagent@0.2.2-alpha.3",
|
|
33
|
+
"@deepseek-ai/dsh-tool-todo": "npm:@fishwithcat/dsh-tool-todo@0.2.2-alpha.3",
|
|
34
|
+
"@deepseek-ai/dsh-tui-app": "npm:@fishwithcat/dsh-tui-app@0.2.2-alpha.3.fork.1"
|
|
35
|
+
}
|
|
36
|
+
}
|