mirror of
https://github.com/deepseek-ai/deepseek-harness
synced 2026-08-15 21:04:50 +00:00
fix(ui): surface declarative startup failures
This commit is contained in:
@@ -23,7 +23,7 @@ Each run starts a fresh session by default (its event log lands under `./.sessio
|
||||
RESUME_SESSION_ID=<prior-session-id> pnpm run demo:repl
|
||||
```
|
||||
|
||||
The id is wired through `cordis.yml` (`resumeSessionId: !!js process.env.RESUME_SESSION_ID`); unset, the agent starts a new session. A missing or unreadable id starts no `main` agent, so unset it or choose an existing session id.
|
||||
The id is wired through `cordis.yml` (`resumeSessionId: !!js process.env.RESUME_SESSION_ID`); unset, the agent starts a new session. A missing or unreadable id starts no `main` agent and emits `agent/start-failed`; both terminal front doors print the failure and exit nonzero, so unset it or choose an existing session id.
|
||||
|
||||
## Code Mode
|
||||
|
||||
|
||||
@@ -13,7 +13,7 @@ const tsxLoader = fileURLToPath(import.meta.resolve('tsx'))
|
||||
|
||||
const PTY_DRIVER = String.raw`
|
||||
import errno, os, pty, select, signal, sys, time
|
||||
node, tsx_loader, bin_script, config_path, tsconfig_path, cwd = sys.argv[1:]
|
||||
node, tsx_loader, bin_script, config_path, tsconfig_path, cwd, resume_session_id = sys.argv[1:]
|
||||
env = os.environ.copy()
|
||||
env.update({
|
||||
"DEEPSEEK_API_KEY": "keyless-tui-no-call",
|
||||
@@ -21,6 +21,8 @@ env.update({
|
||||
"DSH_AGENTS_HOME": os.path.join(cwd, ".agents"),
|
||||
"TSX_TSCONFIG_PATH": tsconfig_path,
|
||||
})
|
||||
if resume_session_id:
|
||||
env["RESUME_SESSION_ID"] = resume_session_id
|
||||
pid, fd = pty.fork()
|
||||
if pid == 0:
|
||||
os.chdir(cwd)
|
||||
@@ -53,15 +55,23 @@ if status is None:
|
||||
os.kill(pid, signal.SIGKILL)
|
||||
_, status = os.waitpid(pid, 0)
|
||||
sys.stdout.buffer.write(output)
|
||||
if not sent_exit:
|
||||
sys.stderr.write("TUI did not render its welcome marker before timeout\n")
|
||||
sys.exit(124)
|
||||
if not os.WIFEXITED(status) or os.WEXITSTATUS(status) != 0:
|
||||
sys.stderr.write("TUI child did not exit cleanly\n")
|
||||
sys.exit(125)
|
||||
if resume_session_id:
|
||||
if b'ui-tui: agent "main" failed to start:' not in output:
|
||||
sys.stderr.write("TUI did not render the startup failure before timeout\n")
|
||||
sys.exit(126)
|
||||
if not os.WIFEXITED(status) or os.WEXITSTATUS(status) != 1:
|
||||
sys.stderr.write("TUI startup failure did not exit with status 1\n")
|
||||
sys.exit(127)
|
||||
else:
|
||||
if not sent_exit:
|
||||
sys.stderr.write("TUI did not render its welcome marker before timeout\n")
|
||||
sys.exit(124)
|
||||
if not os.WIFEXITED(status) or os.WEXITSTATUS(status) != 0:
|
||||
sys.stderr.write("TUI child did not exit cleanly\n")
|
||||
sys.exit(125)
|
||||
`
|
||||
|
||||
async function runTuiLoaderSmoke(): Promise<string> {
|
||||
async function runTuiLoaderSmoke(resumeSessionId = ''): Promise<string> {
|
||||
const cwd = await mkdtemp(join(tmpdir(), 'coding-tui-smoke-'))
|
||||
try {
|
||||
return await new Promise((resolve, reject) => {
|
||||
@@ -74,6 +84,7 @@ async function runTuiLoaderSmoke(): Promise<string> {
|
||||
configPath,
|
||||
tsconfigPath,
|
||||
cwd,
|
||||
resumeSessionId,
|
||||
], { stdio: ['ignore', 'pipe', 'pipe'] })
|
||||
let stdout = ''
|
||||
let stderr = ''
|
||||
@@ -98,4 +109,10 @@ describe('coding-agent TUI keyless smoke (real Loader tree in a PTY)', () => {
|
||||
expect(output).toContain('DEEPSEEK')
|
||||
expect(output).toContain('agent REPL ready.')
|
||||
}, LOADER_SMOKE_TEST_TIMEOUT_MS)
|
||||
|
||||
it('prints a config-resume failure and exits instead of leaving a blank terminal', async () => {
|
||||
const output = await runTuiLoaderSmoke('missing-session')
|
||||
expect(output).toContain('ui-tui: agent "main" failed to start:')
|
||||
expect(output).toContain('missing-session')
|
||||
}, LOADER_SMOKE_TEST_TIMEOUT_MS)
|
||||
})
|
||||
|
||||
Reference in New Issue
Block a user