React-native-vector-icons: Crashes in Release mode on 0.56.0

Created on 31 Jul 2018  ·  19Comments  ·  Source: oblador/react-native-vector-icons

I'm having some insanely strange bug, that I think is related to http://babeljs.io/docs/en/babel-plugin-transform-class-constructor-call being removed in @babel 7

I've spent all day trying to debug this, and it comes down to the icons. As soon as I remove all calls to <Icon ... />, the app works again.

This is with:
Xcode: 9.4
OS: MacOS High Sierra

This happens on Android too, so this is most likely a problem with transpiling one way or another.
Icons are linked properly, and debug mode works fine. This is with all babel dependencies forced to 7.0.beta47. It crashes with the following message:

2018-07-31 01:55:28.772888+0200 App[645:152282] { [TypeError: TypeError: TypeError: TypeError: undefined is not an object (evaluating '_getPrototypeOf2.default')

This error is located at:
    in Icon
    in RCTView
    in RCTView
    in TouchableHighlight
    in IconButton
    in RCTView
    in RCTView
    in KeyboardAvoidingView
    in RCTView
    in AnimatedComponent
    in withAnimatable(Component)
    in BVLinearGradient
    in LinearGradient
    in LoginScreen
    in Auth0Consumer
    in UserConsumer
    in SceneView
    in RCTView
    in AnimatedComponent
    in Card
    in Container
    in RCTView
    in RCTView
    in StackViewLayout
    in withOrientation
    in RCTView
    in Transitioner
    in StackView
    in Navigator
    in KeyboardAwareNavigator
    in NavigationContainer
    in SceneView
    in SwitchView
    in Navigator
    in NavigationContainer
    in UserConsumer
    in RCTView
    in WebProvider
    in PaymentsProvider
    in Mutation
    in Apollo(PaymentsProvider)
    in UserProvider
    in Mutation
    in Apollo(UserProvider)
    in Mutation
    in Apollo(Apollo(UserProvider))
    in Query
    in Apollo(Apollo(Apollo(UserProvider)))
    in Auth0Consumer
    in OneSignalConsumer
    in CacheConsumer
    in OneSignalProvider
    in ApolloProvider
    in GraphQLProvider
    in AuthorizedFetchConsumer
    in FetchProvider
    in CacheConsumer
    in CacheProvider
    in Auth0Consumer
    in Auth0Provider
    in RootContainer
    in App
    in RCTView
    in RCTView
    in AppContainer

Most helpful comment

Holy shit! It works! Thank you @jrnk!

If anybody else runs into this, this is what I've done:

1. Updated .babelrc to this:

{
  "env": {
    "development": {
      "presets": ["react-native", "@babel/preset-flow"],
      "plugins": [
        ["@babel/plugin-proposal-decorators", { "legacy": true }],
        "graphql-tag",
        "@babel/plugin-proposal-object-rest-spread",
        [
          "@babel/plugin-transform-runtime",
          {
            "helpers": true,
            "polyfill": false,
            "regenerator": false
          }
        ]
      ]
    },
    "production": {
      "presets": ["react-native", "@babel/preset-flow"],
      "plugins": [
        ["@babel/plugin-proposal-decorators", { "legacy": true }],
        "graphql-tag",
        "transform-remove-console"
      ]
    }
  }
}

2. package.json has this:

"resolutions": {
    "@babel/core": "7.0.0-beta.47",
    "@babel/runtime": "7.0.0-beta.47",
    "@babel/code-frame": "7.0.0-beta.47",
    "@babel/traverse": "7.0.0-beta.47",
    "@babel/types": "7.0.0-beta.47",
    "@babel/helper-module-imports": "7.0.0-beta.47",
    "@babel/register": "7.0.0-beta.47",
    "babel-core": "^7.0.0-bridge.0",
    "metro": "^0.38.2",
    "metro-babel-register": "^0.38.2",
    "metro-core": "^0.38.2",
    "metro-memory-fs": "^0.38.2",
    "babel-preset-react-native": "^5.0.2"
  },

3. index.js

import { AppRegistry } from 'react-native';
import applyDecoratedDescriptor from '@babel/runtime/helpers/es6/applyDecoratedDescriptor';
import initializerDefineProperty from '@babel/runtime/helpers/es6/initializerDefineProperty';
Object.assign(babelHelpers, {
  applyDecoratedDescriptor,
  initializerDefineProperty,
});

// RN 0.56 Release version crashes
// Workaround: RN 0.56 Release version crashes
// Sources:
//      https://github.com/facebook/react-native/issues/19827
//      https://github.com/facebook/react-native/issues/20150
AppRegistry.registerComponent(
  'Coinalyze',
  () => require('./App/Containers/App').default,
);

All 19 comments

Same here, TypeError · TypeError: undefined is not an object (evaluating 'e.default') This error is located at: in r in Styled(r) in RCTView
My stacktrace pinpoints it at node_modules/react-native-vector-icons/lib/create-icon-set.js:21:70

@jrnk You've got a much more precise stack trace than I, have you found a workaround?

Wondering if it could be that https://github.com/oblador/react-native-vector-icons/blob/master/lib/create-icon-set.js#L40 this const is uppercase and babel (incorrectly) assumes this should be a class? I've had this problem with other non-class uppercase stuff since @babel 7, having to do stuff like:

import { Platform as platform } from "react-native";

This is preventing me from release at the moment :(

@Amnesthesia not yet. Will post here if I do of course.
I'm also pretty confident it's a babel 7 transpiling issue; Not yet sure which one though :)

@jrnk I find it strange that this hasn't been caught (or reported) already, since 0.56 has been out for a month already What does your .babelrc look like?

{
  "presets": ["react-native"],
  "plugins": [
    ["@babel/plugin-proposal-decorators", { "legacy": true }],
    [
      "@babel/plugin-transform-runtime",
      {
        "helpers": true,
        "polyfill": false,
        "regenerator": false
      }
    ]
  ]
}

Damn. Pretty much the same as mine, except I have flow as well.

@Amnesthesia found the culprit.
See https://github.com/facebook/react-native/issues/20150
Changing the app initialization to a require(workaround 2 in the OP) statement solved the release builds for now.

@jrnk I'm already doing that — so that must be something else :(

@Amnesthesia mm :( did you also remove @babel/plugin-transform-runtime ?

@jrnk No! I didn't!! Oh my god please be that. I'm gonna give it a shot

Holy shit! It works! Thank you @jrnk!

If anybody else runs into this, this is what I've done:

1. Updated .babelrc to this:

{
  "env": {
    "development": {
      "presets": ["react-native", "@babel/preset-flow"],
      "plugins": [
        ["@babel/plugin-proposal-decorators", { "legacy": true }],
        "graphql-tag",
        "@babel/plugin-proposal-object-rest-spread",
        [
          "@babel/plugin-transform-runtime",
          {
            "helpers": true,
            "polyfill": false,
            "regenerator": false
          }
        ]
      ]
    },
    "production": {
      "presets": ["react-native", "@babel/preset-flow"],
      "plugins": [
        ["@babel/plugin-proposal-decorators", { "legacy": true }],
        "graphql-tag",
        "transform-remove-console"
      ]
    }
  }
}

2. package.json has this:

"resolutions": {
    "@babel/core": "7.0.0-beta.47",
    "@babel/runtime": "7.0.0-beta.47",
    "@babel/code-frame": "7.0.0-beta.47",
    "@babel/traverse": "7.0.0-beta.47",
    "@babel/types": "7.0.0-beta.47",
    "@babel/helper-module-imports": "7.0.0-beta.47",
    "@babel/register": "7.0.0-beta.47",
    "babel-core": "^7.0.0-bridge.0",
    "metro": "^0.38.2",
    "metro-babel-register": "^0.38.2",
    "metro-core": "^0.38.2",
    "metro-memory-fs": "^0.38.2",
    "babel-preset-react-native": "^5.0.2"
  },

3. index.js

import { AppRegistry } from 'react-native';
import applyDecoratedDescriptor from '@babel/runtime/helpers/es6/applyDecoratedDescriptor';
import initializerDefineProperty from '@babel/runtime/helpers/es6/initializerDefineProperty';
Object.assign(babelHelpers, {
  applyDecoratedDescriptor,
  initializerDefineProperty,
});

// RN 0.56 Release version crashes
// Workaround: RN 0.56 Release version crashes
// Sources:
//      https://github.com/facebook/react-native/issues/19827
//      https://github.com/facebook/react-native/issues/20150
AppRegistry.registerComponent(
  'Coinalyze',
  () => require('./App/Containers/App').default,
);

OMG 🙀 @Amnesthesia @jrnk ❤️❤️❤️

I am trying to build for release for a RN 0.56 project with mobx decorators for two days now and your solution just worked!!!
Thanks a lot! 🤗

@rborn im trying to do the same since couple of days, and the release build is crashing.
This problem only occurs when using mobx-react.

I have also raised an issue in mobx-react repo.
Possible for you to share some info on the fix as im still getting below crash:

[tid:com.facebook.react.ExceptionsManagerQueue] Unhandled JS Exception: babelHelpers.applyDecoratedDescriptor is not a function.

@fahidmohammad you need to have .babelrc split in dev/production like here https://github.com/oblador/react-native-vector-icons/issues/801#issuecomment-409268915

Alsop keep @babel/* vesions to 7.0.0-beta.47

@rborn After updating the @babel/* version to 7.0.0-beta.47 and the .babelrc file all working fine now.

thank you so much for the help.

Hi @rborn, thanks, it works now, but i've another problem. How do i do this with Higher Order Components?

Here is my new code:

import './shim'
import './ReactotronConfig'
import { AppRegistry } from 'react-native';
import applyDecoratedDescriptor from '@babel/runtime/helpers/es6/applyDecoratedDescriptor';
import initializerDefineProperty from '@babel/runtime/helpers/es6/initializerDefineProperty';
Object.assign(babelHelpers, {
  applyDecoratedDescriptor,
  initializerDefineProperty,
});

// RN 0.56 Release version crashes
// Workaround: RN 0.56 Release version crashes
// Sources:
//      https://github.com/facebook/react-native/issues/19827
//      https://github.com/facebook/react-native/issues/20150
AppRegistry.registerComponent(
  'AppName',
  () => require('./index_app').default,
);
import './shim'

import React from 'react'
import { AppRegistry } from 'react-native';
import Provider from './src/mobx'
import Amplify, { Auth} from 'aws-amplify'
import config from './src/aws-exports'
import { ApolloProvider } from 'react-apollo'
import App from './App';

import ApolloClient from "apollo-boost";

const client = new ApolloClient({
  request: async operation => {
   operation.setContext({
     headers: {
       referrer: "https://abc.com"
     }
   });
 },
 uri: "https://xyz-east-2.amazonaws.com/dev/graphql/"
});

export default class AppHome extends React.Component {
  constructor(props) {
    super(props);
    Amplify.configure(config)
  }
render() {
  return (
  <Provider>
    <ApolloProvider client={client}>
      <App />
    </ApolloProvider>
  </Provider>
  )
}
}

With this setup, i'm unable to access mobx stores, is there a way to use this and still access mobx stores with Higher Order Components?

My previous index.js was like this and could access all the mobx stores set in './src/mobx'

import './shim'

import React from 'react'
import { AppRegistry } from 'react-native';
import App from './App';
import Provider from './src/mobx'
import Amplify, { Auth} from 'aws-amplify'
import config from './src/aws-exports'
import { ApolloProvider } from 'react-apollo'

import ApolloClient from "apollo-boost";

const client = new ApolloClient({
   request: async operation => {
    operation.setContext({
      headers: {
       referrer: "https://abc.com"
      }
    });
  },
 uri: "https://xyz-east-2.amazonaws.com/dev/graphql/"
});


Amplify.configure(config)

const AppWithData = () => (
  <Provider>
    <ApolloProvider client={client}>
      <App />
    </ApolloProvider>
  </Provider>
)

console.ignoredYellowBox = ['Warning', 'Remote']
AppRegistry.registerComponent('AppName', () => AppWithData);

@fahidmohammad where and how do you set your mobx stores?

Thanks,
Alp

@ungaro donno :(

@ungaro im using createStackNavigator below i have mentioned the implementation.

router.js

import { createStackNavigator } from 'react-navigation';

import ComponentA from './containers/ComponentA';
import ComponentB from './containers/ComponentB';

const stackNavigatorConfig = {
  initialRouteName: 'ComponentA',
  navigationOptions: {
    gesturesEnabled: false
  },
  // For disabling Animation
  transitionConfig: () => ({
    transitionSpec: {
      duration: 0,
      timing: Animated.timing,
      easing: Easing.step0
    }
  })
};

export default createStackNavigator({
  ComponentA: {
    screen: ComponentA,
  },
  ComponentB: {
    screen: ComponentB,
  }
}, stackNavigatorConfig);

/stores/index.js

import StoreItemA from './StoreItemA';

export default {
  StoreItemA: new StoreItemA()
};

/store/StoreItemA.js

import { observable } from 'mobx';

export default class StoreItemA {
  @observable query;
}

index.js

import React, { Component } from 'react';
import {
  AppRegistry,
} from 'react-native';
import { Provider } from 'mobx-react';
import {name as appName} from '../app.json';

import Stack from './router';

import stores from './stores';

export default class MobXApp extends Component {
  render() {
    return (
      <Provider {...stores}>
        <Stack />
      </Provider>
    );
  }
}

AppRegistry.registerComponent(appName, () => MobXApp);

But now i have another issue with MobX over React Navigation. The state management does not work properly with the above approach. Still digging a better approach.

If anyone can suggest a better implementation modal, will be highly appreciated.

@ungaro Can you show your .babelrc and package.json? The decision what was provided here https://github.com/oblador/react-native-vector-icons/issues/801#issuecomment-409268915 is not working for me - I'm using mobx too.

Was this page helpful?
0 / 5 - 0 ratings

Related issues

emretekince picture emretekince  ·  4Comments

jszcl picture jszcl  ·  3Comments

AbhayVarshney picture AbhayVarshney  ·  3Comments

arjs1000 picture arjs1000  ·  3Comments

venux92 picture venux92  ·  3Comments