为跨 Android、IOS 和 Web 的 expo 应用程序统一 localhost dev api 服务器访问?
Posted
技术标签:
【中文标题】为跨 Android、IOS 和 Web 的 expo 应用程序统一 localhost dev api 服务器访问?【英文标题】:Unifying localhost dev api server access for expo app across Android, IOS, and web? 【发布时间】:2020-08-17 13:01:36 【问题描述】:我正在为 Expo 上的几个学生设置一个简单的 React Native 学习应用程序,该应用程序还与学生正在学习编码的 API 服务器通信。
学生的 API 服务器通过node server.js
运行,并在学生机器上的localhost:3000
上提供服务。与世博无关。
我希望学生能够通过expo start --android
、expo start --ios
或expo start --web
中的任何一个在运行其 API 服务器的同一台机器上运行他们的应用程序。每个学生都在家中使用不同的家庭 wifi 网络,不一定知道 IP 地址或网络的来龙去脉。
当使用expo start --web
时,我们会遇到 CORS 异常,除非我们使用自定义的webpack.config.js
解决方法(首先通过https://docs.expo.io/guides/customizing-webpack/ 创建webpack.config.js
,然后将其放入webpack.config.js
):
const createExpoWebpackConfigAsync = require('@expo/webpack-config');
module.exports = async function(env, argv)
const config = await createExpoWebpackConfigAsync(env, argv);
if (config.mode === 'development')
config.devServer.proxy =
'/**':
target:
host: 'localhost',
protocol: 'http:',
port: 3000,
,
secure: false,
changeOrigin: true,
logLevel: 'info',
,
;
return config;
;
这很好,因为我们可以在不知道学生的 IP 地址的情况下对 ./end/point
进行 api 调用,并且 expo-cli 启动的 webpack devServer 有效地代理到学生的开发机器上的 http://localhost:3000/end/point
。
同时,对于 iOS 和 Android,我发现了这个 sn-p:
import Constants from "expo-constants";
const manifest = Constants;
const SERVER_URL = "http://"+manifest.debuggerHost.split(`:`).shift().concat(`:3000`)+"/";
然后在使用fetch()
时使用SERVER_URL
。
但是,我们缺少一个统一的解决方案,它与我们所处的环境(web、ios 或 android)无关。 webpack 代理仅在使用 expo web 客户端时才出现并工作(expo-cli 不会为 ios 或 android 启动 webpack),并且第二个选项 (A) 在 web 和 ( B) 无论如何都会触发 CORS 异常。
我怎样才能优雅地编写一段代码,或者以其他方式为学生设置项目,以便(A)他们不需要知道他们的开发机器的 IP 地址,或者这意味着什么,以及(B)它无论它们是在 web、android 还是 ios expo 客户端中都可以工作?
【问题讨论】:
【参考方案1】:不喜欢这个作为答案,希望知道的人更好地指出,但这是我最终使用的似乎有效的方法,至少在开发中:
// Some chatter that Contants.manifest needs to come from a different package?
import Constants from "expo-constants";
const manifest = Constants;
const SERVER_URL = (() =>
// TODO - put a "prod" api server somewhere
// Android / IOS - no CORS issue.
if (!!manifest.debuggerHost)
return "http://"+manifest.debuggerHost.split(`:`).shift().concat(`:3000/`);
// Expo Web client, making use of webpack.config.js (see original question) for devServer proxy.
else
return "./";
)();
...
fetch(SERVER_URL + 'some_endpoint/').then(...)
【讨论】:
以上是关于为跨 Android、IOS 和 Web 的 expo 应用程序统一 localhost dev api 服务器访问?的主要内容,如果未能解决你的问题,请参考以下文章
无法从 Flutter Web 读取 Firestore 中的数据(适用于 iOS 和 android)
如何在 React Native 中实现 Google 地图以在 Web、Android 和 iOS 上运行?