Visual Studio 即使定义了变量,代码也会显示红色波浪线
Visual Studio Code shows red swiggly lines even when variable is defined
我在 visual studio 代码中有红色波浪线,即使定义了变量(错误消息)也是如此。
如果我禁用 eslint,它就会消失,但我认为这不是正确的方法,这将停止检查 ts/js 文件的其余部分。 (我安装了 ESLint 扩展)
我有 Visual Studio 代码:Mac OS Catalina 上的 1.57.1(通用)。
我可以右键单击并转到 browser
定义。
beforeAll(async () => {
await browser.url('https://example.com/');
})
如果我去定义它看起来像下面这样
代码片段在 .js 文件中,这是 visual studio 代码
的右下角
我该如何解决这个问题?
我也尝试在此处提到的解决方案之一中删除此 .vs 文件夹,但没有成功:Visual Studio compiles fine, but it still shows red lines
还在我的代码中安装了这些库:
npm i
npm install @wdio/cli (https://webdriver.io/docs/gettingstarted/)
npx wdio config
我可以编译我的项目,但是如何在不禁用 ESLint 的情况下去除这些红线?
感谢您的帮助!
beforeAll(async () => {
await browser.url('https://example.com/');
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/1.2.3/jquery.min.js">
</script>
注意:我不确定如何创建此代码的 mvp。
但是 beforeAll 是从节点模块定义的。我在下面包含了相关文件。
node_modules/@types/jest/index.d.ts
declare var beforeAll: jest.Lifecycle;
我的 package.json 文件看起来像这样
{
"name": "test-app",
"version": "0.1.0",
"private": true,
"dependencies": {
"@testing-library/jest-dom": "^5.11.4",
"@testing-library/user-event": "^12.1.10",
"@types/jest": "^26.0.15",
"@types/node": "^12.0.0",
"@types/react": "^16.14.2",
"@types/react-dom": "^16.9.8",
"axios": "^0.21.1",
"react": "^17.0.1",
"react-dom": "^17.0.1",
"react-scripts": "4.0.1",
"web-vitals": "^0.2.4"
},
"jest": {
"preset": "jest-playwright-preset"
},
"globals": {
"browserName": "BrowserType",
"browser": "Browser",
"context": "BrowserContext",
"page": "page"
},
"devDependencies": {
"@testing-library/react": "^11.2.3",
"@wdio/cli": "^7.7.4",
"@wdio/jasmine-framework": "^7.7.3",
"@wdio/local-runner": "^7.7.4",
"@wdio/mocha-framework": "^7.7.4",
"@wdio/spec-reporter": "^7.7.3",
"chromedriver": "^91.0.1",
"jest": "^26.6.0",
"jest-junit": "^12.0.0",
"jest-playwright-preset": "^1.6.1",
"playwright": "^1.12.3",
"ts-jest": "^26.5.4",
"ts-node": "^10.0.0",
"typescript": "^4.2.4",
"wdio-chromedriver-service": "^7.1.1",
"webdriverio": "^7.5.7"
},
"proxy": "https://localhost:5001",
"eslintConfig": {
"extends": [
"react-app",
"react-app/jest"
]
}
}
这是使用 Jest 和 Web Driver UI 浏览器自动化
这是上面截图中的node_modules/jest-playwright-preset/types/global.d.ts文件
import {
Browser,
BrowserContext,
Page,
BrowserContextOptions,
LaunchOptions,
ConnectOptions,
ConnectOverCDPOptions,
BrowserType as PlaywrightBrowserType,
ViewportSize,
ChromiumBrowser,
FirefoxBrowser,
WebKitBrowser,
devices,
} from 'playwright-core'
import { Config as JestConfig } from '@jest/types'
import { Test } from 'jest-runner'
import { JestProcessManagerOptions } from 'jest-process-manager'
// TODO Find out flex ways to reuse constants
declare const IMPORT_KIND_PLAYWRIGHT = 'playwright'
declare const CHROMIUM = 'chromium'
declare const FIREFOX = 'firefox'
declare const WEBKIT = 'webkit'
declare const LAUNCH = 'LAUNCH'
declare const PERSISTENT = 'PERSISTENT'
declare const SERVER = 'SERVER'
declare module 'jest-playwright-preset' {
const globalSetup: (config: JestConfig.GlobalConfig) => void
const globalTeardown: (config: JestConfig.GlobalConfig) => void
const getPlaywrightEnv: (env?: string) => void
}
export type BrowserType = typeof CHROMIUM | typeof FIREFOX | typeof WEBKIT
export type SkipOption = {
browsers: BrowserType[]
devices?: string[] | RegExp
}
export interface TestPlaywrightConfigOptions extends JestPlaywrightConfig {
browser?: BrowserType
device?: ConfigDeviceType
}
export type GenericBrowser = PlaywrightBrowserType<
WebKitBrowser | ChromiumBrowser | FirefoxBrowser
>
type Nullable<T> = T | null
interface JestPlaywright {
/**
* Reset global.page
*
* ```ts
* it('should reset page', async () => {
* await jestPlaywright.resetPage()
* })
* ```
*/
resetPage: () => Promise<void>
/**
* Reset global.context
*
* ```ts
* it('should reset context', async () => {
* await jestPlaywright.resetContext()
* })
* ```
*/
resetContext: (newOptions?: BrowserContextOptions) => Promise<void>
/**
* Reset global.browser, global.context, and global.page
*
* ```ts
* it('should reset page', async () => {
* await jestPlaywright.resetBrowser()
* })
* ```
*/
resetBrowser: (newOptions?: BrowserContextOptions) => Promise<void>
/**
* Saves the coverage to the disk which will only work if `collectCoverage`
* in `jest-playwright.config.js` file is set to true. The merged coverage file
* is then available in `.nyc_output/coverage.json`. Mostly its needed in the
* `afterEach` handler like that:
*
* ```ts
* afterEach(async () => {
* await jestPlaywright.saveCoverage(page)
* })
* ```
*/
saveCoverage: (page: Page) => Promise<void>
configSeparateEnv: (
config: Partial<TestPlaywrightConfigOptions>,
isDebug?: boolean,
) => Promise<ConfigParams>
}
interface JestParams<T> {
(options: T, name: string, fn?: jest.ProvidesCallback, timeout?: number): void
}
type ProvidesCallback = (cb: ConfigParams) => void
interface JestParamsWithConfigParams<T> {
(
options: Partial<T>,
name: string,
fn?: ProvidesCallback,
timeout?: number,
): void
}
interface JestPlaywrightTestDebug
extends JestParamsWithConfigParams<JestPlaywrightConfig> {
(name: string, fn?: ProvidesCallback, timeout?: number): void
skip:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestDebug
only:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestDebug
}
interface JestPlaywrightTestConfig
extends JestParamsWithConfigParams<JestPlaywrightConfig> {
skip:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestConfig
only:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestConfig
}
declare global {
const browserName: BrowserType
const deviceName: Nullable<string>
const page: Page
const browser: Browser
const context: BrowserContext
const jestPlaywright: JestPlaywright
namespace jest {
interface It {
jestPlaywrightSkip: JestParams<SkipOption>
jestPlaywrightDebug: JestPlaywrightTestDebug
jestPlaywrightConfig: JestPlaywrightTestConfig
}
interface Describe {
jestPlaywrightSkip: JestParams<SkipOption>
}
}
}
type DeviceDescriptor = {
viewport: Nullable<ViewportSize>
userAgent: string
deviceScaleFactor: number
isMobile: boolean
hasTouch: boolean
defaultBrowserType: BrowserType
}
export type CustomDeviceType = Partial<DeviceDescriptor> & {
name: string
}
export type ConfigDeviceType = CustomDeviceType | string
export type DeviceType = Nullable<ConfigDeviceType>
export type WsEndpointType = Nullable<string>
export type SelectorType = {
script: string | Function | { path?: string; content?: string }
name: string
}
export type PlaywrightRequireType = BrowserType | typeof IMPORT_KIND_PLAYWRIGHT
export interface Playwright {
name: PlaywrightRequireType
instance: GenericBrowser | Record<BrowserType, GenericBrowser>
devices: typeof devices
}
type LaunchType = typeof LAUNCH | typeof SERVER | typeof PERSISTENT
type Options<T> = T & Partial<Record<BrowserType, T>>
export type ServerOptions = JestProcessManagerOptions & {
teardown?: string
}
export interface JestPlaywrightConfig {
haveSkippedTests?: boolean
skipInitialization?: boolean
debugOptions?: JestPlaywrightConfig
launchType?: LaunchType
launchOptions?: Options<LaunchOptions>
connectOptions?: Options<ConnectOptions | ConnectOverCDPOptions>
contextOptions?: Options<BrowserContextOptions>
userDataDir?: string
exitOnPageError?: boolean
displayName?: string
browsers: (BrowserType | (JestPlaywrightConfig & { name: BrowserType }))[]
devices?: ConfigDeviceType[] | RegExp
useDefaultBrowserType?: boolean
serverOptions?: ServerOptions | ServerOptions[]
selectors?: SelectorType[]
collectCoverage?: boolean
}
export type JestPlaywrightProjectConfig = Test['context']['config'] & {
browserName: BrowserType
wsEndpoint: WsEndpointType
device: DeviceType
}
export type JestPlaywrightContext = Omit<Test['context'], 'config'> & {
config: JestPlaywrightProjectConfig
}
export type JestPlaywrightTest = Omit<Test, 'context'> & {
context: JestPlaywrightContext
}
export interface BrowserTest {
test: JestPlaywrightTest
config: JestPlaywrightConfig
browser: BrowserType
wsEndpoint: WsEndpointType
device: DeviceType
}
export type ConfigParams = {
browserName: BrowserType
deviceName: Nullable<string>
browser: Nullable<Browser | BrowserContext>
context: BrowserContext
page: Page
}
Eslint 不了解全局变量。要解决这个问题,您有两个选择:
- 告诉eslint定义了哪些变量
- 禁用检查未定义变量的 eslint 规则
要告诉 eslint 定义了哪些全局变量,请将它们添加到您的 eslint 配置文件中
{
"globals": {
"var1": true,
}
}
文档:https://eslint.org/docs/2.13.1/user-guide/configuring#specifying-globals
为了简化这一点,eslint 提供了所谓的 'environments',其中包括所有全局变量,例如此处描述的框架:https://eslint.org/docs/2.13.1/user-guide/configuring#specifying-environments
我在 visual studio 代码中有红色波浪线,即使定义了变量(错误消息)也是如此。
如果我禁用 eslint,它就会消失,但我认为这不是正确的方法,这将停止检查 ts/js 文件的其余部分。 (我安装了 ESLint 扩展)
我有 Visual Studio 代码:Mac OS Catalina 上的 1.57.1(通用)。
我可以右键单击并转到 browser
定义。
beforeAll(async () => {
await browser.url('https://example.com/');
})
如果我去定义它看起来像下面这样
代码片段在 .js 文件中,这是 visual studio 代码
的右下角我该如何解决这个问题? 我也尝试在此处提到的解决方案之一中删除此 .vs 文件夹,但没有成功:Visual Studio compiles fine, but it still shows red lines
还在我的代码中安装了这些库:
npm i
npm install @wdio/cli (https://webdriver.io/docs/gettingstarted/)
npx wdio config
我可以编译我的项目,但是如何在不禁用 ESLint 的情况下去除这些红线?
感谢您的帮助!
beforeAll(async () => {
await browser.url('https://example.com/');
})
<script src="https://cdnjs.cloudflare.com/ajax/libs/jquery/1.2.3/jquery.min.js">
</script>
注意:我不确定如何创建此代码的 mvp。
但是 beforeAll 是从节点模块定义的。我在下面包含了相关文件。
node_modules/@types/jest/index.d.ts
declare var beforeAll: jest.Lifecycle;
我的 package.json 文件看起来像这样
{
"name": "test-app",
"version": "0.1.0",
"private": true,
"dependencies": {
"@testing-library/jest-dom": "^5.11.4",
"@testing-library/user-event": "^12.1.10",
"@types/jest": "^26.0.15",
"@types/node": "^12.0.0",
"@types/react": "^16.14.2",
"@types/react-dom": "^16.9.8",
"axios": "^0.21.1",
"react": "^17.0.1",
"react-dom": "^17.0.1",
"react-scripts": "4.0.1",
"web-vitals": "^0.2.4"
},
"jest": {
"preset": "jest-playwright-preset"
},
"globals": {
"browserName": "BrowserType",
"browser": "Browser",
"context": "BrowserContext",
"page": "page"
},
"devDependencies": {
"@testing-library/react": "^11.2.3",
"@wdio/cli": "^7.7.4",
"@wdio/jasmine-framework": "^7.7.3",
"@wdio/local-runner": "^7.7.4",
"@wdio/mocha-framework": "^7.7.4",
"@wdio/spec-reporter": "^7.7.3",
"chromedriver": "^91.0.1",
"jest": "^26.6.0",
"jest-junit": "^12.0.0",
"jest-playwright-preset": "^1.6.1",
"playwright": "^1.12.3",
"ts-jest": "^26.5.4",
"ts-node": "^10.0.0",
"typescript": "^4.2.4",
"wdio-chromedriver-service": "^7.1.1",
"webdriverio": "^7.5.7"
},
"proxy": "https://localhost:5001",
"eslintConfig": {
"extends": [
"react-app",
"react-app/jest"
]
}
}
这是使用 Jest 和 Web Driver UI 浏览器自动化
这是上面截图中的node_modules/jest-playwright-preset/types/global.d.ts文件
import {
Browser,
BrowserContext,
Page,
BrowserContextOptions,
LaunchOptions,
ConnectOptions,
ConnectOverCDPOptions,
BrowserType as PlaywrightBrowserType,
ViewportSize,
ChromiumBrowser,
FirefoxBrowser,
WebKitBrowser,
devices,
} from 'playwright-core'
import { Config as JestConfig } from '@jest/types'
import { Test } from 'jest-runner'
import { JestProcessManagerOptions } from 'jest-process-manager'
// TODO Find out flex ways to reuse constants
declare const IMPORT_KIND_PLAYWRIGHT = 'playwright'
declare const CHROMIUM = 'chromium'
declare const FIREFOX = 'firefox'
declare const WEBKIT = 'webkit'
declare const LAUNCH = 'LAUNCH'
declare const PERSISTENT = 'PERSISTENT'
declare const SERVER = 'SERVER'
declare module 'jest-playwright-preset' {
const globalSetup: (config: JestConfig.GlobalConfig) => void
const globalTeardown: (config: JestConfig.GlobalConfig) => void
const getPlaywrightEnv: (env?: string) => void
}
export type BrowserType = typeof CHROMIUM | typeof FIREFOX | typeof WEBKIT
export type SkipOption = {
browsers: BrowserType[]
devices?: string[] | RegExp
}
export interface TestPlaywrightConfigOptions extends JestPlaywrightConfig {
browser?: BrowserType
device?: ConfigDeviceType
}
export type GenericBrowser = PlaywrightBrowserType<
WebKitBrowser | ChromiumBrowser | FirefoxBrowser
>
type Nullable<T> = T | null
interface JestPlaywright {
/**
* Reset global.page
*
* ```ts
* it('should reset page', async () => {
* await jestPlaywright.resetPage()
* })
* ```
*/
resetPage: () => Promise<void>
/**
* Reset global.context
*
* ```ts
* it('should reset context', async () => {
* await jestPlaywright.resetContext()
* })
* ```
*/
resetContext: (newOptions?: BrowserContextOptions) => Promise<void>
/**
* Reset global.browser, global.context, and global.page
*
* ```ts
* it('should reset page', async () => {
* await jestPlaywright.resetBrowser()
* })
* ```
*/
resetBrowser: (newOptions?: BrowserContextOptions) => Promise<void>
/**
* Saves the coverage to the disk which will only work if `collectCoverage`
* in `jest-playwright.config.js` file is set to true. The merged coverage file
* is then available in `.nyc_output/coverage.json`. Mostly its needed in the
* `afterEach` handler like that:
*
* ```ts
* afterEach(async () => {
* await jestPlaywright.saveCoverage(page)
* })
* ```
*/
saveCoverage: (page: Page) => Promise<void>
configSeparateEnv: (
config: Partial<TestPlaywrightConfigOptions>,
isDebug?: boolean,
) => Promise<ConfigParams>
}
interface JestParams<T> {
(options: T, name: string, fn?: jest.ProvidesCallback, timeout?: number): void
}
type ProvidesCallback = (cb: ConfigParams) => void
interface JestParamsWithConfigParams<T> {
(
options: Partial<T>,
name: string,
fn?: ProvidesCallback,
timeout?: number,
): void
}
interface JestPlaywrightTestDebug
extends JestParamsWithConfigParams<JestPlaywrightConfig> {
(name: string, fn?: ProvidesCallback, timeout?: number): void
skip:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestDebug
only:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestDebug
}
interface JestPlaywrightTestConfig
extends JestParamsWithConfigParams<JestPlaywrightConfig> {
skip:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestConfig
only:
| JestParamsWithConfigParams<JestPlaywrightConfig>
| JestPlaywrightTestConfig
}
declare global {
const browserName: BrowserType
const deviceName: Nullable<string>
const page: Page
const browser: Browser
const context: BrowserContext
const jestPlaywright: JestPlaywright
namespace jest {
interface It {
jestPlaywrightSkip: JestParams<SkipOption>
jestPlaywrightDebug: JestPlaywrightTestDebug
jestPlaywrightConfig: JestPlaywrightTestConfig
}
interface Describe {
jestPlaywrightSkip: JestParams<SkipOption>
}
}
}
type DeviceDescriptor = {
viewport: Nullable<ViewportSize>
userAgent: string
deviceScaleFactor: number
isMobile: boolean
hasTouch: boolean
defaultBrowserType: BrowserType
}
export type CustomDeviceType = Partial<DeviceDescriptor> & {
name: string
}
export type ConfigDeviceType = CustomDeviceType | string
export type DeviceType = Nullable<ConfigDeviceType>
export type WsEndpointType = Nullable<string>
export type SelectorType = {
script: string | Function | { path?: string; content?: string }
name: string
}
export type PlaywrightRequireType = BrowserType | typeof IMPORT_KIND_PLAYWRIGHT
export interface Playwright {
name: PlaywrightRequireType
instance: GenericBrowser | Record<BrowserType, GenericBrowser>
devices: typeof devices
}
type LaunchType = typeof LAUNCH | typeof SERVER | typeof PERSISTENT
type Options<T> = T & Partial<Record<BrowserType, T>>
export type ServerOptions = JestProcessManagerOptions & {
teardown?: string
}
export interface JestPlaywrightConfig {
haveSkippedTests?: boolean
skipInitialization?: boolean
debugOptions?: JestPlaywrightConfig
launchType?: LaunchType
launchOptions?: Options<LaunchOptions>
connectOptions?: Options<ConnectOptions | ConnectOverCDPOptions>
contextOptions?: Options<BrowserContextOptions>
userDataDir?: string
exitOnPageError?: boolean
displayName?: string
browsers: (BrowserType | (JestPlaywrightConfig & { name: BrowserType }))[]
devices?: ConfigDeviceType[] | RegExp
useDefaultBrowserType?: boolean
serverOptions?: ServerOptions | ServerOptions[]
selectors?: SelectorType[]
collectCoverage?: boolean
}
export type JestPlaywrightProjectConfig = Test['context']['config'] & {
browserName: BrowserType
wsEndpoint: WsEndpointType
device: DeviceType
}
export type JestPlaywrightContext = Omit<Test['context'], 'config'> & {
config: JestPlaywrightProjectConfig
}
export type JestPlaywrightTest = Omit<Test, 'context'> & {
context: JestPlaywrightContext
}
export interface BrowserTest {
test: JestPlaywrightTest
config: JestPlaywrightConfig
browser: BrowserType
wsEndpoint: WsEndpointType
device: DeviceType
}
export type ConfigParams = {
browserName: BrowserType
deviceName: Nullable<string>
browser: Nullable<Browser | BrowserContext>
context: BrowserContext
page: Page
}
Eslint 不了解全局变量。要解决这个问题,您有两个选择:
- 告诉eslint定义了哪些变量
- 禁用检查未定义变量的 eslint 规则
要告诉 eslint 定义了哪些全局变量,请将它们添加到您的 eslint 配置文件中
{
"globals": {
"var1": true,
}
}
文档:https://eslint.org/docs/2.13.1/user-guide/configuring#specifying-globals
为了简化这一点,eslint 提供了所谓的 'environments',其中包括所有全局变量,例如此处描述的框架:https://eslint.org/docs/2.13.1/user-guide/configuring#specifying-environments