【问题标题】:after updating expo: Element type is invalid: expected a string (for built-in components) or a class/function更新博览会后:元素类型无效:需要字符串(用于内置组件)或类/函数
【发布时间】:2021-09-25 06:20:38
【问题描述】:

在我将 Expo SDK 从 39 更新到 42 后,尝试启动应用时出现以下错误:

错误:元素类型无效:应为字符串(对于内置 组件)或类/函数(用于复合组件),但得到: 不明确的。您可能忘记从文件中导出组件 它是在中定义的,或者您可能混淆了默认导入和命名导入。

查看App的渲染方法。

此错误位于: 在 App 中(由 ExpoRoot 创建) 在 ExpoRoot (在 renderApplication.js:45) 在 RCTView 中(在 View.js:34) 在视图中(在 AppContainer.js:106) 在 RCTView 中(在 View.js:34) 在视图中(在 AppContainer.js:132) 在 AppContainer 中(在 renderApplication.js:39 处)

从错误报告中我得出结论,错误位于我的 App.js 文件中,即使除了升级我的 expo 版本之外我没有更改任何内容。

App.js:

//Automatic imports
import React, {useState} from 'react';
import { StyleSheet, Text, View } from 'react-native';
import { Provider } from 'react-redux';

//My imports
import * as Font from 'expo-font';
import {AppLoading} from 'expo';
import ReduxThunk from 'redux-thunk';
import { createStore, combineReducers, applyMiddleware } from 'redux';


//import other screens
import NavigationContainer from './navigation/NavigationContainer';

//import Reducers
import authReducer from './store/reducers/auth';
import pigeonReducer from './store/reducers/pigeon';
import badgesReducer from './store/reducers/badges';
import languagesReducer from './store/reducers/language';

//imports related to firebase
import * as firebase from "firebase";
import ApiKeys from "./constants/ApiKeys";

//Loading Fonts, returns promise
const fetchFonts = () => {
  return Font.loadAsync({
    'Magnus' : require('./assets/fonts/MagnusText.ttf'),
    'AmaticBold' : require('./assets/fonts/Amatic-Bold.ttf'),
    'AmaticRegular' : require('./assets/fonts/AmaticSC-Regular.ttf'),
    'SEASRN' : require('./assets/fonts/SEASRN.ttf'),
    'Otto' : require('./assets/fonts/Otto.ttf'),
    'Gwibble' : require('./assets/fonts/GWIBBLE.ttf'),
    'GTA' : require('./assets/fonts/pricedown.otf')
  });
};

const rootReducer = combineReducers({
  auth: authReducer,
  myPigeons: pigeonReducer,
  myBadges: badgesReducer,
  myLanguage: languagesReducer
});

const store = createStore(rootReducer, applyMiddleware(ReduxThunk));


export default function App() {
  //firebase project initialisation
  if (!firebase.apps.length) {
    firebase.initializeApp(ApiKeys);
    //console.log("DB INITIALISED"); FIRING IF DATABASE INITIALISED
  };

  const [dataLoaded, setDataLoaded] = useState(false); //are fonts loaded?

  if(!dataLoaded){ //will go into if clause because fonts are not loaded
    return(
      <AppLoading 
        startAsync={fetchFonts} 
        onFinish={() => setDataLoaded(true)}
        onError={(err) => console.log(err)}
      />
    )
  }
  return (
    <Provider store={store}>
      <NavigationContainer/>
    </Provider>
  );
}

const styles = StyleSheet.create({
  container: {
    flex: 1,
    backgroundColor: '#fff',
    alignItems: 'center',
    justifyContent: 'center',
  },
});

我知道有几个人遇到同样的错误,但是他们的问题有很多对我不起作用的答案,也许有人知道如何解决我的问题。 如果您需要我项目中的其他代码示例,请告诉我,我会更新这个问题。

【问题讨论】:

  • 99% 的情况下,此错误意味着您正在从某处导入 Xyz,但它实际上并不作为导出存在。因此,当您尝试执行&lt;Xyz ... /&gt; 时,您会看到您看到的错误。例如,您有 import {AppLoading} from 'expo'; 只需尝试将 console.log(AppLoading); 直接放在导入行之后并检查它是否是实际组件。
  • @ChrisG 完美的方法,我从中获得了不确定性。更新了这个包并正确导入它,我修复了它。如果你愿意,请回复这篇文章,我给你一个绿色的钩子。
  • 我愿意,但这绝对是重复的。这是一个非常常见的错误。
  • 发现几乎完全一样的骗局:stackoverflow.com/questions/66924778/…
  • 是的,我知道这一切。重复项的一个问题是发布答案的人都指的是非常具体的库和导入,而不是提供问题的实际根本原因,即其中一个导入未定义。所以我实际上要发布一个答案:)

标签: javascript react-native expo


【解决方案1】:

99% 的情况下,此错误意味着您正在从某个地方导入 Xyz,但它实际上并不作为导出存在。

因此,当您尝试在 JSX 中执行 &lt;Xyz ... /&gt; 时,您会收到错误,我将在此处重现:

错误:元素类型无效:应为字符串(对于内置组件)或类/函数(对于复合组件),但得到:undefined。您可能忘记从定义组件的文件中导出组件,或者您可能混淆了默认导入和命名导入。

(强调我的)

undefined 是这里的关键,例如你有

import {AppLoading} from 'expo';

然而,根据当前文档的行是

import AppLoading from 'expo-app-loading';

要调试它,只需记录导入的组件即可:

console.log(AppLoading);

您会很快找到 undefined 的导入,这就是导致错误的原因。

【讨论】:

  • 谢谢。我升级到 41 Expo 版本后,它是“expo-app-loading”
猜你喜欢
  • 2019-02-16
  • 1970-01-01
  • 2021-01-23
  • 1970-01-01
  • 2017-12-07
  • 1970-01-01
  • 1970-01-01
  • 2019-07-10
  • 2018-10-28
相关资源
最近更新 更多