xterm add

This commit is contained in:
Sourabh Jain 2025-02-18 17:11:39 +05:30
parent 0babb1fa13
commit 1678ec0a23
4 changed files with 77 additions and 47 deletions

15
package-lock.json generated
View File

@ -18,7 +18,6 @@
"@babel/plugin-proposal-decorators": "7.12.12", "@babel/plugin-proposal-decorators": "7.12.12",
"@fluentui/react": "8.119.0", "@fluentui/react": "8.119.0",
"@fluentui/react-components": "9.54.2", "@fluentui/react-components": "9.54.2",
"@jupyterlab/services": "6.0.2",
"@jupyterlab/terminal": "3.0.3", "@jupyterlab/terminal": "3.0.3",
"@microsoft/applicationinsights-web": "2.6.1", "@microsoft/applicationinsights-web": "2.6.1",
"@nteract/commutable": "7.5.1", "@nteract/commutable": "7.5.1",
@ -114,6 +113,7 @@
"tinykeys": "2.1.0", "tinykeys": "2.1.0",
"underscore": "1.12.1", "underscore": "1.12.1",
"utility-types": "3.10.0", "utility-types": "3.10.0",
"xterm-for-react": "1.0.4",
"zustand": "3.5.0" "zustand": "3.5.0"
}, },
"devDependencies": { "devDependencies": {
@ -36550,6 +36550,19 @@
"xterm": "^4.0.0" "xterm": "^4.0.0"
} }
}, },
"node_modules/xterm-for-react": {
"version": "1.0.4",
"resolved": "https://registry.npmjs.org/xterm-for-react/-/xterm-for-react-1.0.4.tgz",
"integrity": "sha512-DCkLR9ZXeW907YyyaCTk/3Ol34VRHfCnf3MAPOkj3dUNA85sDqHvTXN8efw4g7bx7gWdJQRsEpGt2tJOXKG3EQ==",
"dependencies": {
"prop-types": "^15.7.2",
"xterm": "^4.5.0"
},
"peerDependencies": {
"react": "^16.0.0",
"react-dom": "^16.0.0"
}
},
"node_modules/y18n": { "node_modules/y18n": {
"version": "4.0.3", "version": "4.0.3",
"license": "ISC" "license": "ISC"

View File

@ -13,7 +13,6 @@
"@babel/plugin-proposal-decorators": "7.12.12", "@babel/plugin-proposal-decorators": "7.12.12",
"@fluentui/react": "8.119.0", "@fluentui/react": "8.119.0",
"@fluentui/react-components": "9.54.2", "@fluentui/react-components": "9.54.2",
"@jupyterlab/services": "6.0.2",
"@jupyterlab/terminal": "3.0.3", "@jupyterlab/terminal": "3.0.3",
"@microsoft/applicationinsights-web": "2.6.1", "@microsoft/applicationinsights-web": "2.6.1",
"@nteract/commutable": "7.5.1", "@nteract/commutable": "7.5.1",
@ -46,6 +45,7 @@
"@types/mkdirp": "1.0.1", "@types/mkdirp": "1.0.1",
"@types/node-fetch": "2.5.7", "@types/node-fetch": "2.5.7",
"@xmldom/xmldom": "0.7.13", "@xmldom/xmldom": "0.7.13",
"xterm-for-react":"1.0.4",
"allotment": "1.20.2", "allotment": "1.20.2",
"applicationinsights": "1.8.0", "applicationinsights": "1.8.0",
"bootstrap": "3.4.1", "bootstrap": "3.4.1",

View File

@ -10,10 +10,11 @@ import * as DataModels from "../../Contracts/DataModels";
import * as ViewModels from "../../Contracts/ViewModels"; import * as ViewModels from "../../Contracts/ViewModels";
import { userContext } from "../../UserContext"; import { userContext } from "../../UserContext";
import { CommandButtonComponentProps } from "../Controls/CommandButton/CommandButtonComponent"; import { CommandButtonComponentProps } from "../Controls/CommandButton/CommandButtonComponent";
import { NotebookTerminalComponent } from "../Controls/Notebook/NotebookTerminalComponent";
import Explorer from "../Explorer"; import Explorer from "../Explorer";
import { useNotebook } from "../Notebook/useNotebook"; //import { useNotebook } from "../Notebook/useNotebook";
import TabsBase from "./TabsBase"; import TabsBase from "./TabsBase";
import XTermComponent from "./XTermComponent";
export interface TerminalTabOptions extends ViewModels.TabOptions { export interface TerminalTabOptions extends ViewModels.TabOptions {
account: DataModels.DatabaseAccount; account: DataModels.DatabaseAccount;
@ -25,7 +26,7 @@ export interface TerminalTabOptions extends ViewModels.TabOptions {
/** /**
* Notebook terminal tab * Notebook terminal tab
*/ */
class NotebookTerminalComponentAdapter implements ReactAdapter { class XTermAdapter implements ReactAdapter {
// parameters: true: show, false: hide // parameters: true: show, false: hide
public parameters: ko.Computed<boolean>; public parameters: ko.Computed<boolean>;
constructor( constructor(
@ -47,14 +48,14 @@ class NotebookTerminalComponentAdapter implements ReactAdapter {
/> />
); );
} }
return this.parameters() ? ( return this.parameters() ? (
<NotebookTerminalComponent <XTermComponent />
notebookServerInfo={this.getNotebookServerInfo()} // <NotebookTerminalComponent
databaseAccount={this.getDatabaseAccount()} // notebookServerInfo={this.getNotebookServerInfo()}
tabId={this.getTabId()} // databaseAccount={this.getDatabaseAccount()}
username={this.getUsername()} // tabId={this.getTabId()}
/> // username={this.getUsername()}
// />
) : ( ) : (
<Spinner styles={{ root: { marginTop: 10 } }} size={SpinnerSize.large}></Spinner> <Spinner styles={{ root: { marginTop: 10 } }} size={SpinnerSize.large}></Spinner>
); );
@ -74,28 +75,28 @@ class NotebookTerminalComponentAdapter implements ReactAdapter {
} }
export default class TerminalTab extends TabsBase { export default class TerminalTab extends TabsBase {
public readonly html = '<div style="height: 100%" data-bind="react:notebookTerminalComponentAdapter"></div> '; public readonly html = '<div style="height: 100%" data-bind="react: xtermAdapter"></div>';
private container: Explorer; private container: Explorer;
private notebookTerminalComponentAdapter: NotebookTerminalComponentAdapter; private xtermAdapter: XTermAdapter;
private isAllPublicIPAddressesEnabled: ko.Observable<boolean>; private isAllPublicIPAddressesEnabled: ko.Observable<boolean>;
constructor(options: TerminalTabOptions) { constructor(options: TerminalTabOptions) {
super(options); super(options);
this.container = options.container; this.container = options.container;
this.isAllPublicIPAddressesEnabled = ko.observable(true); this.isAllPublicIPAddressesEnabled = ko.observable(true);
this.notebookTerminalComponentAdapter = new NotebookTerminalComponentAdapter( this.xtermAdapter = new XTermAdapter(
() => this.getNotebookServerInfo(options), () => null,
() => userContext?.databaseAccount, () => userContext?.databaseAccount,
() => this.tabId, () => this.tabId,
() => this.getUsername(), () => this.getUsername(),
this.isAllPublicIPAddressesEnabled, this.isAllPublicIPAddressesEnabled,
options.kind, options.kind,
); );
this.notebookTerminalComponentAdapter.parameters = ko.computed<boolean>(() => { this.xtermAdapter.parameters = ko.computed<boolean>(() => {
if ( if (
this.isTemplateReady() && this.isTemplateReady() &&
useNotebook.getState().isNotebookEnabled && // useNotebook.getState().isNotebookEnabled &&
useNotebook.getState().notebookServerInfo?.notebookServerEndpoint && // useNotebook.getState().notebookServerInfo?.notebookServerEndpoint &&
this.isAllPublicIPAddressesEnabled() this.isAllPublicIPAddressesEnabled()
) { ) {
return true; return true;
@ -134,41 +135,41 @@ export default class TerminalTab extends TabsBase {
this.updateNavbarWithTabsButtons(); this.updateNavbarWithTabsButtons();
} }
private getNotebookServerInfo(options: TerminalTabOptions): DataModels.NotebookWorkspaceConnectionInfo { // private getNotebookServerInfo(options: TerminalTabOptions): DataModels.NotebookWorkspaceConnectionInfo {
let endpointSuffix: string; // let endpointSuffix: string;
switch (options.kind) { // switch (options.kind) {
case ViewModels.TerminalKind.Default: // case ViewModels.TerminalKind.Default:
endpointSuffix = ""; // endpointSuffix = "";
break; // break;
case ViewModels.TerminalKind.Mongo: // case ViewModels.TerminalKind.Mongo:
endpointSuffix = "mongo"; // endpointSuffix = "mongo";
break; // break;
case ViewModels.TerminalKind.Cassandra: // case ViewModels.TerminalKind.Cassandra:
endpointSuffix = "cassandra"; // endpointSuffix = "cassandra";
break; // break;
case ViewModels.TerminalKind.Postgres: // case ViewModels.TerminalKind.Postgres:
endpointSuffix = "postgresql"; // endpointSuffix = "postgresql";
break; // break;
case ViewModels.TerminalKind.VCoreMongo: // case ViewModels.TerminalKind.VCoreMongo:
endpointSuffix = "mongovcore"; // endpointSuffix = "mongovcore";
break; // break;
default: // default:
throw new Error(`Terminal kind: ${options.kind} not supported`); // throw new Error(`Terminal kind: ${options.kind} not supported`);
} // }
const info: DataModels.NotebookWorkspaceConnectionInfo = useNotebook.getState().notebookServerInfo; // const info: DataModels.NotebookWorkspaceConnectionInfo = useNotebook.getState().notebookServerInfo;
return { // return {
authToken: info.authToken, // authToken: info.authToken,
notebookServerEndpoint: `${info.notebookServerEndpoint.replace(/\/+$/, "")}/${endpointSuffix}`, // notebookServerEndpoint: `${info.notebookServerEndpoint.replace(/\/+$/, "")}/${endpointSuffix}`,
forwardingId: info.forwardingId, // forwardingId: info.forwardingId,
}; // };
} // }
private getUsername(): string { private getUsername(): string {
if (userContext.apiType !== "VCoreMongo" || !userContext?.vcoreMongoConnectionParams?.adminLogin) { if (userContext.apiType !== "VCoreMongo" || !userContext?.vcoreMongoConnectionParams?.adminLogin) {

View File

@ -0,0 +1,16 @@
import React, { useEffect, useRef } from "react";
import { XTerm } from "xterm-for-react";
const XTermComponent: React.FC = () => {
const xtermRef = useRef(null);
useEffect(() => {
if (xtermRef.current) {
xtermRef.current.terminal.writeln("Hello, World!");
}
}, []);
return <XTerm ref={xtermRef} />;
};
export default XTermComponent;