Skip to content
This repository has been archived by the owner on Nov 4, 2024. It is now read-only.

Jest compatibility #97

Closed
aemino opened this issue Sep 17, 2017 · 28 comments
Closed

Jest compatibility #97

aemino opened this issue Sep 17, 2017 · 28 comments

Comments

@aemino
Copy link

aemino commented Sep 17, 2017

Hello,
This is less of an issue and more like a compatibility request. I've been trying to use Jest with this package and it doesn't seem that the two packages currently work very harmoniously. In my test files, I'm using the regular, un-modified require function to load index.js, which uses @std/esm to load other ESM files.

// index.js
require = require('@std/esm')(module);

module.exports = require('./Registry').default;
// ... other exports

This is the resulting error when I try to run my tests with Jest. I'm using npm run test which runs jest. I saw this same stack trace in #28 but I thought I'd open a new issue just to keep things more organized.
image

Thanks!

@jdalton
Copy link
Member

jdalton commented Sep 17, 2017

Hi @aemino!

What version of @std/esm are you using?
It shouldn't be exposing its internals when erroring (an older version accidentally did though).

Can you create a simple repro repo?

@aemino
Copy link
Author

aemino commented Sep 17, 2017

I'm using the latest version of @std/esm, version 0.9.2.
I've created a simple repro at aemino/esm-repro.

@jdalton
Copy link
Member

jdalton commented Sep 17, 2017

Interesting... Jest is somehow creating a module object without an exports property.

Update:
It looks like Jest is mocking the Module constructor. When it does though it forgot to set its constructor property up so the modules it produces have a .constructor of Object instead of the actual constructor. So when I use module.constructor I get Object and when I pass an id to it I get a string object back which doesn't have an exports property. What's even more interesting is its Object of another realm so checks for module.constructor === Object fail.

@jdalton jdalton added the bug label Sep 17, 2017
@jdalton
Copy link
Member

jdalton commented Sep 17, 2017

Patched ab92c9b and bumped to v0.10.0 🎉

@aemino
Copy link
Author

aemino commented Sep 17, 2017

Awesome! This solved the issue for me. Thank you very much for your work. 👍

@eliw00d
Copy link

eliw00d commented Sep 19, 2017

I am having a different problem, where I get Unexpected token import errors when trying to run Jest tests. Here is a repro repo:

https://github.com/eliw00d/jest-esm

@jdalton
Copy link
Member

jdalton commented Sep 19, 2017

@eliw00d Your src/main/index.js isn't being loaded by the loader. You've set it up for the loader to load a few test files but beyond that the trail runs cold. I'm guessing Jest picks things up and loads them with its own loader (it is mocking things). Your package entry script should have a loader hook-up like your test script.

@eliw00d
Copy link

eliw00d commented Sep 19, 2017

Ah, I see now. But that could mean a lot of work rewriting tests to require the index rather than the file itself. Thanks.

@jdalton
Copy link
Member

jdalton commented Sep 19, 2017

@eliw00d For testing you can enable the omnipresent hook using node -r @std/esm
or the NODE_OPTIONS environment variable.

For package consumption heads up that your module entry is just a bare ESM module which won't work without a loader. Your package's entry point should be a CJS module that initializes the loader as our getting started section suggests.

@kenotron
Copy link

Seeing as how this is the first google result from people search "esm jest," I'd like to post a solution that works.

Hacked up something that would work even if your tests are use esnext modules (say, from a typescript compile output):

https://github.com/kenotron/esm-jest

Inspiration is from here:

https://stackoverflow.com/questions/46433678/specify-code-to-run-before-any-jest-setup-happens

@kenotron
Copy link

kenotron commented Mar 25, 2018

I've updated this example with your PR, @jdalton - thanks! It looks much cleaner and adds caching 👍
My next trick is to integrate this in a large codebase written in Typescript to see if it still works!

@dandv
Copy link

dandv commented Oct 6, 2018

@jdalton: how exactly can NODE_OPTIONS be used to just run jest when the test file uses import syntax?

NODE_OPTIONS='-r esm' npx jest fails with SyntaxError: Unexpected token {.

index.test.js is import { foo } from './main';

@kenotron's solution is far from simple and it doesn't support import.

TL;DR - what's the recipe for using Jest to test ES modules? I couldn't find that in the README or in the Medium post.

@jdalton
Copy link
Member

jdalton commented Oct 6, 2018

Hi @dandv!

There isn't a clean way at the moment. However, in the next esm release you'll be able to specify esm as a transform in your jest.config.json:

  "transform": {
    "\\.m?js$": "esm"
  },
  "transformIgnorePatterns": []

@pi0
Copy link

pi0 commented Oct 14, 2018

@jdalton We are really looking forward to this solution <3

@jdalton
Copy link
Member

jdalton commented Oct 14, 2018

Thanks @pi0!

Still in the process of cleaning it up. I got caught up with the Node+JS Interactive conference and improving support for new dynamic import() test262 tests.

@cabbiepete
Copy link

@jdalton I presume the next esm release will resolve the current jest with esm issue if you configure esm as a transform as above?

Putting this here to let you know in case you were not aware already.

TypeError: Jest: a transform must export a `process` function.

@jdalton
Copy link
Member

jdalton commented Oct 23, 2018

@cabbiepete

I presume the next esm release will resolve the current jest with esm issue if you configure esm as a transform as above?

Correct. It's not available in the current installable release. It will be in the next release though.

@kenotron
Copy link

Do you know when you will have that release? Is that code available in a branch we can poke at?

@jdalton
Copy link
Member

jdalton commented Oct 29, 2018

@kenotron It's in master branch but is not suitable for shipping and may be broken at the moment. Fixing some things so its support is in flux.

@kenotron
Copy link

ooh ooh i'll settle for playing around with on master branch :) That's SOMETHING to hang on to :P

@danturu
Copy link

danturu commented Nov 18, 2018

@jdalton I know that this feature is still in progress, but installing esm from the master fails jest:

 TypeError: Cannot destructure property `dir` of 'undefined' or 'null'.

      at Object.<anonymous> (../../node_modules/esm/esm.js:233:26)

The snippet:

if (cachePath !== "") {
  const { dir } = shared.package // HERE package is undefined!

May be it helps you to land the upcoming release faster.

@kenotron
Copy link

esm 3.1.0 came out! Will have to mess around with jest + esm to see how that is done

@kenotron
Copy link

I am trying out esm 3.1.0 with https://github.com/kenotron/esm-jest

It still fails :(

TypeError: Cannot read property 'next' of undefined
      at Object.n.(anonymous function) (node_modules/esm/esm.js:1:1796)

Basically it fails to find a ".next" from the _runResults

@jdalton
Copy link
Member

jdalton commented Jan 16, 2019

Correct @kenotron! When trying to get Jest support finished I ran into some blockers that prevented it from making it into the 3.1.0 release. I'll be in a follow-up release for sure.

@kenotron
Copy link

kenotron commented Jan 16, 2019

you're not far! i started a new issue to track some issues that i'm finding here #706.

Hmmm, maybe you can edit it and enumerate the blockers on this support? I would love to see this happen - am willing to roll up my sleeves to help test / help fix

@chrisdothtml
Copy link

For anyone wondering, you can still use the esm require approach in your tests without the jest transform option. e.g.

my-module.test.js

const esmRequire = require('esm')(module)
const { foo } = esmRequire('./my-module.js')

describe('my es-module', () => {
//...

my-module.js

export function foo () {
  //...
}

@edmand46
Copy link

Any news?

@jdalton
Copy link
Member

jdalton commented May 21, 2019

Moved to #706.

@standard-things standard-things locked and limited conversation to collaborators May 21, 2019
@jdalton jdalton added duplicate and removed bug labels May 21, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Development

No branches or pull requests

10 participants