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

Stripe支付报错Invalid source object,请求排查代码问题

解决你的Stripe支付InvalidRequest错误

嘿,我来帮你拆解这个错误并修复代码里的问题。首先看你遇到的错误:

错误信息: [16-May-2018 22:16:06 UTC] PHP致命错误:未捕获异常 'Stripe\Error\InvalidRequest',消息为 'Invalid source object: must be a dictionary or a non-empty string. 请查看API文档',位于/home/autravelservice/public_html/wp-content/plugins/ats/libraries/stripe-php-6.0.0/lib/ApiRequestor.php:120,来自API请求 'req_6uGybuHR3adjqW'

这个错误的核心是你传递给Stripe的支付凭证(token)格式不对,或者代码用了过时的API参数。结合你的代码,主要有这几个问题:


1. 过时的API参数:card 已被废弃,改用 source

你用的是Stripe PHP库v6.0.0,这个版本里创建Customer的card参数已经被淘汰了,官方要求用source来传递支付token。继续用card会导致Stripe无法正确解析你传入的凭证,直接触发InvalidRequest错误。

2. 没做$token的有效性校验

你直接拿$payment_details['token']来用,但没检查这个值是不是存在、是不是非空字符串。如果前端没传对token,或者token是空的,Stripe肯定会报错。

3. 冗余的foreach循环逻辑

你在foreach里只处理第一个申请人($i++ == 0),完全没必要写循环,直接取第一个申请人的数据就行,避免代码啰嗦。

4. shuffle的使用错误

你写了$counter= shuffle($counter);,但shuffle是直接修改原数组的,不需要赋值;而且直接把数组拼到orderid里会输出Array字样,得把数组转成字符串。


修复后的完整代码

// Set your secret key: remember to change this to your live secret key in production
\Stripe\Stripe::setApiKey($sk);

// 先校验支付token是否有效
$token = isset($payment_details['token']) ? trim($payment_details['token']) : '';
if (empty($token)) {
    die('Invalid payment token received. Please try again.');
}

// 获取第一个申请人的信息(去掉冗余的foreach)
$applicants = get_field('applicant', $post_id);
if (empty($applicants)) {
    die('No applicant information found.');
}
$applicant = $applicants[0];
$applicant_details = $applicant['applicant_details'];
$contact_details = $applicant['contact_details'];
$name_first = $applicant_details['first_name'];
$name_last = $applicant_details['last_name'];
$email = $contact_details['email'];

$user_info = [
    "First Name" => $name_first,
    "Last Name" => $name_last
];

try {
    // 创建Customer:用source替代废弃的card参数
    $customer = \Stripe\Customer::create([
        "email" => $email,
        "source" => $token,
        "metadata" => $user_info
    ]);

    // 发起支付请求
    $charge = \Stripe\Charge::create([
        "customer" => $customer->id,
        "amount" => $pay_amount,
        "currency" => "usd",
        "description" => "Australian Travel Service"
    ]);

    if ($charge->status === 'succeeded') {
        $counter = range(1, 5);
        shuffle($counter); // 直接修改原数组,不需要赋值
        $orderid = 'AUS-CU-' . date('Ymd') . $post_id . implode('', $counter); // 把数组转成字符串

        echo '<input type="hidden" name="orderid" id="app_order_id" value="'.$orderid.'">';
        echo '<input type="hidden" id="applicant_count" value="'.$applicant_count.'">';
        echo '<input type="hidden" id="processing_type" value="'.$processing_fee_type[0].'">';
        echo '<input type="hidden" id="order_total" value="'.$pay_amount.'">';
        
        appFormAdminMail($post_id, $orderid);
        
        acf_form([
            'id' => 'survey-form',
            'post_id' => $post_id,
            'field_groups' => [158],
            'return' => './survey-thank-you/?record=%post_id%',
            'submit_value' => 'SUBMIT SURVEY',
            'html_submit_button' => '<button type="submit" class="acf-btn red-btn rounded-btn">%s</button>'
        ]);
    } else {
        echo 'Payment failed: Charge was not successful.';
    }
} catch (\Stripe\Error\InvalidRequest $e) {
    // 捕获Stripe的请求错误,给用户友好提示
    echo 'Payment error: ' . $e->getMessage();
} catch (\Exception $e) {
    // 捕获其他所有异常
    echo 'Unexpected error occurred: ' . $e->getMessage();
}

额外提醒

  • 一定要确保前端通过Stripe Checkout/Elements生成的token是有效的(格式类似tok_xxxxxx),如果前端没正确传递,后端肯定会报错。
  • 把所有Stripe API调用放到try-catch块里,这样可以优雅处理错误,而不是直接抛出致命错误让用户看到一堆代码路径。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.28 04:16:44