使用JavaScript
本主题介绍了Visual Studio Code支持的一些高级JavaScript功能。使用TypeScript语言服务,VS Code可以提供智能补全(IntelliSense)以及JavaScript的类型检查。
智能感知
Visual Studio Code 的 JavaScript IntelliSense 提供了智能代码补全、参数信息、引用搜索和许多其他高级语言功能。我们的 JavaScript IntelliSense 由 TypeScript 团队开发的 JavaScript 语言服务 提供支持。虽然 IntelliSense 应该可以在大多数 JavaScript 项目中无需任何配置即可工作,但您可以通过 JSDoc 或配置 jsconfig.json
项目使 IntelliSense 更加有用。
有关JavaScript IntelliSense如何工作的详细信息,包括基于类型推断、JSDoc注释、TypeScript声明以及混合JavaScript和TypeScript项目,请参阅JavaScript语言服务文档。
当类型推断无法提供所需信息时,可以通过JSDoc注释显式提供类型信息。本文档描述了当前支持的JSDoc注释。
除了对象、方法和属性外,JavaScript IntelliSense 窗口还为您文件中的符号提供基本的单词补全功能。
类型定义和自动类型获取
JavaScript库和框架的IntelliSense功能由TypeScript类型声明(typings)文件提供支持。类型声明文件是用TypeScript编写的,因此它们可以表达参数和函数的数据类型,使VS Code能够以高效的方式提供丰富的IntelliSense体验。
许多流行的库都附带了类型定义文件,因此您可以自动获得它们的IntelliSense。对于不包含类型定义的库,VS Code的Automatic Type Acquisition
将自动为您安装社区维护的类型定义文件。
自动类型获取需要npmjs,即Node.js的包管理器,它包含在Node.js运行时中。在这张图片中,您可以看到IntelliSense,包括方法签名、参数信息以及流行的lodash库的方法文档。
类型声明文件由Visual Studio Code自动下载和管理,适用于项目中package.json
列出的包或您导入到JavaScript文件中的包。
{
"dependencies": {
"lodash": "^4.17.0"
}
}
你也可以在jsconfig.json中明确列出需要获取类型声明文件的包。
{
"typeAcquisition": {
"include": ["jquery"]
}
}
大多数常见的JavaScript库都附带声明文件或提供类型声明文件。
修复自动类型获取的npm未安装警告
自动类型获取使用npm,即Node.js包管理器,来安装和管理类型声明(typings)文件。为了确保自动类型获取正常工作,首先请确保您的机器上已安装npm。
从终端或命令提示符运行npm --version
,以快速检查npm是否已安装并可用。
npm 随 Node.js 运行时一起安装,可以从 Nodejs.org 下载。安装当前的 LTS(长期支持)版本,npm 可执行文件将默认添加到您的系统路径中。
如果您已经安装了npm但仍然看到警告信息,您可以通过typescript.npm
设置明确告诉VS Code npm的安装位置。这应该设置为您的机器上npm可执行文件的完整路径,并且这不必与您用于管理工作区中包的npm版本匹配。typescript.npm
需要TypeScript 2.3.4+。
例如,在Windows上,您需要将如下路径添加到您的settings.json
文件中:
{
"typescript.npm": "C:\\Program Files\\nodejs\\npm.cmd"
}
JavaScript 项目 (jsconfig.json)
目录中存在jsconfig.json文件表示该目录是JavaScript项目的根目录。jsconfig.json
指定了根文件以及由JavaScript语言服务提供的语言功能的选项。对于常见的设置,不需要jsconfig.json
文件,但在某些情况下,您可能需要添加一个jsconfig.json
。
- 并非所有文件都应包含在您的JavaScript项目中(例如,您可能希望排除某些文件以不显示IntelliSense)。这种情况在前端和后端代码中很常见。
- 您的工作区包含多个项目上下文。在这种情况下,您应该为每个项目在根文件夹中添加一个
jsconfig.json
文件。 - 您正在使用TypeScript编译器对JavaScript源代码进行降级编译。
jsconfig.json 的位置
要将我们的代码定义为JavaScript项目,请在JavaScript代码的根目录下创建jsconfig.json
,如下所示。JavaScript项目是项目的源文件,不应包含派生或打包的文件(例如dist
目录)。
在更复杂的项目中,您可能在工作区内定义了多个jsconfig.json
文件。您会希望这样做,以便一个项目的源代码不会出现在另一个项目的IntelliSense中。
下面展示的是一个包含client
和server
文件夹的项目,显示了两个独立的JavaScript项目:
编写 jsconfig.json
下面是一个简单的jsconfig.json
文件模板,它定义了JavaScript的target
为ES6
,并且exclude
属性排除了node_modules
文件夹。你可以将此代码复制并粘贴到你的jsconfig.json
文件中。
{
"compilerOptions": {
"module": "CommonJS",
"target": "ES6"
},
"exclude": ["node_modules", "**/node_modules/*"]
}
exclude
属性告诉语言服务哪些文件不是你的源代码的一部分。如果 IntelliSense 运行缓慢,请将文件夹添加到你的 exclude
列表中(如果 VS Code 检测到补全速度慢,它会提示你这样做)。你可能希望 exclude
由构建过程生成的文件(例如 dist
目录)。这些文件会导致建议显示两次,并会减慢 IntelliSense 的速度。
您可以使用include
属性明确设置项目中的文件。如果没有include
属性,则默认包含包含目录及其子目录中的所有文件。当指定了include
属性时,仅包含这些文件。
这里是一个带有显式 include
属性的示例:
{
"compilerOptions": {
"module": "CommonJS",
"target": "ES6"
},
"include": ["src/**/*"]
}
最佳实践,也是最少出错的方法,是使用带有单个src
文件夹的include
属性。请注意,exclude
和include
中的文件路径是相对于jsconfig.json
的位置。
欲了解更多信息,请参阅完整的jsconfig.json 文档。
迁移到 TypeScript
可以在项目中混合使用TypeScript和JavaScript。要开始迁移到TypeScript,请将您的jsconfig.json
文件重命名为tsconfig.json
,并将allowJs
属性设置为true
。有关更多信息,请参阅从JavaScript迁移。
注意:
jsconfig.json
文件与tsconfig.json
文件相同,只是将allowJs
设置为 true。请参阅tsconfig.json
的文档 以查看其他可用的选项。
JavaScript 类型检查
VS Code 允许您在常规的 JavaScript 文件中利用 TypeScript 的一些高级类型检查和错误报告功能。这是捕捉常见编程错误的好方法。这些类型检查还为 JavaScript 提供了一些令人兴奋的快速修复功能,包括 添加缺失的导入 和 添加缺失的属性。
TypeScript 可以在 .js
文件中推断类型,就像在 .ts
文件中一样。当无法推断类型时,可以使用 JSDoc 注释来指定类型。你可以在 Type Checking JavaScript Files 中阅读更多关于 TypeScript 如何使用 JSDoc 进行 JavaScript 类型检查的信息。
JavaScript的类型检查是可选的并且需要手动启用。现有的JavaScript验证工具,如ESLint,可以与新的内置类型检查功能一起使用。
您可以根据需要以几种不同的方式开始进行类型检查。
每个文件
在JavaScript文件中启用类型检查的最简单方法是在文件顶部添加// @ts-check
。
// @ts-check
let itsAsEasyAs = 'abc';
itsAsEasyAs = 123; // Error: Type '123' is not assignable to type 'string'
使用 // @ts-check
是一个很好的方法,如果你只想在几个文件中尝试类型检查,但还没有为整个代码库启用它。
使用设置
要为所有JavaScript文件启用类型检查而不更改任何代码,只需将"js/ts.implicitProjectConfig.checkJs": true
添加到您的工作区或用户设置中。这将为不属于jsconfig.json
或tsconfig.json
项目的任何JavaScript文件启用类型检查。
你可以通过在文件顶部添加一个// @ts-nocheck
注释来选择性地将单个文件排除在类型检查之外:
// @ts-nocheck
let easy = 'abc';
easy = 123; // no error
你也可以在JavaScript文件中使用// @ts-ignore
注释来禁用单个错误,注释放在错误所在行的前面:
let easy = 'abc';
// @ts-ignore
easy = 123; // no error
使用 jsconfig 或 tsconfig
要为属于jsconfig.json
或tsconfig.json
的JavaScript文件启用类型检查,请将"checkJs": true
添加到项目的编译器选项中:
jsconfig.json
:
{
"compilerOptions": {
"checkJs": true
},
"exclude": ["node_modules", "**/node_modules/*"]
}
tsconfig.json
:
{
"compilerOptions": {
"allowJs": true,
"checkJs": true
},
"exclude": ["node_modules", "**/node_modules/*"]
}
这为项目中的所有JavaScript文件启用了类型检查。您可以使用// @ts-nocheck
来禁用每个文件的类型检查。
JavaScript 类型检查需要 TypeScript 2.3。如果您不确定当前工作区中激活的 TypeScript 版本,请运行 TypeScript: 选择 TypeScript 版本 命令进行检查。您必须在编辑器中打开一个 .js/.ts
文件才能运行此命令。如果您打开一个 TypeScript 文件,版本号会显示在右下角。
全局变量和类型检查
假设你正在使用全局变量或非标准DOM API的遗留JavaScript代码中工作:
window.onload = function() {
if (window.webkitNotifications.requestPermission() === CAN_NOTIFY) {
window.webkitNotifications.createNotification(null, 'Woof!', '🐶').show();
} else {
alert('Could not notify');
}
};
如果你尝试在上述代码中使用 // @ts-check
,你会看到一些关于使用全局变量的错误:
Line 2
-Property 'webkitNotifications' does not exist on type 'Window'.
Line 2
-无法找到名称 'CAN_NOTIFY'。
Line 3
-Property 'webkitNotifications' does not exist on type 'Window'.
如果你想继续使用// @ts-check
,但确信这些不是应用程序的实际问题,你必须让TypeScript知道这些全局变量。
首先,在项目的根目录下创建一个jsconfig.json
:
{
"compilerOptions": {},
"exclude": ["node_modules", "**/node_modules/*"]
}
然后重新加载VS Code以确保更改已应用。jsconfig.json
的存在让TypeScript知道你的Javascript文件是一个更大项目的一部分。
现在在你的工作区中创建一个globals.d.ts
文件:
interface Window {
webkitNotifications: any;
}
declare var CAN_NOTIFY: number;
d.ts
文件是类型声明文件。在这个例子中,globals.d.ts
让 TypeScript 知道存在一个全局的 CAN_NOTIFY
,并且在 window
上存在一个 webkitNotifications
属性。你可以在 TypeScript 文档 中阅读更多关于编写 d.ts
文件的内容。d.ts
文件不会改变 JavaScript 的评估方式,它们仅用于提供更好的 JavaScript 语言支持。
使用任务
使用 TypeScript 编译器
TypeScript 的关键特性之一是能够使用最新的 JavaScript 语言特性,并生成可以在尚未理解这些新特性的 JavaScript 运行时中执行的代码。通过使用相同的语言服务,JavaScript 现在也可以利用这一相同的特性。
TypeScript 编译器 tsc
可以将 JavaScript 文件从 ES6 降级编译到另一个语言级别。使用所需的选项配置 jsconfig.json
,然后使用 –p 参数使 tsc
使用你的 jsconfig.json
文件,例如 tsc -p jsconfig.json
来进行降级编译。
在jsconfig 文档中阅读更多关于降级编译的编译器选项。
运行 Babel
Babel 转译器将 ES6 文件转换为可读的 ES5 JavaScript,并生成源映射。你可以通过将以下配置添加到你的 tasks.json
文件(位于工作区的 .vscode
文件夹下)中,轻松将 Babel 集成到你的工作流程中。group
设置使此任务成为默认的 任务:运行构建任务 手势。isBackground
告诉 VS Code 在后台持续运行此任务。要了解更多信息,请访问 任务。
{
"version": "2.0.0",
"tasks": [
{
"label": "watch",
"command": "${workspaceFolder}/node_modules/.bin/babel",
"args": ["src", "--out-dir", "lib", "-w", "--source-maps"],
"type": "shell",
"group": { "kind": "build", "isDefault": true },
"isBackground": true
}
]
}
一旦你添加了这个,你可以使用⇧⌘B (Windows, Linux Ctrl+Shift+B) (运行构建任务) 命令启动Babel,它将把src
目录中的所有文件编译到lib
目录中。
提示:如需帮助使用 Babel CLI,请参阅 使用 Babel 中的说明。上面的示例使用了 CLI 选项。
禁用JavaScript支持
如果您更喜欢使用其他JavaScript语言工具(如Flow)支持的JavaScript语言特性,您可以禁用VS Code的内置JavaScript支持。您可以通过禁用内置的TypeScript语言扩展TypeScript and JavaScript Language Features(vscode.typescript-language-features)来实现这一点,该扩展也提供了JavaScript语言支持。
要禁用JavaScript/TypeScript支持,请转到扩展视图(⇧⌘X (Windows, Linux Ctrl+Shift+X))并过滤内置扩展(在... 更多操作下拉菜单中选择显示内置扩展),然后输入'typescript'。选择TypeScript和JavaScript语言功能扩展并按下禁用按钮。VS Code内置扩展无法卸载,只能禁用,并且可以随时重新启用。
部分智能感知模式
VS Code 尝试为 JavaScript 和 TypeScript 提供项目范围的 IntelliSense,这使得诸如自动导入和转到定义等功能成为可能。然而,在某些情况下,VS Code 仅限于处理您当前打开的文件,无法加载构成您的 JavaScript 或 TypeScript 项目的其他文件。
这可能在几种情况下发生:
- 您正在vscode.dev或github.dev上使用JavaScript或TypeScript代码,并且VS Code正在浏览器中运行。
- 您从虚拟文件系统中打开一个文件(例如,当使用GitHub Repositories扩展时)。
- 项目当前正在加载。加载完成后,您将开始获得项目范围的智能感知。
在这些情况下,VS Code 的 IntelliSense 将以部分模式运行。部分模式会尽力为您打开的任何 JavaScript 或 TypeScript 文件提供 IntelliSense,但功能有限,无法提供任何跨文件的 IntelliSense 功能。
哪些功能受到影响?
以下是不完整的功能列表,这些功能在部分模式下被禁用或功能受限:
- 所有打开的文件都被视为单个项目的一部分。
- 您的
jsconfig
或tsconfig
中的配置选项(如target
)未被遵循。 - 仅报告语法错误。语义错误——例如访问未知属性或将错误类型传递给函数——不会报告。
- 语义错误的快速修复已禁用。
- 符号只能在当前文件中解析。从其他文件导入的任何符号将被视为
any
类型。 - 诸如转到定义和查找所有引用等命令将仅适用于已打开的文件,而不是整个项目。这也意味着,安装在
node_module
下的任何包中的符号将不会被解析。 - 工作区符号搜索将仅包括当前打开文件中的符号。
- 自动导入已禁用。
- 重命名功能已禁用。
- 许多重构功能被禁用。
一些附加功能在vscode.dev
和github.dev
上被禁用:
- 自动类型获取目前不支持。
检查是否处于部分模式
要检查当前文件是否使用部分模式IntelliSense而不是项目范围的IntelliSense,请将鼠标悬停在状态栏中的JavaScript
或TypeScript
语言状态项上:
如果当前文件处于部分模式,状态项将显示Partial mode
。