You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

React Native发起AJAX请求提示Can't find variable: res错误如何解决

问题排查与修复方案

直接报错原因

你遇到的Can't find variable: res报错,是因为res仅作为fetch请求第一个回调的局部参数存在,仅在.then(res => res.json())的作用域内有效,你在render函数中直接调用res变量,该作用域下没有定义res,所以触发未定义变量报错。

其他隐含问题

除了上述报错外,你的代码还存在多处会触发后续报错的问题:

  • render函数中没有从this.state中取出你存储的请求状态,直接使用error、isLoaded也会触发变量未定义报错
  • 没有导入Text组件,渲染错误提示和加载态时会找不到Text变量
  • 遍历披萨列表时直接使用pizza.map,但pizza变量未定义,你请求返回的列表存在this.state.items中,应该遍历该变量
  • Expo环境下使用127.0.0.1访问本地服务会失败:移动设备/模拟器的127.0.0.1指向设备本身,而非你运行Node服务的电脑,需要替换为电脑的局域网IP

修复后完整代码

import React from 'react'
// 补充导入Text组件
import {
    ScrollView,
    StyleSheet,
    View,
    Text
} from 'react-native';
import Card from '../components/Card'
import CardList from '../components/CardList'

export default class HomeScreen extends React.Component {
    constructor(props) {
        super(props);
        this.state = {
            error: null,
            isLoaded: false,
            items: []
        };
    }

    static navigationOptions = {
        title: 'Menu',
    };
    componentDidMount() {
        // 这里的127.0.0.1替换为你电脑的局域网IP,格式如192.168.3.4
        fetch("http://你的电脑局域网IP:4001/menu")
            .then(res => res.json())
            .then(
                (result) => {
                    this.setState({
                        isLoaded: true,
                        items: result.items
                    });
                },
                (error) => {
                    this.setState({
                        isLoaded: true,
                        error
                    });
                }
            )
    }


    render() {
        // 先从state取出所有需要的变量
        const { error, isLoaded, items } = this.state;
        // 判断error而非res
        if (error) {
            return <View><Text>Error: {error.message}</Text></View>;
        } else if (!isLoaded) {
            return <View><Text>Loading...</Text></View>;
        } else {
            return (
                <View style={styles.container}>
                    <ScrollView style={styles.scrollViewContainer}>
                        <View >
                            <CardList title={'Pizzas'}>
                                {/* 遍历state里的items,注意和你接口返回的字段对应 */}
                                {items.map(pizza => (<Card style={styles.card} name={pizza.name} description={pizza.desc} />))}
                            </CardList>
                            <CardList title={'others'}>
                                <Card style={styles.card} />
                                <Card style={styles.card} />
                                <Card style={styles.card} />
                                <Card style={styles.card} />
                                <Card style={styles.card} />
                                <Card style={styles.card} />
                                <Card style={styles.card} />
                            </CardList>

                        </View>
                    </ScrollView>
                    <View style={styles.headerContainer}></View>
                </View>
            )
        }
    }
}

// 可根据自己的需求调整样式
const styles = StyleSheet.create({
    container: {
        flex: 1,
    },
    scrollViewContainer: {
        flex: 1,
    },
    card: {
        marginBottom: 12,
    },
    headerContainer: {
        height: 50,
    }
})

额外注意点

  • 确认你的接口返回的result.items中每个元素的字段是否正确,比如描述字段如果是desc就不要写decs避免取值为空
  • 本地Node服务要开启局域网访问权限,关闭电脑防火墙避免端口被拦截
  • 如果你的本地服务没有配置HTTPS,需要在Expo项目中配置允许HTTP请求权限,避免请求被系统拦截

内容的提问来源于stack exchange,提问作者Misa

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.10.10 07:00:05