undefined不是一个函数(评估'fetch('apiurl')')

时间:2017-05-21 10:17:52

标签: reactjs react-native react-native-router-flux

我正在使用以下版本

  1. react-native-router-flux ^ 3.39.1
  2. react-native 0.44.0
  3. 我希望通过“fetch”调用我正在使用的API 已使用componentDidMount但它显示另一个错误

      

    undefined不是对象(评估'this._component.getScrollableNode')

    但我的错误输出低于

    enter image description here enter image description here

    重现的步骤

    1. 使用路由器通量创建三个场景(在我的情况下,App,Login,Home)
    2. 使用ScrollView创建Login.js创建按钮
    3. 使用TouchableHighlight之后用函数调用fetch 使用像onPress={ () => this.fetchData() }
    4. 这样的onPress

      下面的代码,我用于App.js

      import React, { Component } from 'react';
      import {
          View,
          Text,
          StyleSheet,
          AsyncStorage,
      } from 'react-native';
      
      import Login from './components/Login'
      import Register from './components/Register'
      import Home from './components/Home'
      import { Scene, Router, TabBar, Modal, Schema, Actions, Reducer, ActionConst } from 'react-native-router-flux'
      
      const reducerCreate = params=>{
          const defaultReducer = Reducer(params);
          return (state, action)=>{
              console.log("ACTION:", action);
              return defaultReducer(state, action);
          }
      };
      
      export default class App extends Component {
      
          constructor(props, context) {
              super(props, context);
              this.state = {
                  logged: false,
                  loading: true,
              };
          };
      
          componentWillMount(){
              self = this;
              AsyncStorage.getItem('token')
              .then( (value) =>{
                  if (value != null){
                      this.setState({
                          logged: true,
                          loading: false,
                      });
                  }
                  else {
                      this.setState({
                          loading: false,
                      })
                  }
              });
          };
      
          render() {
              if (this.state.loading) {
                  return <View><Text>Loading</Text></View>;
              }
              return (
                  <Router>
                      <Scene hideNavBar={true} key="root">
                          <Scene key="logIn" component={Login} title="Login" initial={!this.state.logged}/>
                          <Scene key="regisTer" component={Register} title="Register"/>
                          <Scene key="home" component={Home} title="home"  initial={this.state.logged}/>
                      </Scene>
                  </Router>
              )
          }
      }
      
      const styles = StyleSheet.create({
          container: {
              flex: 1,
          },
      });
      

      以下代码,用于Login.js

      /* @flow */
      
      import React, { Component } from 'react';
      
      import {
          View,
          StyleSheet,
          Image,
          ScrollView,
          TextInput,
          Text,
          TouchableHighlight,
          Alert,
      } from 'react-native';
      import { Container, Content, InputGroup, Input, Icon, Item } from 'native-base';
      import Button from 'react-native-button'
      import {Actions} from 'react-native-router-flux'
      import ResponsiveImage from 'react-native-responsive-image'
      
      export default class Login extends Component {
      
          constructor(props){
              super(props)
              this.state = {
                  email: '',
                  password: '',
                  data: '',
              }
          }
      
          fetchData() {
              fetch('http://allstariq.tbltechnerds.com/api/login/?username=andress&password=23434')
              .then((response) => response.json())
              .then((responseData) => {
                  this.setState({
                      data: responseData.movies,
                  });
              })
              .done();
          }
      
          render() {
              return (
                  <View style={styles.container}>
      
                  <ScrollView>
      
                      <View style={ styles.logoContainer }>
      
                          <View style={{flexDirection: 'row',}}>
                              <ResponsiveImage
                              source={require('../assets/logo.png')}
                              initWidth="300"
                              initHeight="160" />
                          </View>
      
                      </View>
      
                      <View style={ styles.formContainer }>
                          <Item>
                              <Icon active name='mail' />
                              <Input
                                  onChangeText={(text) => this.setState({email: text})}
                                  value={this.state.email}
                                  placeholder='Email'/>
                          </Item>
      
                          <Item>
                              <Icon active name='key' />
                              <Input
                                  onChangeText={(text) => this.setState({password: text})}
                                  value={this.state.password}
                                  placeholder='Password'/>
                          </Item>
                          <TouchableHighlight
                              style={ styles.loginButton }
                              onPress={ () => this.fetchData() }>
                              <Text style={ styles.btnText}>Login</Text>
                          </TouchableHighlight>
                      </View>
      
                      <View style={ styles.bottomContainer }>
                          <Text style={ styles.cenText }>Dont worry if you haven't an account yet . . </Text>
                          <Text
                          style={ styles.blueText}
                          onPress={ Actions.regisTer }
                          >Register Now</Text>
                      </View>
      
                  </ScrollView>
      
                  </View>
              );
          }
      }
      
      const styles = StyleSheet.create({
          container: {
              flex: 1,
          },
          logoContainer: {
              flex: .5,
              padding: 10,
              justifyContent: 'center',
              alignItems: 'center',
          },
          logoItem: {
              width: null,
              height: null,
              resizeMode: 'cover',
          },
          formContainer: {
              flex: 4,
              padding: 10,
          },
          inputelm: {
              marginBottom: 10,
              backgroundColor: '#999',
              borderWidth: 0,
              fontSize: 20,
              color: '#FFF',
              fontFamily: 'AmaticSC-Bold',
          },
          loginButton: {
              borderRadius: 3,
              marginBottom: 20,
              marginTop: 20,
              paddingLeft: 10,
              paddingRight: 10,
              backgroundColor: '#2196f3',
              elevation: 4,
          },
          signupButton: {
              borderRadius: 3,
              marginBottom: 20,
              marginTop: 20,
              paddingLeft: 10,
              paddingRight: 10,
              backgroundColor: '#7cb342',
              elevation: 4,
          },
          btnText: {
              textAlign: 'center',
              color: '#FFF',
              fontSize: 30,
              lineHeight: 40,
          },
          blueText: {
              textAlign: 'center',
              color: '#2196f3',
              fontSize: 20,
              lineHeight: 40,
          },
          bottomContainer: {
              flex: 1,
              padding: 10,
          },
          cenText: {
              textAlign: 'center',
              fontSize: 16,
          },
      });
      

      使用react-native-router-flux获取fetch的实际方法是什么?我是新来的,请帮助我。

3 个答案:

答案 0 :(得分:0)

您是否尝试过导入该库?

Import fetch from "fetch";

答案 1 :(得分:0)

您尚未导入fetch功能,请从node-fetch模块中导入

import fetch from 'node-fetch'

答案 2 :(得分:0)

嗯,它迟了几个月,但问题是你的fetchData方法无法访问这个,因为当你声明这样的方法时:

fetchData() {

}

引擎盖下的反应是以这种方式创造一种功能:

this.fetchData = function() {

}

当你使用function关键字声明一个函数时,{}之间的所有内容都有自己的&#34;这个&#34;并且您的方法将无法访问&#34;此&#34;组件上下文。

这就是你得到&#34; undefined&#34;的原因,因为你正在调用&#34; this.setState&#34;在fetch返回的promise中,所以错误不是fetch,而是这个。

要解决此问题,您可以通过以下方式定义方法:

fetchData = () => {

}

因为使用胖箭头定义的函数不会创建自己的范围,所以组件&#34; this&#34;将在您的方法中提供。