enzyme_adapter_react_16_1.default is not a constructor

Created on 20 Oct 2017  Â·  26Comments  Â·  Source: enzymejs/enzyme

package.json

{
  "name": "my-app",
  "version": "0.1.0",
  "private": true,
  "dependencies": {
    "@types/jquery": "^3.2.15",
    "@types/react-bootstrap": "^0.31.6",
    "@types/react-router-dom": "^4.0.8",
    "jquery": "^3.2.1",
    "react": "^16.0.0",
    "react-bootstrap": "^0.31.3",
    "react-dom": "^16.0.0",
    "react-router-dom": "^4.2.2",
    "react-scripts-ts": "2.8.0"
  },
  "scripts": {
    "start": "react-scripts-ts start",
    "build": "react-scripts-ts build",
    "test": "react-scripts-ts test --env=jsdom --setupTestFrameworkScriptFile=raf/polyfill",
    "eject": "react-scripts-ts eject"
  },
  "devDependencies": {
    "@types/enzyme": "^3.1.0",
    "@types/enzyme-adapter-react-16": "^1.0.0",
    "@types/jest": "^21.1.4",
    "@types/node": "^8.0.45",
    "@types/react": "^16.0.14",
    "@types/react-dom": "^16.0.1",
    "enzyme": "^3.1.0",
    "enzyme-adapter-react-16": "^1.0.2",
    "react-addons-test-utils": "^15.6.2",
    "react-test-renderer": "^16.0.0"
  }
}

test file:

import * as Enzyme from 'enzyme';
import Adapter from 'enzyme-adapter-react-16';

Enzyme.configure({ adapter: new Adapter() });

import React from 'react';
import { shallow, mount, render } from 'enzyme';
import Header from './Header';


it('expects Header title to be DMA Migration', () => {
    const header = shallow(<Header />);
    expect(header.find(".migration-title").text()).toEqual('DMA Migration')
});

error:

Test suite failed to run

    TypeError: enzyme_adapter_react_16_1.default is not a constructor

      at Object.<anonymous> (src/components/Header.test.tsx:5:29)

Most helpful comment

Based on the above answers, what i did to solve this is:

yarn add --dev types/enzyme-adapter-react-16 types/enzyme and changed imports to

import * as Enzyme from 'enzyme';
import * as Adapter from 'enzyme-adapter-react-16';

All 26 comments

See https://github.com/airbnb/enzyme/pull/1264

TypeScript doesn't yet create synthetic default imports like Babel does

This is definitely a TypeScript bug. Closing in favor of #1264.

thanks!!

Based on the above answers, what i did to solve this is:

yarn add --dev types/enzyme-adapter-react-16 types/enzyme and changed imports to

import * as Enzyme from 'enzyme';
import * as Adapter from 'enzyme-adapter-react-16';

Incase anyone stumbles across this thread, I found the import * as Adapter solution not to work but if I imported the ReactSixteenAdapter specifically it works.

import * as Enzyme from 'enzyme';
import ReactSixteenAdapter from 'enzyme-adapter-react-16';

Enzyme.configure({ adapter: new ReactSixteenAdapter() });

@mattjegan this works for me!! thank you

You shouldn't need import * as - if you're using TypeScript, you need to allow synthetic imports to get spec-compliant import behavior.

It doesn't work for me

TypeScript:
import { configure } from 'enzyme';
import * as ReactSixteenAdapter from 'enzyme-adapter-react-16';
const adapter = ReactSixteenAdapter as any;
configure({ adapter: new adapter.default() });
It work for me.

@bazyliszek10000 in your case you should just import Adapter from ‘enzyme-adapter-react-16’ and new Adapter()

@ljharb. With the current typing "@types/enzyme-adapter-react-16" (Type definitions for enzyme-adapter-react-16 1.0) you can not simply import the "Adapter". There are no export default type in the d.ts file, none of the exported types is called "Adapter". The solution is certainly not elegant, but it shows where the problem is.

this:

  • import Adapter from 'enzyme-adapter-react-16'
  • import {Adapter} from 'enzyme-adapter-react-16'
  • import {ReactSixteenAdapter} from 'enzyme-adapter-react-16'
    it does not work, and the following code does not call the constructor and it does not work too:
    import * as Adapter from 'enzyme-adapter-react-16';
    Enzyme.configure({ adapter: new Adapter() });

@bazyliszek10000 then those types are incorrect; and you should file a bug upstream. import Adapter from 'enzyme-adapter-react-16' is the proper way to import it, and anything else is wrong. You may need to enable syntheticImports or esModuleInterop in your TS settings to get it to not violate the JS spec.

Incase anyone stumbles across this thread, I found the import * as Adapter solution not to work but if I imported the ReactSixteenAdapter specifically it works.

import * as Enzyme from 'enzyme';
import ReactSixteenAdapter from 'enzyme-adapter-react-16';

Enzyme.configure({ adapter: new ReactSixteenAdapter() });

this solution works with create react app and typescript, thanks @mattjegan

You need to use the import like this:

import Adapter from 'enzyme-adapter-react-16';

Incase anyone stumbles across this thread, I found the import * as Adapter solution not to work but if I imported the ReactSixteenAdapter specifically it works.

import * as Enzyme from 'enzyme';
import ReactSixteenAdapter from 'enzyme-adapter-react-16';

Enzyme.configure({ adapter: new ReactSixteenAdapter() });

Another prerequisite for this to work is esModuleInterop enabled in tsconfig.json.
Tested with

[email protected]
[email protected]
[email protected]

The reason is described here: https://github.com/airbnb/enzyme/pull/1264#discussion_r144713875

@InvictusMB THANK YOU! I've been at this all day...

Another prerequisite for this to work is esModuleInterop enabled in tsconfig.json

This was a critical piece of information in my journey to get enzyme to stop complaining. In tsconfig.js I added "esModuleInterop": true.

Add "esModuleInterop": true it worked also for me.

Thanks @bradgreens

I also have such a problem

my solution:
add "esModuleInterop": true to tsconfig.json
but there is still a problem, import Adapter from 'enzyme-adapter-react-16' doesn't pass the eslint check

@Myqilixiang you probably also need synthetic imports turned on.

Incase anyone stumbles across this thread, I found the import * as Adapter solution not to work but if I imported the ReactSixteenAdapter specifically it works.

import * as Enzyme from 'enzyme';
import ReactSixteenAdapter from 'enzyme-adapter-react-16';

Enzyme.configure({ adapter: new ReactSixteenAdapter() });

Works for me!

import * as Enzyme from 'enzyme';
import * as Adapter from 'enzyme-adapter-react-16';

Enzyme.configure({ adapter: new Adapter() });

not working this

You should never need import * as; typescript’s module system is broken unless you enable synthetic imports and esModuleInterop.

Actually, the types look correct. Here's what I'm thinking, correct me if I'm wrong:

The code is a commonJS style code that does:

module.exports = ReactSixteenAdapter;

Which means you shouldn't be able to default import anything. The built version isn't any different, so if in a commonjs module you'd import it, you'd say:

const Adapter = require('enzyme-adapter-react-16');

So the types accordingly say:

export = ReactSixteenAdapter;

The only reason this works as you show in examples and in this thread, is because on the receiver end, you are using babel, and babel wraps legacy commonjs modules in _interopRequireDefault which will allow you to get the module.exports as a default export. But this still relies on the receiver using babel.

@delanni that's all correct, however, with esModuleInterop and synthetic imports enabled in TS (which tsc --init does for you, because it's the only way to not have a broken module system) you'd import Adapter from 'enzyme-adapter-react-16' instead of having to use require.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

modemuser picture modemuser  Â·  3Comments

ivanbtrujillo picture ivanbtrujillo  Â·  3Comments

SandroMachado picture SandroMachado  Â·  3Comments

ahuth picture ahuth  Â·  3Comments

potapovDim picture potapovDim  Â·  3Comments