feat(terminal): POSIX 也预检 shell 可执行文件,统一 shell-not-found 错误码
This commit is contained in:
@@ -25,6 +25,7 @@ import {
|
||||
splitShellArgs,
|
||||
unquotePath,
|
||||
} from '../src/pty-manager.ts'
|
||||
import { SidebarError } from '../src/wire.ts'
|
||||
|
||||
describe('pty helpers', () => {
|
||||
it('prefers an explicit shell, then SHELL, then the account login shell on POSIX', () => {
|
||||
@@ -114,8 +115,41 @@ describe('pty helpers', () => {
|
||||
.toThrow('shell executable not found: "missing-shell"')
|
||||
})
|
||||
|
||||
it('keeps POSIX bare shell resolution delegated to execvp', () => {
|
||||
expect(resolveShellExecutable(' zsh ', { platform: 'linux', env: {}, exists: () => false })).toBe('zsh')
|
||||
it('POSIX: resolves bare names along PATH and names a missing configured shell', () => {
|
||||
const options = {
|
||||
platform: 'linux' as const,
|
||||
env: { PATH: '/usr/local/bin:/usr/bin' },
|
||||
exists: (path: string) => path === join('/usr/bin', 'zsh'),
|
||||
}
|
||||
expect(resolveShellExecutable('zsh', options)).toBe(join('/usr/bin', 'zsh'))
|
||||
const thrown = (() => {
|
||||
try {
|
||||
resolveShellExecutable('nope', options)
|
||||
return undefined
|
||||
} catch (error) {
|
||||
return error
|
||||
}
|
||||
})()
|
||||
expect(thrown).toBeInstanceOf(SidebarError)
|
||||
expect((thrown as SidebarError).code).toBe('shell-not-found')
|
||||
expect((thrown as SidebarError).message).toBe('shell executable not found: "nope"')
|
||||
expect((thrown as SidebarError).meta?.shell).toBe('nope')
|
||||
})
|
||||
|
||||
it('POSIX: checks an absolute path exists and passes it through verbatim', () => {
|
||||
expect(resolveShellExecutable('/explicit/zsh', { platform: 'linux', env: {}, exists: () => true }))
|
||||
.toBe('/explicit/zsh')
|
||||
expect(() => resolveShellExecutable('/missing/zsh', { platform: 'linux', env: {}, exists: () => false }))
|
||||
.toThrow('shell executable not found: "/missing/zsh"')
|
||||
})
|
||||
|
||||
it('unquotes the configured shell before resolving (Windows probe included)', () => {
|
||||
const options = {
|
||||
platform: 'win32' as const,
|
||||
env: { PATH: 'C:\\Tools' },
|
||||
exists: (path: string) => path.replaceAll('\\', '/') === 'C:/Tools/pwsh.exe',
|
||||
}
|
||||
expect(resolveShellExecutable('"pwsh.exe"', options).replaceAll('\\', '/')).toBe('C:/Tools/pwsh.exe')
|
||||
})
|
||||
|
||||
it('trims the configured shell and defaults it to auto for old documents', () => {
|
||||
|
||||
Reference in New Issue
Block a user