PHP调用API时凭证无效求助(Postman可正常请求)
GSTZen EWB API调用凭证无效问题排查(Postman正常但PHP报错)
问题描述
通过PHP代码POST调用GSTZen的EWB API时,返回「请求中提供的用户凭证无效」,但使用相同凭证在Postman中可成功生成电子运单(EWB)。
凭证获取代码
<?php session_start(); error_reporting(E_ALL); // 开启所有错误用于调试 // 数据库连接(示例使用PDO) // 从apiusers表获取API用户名和密码 try { $sql = 'SELECT username, password FROM apiusers WHERE BPD_ID = :BPD_ID'; $stmt = $pdo->prepare($sql); $stmt->bindParam(':BPD_ID', $BPD_ID); $stmt->execute(); $user = $stmt->fetch(PDO::FETCH_ASSOC); $apiUsername = $user['username']; $apiPassword = $user['password']; // 在控制台输出用户名和密码 echo "<script>console.log('Username: " . addslashes($apiUsername) . "');</script>"; echo "<script>console.log('Password: " . addslashes($apiPassword) . "');</script>"; } catch (Exception $e) { die('获取API用户数据失败: ' . $e->getMessage()); }
请求数据构建
// 构建postData数组 $postData = json_encode([ "supplyType" => "O", "subSupplyType" => "8", "subSupplyDesc" => "DC", ......... "vehicleType" => "R", "itemList" => $itemData ]); // 在页面输出请求数据 echo "<pre>"; print_r($postData); echo "</pre>"; echo "<pre>"; print_r($itemData); echo "</pre>";
完整请求JSON
{ "supplyType": "O", "subSupplyType": "8", "subSupplyDesc": "DELIVERY CHALLAN", "docType": "CHL", "docNo": "DC242501", "docDate": "01/08/2024", "fromGstin": "29AAFCC9980M1ZR", "fromTrdName": "welton", "fromAddr1": "2ND CROSS NO 59 19 A", "fromAddr2": "GROUND FLOOR OSBORNE ROAD", "fromPlace": "FRAZER TOWN", "fromPincode": 560090, "actFromStateCode": 29, "fromStateCode": 29, "toGstin": "29AEKPV7203E1Z9", "toTrdName": "sthuthya", "toAddr1": "Shree Nilaya", "toAddr2": "Dasarahosahalli", "toPlace": "Beml Nagar", "toPincode": 560090, "actToStateCode": 29, "toStateCode": 29, "transactionType": 1, "otherValue": "0", "totalValue": 40000, "cgstValue": 0, "sgstValue": 0, "igstValue": 0, "cessValue": 0, "cessNonAdvolValue": 0, "totInvValue": 47200, "transporterId": "", "transporterName": "", "transDocNo": "", "transMode": "1", "transDistance": "100", "transDocDate": "", "vehicleNo": "PVC1234", "vehicleType": "R", "itemList": [ { "productName": "MS & SCRAP", "productDesc": "SCRAP", "hsnCode": 7402, "quantity": 4, "qtyUnit": "BOX", "cgstRate": 9, "sgstRate": 9, "igstRate": 0, "cessRate": 0, "cessNonadvol": 0, "taxableAmount": 40000 } ] }
cURL请求代码
$url = 'https://my.gstzen.in/~gstzen/a/ewbapi/generate/?username=' . rawurlencode($apiUsername) . '&password=' . rawurlencode($apiPassword); $apiKey = 'de3a3a01-273a-4a81-8b75-13fe37f14d'; $gstin = '29AAFCC9980M1'; // GSTIN值 /* $gstin = $mainData['COMP_GSTIN']; // GSTIN值 */ // 初始化cURL会话 $ch = curl_init($url); // 设置cURL选项 curl_setopt($ch, CURLOPT_SSL_VERIFYPEER, false); curl_setopt($ch, CURLOPT_SSL_VERIFYHOST, false); curl_setopt($ch, CURLOPT_RETURNTRANSFER, true); curl_setopt($ch, CURLOPT_HTTPHEADER, [ 'Content-Type: application/json', 'Authorization: API key ' . $apiKey, 'gstin: ' . $gstin ]); curl_setopt($ch, CURLOPT_POST, true); curl_setopt($ch, CURLOPT_POSTFIELDS, $postData); // 执行cURL请求并获取响应 $response = curl_exec($ch); if (curl_errno($ch)) { echo 'cURL错误: ' . curl_error($ch); exit; } curl_close($ch); // 解码JSON响应 $responseData = json_decode($response, true); if (json_last_error() !== JSON_ERROR_NONE) { die('JSON解码错误: ' . json_last_error_msg()); } // 调试API响应 echo "<script>console.log('API Response: " . addslashes(json_encode($responseData)) . "');</script>"; // 检查认证错误 if (isset($responseData['status']) && $responseData['status'] === 'error' && isset($responseData['message'])) { die('API错误: ' . $responseData['message']); } // 插入数据到数据库 $pdo->commit(); echo '数据插入成功'; } catch (Exception $e) { $pdo->rollBack(); echo '数据插入失败: ' . $e->getMessage(); } ?>
PHP请求的API响应
{"status":0,"message":"请求中提供的用户凭证无效。"}
Postman成功响应JSON
{ "status": 1, "uuid": "cc1e4f5d-43ca-4373-9fd4-6e059fb6716a", "message": "EWB Generated", "alert": "", "validUpto": "06/08/2024 11:59:00 PM", "ewayBillNo": 171010516152, "ewayBillDate": "05/08/2024 07:16:00 PM", "EWayBillPdfUrl": "/~fnsjdjszvw/a/eway-bill/cc1e4f5d-43ca-4373-9fd4-6e059fb6716a/ewb/.pdf/", "EWayBillQrCodeUrl": "/~fnsjdjszvw/a/ewaybill/cc1e4f5d-43ca-4373-9fd4-6e059fb6716a/qr-code/", "Distance": "100" }
排查建议
- 核对URL参数编码:对比PHP生成的URL和Postman的请求URL,确认
username和password的编码结果完全一致,重点检查特殊字符(如空格、&、%)的处理。 - 验证GSTIN完整性:代码中
$gstin值为29AAFCC9980M1,但请求JSON中的fromGstin是29AAFCC9980M1ZR,检查Postman使用的GSTIN是否完整,是否因PHP中GSTIN缺失后缀导致验证失败。 - 检查请求头一致性:对比Postman和PHP的请求头,重点确认
Authorization格式(API key是否完整,原代码中API key疑似少一位)、gstin字段的大小写和值是否匹配。 - 输出完整请求日志:在PHP中添加代码输出完整请求信息,和Postman逐字段对比:
// 在curl_exec前添加 echo "<pre>请求URL: $url</pre>"; echo "<pre>请求头: " . print_r(curl_getinfo($ch, CURLINFO_HEADER_OUT), true) . "</pre>"; - 清理凭证前后空格:数据库取出的凭证可能包含隐形空格,使用
trim()处理后再传入URL:$apiUsername = trim($user['username']); $apiPassword = trim($user['password']); - 测试SSL验证设置:尝试开启SSL验证(注释掉
CURLOPT_SSL_VERIFYPEER和CURLOPT_SSL_VERIFYHOST的设置),部分API会因SSL验证关闭拒绝请求。
内容的提问来源于stack exchange,提问作者Syed Mujahid
相关产品推荐
相关产品推荐

