mirror of
https://github.com/google-gemini/gemini-cli.git
synced 2026-05-13 05:12:55 -07:00
fix: Ignore correct errors thrown when resizing or scrolling an exited pty (#11440)
This commit is contained in:
@@ -291,6 +291,54 @@ describe('ShellExecutionService', () => {
|
|||||||
expect(mockHeadlessTerminal.resize).toHaveBeenCalledWith(100, 40);
|
expect(mockHeadlessTerminal.resize).toHaveBeenCalledWith(100, 40);
|
||||||
});
|
});
|
||||||
|
|
||||||
|
it('should not resize the pty if it is not active', async () => {
|
||||||
|
const isPtyActiveSpy = vi
|
||||||
|
.spyOn(ShellExecutionService, 'isPtyActive')
|
||||||
|
.mockReturnValue(false);
|
||||||
|
|
||||||
|
await simulateExecution('ls -l', (pty) => {
|
||||||
|
ShellExecutionService.resizePty(pty.pid!, 100, 40);
|
||||||
|
pty.onExit.mock.calls[0][0]({ exitCode: 0, signal: null });
|
||||||
|
});
|
||||||
|
|
||||||
|
expect(mockPtyProcess.resize).not.toHaveBeenCalled();
|
||||||
|
expect(mockHeadlessTerminal.resize).not.toHaveBeenCalled();
|
||||||
|
isPtyActiveSpy.mockRestore();
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should ignore errors when resizing an exited pty', async () => {
|
||||||
|
const resizeError = new Error(
|
||||||
|
'Cannot resize a pty that has already exited',
|
||||||
|
);
|
||||||
|
mockPtyProcess.resize.mockImplementation(() => {
|
||||||
|
throw resizeError;
|
||||||
|
});
|
||||||
|
|
||||||
|
// We don't expect this test to throw an error
|
||||||
|
await expect(
|
||||||
|
simulateExecution('ls -l', (pty) => {
|
||||||
|
ShellExecutionService.resizePty(pty.pid!, 100, 40);
|
||||||
|
pty.onExit.mock.calls[0][0]({ exitCode: 0, signal: null });
|
||||||
|
}),
|
||||||
|
).resolves.not.toThrow();
|
||||||
|
|
||||||
|
expect(mockPtyProcess.resize).toHaveBeenCalledWith(100, 40);
|
||||||
|
});
|
||||||
|
|
||||||
|
it('should re-throw other errors during resize', async () => {
|
||||||
|
const otherError = new Error('Some other error');
|
||||||
|
mockPtyProcess.resize.mockImplementation(() => {
|
||||||
|
throw otherError;
|
||||||
|
});
|
||||||
|
|
||||||
|
await expect(
|
||||||
|
simulateExecution('ls -l', (pty) => {
|
||||||
|
ShellExecutionService.resizePty(pty.pid!, 100, 40);
|
||||||
|
pty.onExit.mock.calls[0][0]({ exitCode: 0, signal: null });
|
||||||
|
}),
|
||||||
|
).rejects.toThrow('Some other error');
|
||||||
|
});
|
||||||
|
|
||||||
it('should scroll the headless terminal', async () => {
|
it('should scroll the headless terminal', async () => {
|
||||||
await simulateExecution('ls -l', (pty) => {
|
await simulateExecution('ls -l', (pty) => {
|
||||||
pty.onData.mock.calls[0][0]('file1.txt\n');
|
pty.onData.mock.calls[0][0]('file1.txt\n');
|
||||||
|
|||||||
@@ -750,7 +750,11 @@ export class ShellExecutionService {
|
|||||||
} catch (e) {
|
} catch (e) {
|
||||||
// Ignore errors if the pty has already exited, which can happen
|
// Ignore errors if the pty has already exited, which can happen
|
||||||
// due to a race condition between the exit event and this call.
|
// due to a race condition between the exit event and this call.
|
||||||
if (e instanceof Error && 'code' in e && e.code === 'ESRCH') {
|
if (
|
||||||
|
e instanceof Error &&
|
||||||
|
(('code' in e && e.code === 'ESRCH') ||
|
||||||
|
e.message === 'Cannot resize a pty that has already exited')
|
||||||
|
) {
|
||||||
// ignore
|
// ignore
|
||||||
} else {
|
} else {
|
||||||
throw e;
|
throw e;
|
||||||
|
|||||||
Reference in New Issue
Block a user