交换订阅计划出现错误 "Call to a member function asStripeCustomer() on null" [Laravel 收银台]

Swapping subscription plan gives error "Call to a member function asStripeCustomer() on null" [Laravel Cashier]

尝试交换订阅计划时,Laravel returns 此错误:

Call to a member function asStripeCustomer() on null

这是它在堆栈跟踪中引用的代码:

$tenant->subscription('main')->swap('plan_xxxxxxxxx');

我的代码与 Laravel 文档之间的唯一实现差异是我使用自己的 tenant 模型,而不是默认的 user 模型。我确保将 Billable 模型添加到我的租户模型中,并在订阅 table.

中将 user_id 更改为 tenant_id

完整的堆栈跟踪如下:

[2018-12-16 22:21:27] local.ERROR: Call to a member function asStripeCustomer() on null {"exception":"[object] (Symfony\Component\Debug\Exception\FatalThrowableError(code: 0): Call to a member function asStripeCustomer() on null at /var/www/html/project/vendor/laravel/cashier/src/Subscription.php:407)
[stacktrace]
#0 /var/www/html/project/vendor/laravel/cashier/src/Subscription.php(251): Laravel\Cashier\Subscription->asStripeSubscription()
#1 /var/www/html/project/app/Http/Controllers/BillingController.php(103): Laravel\Cashier\Subscription->swap('plan_xxxxxxxx...')
#2 [internal function]: App\Http\Controllers\BillingController->UpdatePlan(Object(Illuminate\Http\Request))
#3 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Controller.php(54): call_user_func_array(Array, Array)
#4 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/ControllerDispatcher.php(45): Illuminate\Routing\Controller->callAction('UpdatePlan', Array)
#5 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Route.php(212): Illuminate\Routing\ControllerDispatcher->dispatch(Object(Illuminate\Routing\Route), Object(App\Http\Controllers\BillingController), 'UpdatePlan')
#6 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Route.php(169): Illuminate\Routing\Route->runController()
#7 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Router.php(679): Illuminate\Routing\Route->run()
#8 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(30): Illuminate\Routing\Router->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#9 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Middleware/SubstituteBindings.php(41): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#10 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Routing\Middleware\SubstituteBindings->handle(Object(Illuminate\Http\Request), Object(Closure))
#11 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#12 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/VerifyCsrfToken.php(75): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#13 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Foundation\Http\Middleware\VerifyCsrfToken->handle(Object(Illuminate\Http\Request), Object(Closure))
#14 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#15 /var/www/html/project/vendor/laravel/framework/src/Illuminate/View/Middleware/ShareErrorsFromSession.php(49): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#16 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\View\Middleware\ShareErrorsFromSession->handle(Object(Illuminate\Http\Request), Object(Closure))
#17 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#18 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Session/Middleware/StartSession.php(63): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#19 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Session\Middleware\StartSession->handle(Object(Illuminate\Http\Request), Object(Closure))
#20 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#21 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Cookie/Middleware/AddQueuedCookiesToResponse.php(37): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#22 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Cookie\Middleware\AddQueuedCookiesToResponse->handle(Object(Illuminate\Http\Request), Object(Closure))
#23 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#24 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Cookie/Middleware/EncryptCookies.php(66): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#25 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Cookie\Middleware\EncryptCookies->handle(Object(Illuminate\Http\Request), Object(Closure))
#26 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#27 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(104): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#28 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Router.php(681): Illuminate\Pipeline\Pipeline->then(Object(Closure))
#29 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Router.php(656): Illuminate\Routing\Router->runRouteWithinStack(Object(Illuminate\Routing\Route), Object(Illuminate\Http\Request))
#30 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Router.php(622): Illuminate\Routing\Router->runRoute(Object(Illuminate\Http\Request), Object(Illuminate\Routing\Route))
#31 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Router.php(611): Illuminate\Routing\Router->dispatchToRoute(Object(Illuminate\Http\Request))
#32 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php(176): Illuminate\Routing\Router->dispatch(Object(Illuminate\Http\Request))
#33 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(30): Illuminate\Foundation\Http\Kernel->Illuminate\Foundation\Http\{closure}(Object(Illuminate\Http\Request))
#34 /var/www/html/project/vendor/fideloper/proxy/src/TrustProxies.php(57): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#35 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Fideloper\Proxy\TrustProxies->handle(Object(Illuminate\Http\Request), Object(Closure))
#36 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#37 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TransformsRequest.php(31): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#38 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Foundation\Http\Middleware\TransformsRequest->handle(Object(Illuminate\Http\Request), Object(Closure))
#39 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#40 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/TransformsRequest.php(31): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#41 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Foundation\Http\Middleware\TransformsRequest->handle(Object(Illuminate\Http\Request), Object(Closure))
#42 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#43 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/ValidatePostSize.php(27): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#44 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Foundation\Http\Middleware\ValidatePostSize->handle(Object(Illuminate\Http\Request), Object(Closure))
#45 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#46 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Middleware/CheckForMaintenanceMode.php(62): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#47 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(151): Illuminate\Foundation\Http\Middleware\CheckForMaintenanceMode->handle(Object(Illuminate\Http\Request), Object(Closure))
#48 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Routing/Pipeline.php(53): Illuminate\Pipeline\Pipeline->Illuminate\Pipeline\{closure}(Object(Illuminate\Http\Request))
#49 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Pipeline/Pipeline.php(104): Illuminate\Routing\Pipeline->Illuminate\Routing\{closure}(Object(Illuminate\Http\Request))
#50 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php(151): Illuminate\Pipeline\Pipeline->then(Object(Closure))
#51 /var/www/html/project/vendor/laravel/framework/src/Illuminate/Foundation/Http/Kernel.php(116): Illuminate\Foundation\Http\Kernel->sendRequestThroughRouter(Object(Illuminate\Http\Request))
#52 /var/www/html/project/public/index.php(55): Illuminate\Foundation\Http\Kernel->handle(Object(Illuminate\Http\Request))
#53 {main}

欢迎任何帮助。谢谢。

编辑

应要求,这里是Laravel出纳的相关方法

public function swap($plan)
{
    $subscription = $this->asStripeSubscription();

    $subscription->plan = $plan;

    $subscription->prorate = $this->prorate;

    $subscription->cancel_at_period_end = false;

    if (! is_null($this->billingCycleAnchor)) {
        $subscription->billing_cycle_anchor = $this->billingCycleAnchor;
    }

    // If no specific trial end date has been set, the default behavior should be
    // to maintain the current trial state, whether that is "active" or to run
    // the swap out with the exact number of days left on this current plan.
    if ($this->onTrial()) {
        $subscription->trial_end = $this->trial_ends_at->getTimestamp();
    } else {
        $subscription->trial_end = 'now';
    }

    // Again, if no explicit quantity was set, the default behaviors should be to
    // maintain the current quantity onto the new plan. This is a sensible one
    // that should be the expected behavior for most developers with Stripe.
    if ($this->quantity) {
        $subscription->quantity = $this->quantity;
    }

    $subscription->save();

    $this->user->invoice();

    $this->fill([
        'stripe_plan' => $plan,
        'ends_at' => null,
    ])->save();

    return $this;
}

public function asStripeSubscription()
{                         
    $subscriptions = $this->user->asStripeCustomer()->subscriptions;

    if (! $subscriptions) {
        throw new LogicException('The Stripe customer does not have any subscriptions.');
    }

    return $subscriptions->retrieve($this->stripe_id);
}

编辑 2

看起来 user 属性在 asStripeSubscription 函数中返回 null。

根据您发布的代码,$this->user 返回空值。您提到您将默认用户更改为租户,包括数据库字段。仅这些更改就会导致 Subscription 模型上的默认用户关系不再有效。

快速查看代码表明您还需要将 services.stripe.model 配置值设置为 Tenant 模型,或者在 [=] 中设置 STRIPE_MODEL 环境变量15=] 到您的 Tenant 模型。

这个解决方案对我有用: - 从这里修改 Sunscription.php 第 391 行;

$this->fill([

'stripe_plan' => $plan,

'ends_at' => null,

])->save();

为此:

$this->fill([

'name' => $plan,

'stripe_plan' => $plan,

'ends_at' => null,

])->save();

这应该会相应地更新您的计划。