From 24df825774edb759badc88d26553da3c6b9a738f Mon Sep 17 00:00:00 2001 From: "Anantachai Saothong (Manta)" Date: Sat, 16 Jun 2018 00:12:18 +0700 Subject: [PATCH] Added ability to import TypeScript files to JavaScript files --- CHANGELOG.md | 3 +++ edge/JavaScript.ts | 45 ++++++++++++++++++++++++++------------------- edge/TypeScript.ts | 13 ++++++++----- edge/global.ts | 2 +- package.json | 7 ++++++- 5 files changed, 44 insertions(+), 26 deletions(-) diff --git a/CHANGELOG.md b/CHANGELOG.md index 728ca3d..8ded21f 100644 --- a/CHANGELOG.md +++ b/CHANGELOG.md @@ -1,3 +1,6 @@ +### 1.5.0 +- Added ability to import TypeScript files to JavaScript files. + ### 1.4.0 - Amended picking the closest `package.json` from the current active document. - Fixed TypeScript compilation errors. diff --git a/edge/JavaScript.ts b/edge/JavaScript.ts index ae03431..63d11d1 100644 --- a/edge/JavaScript.ts +++ b/edge/JavaScript.ts @@ -19,43 +19,51 @@ export interface LanguageOptions { filteredFileList: object } +export interface ExclusiveLanguageOptions extends LanguageOptions { + allowTypeScriptFiles: boolean +} + +const TYPESCRIPT_EXTENSION = /^tsx?$/ + export default class JavaScript implements Language { protected baseConfig: RootConfigurations private fileItemCache: Array private nodeItemCache: Array - protected SUPPORTED_LANGUAGE = /^javascript(react)?/i - protected SUPPORTED_EXTENSION = /^jsx?$/ + protected WORKING_LANGUAGE = /^javascript(react)?/i + protected WORKING_EXTENSION = /^jsx?$/ + protected allowTypeScriptFiles = false constructor(baseConfig: RootConfigurations) { this.baseConfig = baseConfig - } - protected rejectSomeFiles(item: FileItem) { - // Remove TypeScript files as JavaScript does not recognize them anyway - return /^tsx?$/.test(item.fileInfo.fileExtensionWithoutLeadingDot) + const exclusiveConfig: ExclusiveLanguageOptions = this.baseConfig.javascript + if (exclusiveConfig && exclusiveConfig.allowTypeScriptFiles) { + this.allowTypeScriptFiles = true + + this.WORKING_EXTENSION = /^(j|t)sx?$/ + } } protected getLanguageOptions() { - return this.baseConfig.javascript + return this.baseConfig.javascript as LanguageOptions } async getItems(document: vscode.TextDocument) { - if (this.SUPPORTED_LANGUAGE.test(document.languageId) === false) { + if (this.WORKING_LANGUAGE.test(document.languageId) === false) { return null } let items: Array const documentFileInfo = new FileInfo(document.fileName) - const documentIsJavaScript = /^jsx?$/.test(documentFileInfo.fileExtensionWithoutLeadingDot) const rootPath = vscode.workspace.getWorkspaceFolder(document.uri).uri.fsPath if (!this.fileItemCache) { const fileLinks = await vscode.workspace.findFiles('**/*.*') this.fileItemCache = fileLinks - .map(fileLink => new FileItem(fileLink.fsPath, rootPath, this.getLanguageOptions(), this.SUPPORTED_EXTENSION)) + .map(fileLink => new FileItem(fileLink.fsPath, rootPath, this.getLanguageOptions(), this.WORKING_EXTENSION)) } const fileFilterRule = _.toPairs(this.getLanguageOptions().filteredFileList) @@ -64,7 +72,8 @@ export default class JavaScript implements Language { items = _.chain(this.fileItemCache) .reject(item => item.fileInfo.fullPath === documentFileInfo.fullPath) // Remove the current file - .reject(item => this.rejectSomeFiles(item)) + .filter(item => this.allowTypeScriptFiles || + !TYPESCRIPT_EXTENSION.test(item.fileInfo.fileExtensionWithoutLeadingDot)) .filter(item => fileFilterRule ? fileFilterRule.filePathPattern.test(item.fileInfo.fullPathForPOSIX) : true) .forEach(item => item.sortablePath = getSortablePath(item.fileInfo, documentFileInfo)) .value() @@ -102,7 +111,7 @@ export default class JavaScript implements Language { addItem(filePath: string) { if (this.fileItemCache) { const rootPath = vscode.workspace.getWorkspaceFolder(vscode.Uri.file(filePath)).uri.fsPath - this.fileItemCache.push(new FileItem(filePath, rootPath, this.getLanguageOptions(), this.SUPPORTED_EXTENSION)) + this.fileItemCache.push(new FileItem(filePath, rootPath, this.getLanguageOptions(), this.WORKING_EXTENSION)) } } @@ -117,12 +126,10 @@ export default class JavaScript implements Language { } async fixImport(editor: vscode.TextEditor, document: vscode.TextDocument, cancellationToken: vscode.CancellationToken) { - if (this.SUPPORTED_LANGUAGE.test(document.languageId) === false) { + if (this.WORKING_LANGUAGE.test(document.languageId) === false) { return false } - const actions: Array<(worker: vscode.TextEditorEdit) => void> = [] - const documentFileInfo = new FileInfo(document.fileName) const rootPath = vscode.workspace.getWorkspaceFolder(document.uri).uri.fsPath @@ -158,7 +165,7 @@ export default class JavaScript implements Language { readonly description: string readonly fullPath: string - constructor(fullPath: string, originalRelativePath: string) { + constructor(fullPath: string) { this.fullPath = fullPath this.label = fullPath.substring(rootPath.length).replace(/\\/g, '/') } @@ -206,7 +213,7 @@ export default class JavaScript implements Language { } else if (matchingFullPaths.length === 1) { await editor.edit(worker => { - const { path } = new FileItem(matchingFullPaths[0], rootPath, this.getLanguageOptions(), this.SUPPORTED_EXTENSION).getNameAndRelativePath(documentFileInfo.directoryPath) + const { path } = new FileItem(matchingFullPaths[0], rootPath, this.getLanguageOptions(), this.WORKING_EXTENSION).getNameAndRelativePath(documentFileInfo.directoryPath) worker.replace(item.editableRange, `${item.quoteChar}${path}${item.quoteChar}`) }) @@ -218,7 +225,7 @@ export default class JavaScript implements Language { for (const item of manualSolvableImports) { const matchingFullPaths = await item.search() - const candidateItems = matchingFullPaths.map(path => new FileItemForFixingImport(path, item.originalRelativePath)) + const candidateItems = matchingFullPaths.map(path => new FileItemForFixingImport(path)) const selectedItem = await vscode.window.showQuickPick(candidateItems, { placeHolder: item.originalRelativePath, ignoreFocusOut: true }) if (!selectedItem) { return null @@ -229,7 +236,7 @@ export default class JavaScript implements Language { } await editor.edit(worker => { - const { path } = new FileItem(selectedItem.fullPath, rootPath, this.getLanguageOptions(), this.SUPPORTED_EXTENSION).getNameAndRelativePath(documentFileInfo.directoryPath) + const { path } = new FileItem(selectedItem.fullPath, rootPath, this.getLanguageOptions(), this.WORKING_EXTENSION).getNameAndRelativePath(documentFileInfo.directoryPath) worker.replace(item.editableRange, `${item.quoteChar}${path}${item.quoteChar}`) }) } diff --git a/edge/TypeScript.ts b/edge/TypeScript.ts index 33dba26..bcc2097 100644 --- a/edge/TypeScript.ts +++ b/edge/TypeScript.ts @@ -1,11 +1,14 @@ -import JavaScript, { FileItem } from './JavaScript' +import { RootConfigurations } from './global' +import JavaScript from './JavaScript' export default class TypeScript extends JavaScript { - protected SUPPORTED_LANGUAGE = /^typescript(react)?/i - protected SUPPORTED_EXTENSION = /^(j|t)sx?$/ + protected WORKING_LANGUAGE = /^typescript(react)?/i + protected WORKING_EXTENSION = /^(j|t)sx?$/ - protected rejectSomeFiles(item: FileItem) { - return false + constructor(baseConfig: RootConfigurations) { + super(baseConfig) + + this.allowTypeScriptFiles = true } protected getLanguageOptions() { diff --git a/edge/global.ts b/edge/global.ts index c52d48c..fd4da96 100644 --- a/edge/global.ts +++ b/edge/global.ts @@ -7,7 +7,7 @@ import * as Stylus from './Stylus' export interface RootConfigurations { history: number - javascript: JavaScript.LanguageOptions + javascript: JavaScript.ExclusiveLanguageOptions typescript: JavaScript.LanguageOptions stylus: Stylus.LanguageOptions } diff --git a/package.json b/package.json index 74b286a..b78f310 100644 --- a/package.json +++ b/package.json @@ -124,6 +124,11 @@ }, "default": {} }, + "codeQuicken.javascript.allowTypeScriptFiles": { + "description": "Allow inserting TypeScript files.", + "type": "boolean", + "default": false + }, "codeQuicken.typescript.syntax": { "description": "Insert either ES2015's import or AMD's require syntax.", "type": "string", @@ -255,4 +260,4 @@ "lodash": "^4.17.10", "stylus": "^0.54.5" } -} +} \ No newline at end of file