1import { withErrorOverlay } from '@expo/metro-runtime/error-overlay'; 2import { registerRootComponent } from 'expo'; 3import React from 'react'; 4import { Platform, View } from 'react-native'; 5import { SplashScreen, _internal_preventAutoHideAsync } from './views/Splash'; 6function isBaseObject(obj) { 7 if (Object.prototype.toString.call(obj) !== '[object Object]') { 8 return false; 9 } 10 const proto = Object.getPrototypeOf(obj); 11 if (proto === null) { 12 return true; 13 } 14 return proto === Object.prototype; 15} 16function isErrorShaped(error) { 17 return (error && 18 typeof error === 'object' && 19 typeof error.name === 'string' && 20 typeof error.message === 'string'); 21} 22/** 23 * After we throw this error, any number of tools could handle it. 24 * This check ensures the error is always in a reason state before surfacing it to the runtime. 25 */ 26function convertError(error) { 27 if (isErrorShaped(error)) { 28 return error; 29 } 30 if (process.env.NODE_ENV === 'development') { 31 if (error == null) { 32 return new Error('A null/undefined error was thrown.'); 33 } 34 } 35 if (isBaseObject(error)) { 36 return new Error(JSON.stringify(error)); 37 } 38 return new Error(String(error)); 39} 40/** 41 * Register and mount the root component using the predefined rendering 42 * method. This function ensures the Splash Screen and errors are handled correctly. 43 */ 44export function renderRootComponent(Component) { 45 try { 46 // This must be delayed so the user has a chance to call it first. 47 setTimeout(() => { 48 _internal_preventAutoHideAsync(); 49 }); 50 if (process.env.NODE_ENV !== 'production') { 51 registerRootComponent(withErrorOverlay(Component)); 52 } 53 else { 54 registerRootComponent(Component); 55 } 56 } 57 catch (e) { 58 // Hide the splash screen if there was an error so the user can see it. 59 SplashScreen.hideAsync(); 60 const error = convertError(e); 61 // Prevent the app from throwing confusing: 62 // ERROR Invariant Violation: "main" has not been registered. This can happen if: 63 // * Metro (the local dev server) is run from the wrong folder. Check if Metro is running, stop it and restart it in the current project. 64 // * A module failed to load due to an error and `AppRegistry.registerComponent` wasn't called. 65 registerRootComponent(() => React.createElement(View, null)); 66 // Console is pretty useless on native, on web you get interactive stack traces. 67 if (Platform.OS === 'web') { 68 console.error(error); 69 console.error(`A runtime error has occurred while rendering the root component.`); 70 } 71 // Give React a tick to render before throwing. 72 setTimeout(() => { 73 throw error; 74 }); 75 // TODO: Render a production-only error screen. 76 } 77} 78//# sourceMappingURL=renderRootComponent.js.map