From fd9fe525297aea33b3dcc6902997034e42442821 Mon Sep 17 00:00:00 2001 From: Levi Yan Date: Tue, 2 Jul 2024 12:15:39 +0800 Subject: [PATCH] refactor: convert js to ts --- .eslintrc.js | 70 ------------ .eslintrc.json | 30 ++++++ .vscode/launch.json | 6 +- .vscode/tasks.json | 17 ++- package.json | 27 +++-- src/home.js | 79 -------------- src/home.ts | 78 ++++++++++++++ src/{main.js => main.ts} | 101 +++++++----------- src/utils.js | 5 - src/utils.ts | 0 ...ck-access-tree.js => quick-access-tree.ts} | 8 +- tsconfig.json | 20 ++++ 12 files changed, 207 insertions(+), 234 deletions(-) delete mode 100644 .eslintrc.js create mode 100644 .eslintrc.json delete mode 100644 src/home.js create mode 100644 src/home.ts rename src/{main.js => main.ts} (54%) delete mode 100644 src/utils.js create mode 100644 src/utils.ts rename src/views/{quick-access-tree.js => quick-access-tree.ts} (77%) create mode 100644 tsconfig.json diff --git a/.eslintrc.js b/.eslintrc.js deleted file mode 100644 index 1aedf16..0000000 --- a/.eslintrc.js +++ /dev/null @@ -1,70 +0,0 @@ -module.exports = { - 'env': { - 'browser': false, - 'es6': true, - 'node': true, - 'jasmine': true, - }, - 'plugins': [ - 'import' - ], - 'extends': [ - 'eslint:recommended', - 'plugin:import/errors', - 'plugin:import/warnings' - ], - 'parser': '@babel/eslint-parser', - 'parserOptions': { - 'ecmaVersion': 6, - 'sourceType': 'module' - }, - 'settings': { - 'import/core-modules': [ - 'vscode' - ] - }, - 'rules': { - 'comma-dangle': [ - 'error', - 'only-multiline' - ], - 'curly': [ - 'warn', - 'all' - ], - 'linebreak-style': [ - // 'error', - 'unix' - ], - 'no-console': [ - 'error', - { - 'allow': ['warn', 'error', 'info'] - }, - ], - 'prefer-const': 'error', - 'quotes': [ - 'error', - 'single', - 'avoid-escape' - ], - 'semi': [ - 'error', - 'always' - ], - 'sort-imports': [ - 'warn', - { - 'ignoreCase': false, - 'ignoreMemberSort': false, - 'memberSyntaxSortOrder': ['none', 'all', 'multiple', 'single'] - } - ], - 'no-useless-escape': [ - 'off' - ], - 'no-empty': [2, { - 'allowEmptyCatch': true - }] - }, -}; \ No newline at end of file diff --git a/.eslintrc.json b/.eslintrc.json new file mode 100644 index 0000000..86c86f3 --- /dev/null +++ b/.eslintrc.json @@ -0,0 +1,30 @@ +{ + "root": true, + "parser": "@typescript-eslint/parser", + "parserOptions": { + "ecmaVersion": 6, + "sourceType": "module" + }, + "plugins": [ + "@typescript-eslint" + ], + "rules": { + "@typescript-eslint/naming-convention": [ + "warn", + { + "selector": "import", + "format": [ "camelCase", "PascalCase" ] + } + ], + "@typescript-eslint/semi": "warn", + "curly": "warn", + "eqeqeq": "warn", + "no-throw-literal": "warn", + "semi": "off" + }, + "ignorePatterns": [ + "out", + "dist", + "**/*.d.ts" + ] +} \ No newline at end of file diff --git a/.vscode/launch.json b/.vscode/launch.json index 8c25449..1167fa0 100644 --- a/.vscode/launch.json +++ b/.vscode/launch.json @@ -6,12 +6,9 @@ "name": "Launch Extension", "type": "extensionHost", "request": "launch", - "runtimeExecutable": "${execPath}", "args": ["--extensionDevelopmentPath=${workspaceRoot}"], - "preLaunchTask": "npm: build", + "preLaunchTask": "tsc: build - tsconfig.json", "outFiles": ["${workspaceFolder}/dist/**/*.js"], - "sourceMaps": true, - "stopOnEntry": false }, { "name": "Launch Tests", @@ -23,7 +20,6 @@ "--extensionTestsPath=${workspaceRoot}/test" ], "preLaunchTask": "npm: build", - "stopOnEntry": false } ] } diff --git a/.vscode/tasks.json b/.vscode/tasks.json index 51aa926..cce1805 100644 --- a/.vscode/tasks.json +++ b/.vscode/tasks.json @@ -15,6 +15,21 @@ "problemMatcher": [], "label": "npm: format", "detail": "prettier --single-quote --print-width 88 --write \"src/**/*.js\"" - } + }, + { + "type": "npm", + "script": "watch", + "problemMatcher": "$ts-webpack-watch", + "isBackground": true, + "presentation": { + "reveal": "never", + "group": "watchers" + }, + "group": { + "kind": "build", + "isDefault": true + } + }, + ] } \ No newline at end of file diff --git a/package.json b/package.json index 3653033..4a1c2d7 100644 --- a/package.json +++ b/package.json @@ -1,6 +1,6 @@ { "name": "superide", - "version": "0.0.1", + "version": "0.1.0", "publisher": "mengning", "engines": { "vscode": "^1.65.0" @@ -91,9 +91,16 @@ }, "scripts": { "build": "webpack --mode production", - "lint": "eslint .eslintrc.js src", - "format": "prettier --single-quote --print-width 88 --write \"src/**/*.js\"", - "vscode:package": "webpack --mode production && vsce package" + "vscode:package": "webpack --mode production && vsce package", + "vscode:prepublish": "npm run package", + "compile": "webpack", + "watch": "webpack --watch", + "package": "webpack --mode production --devtool hidden-source-map", + "compile-tests": "tsc -p . --outDir out", + "watch-tests": "tsc -p . -w --outDir out", + "pretest": "npm run compile-tests && npm run compile && npm run lint", + "lint": "eslint src --ext ts", + "test": "vscode-test" }, "dependencies": { "fs-plus": "~3.1.1", @@ -104,16 +111,22 @@ "@babel/eslint-parser": "~7.21.3", "@babel/plugin-proposal-class-properties": "~7.18.6", "@babel/preset-env": "~7.20.2", - "@types/node": "~14", "@types/vscode": "~1.65.0", + "@types/node": "18.x", "@vscode/vsce": "^2.29.0", "babel-loader": "~9.1.2", - "eslint": "~8.36.0", "eslint-import-resolver-webpack": "~0.13.2", "eslint-plugin-import": "~2.27.5", "prettier": "~2.8.4", "webpack": "~5.76.2", - "webpack-cli": "~5.0.1" + "webpack-cli": "~5.0.1", + "@types/mocha": "^10.0.6", + "@typescript-eslint/eslint-plugin": "^7.11.0", + "@typescript-eslint/parser": "^7.11.0", + "typescript": "^5.4.5", + "ts-loader": "^9.5.1", + "@vscode/test-cli": "^0.0.9", + "@vscode/test-electron": "^2.4.0" }, "extensionDependencies": [ "ms-vscode.cpptools" diff --git a/src/home.js b/src/home.js deleted file mode 100644 index 4a830ef..0000000 --- a/src/home.js +++ /dev/null @@ -1,79 +0,0 @@ -import * as vscode from 'vscode'; - -export default class SIHome { - constructor(context) { - this.context = context; - } - - toggle(url) { - const panel = vscode.window.createWebviewPanel( - 'myWebview', - 'My Webview', - vscode.ViewColumn.One, - {} - ); - - panel.webview.options = { - enableScripts: true, - }; - - panel.webview.html = this.getWebviewContent(); - - panel.webview.onDidReceiveMessage( - (message) => { - switch (message.command) { - case 'alert': - vscode.window.showInformationMessage(message.text); - return; - case 'openFolder': - this.openFolderInVSCode(message.path); - return; - } - }, - undefined, - this.context.subscriptions - ); - } - - - openFolderInVSCode(path) { - vscode.commands.executeCommand('vscode.openFolder', vscode.Uri.file(path)) - .then((result) => { - console.log('Opened folder: ', result); - }) - .catch((error) => { - console.error('Error opening folder: ', error); - }); - } - - getWebviewContent() { - return ` - - - - - - Cat Coding - - -

Cat Coding

- - - - - - - - `; - } -} \ No newline at end of file diff --git a/src/home.ts b/src/home.ts new file mode 100644 index 0000000..526154b --- /dev/null +++ b/src/home.ts @@ -0,0 +1,78 @@ +import * as vscode from 'vscode'; + +export default class SIHome { + + constructor() { + } + + toggle(url: string) { + console.log('url: ', url) + const panel = vscode.window.createWebviewPanel( + 'myWebview', + 'My Webview', + vscode.ViewColumn.One, + {} + ); + + panel.webview.options = { + enableScripts: true, + }; + + panel.webview.html = this.getWebviewContent(); + + panel.webview.onDidReceiveMessage( + (message) => { + switch (message.command) { + case 'alert': + vscode.window.showInformationMessage(message.text); + return; + case 'openFolder': + this.openFolderInVSCode(message.path); + return; + } + }, + undefined, + ); + } + + + openFolderInVSCode(path: string): void { + try { + vscode.commands.executeCommand('vscode.openFolder', vscode.Uri.file(path)) + console.log('Opened folder: ', path); + } catch (error) { + console.error('Error opening folder: ', error); + } + } + + getWebviewContent() { + return ` + + + + + + Cat Coding + + +

Cat Coding

+ + + + + + + + `; + } +} \ No newline at end of file diff --git a/src/main.js b/src/main.ts similarity index 54% rename from src/main.js rename to src/main.ts index 30116ff..d6eb738 100644 --- a/src/main.js +++ b/src/main.ts @@ -4,29 +4,23 @@ import path from 'path'; import os from 'os'; import QuickAccessTreeProvider from './views/quick-access-tree'; import SIHome from './home'; -import * as utils from './utils'; -const {NodeSSH} = require('node-ssh') +const { NodeSSH } = require('node-ssh') -class SuperIDEExtension { - constructor() { - this.siHome = undefined; - this.context = undefined; - this.subscriptions = []; - } +export class SuperIDEExtension { + siHome: SIHome; - async activate(context) { - this.context = context; - this.siHome = new SIHome(context); + constructor(private context: vscode.ExtensionContext) { + this.siHome = new SIHome(); - this.subscriptions.push( + context.subscriptions.push( vscode.window.registerTreeDataProvider( 'superide.quickAccess', new QuickAccessTreeProvider() ) ); - this.registerGlobalCommands(); + this.registerGlobalCommands(context); this.startSuperIDEHome(); } @@ -69,78 +63,57 @@ class SuperIDEExtension { ) // append the host to the local ssh config file - const sshConfigContent = - `\n - Host ${host} - HostName ${host} - Port ${port} - User ${username} - PreferredAuthentications publickey - IdentityFile ~/.ssh/id_rsa - `; + const sshConfigContent = + `\nHost ${host}\n HostName ${host}\n Port ${port}\n User ${username}\n PreferredAuthentications publickey\n IdentityFile ~/.ssh/id_rsa\n `; // append the host to the local ssh config file - fs.writeFileSync(sshConfigPath, sshConfigContent, { encoding: 'utf8', flag: 'a' }); + fs.writeFileSync(sshConfigPath, sshConfigContent, { encoding: 'utf8', flag: 'a' }); console.log('Host registered in local ssh config'); // connect the host with remote-ssh extension - await vscode.commands.executeCommand('opensshremotes.openEmptyWindowInCurrentWindow', host) - .then(() => { - console.log('Connected to host'); - }) - .catch((error) => { - console.error('Error connecting to host: ', error); - }); + try { + await vscode.commands.executeCommand('opensshremotes.openEmptyWindowInCurrentWindow', host) + } catch (error) { + console.log("Error connecting to host: ", error); + } } } } - async firstConnect(host, username, password, port, publicKey) { + async firstConnect(host: string, username: string, password: string, port: number, publicKey: string): Promise { const ssh = new NodeSSH(); - ssh.connect({ - host: host, - username: username, - password: password, - port: port - }).then(() => { - console.log('Connected successfully'); - ssh.execCommand(`mkdir -p ~/.ssh && - echo '${publicKey}' >> ~/.ssh/authorized_keys`, ) - .then(result => { - if (result.stdout) console.log('STDOUT: ' + result.stdout); - if (result.stderr) console.log('STDERR: ' + result.stderr); - }); - }).catch(error => { - console.log('Error: ', error); - }); + + try { + await ssh.connect({ + host: host, + username: username, + password: password, + port: port + }); + + await ssh.execCommand(`mkdir -p ~/.ssh && echo '${publicKey}' >> ~/.ssh/authorized_keys`); + console.log('Public key added to remote authorized_keys'); + } catch (error) { + console.error('Error adding public key: ', error); + } finally { + await ssh.dispose(); + } } - registerGlobalCommands() { - this.subscriptions.push( + registerGlobalCommands(context: vscode.ExtensionContext) { + context.subscriptions.push( vscode.commands.registerCommand('superide.showHome', (url) => this.siHome.toggle(url) ), vscode.commands.registerCommand('superide.connectRemoteContainer', () => - this.connectRemoteContainer() + this.connectRemoteContainer() ) ); } - - disposeSubscriptions() { - utils.disposeSubscriptions(this.subscriptions); - } - - deactivate() { - this.disposeSubscriptions(); - } } -export const extension = new SuperIDEExtension(); - -export function activate(context) { - extension.activate(context); - return extension; +export function activate(context: vscode.ExtensionContext) { + return new SuperIDEExtension(context); } export function deactivate() { - extension.deactivate(); } diff --git a/src/utils.js b/src/utils.js deleted file mode 100644 index bfaf5e8..0000000 --- a/src/utils.js +++ /dev/null @@ -1,5 +0,0 @@ -export function disposeSubscriptions(subscriptions) { - while (subscriptions.length) { - subscriptions.pop().dispose(); - } -} diff --git a/src/utils.ts b/src/utils.ts new file mode 100644 index 0000000..e69de29 diff --git a/src/views/quick-access-tree.js b/src/views/quick-access-tree.ts similarity index 77% rename from src/views/quick-access-tree.js rename to src/views/quick-access-tree.ts index 1a980ba..3d96e90 100644 --- a/src/views/quick-access-tree.js +++ b/src/views/quick-access-tree.ts @@ -1,7 +1,9 @@ import * as vscode from 'vscode'; class QuickItem extends vscode.TreeItem { - constructor(label, command, args, collapsibleState, children) { + customChildren: QuickItem[] | undefined; + + constructor(label: string, command?: string, args?: any, collapsibleState?: vscode.TreeItemCollapsibleState, children?: QuickItem[]) { super(label, collapsibleState); if (command) { this.command = { @@ -15,7 +17,7 @@ class QuickItem extends vscode.TreeItem { } export default class QuickAccessTreeProvider { - getChildren(element) { + getChildren(element: QuickItem) { if (element && element.customChildren) { return element.customChildren; } @@ -38,7 +40,7 @@ export default class QuickAccessTreeProvider { ]; } - getTreeItem(element) { + getTreeItem(element: QuickItem) { return element; } } diff --git a/tsconfig.json b/tsconfig.json new file mode 100644 index 0000000..b995d41 --- /dev/null +++ b/tsconfig.json @@ -0,0 +1,20 @@ +{ + "compilerOptions": { + "module": "Node16", + "target": "ES2022", + "lib": [ + "ES2022" + ], + "sourceMap": true, + "rootDir": "src", + "strict": true, /* enable all strict type-checking options */ + /* Additional Checks */ + "noImplicitReturns": true, /* Report error when not all code paths in function return a value. */ + // "noFallthroughCasesInSwitch": true, /* Report errors for fallthrough cases in switch statement. */ + "noUnusedParameters": true, /* Report errors on unused parameters. */ + /* Emit */ + "outDir": "dist", /* Redirect output structure to the directory. */ + "removeComments": true, /* Do not emit comments to output. */ + "noEmitOnError": true, /* Do not emit outputs if any errors were reported. */ + } +}