Swift上传Token至服务器失败:POST请求无响应问题排查
问题分析与解决方案
看起来你的代码有几个关键问题导致POST请求没正常工作,甚至数据传不到服务器,我来一步步帮你排查和修复:
1. 变量名与初始化问题
你代码里写的是JSONEncoder().encode(Tokeen),但你提到的全局变量是Token——这很可能是笔误!如果全局变量实际叫Token,那这里的Tokeen要么是未定义的变量,要么是未初始化的空值,直接导致编码后的数据为空。
首先确认全局变量的名字拼写完全一致,并且确保它已经被赋值(比如在viewDidLoad之前或者其他合适的地方设置Token = "dchksjdjfs-123anksndjd")。
2. 直接编码字符串的格式问题
即使Tokeen是有效的字符串,用JSONEncoder直接编码单个字符串,得到的是JSON格式的字符串(比如"dchksjdjfs-123anksndjd"),而大多数服务器期望的是一个JSON对象(比如{"token": "dchksjdjfs-123anksndjd"})。如果你的PHP后端是按对象来解析参数,就会找不到对应的值,看起来像是没收到数据。
3. 静默吞掉编码错误
你用了try?来包裹编码操作,这会把所有编码错误都静默忽略掉——比如变量为nil、类型不符合要求等,你根本不知道为什么编码失败。应该换成do-catch来捕获错误,方便调试。
修复后的完整代码
我把你的代码修改并优化了,加入了调试信息和正确的JSON对象格式:
// 先定义一个符合Codable的结构体,用来包装Token,生成服务器期望的JSON对象 struct TokenRequest: Codable { let token: String } override func viewDidLoad() { super.viewDidLoad() timer = Timer.scheduledTimer(timeInterval: 2, target: self, selector: #selector(counterFunc), userInfo: nil, repeats: true) // 确保全局Token在这里或者其他地方已经被赋值 // Token = "dchksjdjfs-123anksndjd" } @objc func counterFunc() { // 先检查全局Token是否有值 guard let globalToken = Token else { print("全局Token为空,无法发送请求") return } // 用结构体包装Token let requestBody = TokenRequest(token: globalToken) do { let uploadData = try JSONEncoder().encode(requestBody) // 把Data转换成字符串打印,更直观看到发送的内容 print("发送的请求体: \(String(data: uploadData, encoding: .utf8) ?? "无法解析的Data")") guard let url = URL(string: "https://...../....php") else { print("URL格式错误") return } var request = URLRequest(url: url) request.httpMethod = "POST" request.setValue("application/json", forHTTPHeaderField: "Content-Type") let task = URLSession.shared.uploadTask(with: request, from: uploadData) { data, response, error in if let error = error { print("请求错误: \(error.localizedDescription)") return } guard let httpResponse = response as? HTTPURLResponse else { print("未收到有效响应") return } print("服务器响应状态码: \(httpResponse.statusCode)") // 处理服务器返回的数据 if let data = data, let responseString = String(data: data, encoding: .utf8) { print("服务器返回内容: \(responseString)") } if (200...299).contains(httpResponse.statusCode) { print("请求成功") } else { print("服务器错误,状态码: \(httpResponse.statusCode)") } } task.resume() } catch { print("编码请求体失败: \(error.localizedDescription)") } }
服务器端PHP代码的注意事项
另外,PHP默认不会自动解析JSON格式的POST请求体,你需要在后端手动读取并解析:
// 读取JSON请求体 $jsonInput = file_get_contents('php://input'); // 解析成关联数组 $requestData = json_decode($jsonInput, true); // 获取token值 $token = $requestData['token'] ?? null; // 后续处理逻辑 if ($token) { echo json_encode(["status" => "success", "received_token" => $token]); } else { echo json_encode(["status" => "error", "message" => "未收到token"]); }
这样修改后,你应该能正常发送Token到服务器,并且看到详细的调试信息来定位问题。
内容的提问来源于stack exchange,提问作者Hybrid engineer
相关产品推荐
相关产品推荐

