React Native中使用fetch API提交扫码数据到SQL Server失败问题
问题排查与修复方案
你的代码无法写入数据库是以下几个问题叠加导致的,逐个修复即可:
前端(scanner.js)存在的问题
- fetch配置字段拼写错误:你写的是单数
header,fetch API识别请求头的字段是复数headers,直接导致设置的Content-Type完全不生效,服务端无法解析请求体。 - 请求地址错误:iOS环境下的
localhost指向的是iOS设备/模拟器自身,不是你运行PHP服务的开发机,请求根本没发到后端接口上。- 模拟器调试:把
localhost换成你开发机的局域网IP(比如192.168.3.12,在电脑网络设置中可查询) - 真机调试:保证手机和开发机连接同一个WiFi,同样使用开发机的局域网IP,同时需要在React Native项目的
Info.plist中添加ATS配置,允许HTTP明文请求,否则iOS会直接拦截非HTTPS请求。
- 模拟器调试:把
- 无错误捕获逻辑:现有代码只处理了请求成功的分支,网络错误、服务端4xx/5xx报错全部被吞,无法定位失败原因。
- 请求参数不全:代码中生成的扫描时间
currentDate没有随请求提交,后端拿不到扫码时间字段。 - 存在冗余导入:开头导入了未使用的
Component、onMount、StatusBar、navigation,虽然不影响功能,但属于无效代码。
修复后的前端submit函数代码
const submit = async () => { try { const res = await fetch("http://你的开发机局域网IP/api/insert.php",{ method:"POST", headers:{ "Accept":"application/json", "Content-Type":"application/json", }, body:JSON.stringify({ userid: userid, scan_time: currentDate }), }); // 打印服务端返回内容,方便调试排查 const responseText = await res.text(); console.log("服务端返回:", responseText); if(res.ok){ console.log("提交成功"); // 可在此处添加提交成功后的逻辑,比如重置扫描状态、跳转页面 // setScanned(false); } else { console.error("提交失败,状态码:", res.status); } } catch (err) { console.error("请求出错:", err); } }
iOS ATS必加配置(否则HTTP请求被系统拦截)
打开项目ios目录下的Info.plist,在根<dict>标签内加入以下配置:
<key>NSAppTransportSecurity</key> <dict> <key>NSAllowsArbitraryLoads</key> <true/> </dict>
后端insert.php注意事项
- PHP默认不会自动解析
Content-Type: application/json格式的请求体,不能直接用$_POST['userid']取值,需要手动读取输入流,参考代码如下:
<?php // 读取json格式请求体 $raw = file_get_contents('php://input'); $data = json_decode($raw, true); // 参数校验 if (!isset($data['userid']) || empty($data['userid'])) { http_response_code(400); echo "缺少userid参数"; exit; } $userid = $data['userid']; $scanTime = $data['scan_time'] ?? date('Y-m-d H:i:s'); // 以下替换为你的SQL Server写入逻辑,注意使用预处理语句防SQL注入 try { $serverName = "你的SQL Server地址"; $connectionInfo = array( "Database"=>"你的数据库名", "UID"=>"数据库用户名", "PWD"=>"数据库密码" ); $conn = sqlsrv_connect($serverName, $connectionInfo); if(!$conn) { http_response_code(500); echo "数据库连接失败:" . print_r(sqlsrv_errors(), true); exit; } // 预处理写入 $sql = "INSERT INTO 你的扫码记录表 (userid, scan_time) VALUES (?, ?)"; $params = array($userid, $scanTime); $stmt = sqlsrv_query($conn, $sql, $params); if($stmt === false) { http_response_code(500); echo "写入失败:" . print_r(sqlsrv_errors(), true); exit; } echo "写入成功"; sqlsrv_free_stmt($stmt); sqlsrv_close($conn); } catch (Exception $e) { http_response_code(500); echo "服务端错误:" . $e->getMessage(); } ?>
- 确保PHP服务已经开启
sqlsrv、pdo_sqlsrv扩展,否则无法连接SQL Server数据库。 - 调试时先在电脑浏览器访问
http://localhost/api/insert.php,确认接口本身能正常返回,再用移动端调试。
内容的提问来源于stack exchange,提问作者d.chan
相关产品推荐
相关产品推荐

