From f1e563ad5ffe732a9709432101fec212faca8f48 Mon Sep 17 00:00:00 2001 From: arencoskun Date: Thu, 1 Feb 2024 11:17:25 +0300 Subject: [PATCH 01/10] Expose API method for writing to application side (#4948) --- src/browser/Terminal.ts | 9 +++++++++ src/browser/TestUtils.test.ts | 3 +++ src/browser/public/Terminal.ts | 3 +++ test/playwright/TestUtils.ts | 1 + typings/xterm.d.ts | 6 ++++++ 5 files changed, 22 insertions(+) diff --git a/src/browser/Terminal.ts b/src/browser/Terminal.ts index 0e945aa92b..6e06855a8a 100644 --- a/src/browser/Terminal.ts +++ b/src/browser/Terminal.ts @@ -1191,6 +1191,15 @@ export class Terminal extends CoreTerminal implements ITerminal { return false; } + + /** + * Input data to application side. + * The data is treated the same way as typed input at the terminal (will appear in the onData event). + */ + public input(data: string): void { + this.coreService.triggerDataEvent(data, true); + return this.write(data); + } /** * Resizes the terminal. diff --git a/src/browser/TestUtils.test.ts b/src/browser/TestUtils.test.ts index 59cc773a47..95f1fbacdc 100644 --- a/src/browser/TestUtils.test.ts +++ b/src/browser/TestUtils.test.ts @@ -72,6 +72,9 @@ export class MockTerminal implements ITerminal { public focus(): void { throw new Error('Method not implemented.'); } + public input(data: string): void { + throw new Error('Method not implemented.'); + } public resize(columns: number, rows: number): void { throw new Error('Method not implemented.'); } diff --git a/src/browser/public/Terminal.ts b/src/browser/public/Terminal.ts index ade46fa482..d8c8315d87 100644 --- a/src/browser/public/Terminal.ts +++ b/src/browser/public/Terminal.ts @@ -138,6 +138,9 @@ export class Terminal extends Disposable implements ITerminalApi { public focus(): void { this._core.focus(); } + public input(data: string): void { + this._core.input(data); + } public resize(columns: number, rows: number): void { this._verifyIntegers(columns, rows); this._core.resize(columns, rows); diff --git a/test/playwright/TestUtils.ts b/test/playwright/TestUtils.ts index 4d4112f07a..facbc881aa 100644 --- a/test/playwright/TestUtils.ts +++ b/test/playwright/TestUtils.ts @@ -216,6 +216,7 @@ export class TerminalProxy implements ITerminalProxyCustomMethods, PlaywrightApi return new Promise(r => term.writeln(typeof data === 'string' ? data : new Uint8Array(data), r)); }, [await this.getHandle(), typeof data === 'string' ? data : Array.from(data)] as const); } + public async input(data: string): Promise { return this.evaluate(([term]) => term.input(data)); } public async resize(cols: number, rows: number): Promise { return this._page.evaluate(([term, cols, rows]) => term.resize(cols, rows), [await this.getHandle(), cols, rows] as const); } public async registerMarker(y?: number | undefined): Promise { return this._page.evaluate(([term, y]) => term.registerMarker(y), [await this.getHandle(), y] as const); } public async registerDecoration(decorationOptions: IDecorationOptions): Promise { return this._page.evaluate(([term, decorationOptions]) => term.registerDecoration(decorationOptions), [await this.getHandle(), decorationOptions] as const); } diff --git a/typings/xterm.d.ts b/typings/xterm.d.ts index 39a9c91a52..9268063979 100644 --- a/typings/xterm.d.ts +++ b/typings/xterm.d.ts @@ -962,6 +962,12 @@ declare module '@xterm/xterm' { * Focus the terminal. */ focus(): void; + + /** + * Input data to application side. + * The data is treated the same way as typed input at the terminal (will appear in the onData event). + */ + input(data: string): void; /** * Resizes the terminal. It's best practice to debounce calls to resize, From bbd1a1dbe2aac4d0463f35d9fdaf2730bdfbcd7f Mon Sep 17 00:00:00 2001 From: arencoskun Date: Thu, 1 Feb 2024 13:05:13 +0300 Subject: [PATCH 02/10] Try to fix linter errors --- src/browser/Terminal.ts | 7 ++++--- 1 file changed, 4 insertions(+), 3 deletions(-) diff --git a/src/browser/Terminal.ts b/src/browser/Terminal.ts index 6e06855a8a..0b4d2e70bf 100644 --- a/src/browser/Terminal.ts +++ b/src/browser/Terminal.ts @@ -1193,9 +1193,10 @@ export class Terminal extends CoreTerminal implements ITerminal { } /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal (will appear in the onData event). - */ + * Input data to application side. + * The data is treated the same way as typed input at the terminal. + * (will appear in the onData event). + */ public input(data: string): void { this.coreService.triggerDataEvent(data, true); return this.write(data); From 09a0dd658d20b8ab623a7a85f1f7e29c36ef9e85 Mon Sep 17 00:00:00 2001 From: arencoskun Date: Thu, 1 Feb 2024 13:11:54 +0300 Subject: [PATCH 03/10] Final fixes --- src/browser/Terminal.ts | 12 ++++++------ 1 file changed, 6 insertions(+), 6 deletions(-) diff --git a/src/browser/Terminal.ts b/src/browser/Terminal.ts index 0b4d2e70bf..b680cc971f 100644 --- a/src/browser/Terminal.ts +++ b/src/browser/Terminal.ts @@ -1191,15 +1191,15 @@ export class Terminal extends CoreTerminal implements ITerminal { return false; } - + /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal. - * (will appear in the onData event). - */ + * Input data to application side. + * The data is treated the same way as typed input at the terminal. + * (will appear in the onData event). + */ public input(data: string): void { this.coreService.triggerDataEvent(data, true); - return this.write(data); + this.write(data); } /** From cae42772e88732a29d7980d4bbb5661f59aaa859 Mon Sep 17 00:00:00 2001 From: arencoskun Date: Thu, 1 Feb 2024 14:11:29 +0300 Subject: [PATCH 04/10] Move function to CoreTerminal, add additional argument to specify if the input was user input or not. --- src/browser/Terminal.ts | 10 ---------- src/browser/TestUtils.test.ts | 2 +- src/browser/public/Terminal.ts | 4 ++-- src/common/CoreTerminal.ts | 13 +++++++++++++ test/playwright/TestUtils.ts | 2 +- typings/xterm.d.ts | 6 +++++- 6 files changed, 22 insertions(+), 15 deletions(-) diff --git a/src/browser/Terminal.ts b/src/browser/Terminal.ts index b680cc971f..0e945aa92b 100644 --- a/src/browser/Terminal.ts +++ b/src/browser/Terminal.ts @@ -1192,16 +1192,6 @@ export class Terminal extends CoreTerminal implements ITerminal { return false; } - /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal. - * (will appear in the onData event). - */ - public input(data: string): void { - this.coreService.triggerDataEvent(data, true); - this.write(data); - } - /** * Resizes the terminal. * diff --git a/src/browser/TestUtils.test.ts b/src/browser/TestUtils.test.ts index 95f1fbacdc..c7c8438cc0 100644 --- a/src/browser/TestUtils.test.ts +++ b/src/browser/TestUtils.test.ts @@ -72,7 +72,7 @@ export class MockTerminal implements ITerminal { public focus(): void { throw new Error('Method not implemented.'); } - public input(data: string): void { + public input(data: string, wasUserInput: boolean = true): void { throw new Error('Method not implemented.'); } public resize(columns: number, rows: number): void { diff --git a/src/browser/public/Terminal.ts b/src/browser/public/Terminal.ts index d8c8315d87..a6349225df 100644 --- a/src/browser/public/Terminal.ts +++ b/src/browser/public/Terminal.ts @@ -138,8 +138,8 @@ export class Terminal extends Disposable implements ITerminalApi { public focus(): void { this._core.focus(); } - public input(data: string): void { - this._core.input(data); + public input(data: string, wasUserInput: boolean = true): void { + this._core.input(data, wasUserInput); } public resize(columns: number, rows: number): void { this._verifyIntegers(columns, rows); diff --git a/src/common/CoreTerminal.ts b/src/common/CoreTerminal.ts index 1789daf8bd..b624245805 100644 --- a/src/common/CoreTerminal.ts +++ b/src/common/CoreTerminal.ts @@ -168,6 +168,19 @@ export abstract class CoreTerminal extends Disposable implements ICoreTerminal { this._writeBuffer.writeSync(data, maxSubsequentCalls); } + /** + * Input data to application side. + * The data is treated the same way as typed input at the terminal. + * (will appear in the onData event). + * wasUserInput indicates, whether the input is genuine user input. + * It is true by default and triggers additional actions like prompt focus or selection clearing. + * Set it to false if your data sent does not resemble what a user would have typed + * (e.g. sequence embedded data). + */ + public input(data: string, wasUserInput: boolean = true): void { + this.coreService.triggerDataEvent(data, wasUserInput); + } + public resize(x: number, y: number): void { if (isNaN(x) || isNaN(y)) { return; diff --git a/test/playwright/TestUtils.ts b/test/playwright/TestUtils.ts index facbc881aa..1427578c11 100644 --- a/test/playwright/TestUtils.ts +++ b/test/playwright/TestUtils.ts @@ -216,7 +216,7 @@ export class TerminalProxy implements ITerminalProxyCustomMethods, PlaywrightApi return new Promise(r => term.writeln(typeof data === 'string' ? data : new Uint8Array(data), r)); }, [await this.getHandle(), typeof data === 'string' ? data : Array.from(data)] as const); } - public async input(data: string): Promise { return this.evaluate(([term]) => term.input(data)); } + public async input(data: string, wasUserInput: boolean = true): Promise { return this.evaluate(([term]) => term.input(data, wasUserInput)); } public async resize(cols: number, rows: number): Promise { return this._page.evaluate(([term, cols, rows]) => term.resize(cols, rows), [await this.getHandle(), cols, rows] as const); } public async registerMarker(y?: number | undefined): Promise { return this._page.evaluate(([term, y]) => term.registerMarker(y), [await this.getHandle(), y] as const); } public async registerDecoration(decorationOptions: IDecorationOptions): Promise { return this._page.evaluate(([term, decorationOptions]) => term.registerDecoration(decorationOptions), [await this.getHandle(), decorationOptions] as const); } diff --git a/typings/xterm.d.ts b/typings/xterm.d.ts index 9268063979..95c368b191 100644 --- a/typings/xterm.d.ts +++ b/typings/xterm.d.ts @@ -966,8 +966,12 @@ declare module '@xterm/xterm' { /** * Input data to application side. * The data is treated the same way as typed input at the terminal (will appear in the onData event). + * wasUserInput indicates, whether the input is genuine user input. + * It is true by default and triggers additional actions like prompt focus or selection clearing. + * Set it to false if your data sent does not resemble what a user would have typed + * (e.g. sequence embedded data). */ - input(data: string): void; + input(data: string, wasUserInput?: boolean): void; /** * Resizes the terminal. It's best practice to debounce calls to resize, From c51a0b745439b60cda5c49d4ecf2873bf08e1dae Mon Sep 17 00:00:00 2001 From: arencoskun Date: Thu, 1 Feb 2024 16:05:02 +0300 Subject: [PATCH 05/10] Fix linter errors (hopefully) --- typings/xterm.d.ts | 12 +++++++----- 1 file changed, 7 insertions(+), 5 deletions(-) diff --git a/typings/xterm.d.ts b/typings/xterm.d.ts index 95c368b191..c8189e18bf 100644 --- a/typings/xterm.d.ts +++ b/typings/xterm.d.ts @@ -962,14 +962,16 @@ declare module '@xterm/xterm' { * Focus the terminal. */ focus(): void; - + /** * Input data to application side. - * The data is treated the same way as typed input at the terminal (will appear in the onData event). + * The data is treated the same way as typed input at the terminal + * (will appear in the onData event). * wasUserInput indicates, whether the input is genuine user input. - * It is true by default and triggers additional actions like prompt focus or selection clearing. - * Set it to false if your data sent does not resemble what a user would have typed - * (e.g. sequence embedded data). + * It is true by default and triggers additional actions like prompt + * focus or selection clearing. + * Set it to false if your data sent does not resemble + * what a user would have typed (e.g. sequence embedded data). */ input(data: string, wasUserInput?: boolean): void; From 06aa2c86df8fcd8e60c1d8df9e02513438db3bb0 Mon Sep 17 00:00:00 2001 From: arencoskun Date: Thu, 1 Feb 2024 16:32:31 +0300 Subject: [PATCH 06/10] Whitespace fix --- typings/xterm.d.ts | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/typings/xterm.d.ts b/typings/xterm.d.ts index c8189e18bf..3de30524d0 100644 --- a/typings/xterm.d.ts +++ b/typings/xterm.d.ts @@ -968,7 +968,7 @@ declare module '@xterm/xterm' { * The data is treated the same way as typed input at the terminal * (will appear in the onData event). * wasUserInput indicates, whether the input is genuine user input. - * It is true by default and triggers additional actions like prompt + * It is true by default and triggers additional actions like prompt * focus or selection clearing. * Set it to false if your data sent does not resemble * what a user would have typed (e.g. sequence embedded data). From cddc888065e849e17543ec7f46394688e1ce09f8 Mon Sep 17 00:00:00 2001 From: arencoskun Date: Thu, 1 Feb 2024 16:49:15 +0300 Subject: [PATCH 07/10] Add definition to xterm-headless.d.ts --- typings/xterm-headless.d.ts | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/typings/xterm-headless.d.ts b/typings/xterm-headless.d.ts index f8cef382f3..81a6aad195 100644 --- a/typings/xterm-headless.d.ts +++ b/typings/xterm-headless.d.ts @@ -718,6 +718,18 @@ declare module '@xterm/headless' { */ onTitleChange: IEvent; + /** + * Input data to application side. + * The data is treated the same way as typed input at the terminal + * (will appear in the onData event). + * wasUserInput indicates, whether the input is genuine user input. + * It is true by default and triggers additional actions like prompt + * focus or selection clearing. + * Set it to false if your data sent does not resemble + * what a user would have typed (e.g. sequence embedded data). + */ + input(data: string, wasUserInput?: boolean): void; + /** * Resizes the terminal. It's best practice to debounce calls to resize, * this will help ensure that the pty can respond to the resize event From dce6e31c89531c3345e4f4fd56acdc7484fa9a63 Mon Sep 17 00:00:00 2001 From: arencoskun Date: Fri, 2 Feb 2024 08:59:57 +0300 Subject: [PATCH 08/10] Add headless definitons --- src/headless/Terminal.ts | 13 +++++++++++++ src/headless/public/Terminal.ts | 3 +++ 2 files changed, 16 insertions(+) diff --git a/src/headless/Terminal.ts b/src/headless/Terminal.ts index 18000c8f7a..c1e4950faa 100644 --- a/src/headless/Terminal.ts +++ b/src/headless/Terminal.ts @@ -81,6 +81,19 @@ export class Terminal extends CoreTerminal { this._onBell.fire(); } + /** + * Input data to application side. + * The data is treated the same way as typed input at the terminal. + * (will appear in the onData event). + * wasUserInput indicates, whether the input is genuine user input. + * It is true by default and triggers additional actions like prompt focus or selection clearing. + * Set it to false if your data sent does not resemble what a user would have typed + * (e.g. sequence embedded data). + */ + public input(data: string, wasUserInput: boolean = true): void { + this.coreService.triggerDataEvent(data, wasUserInput); + } + /** * Resizes the terminal. * diff --git a/src/headless/public/Terminal.ts b/src/headless/public/Terminal.ts index df202660f8..0d73f9d359 100644 --- a/src/headless/public/Terminal.ts +++ b/src/headless/public/Terminal.ts @@ -134,6 +134,9 @@ export class Terminal extends Disposable implements ITerminalApi { this._publicOptions[propName] = options[propName]; } } + public input(data: string, wasUserInput: boolean = true): void { + this._core.input(data, wasUserInput); + } public resize(columns: number, rows: number): void { this._verifyIntegers(columns, rows); this._core.resize(columns, rows); From b1a72b2e839755c0b86754d475e9b8e62450a3ba Mon Sep 17 00:00:00 2001 From: arencoskun Date: Fri, 2 Feb 2024 09:04:53 +0300 Subject: [PATCH 09/10] Linter fix --- src/headless/Terminal.ts | 18 +++++++++--------- 1 file changed, 9 insertions(+), 9 deletions(-) diff --git a/src/headless/Terminal.ts b/src/headless/Terminal.ts index c1e4950faa..a5f7736a2c 100644 --- a/src/headless/Terminal.ts +++ b/src/headless/Terminal.ts @@ -81,15 +81,15 @@ export class Terminal extends CoreTerminal { this._onBell.fire(); } - /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal. - * (will appear in the onData event). - * wasUserInput indicates, whether the input is genuine user input. - * It is true by default and triggers additional actions like prompt focus or selection clearing. - * Set it to false if your data sent does not resemble what a user would have typed - * (e.g. sequence embedded data). - */ + /** + * Input data to application side. + * The data is treated the same way as typed input at the terminal. + * (will appear in the onData event). + * wasUserInput indicates, whether the input is genuine user input. + * It is true by default and triggers additional actions like prompt focus or selection clearing. + * Set it to false if your data sent does not resemble what a user would have typed + * (e.g. sequence embedded data). + */ public input(data: string, wasUserInput: boolean = true): void { this.coreService.triggerDataEvent(data, wasUserInput); } From 8d1771ef646a27c764b3edb7d9d72dcd100359b2 Mon Sep 17 00:00:00 2001 From: Daniel Imms <2193314+Tyriar@users.noreply.github.com> Date: Fri, 2 Feb 2024 12:03:08 -0800 Subject: [PATCH 10/10] Tweak docs --- src/common/CoreTerminal.ts | 9 --------- src/headless/Terminal.ts | 9 --------- typings/xterm-headless.d.ts | 16 ++++++++-------- typings/xterm.d.ts | 16 ++++++++-------- 4 files changed, 16 insertions(+), 34 deletions(-) diff --git a/src/common/CoreTerminal.ts b/src/common/CoreTerminal.ts index b624245805..327b8bc2f7 100644 --- a/src/common/CoreTerminal.ts +++ b/src/common/CoreTerminal.ts @@ -168,15 +168,6 @@ export abstract class CoreTerminal extends Disposable implements ICoreTerminal { this._writeBuffer.writeSync(data, maxSubsequentCalls); } - /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal. - * (will appear in the onData event). - * wasUserInput indicates, whether the input is genuine user input. - * It is true by default and triggers additional actions like prompt focus or selection clearing. - * Set it to false if your data sent does not resemble what a user would have typed - * (e.g. sequence embedded data). - */ public input(data: string, wasUserInput: boolean = true): void { this.coreService.triggerDataEvent(data, wasUserInput); } diff --git a/src/headless/Terminal.ts b/src/headless/Terminal.ts index a5f7736a2c..66040756f6 100644 --- a/src/headless/Terminal.ts +++ b/src/headless/Terminal.ts @@ -81,15 +81,6 @@ export class Terminal extends CoreTerminal { this._onBell.fire(); } - /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal. - * (will appear in the onData event). - * wasUserInput indicates, whether the input is genuine user input. - * It is true by default and triggers additional actions like prompt focus or selection clearing. - * Set it to false if your data sent does not resemble what a user would have typed - * (e.g. sequence embedded data). - */ public input(data: string, wasUserInput: boolean = true): void { this.coreService.triggerDataEvent(data, wasUserInput); } diff --git a/typings/xterm-headless.d.ts b/typings/xterm-headless.d.ts index 81a6aad195..b2ad5745b6 100644 --- a/typings/xterm-headless.d.ts +++ b/typings/xterm-headless.d.ts @@ -719,14 +719,14 @@ declare module '@xterm/headless' { onTitleChange: IEvent; /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal - * (will appear in the onData event). - * wasUserInput indicates, whether the input is genuine user input. - * It is true by default and triggers additional actions like prompt - * focus or selection clearing. - * Set it to false if your data sent does not resemble - * what a user would have typed (e.g. sequence embedded data). + * Input data to application side. The data is treated the same way input + * typed into the terminal would (ie. the {@link onData} event will fire). + * @param data The data to forward to the application. + * @param wasUserInput Whether the input is genuine user input. This is true + * by default and triggers additionalbehavior like focus or selection + * clearing. Set this to false if the data sent should not be treated like + * user input would, for example passing an escape sequence to the + * application. */ input(data: string, wasUserInput?: boolean): void; diff --git a/typings/xterm.d.ts b/typings/xterm.d.ts index 3de30524d0..d957d6551d 100644 --- a/typings/xterm.d.ts +++ b/typings/xterm.d.ts @@ -964,14 +964,14 @@ declare module '@xterm/xterm' { focus(): void; /** - * Input data to application side. - * The data is treated the same way as typed input at the terminal - * (will appear in the onData event). - * wasUserInput indicates, whether the input is genuine user input. - * It is true by default and triggers additional actions like prompt - * focus or selection clearing. - * Set it to false if your data sent does not resemble - * what a user would have typed (e.g. sequence embedded data). + * Input data to application side. The data is treated the same way input + * typed into the terminal would (ie. the {@link onData} event will fire). + * @param data The data to forward to the application. + * @param wasUserInput Whether the input is genuine user input. This is true + * by default and triggers additionalbehavior like focus or selection + * clearing. Set this to false if the data sent should not be treated like + * user input would, for example passing an escape sequence to the + * application. */ input(data: string, wasUserInput?: boolean): void;