According to the truth, the official will be more comfortable with the results, one after another hit a wall, coupled with similar information is really a little little, can only fill.

0. Current problems

First of all, the scaffolding is definitely not CRA (CRA users please directly use the official package test), we will definitely use our own customized scaffolding. When we selected Jest for single test, several problems appeared:

  • typescript
  • Unable to readwebpack
  • css-modules

The second point is so hard that it leads directly to the third point. And I also out of “dare not move the ancestral code” principle, can only continue to fill.

1. Assembly Jest

The installation

Install Jest however you like

npm i -D jest @types/jest #or yarn
Copy the code

Then you need to configure the boot mode

// package.json{..."scripts": {
    "test": "jest". }..."jest": {}}Copy the code

Another method that isn’t officially mentioned (or that I haven’t noticed) is to put a jest. Config.js in your project, which is also configurable for those of you who are squeaky-freaks about package.json.

configuration

B: What do we need first? – the TypeScript.

npm i -D ts-jest # Since we already use TypeScript we don't need to install it again
Copy the code
{
  "jest": {
    "moduleFileExtensions": [
      "ts"."tsx"]."transform": {
      "^.+\\.tsx? $": "ts-jest",}}}Copy the code

Then, we would prefer to put all test cases in the Test folder, although it would be clearer to put single tests for each component in that component’s folder (as CRA does). So set up the test directory and continue to configure

{
  "jest": {
    "moduleFileExtensions": [
      "ts"."tsx"]."transform": {
      "^.+\\.tsx? $": "ts-jest",},"testMatch": [
      "
      
       /test/**/? (*) (spec|test).ts? (x)"
      ].}}Copy the code

In this way, files like ydjNb.test. TSX or ydjNb.spec. ts and so on will be captured as test files for testing.

// ydjnb.spec.ts

test('Jest-typescript tries to run', () => {
  expect(1+1).toBe(2) // Pass
})
Copy the code

At this point, you can use tests for Typescript, but not React.

2. Assembly Enzyme

The Jest document, DOM Testing React Apps, recommends using the Enzyme.

npm i -D enzyme @types/enzyme
Copy the code

Back in ydjNb.spec. ts, the name should now be *.tsx as it relates to JSX

// ydjnb.spec.tsx
import { shallow } from 'enzyme'

test('Jest-react-typescript tries to run', () = > {const renderer = shallow(<div>hello world</div>)
  expect(renderer.text()).toEqual('hello world')})Copy the code

Shallow, of course, is just a “shallow render” that renders only the current component, making assertions. Generally tests care about interaction as well as data, so there are two other methods render, mount.

Problem solving

— Finished! Run it! — ERROR

If you look a little closer, you’ll notice that my code snippet above was not marked // Pass, and you may be looking back now!

enzyme-adapter-react-16

So the first error is easy to solve, because if you look at the test result carefully, the Enzyme has already told you.

Enzyme Internal Error: Enzyme expects an adapter to be configured, but found none. To configure an adapter, you should call Enzyme.configure({ adapter: new Adapter() })before using any of Enzyme’s top level APIs, where Adapter is the adaptercorresponding to the library currently being tested. For example:

import Adapter from ‘enzyme-adapter-react-15’;

To find out more about this, see http://airbnb.io/enzyme/docs/installation/index.html

However, I know THAT I am already using Act-16. The documentation will also mention the solution to this problem.

npm i -D enzyme-adapter-react-16
Copy the code

Back in ydjNb.spec.tsx,

// ydjnb.spec.tsx
import { shallow, configure } from 'enzyme'
import Adapter from 'enzyme-adapter-react-16'

configure({ adapter: new Adapter() })

test('Jest-react-typescript tries to run', () = > {const renderer = shallow(<div>hello world</div>)
  expect(renderer.text()).toEqual('hello world') // Pass
})
Copy the code

css-modules

According to the Jest documentation, add a library to solve the problem: identity-obj-proxy

{
  "moduleNameMapper": {
    "\\.(css|scss)$": "identity-obj-proxy"
  },
  "transform": {... },... }Copy the code

At this point, the requirements are fully operational.