简体   繁体   English

使用 React、React 测试库和 Cypress 为 Typescript 项目设置 ESLint

[英]Setting up ESLint for a Typescript Project using React, React Testing Library, and Cypress

It seems that every time I start using a new library of some sort I run into problems with ESLint, and I can never truly figure out why.似乎每次我开始使用某种新的库时,我都会遇到 ESLint 的问题,而且我永远无法真正弄清楚原因。 I stumble through until the errors and warnings go away, and then deal with it all again later.我跌跌撞撞直到错误和警告 go 消失,然后再处理。 I'm hoping that I can get some answers on how it's supposed to work here.我希望我能得到一些关于它应该如何在这里工作的答案。

I have a React project that is using Typescript.我有一个使用 Typescript 的 React 项目。 We use react-testing-library for tests (with Jest types) as well as Cypress for testing (with Cypress types).我们使用 react-testing-library 进行测试(使用 Jest 类型)以及 Cypress 进行测试(使用 Cypress 类型)。 Jest and Cypress will conflict as they use a lot of the same keywords but from different libraries (ie. describe , expect , context , etc.). Jest 和 Cypress 会发生冲突,因为它们使用许多相同的关键字但来自不同的库(即describeexpectcontext等)。

Furthermore, with cypress is is possible to define your own functions which will extend the global cy object that is used in all cypress tests, however this must also be typed and requires you to write your own definition files.此外,使用 cypress 可以定义您自己的函数,这将扩展用于所有 cypress 测试的全局cy object,但是这也必须输入,并且需要您编写自己的定义文件。

Everything was going well until I tried to add my own type definitions, at which point it started complaining again.一切都很顺利,直到我尝试添加自己的类型定义,此时它又开始抱怨了。 (I would like to note that my project does compile and run as expected with everything I'm doing at the moment. It is simply ESLint that isn't happy). (我想指出,我的项目确实按照我目前正在做的所有事情编译和运行。这只是 ESLint 不高兴)。

The main issue I'm trying to solve is why the type definition doesn't seem to be included in a project.我试图解决的主要问题是为什么类型定义似乎没有包含在项目中。 I'm receiving the following error:我收到以下错误:

Parsing error: "parserOptions.project" has been set for @typescript-eslint/parser.
The file does not match your project config: cypress\support\index.d.ts.
The file must be included in at least one of the projects provided.

As well as whether there is a better way to lay this out.以及是否有更好的方法来解决这个问题。

Thanks to anyone who actually takes the time to read this and make an attempt.感谢任何真正花时间阅读并尝试的人。

The folder structure looks like this:文件夹结构如下所示:

cypress
- fixtures
- integrations
- - file.spec.ts <- Uses the custom functions in a test
- plugins
- support
- - commands.ts <- Contains my custom functions
- - index.d.ts  <- Types for custom functions
- - index.ts
- .eslintrc.js (A)
- tsconfig.json (B)
src (contains all the jest tests)
.eslintrc.js (C)
tsconfig.json (D)
tsconfig.eslint.json

.eslintrc.js (A)

module.exports = {
  extends: ['../.eslintrc.js'],
  parserOptions: {
    project: 'cypress/tsconfig.json',
  },
}

tsconfig.json (B)

{
  "extends": "../tsconfig.json",
  "compilerOptions": {
    "noEmit": true,
    // be explicit about types included
    // to avoid clashing with Jest types
    "types": ["cypress", "cypress-axe"],
    "allowJs": true
  },
  "include": [".eslintrc.js", "../node_modules/cypress", "./**/*"]
}

.eslintrc.js (C)

module.exports = {
  parser: '@typescript-eslint/parser',
  root: true,
  env: {
    es6: true,
    node: true,
    browser: true,
  },
  parserOptions: {
    ecmaVersion: 6,
    sourceType: 'module',
    tsconfigRootDir: __dirname,
    project: './tsconfig.eslint.json',
    ecmaFeatures: {
      jsx: true,
    },
  },
  plugins: ['react', 'react-hooks', '@typescript-eslint', 'cypress'],
  rules: {
    'react-hooks/rules-of-hooks': 'error', // Checks rules of Hooks
    ...
  },
}

tsconfig.json (D)

{
  "compilerOptions": {
    "target": "es5",
    "lib": ["es6", "dom", "dom.iterable", "esnext"],
    "allowJs": true,
    "skipLibCheck": true,
    "esModuleInterop": true,
    "strict": true,
    "module": "esnext",
    "moduleResolution": "node",
    "resolveJsonModule": true,
    "isolatedModules": true,
    "noEmit": true,
    "jsx": "react",
    "baseUrl": "src",
    "types": ["jest"]
  },
  "include": [
    "build-system",
    "src",
    ".eslintrc.js",
    "pretty.js",
    "gulpfile.js"
  ],
  "exclude": ["node_modules", "src/*.test.ts", "src/*.test.tsx"]
}

tsconfig.eslint.json

{
  // extend your base config so you don't have to redefine your compilerOptions
  "extends": "./tsconfig.json",
  "compilerOptions": {
    "noEmit": true
  },
  "exclude": []
}

For what it's worth, I've solved this problem.对于它的价值,我已经解决了这个问题。 Hopefully this can be useful to someone at some point.希望这在某些时候对某人有用。

Essentially the solution was to get rid of the index.d.ts file, and put the types directly in the commands.ts file.本质上,解决方案是摆脱 index.d.ts 文件,并将类型直接放在 commands.ts 文件中。

With a little help from this thread, which states:这个线程的一点帮助下,它指出:

Hi folks, this issue comment helped me work around the issue: cypress-io/add-ypress-custom-command-in-typescript#2 (comment)大家好,这个问题评论帮助我解决了这个问题:cypress-io/add-ypress-custom-command-in-typescript#2(评论)

Fix seems to be declaring Cypress in the global namespace, and your custom command definitions in there (copied from ☝️ ):修复似乎是在全局命名空间中声明赛普拉斯,并且在那里你的自定义命令定义(从☝️复制):

declare global {
  namespace Cypress {
    interface Chainable {
      customCommand: typeof customCommand;
    }
  }
}

function customCommand(input: MyCustomClass) {
  // ...
}

Cypress.Commands.add('customCommand', customCommand);

But agree that the solution suggested in the docs doesn't work但同意文档中建议的解决方案不起作用

So, by adding the the following code to my commands.ts file:因此,通过将以下代码添加到我的 commands.ts 文件中:

declare global {
  namespace Cypress {
    interface Chainable<Subject> {
      /**
       * Custom command to wait for a specific set of network requests to finish
       * @example cy.waitForData()
       */
      waitForData(): Chainable<Subject>
    }
  }
}

as well as adding the following rule to my.eslintrc.js (C) file:以及将以下规则添加到 my.eslintrc.js (C) 文件中:

rules: {
  ...    
  '@typescript-eslint/no-namespace': ['off']
}

I was able to fix the issue.我能够解决这个问题。

Furthermore, if it's relevant, the isolatedModules flag will require that you add an export {} to the commands.ts file as well.此外,如果相关,isolatedModules 标志将要求您也将export {}添加到 commands.ts 文件中。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM