metro v0.48.1 needs react-native v0.53.3 when run test with jest
sasurau4
Posted on October 28, 2018
TL;DR
If you met a problem that test fail unexpectedly after upgrading metro-react-native-babel-preset v 0.48.1, you try to upgrade react-native v0.57.3.
Jest failed situation
One day, I upgraded many libraries. After upgrade, I ran yarn test
and saw jest failed with below error message.
TypeError: Cannot read property 'default' of undefined
at new Icon (node_modules/react-native-vector-icons/lib/create-icon-set.js:42:389)
...
On my environment.
OS: Ubuntu 18.04
node: v11.0.0
react-native: v0.57.2
react-native-elements: v0.19.1
metro-react-native-babel-preset: v0.48.1
react-native-vector-icons: v6.0.2
@babel/runtime: v7.1.2
my package.json
...
"jest": {
"preset": "react-native",
"transform": {
"^.+\\.js$": "<rootDir>/node_modules/react-native/jest/preprocessor.js"
}
...
For more details, see my reproduce repository
Umm, why jest test failed?
The reason why jest failed
It is because that metro changed the default config of using @babel/runtime or not when jest.
This config affects babel use plugin-tranform-runtime or not.
metro-react-native-babel-preset at v0.48.1 use plugin-transform-runtime by default.
https://github.com/facebook/metro/pull/285/files#diff-691dcb134bb2a1276f7a1fea8728f634L150
But preprocessor.js at v0.57.2 has only disableBabelRuntime option.
https://github.com/facebook/react-native/blob/v0.57.2/jest/preprocessor.js#L55
So, our javascript code are transpiled by babel with plugin-transform-runtime.
Upgrade react-native to v0.57.3 solve the problem.
Detailed question: why jest fails with @babel/runtime?
I didn't understand the difference with @babel/runtime or not.
I read https://babeljs.io/docs/en/babel-runtime.
It's sense for me. But still remain unknown point.
My situation has @babel/runtime
in dependencies, why the property 'default' of undefined?
So, I investigated transpiled codes by modifying preprocessor's code.
Jest failed at create-icon-set.js
in react-native-vector-icons package
.
First, I change the file of preprocessor.js to intercept generated code and write it to file.
Here is generated codes.
Babel generated code is minified and not human-readble, so the repo codes are formatted by prettier.
The deference of two files is same as babel's document explained.
I matched generated code and error massage from jest.
The problem is at line 82 in babeled-by-jest-with-runtime.js
...
(_getPrototypeOf2 = (0, _getPrototypeOf2.default)(Icon)).call.apply(
...
This code correspond to static propTypes in react-native-vector-icons
Second, I transpile create-icon-set.js
by @babal\cli
.
The result is here
The result is here
The different point of result is below.
...
(_getPrototypeOf2 = (0, _getPrototypeOf3.default)(Icon)).call.apply(
...
babel by jest code is _getPrototypeOf2.default
, babel by cli is _getPrototypeOf3.default
.
This difference may cause of jest fail.
I'm not convinced because I don't fully understand about jest and babel.
Also, metro use babel runtime from this commit.
From this issue, jest still use old regeneratorRuntime from regeneratro-runtime.
I think it affects the above result.
The full result of analyze is here
I'll happy that this article help you when you show jest fail.
If you found the cause of the proble or my misunderstood, tell me about it!
Thanks for your reading!
Posted on October 28, 2018
Join Our Newsletter. No Spam, Only the good stuff.
Sign up to receive the latest update from our blog.