Laravel Cashier例子之付费会员&分期付款&生成发票

1、在Stripe中创建收费计划

正所谓兵马未动,粮草先行,在正式编写业务逻辑代码之前,我们先要到Stripe个人中心创建订购计划。导航到https://dashboard.stripe.com/test/plans页面创建两个付费会员级别:Silver(银牌会员)和Gold(金牌会员):

注意页面左上角的TEST,我们目前是在Stripe的测试环境进行操作。

2、定义路由

创建好订购计划后,我们在routes.php中为业务逻辑定义好相关路由:

//用户个人主页
Route::get('profile','UserController@profile');
//用户会员级别
Route::get('service','UserController@service');
//付费会员页面
Route::get('subscription','UserController@subscription');
//处理付费逻辑
Route::post('subscribe','UserController@subscribe');
//升级到更高级别
Route::get('upgrade','UserController@upgrade');

3、付费会员实现

接下来自然而然就是到控制器UserController中编写业务逻辑代码,由于之前我们已经讲过如何实现登录认证,这里我们使用GitHub进行登录认证。认证完成后跳转到/profile页面,然后我们的业务逻辑由此开始。

用户中心

首先在profile页面会直接跳转到查看会员级别页面:

public function profile(Request $request)
{
    $user = $request->user();
    return redirect('service');
}

会员级别

然后在service页面我们编写控制器代码如下:

public function service(Request $request){
    $user = $request->user();

    if (!$user->subscribed()) {
        return redirect('subscription');
    }
    if($user->onPlan('silver')){
        $service = ['type'=>1,'name'=>'银牌会员'];
    }else{
        $service = ['type'=>2,'name'=>'金牌会员'];
    }
    return view('user.service',['service'=>$service]);
}
首先,我们从请求中取出认证用户实例,然后调用该实例上的subscribed方法判断用户是否是付费会员,如果不是的话跳转到付费页面,否则通过onPlan方法判断用户是银牌会员还是金牌会员,并渲染对应视图resources/views/user/service.blade.php:

你已经是{{$service['name']}}<br>
@if ($service['type'] == 1)
    <a href="/upgrade">升级为金牌会员</a>
@endif

购买付费会员

升级的事情我们先按下不表,先来看看购买付费会员的实现逻辑。我们在UserController中编写subscription对应的代码如下:

public function subscription(Request $request)
{
    $user = $request->user();
    if($user->subscribed()){
        return redirect('service');
    }
    return view('user.subscription');
}

该页面逻辑很简单,先判断是否已经是付费会员,是的话跳转到会员级别页面,否则才会渲染购买付费页面,接下来我们定义其对应视图文件resources/views/user/subscription.blade.php如下:

<form action="/subscribe" method="post" id="subscription-form">
    <span class="payment-errors"></span>
    {!! csrf_field() !!}
    <div>
        付费计划:
        <select name="plan">
            <option value="silver">银牌会员</option>
            <option value="gold">金牌会员</option>
        </select>
    </div>
    <div>
        信用卡号:
        <input type="text" name="number" id="number">
    </div>
    <div>
        过期时间:
        月份:<input type="text" name="exp_month" id="exp_month">
        年份:<input type="text" name="exp_year" id="exp_year">
    </div>

    <button type="submit">订购服务</button>
</form>
<script type="text/javascript" src="http://libs.baidu.com/jquery/1.9.1/jquery.min.js"></script>
<script type="text/javascript" src="https://js.stripe.com/v2/"></script>
<script>
    Stripe.setPublishableKey('{{config("services.stripe.key")}}');
    jQuery(function($) {
        $('#subscription-form').submit(function(event) {
            var form = $(this);
            form.find('button').prop('disabled', true);
            Stripe.card.createToken({
                number: $('#number').val(),
                exp_month: $('#exp_month').val(),
                exp_year: $('#exp_year').val()
            }, stripeResponseHandler);

            return false;
        });
    });

    var stripeResponseHandler = function(status, response) {
        var form = $('#subscription-form');

        if (response.error) {
            form.find('.payment-errors').text(response.error.message);
            form.find('button').prop('disabled', false);
        } else {
            var token = response.id;
            form.append($('<input type="hidden" name="stripeToken" />').val(token));
            form.get(0).submit();
        }
    };
</script>

该视图文件相对比较复杂,在该视图中我们要选择购买的会员级别,填写信用卡号,以及信用卡对应的过期时间。会员级别对应的值即为我们在Stripe中创建订购计划时对应的计划ID,至于信用卡号和过期时间是用来生成stripeToken的,这个stripeToken就是我们在调用create创建订购计划时要传入的值。Stripe还贴心的为我们提供了一系列可用的信用卡测试账号:

卡号 类型
4242424242424242 Visa
4012888888881881 Visa
4000056655665556 Visa (debit)
5555555555554444 MasterCard
5200828282828210 MasterCard (debit)
5105105105105100 MasterCard (prepaid)
378282246310005 American Express
371449635398431 American Express
6011111111111117 Discover
6011000990139424 Discover
30569309025904 Diners Club
38520000023237 Diners Club
3530111333300000 JCB
3566002020360505 JCB

至于过期时间嘛,只要大于当前时间就好了。可能在别处你还会看到需要输入CVC,这是生成stripeToken的可选参数,既然是可选,这里我们就不费那个事了。

这个页面在浏览器中看上去是这样的:

在点击“订购服务”之前,我们先来编写subscribe对应的代码:

public function subscribe(Request $request)
{
    $plan = $request->input('plan');
    $creditCardToken = $request->input('stripeToken');

    $user = $request->user();
    $user->subscription($plan)->create($creditCardToken);
    if($user->save()){
        return redirect('service');
    }else{
        return back()->withInput();
    }
}

可以看到我们调用:

$user->subscription($plan)->create($creditCardToken);
完成付费操作实现订购。

回到subscription视图页面点击“订购服务”,成功后页面跳转到之前的service页面,页面显示如下:

升级付费会员

最后我们来处理升级逻辑,编写upgrade对应业务逻辑代码如下:

public function upgrade(Request $request){
    $user = $request->user();
    if (!$user->subscribed()) {
        return redirect('subscription');
    }
    if($user->onPlan('gold')){
        exit('您已经是金牌会员了');
    }
    try{
        $user->subscription('gold')->swap();
    }catch(Exception $ex){
        exit('升级失败!');
    }
    return redirect('service');

}

通过

$user->subscription('gold')->swap();

即可实现升级操作。

回到service页面点击“升级到金牌会员”,成功后页面跳转回service页面并显示如下信息:

你已经是金牌会员

好了,至此我们已经完成了付费会员功能的一般逻辑。后续我们将讨论除信用卡外如何支持更多支付方式,比如银联、支付宝、微信支付等。

4、分期付款实现

走完上面的所有流程后,你会发现该实现逻辑和另外一个应用场景非常类似,就是分期付款,我们可以将商品/服务总价格+利息分成若干期,然后算出每月应还款额,然后在Stripe中创建对应分期付款计划。剩下的业务逻辑实现和付费会员并无二致,将会员级别换成商品规格或对应服务级别,剩下的支付&升级参考其实现即可,这里不再赘述。

一次性付清

对于有时候我们需要对分期付款的物品进行一次性付清,比如剩余总额为100美元,可以通过调用如下方法实现:

$user->charge(100);

该方法有返回值,支付成功返回true,否则返回false。

生成发票并下载

支付完成后,如果想要获取发票信息,Laravel Cashier也对此提供了支持。

首先通过调用用户实例上的invoices方法获取该用户所有有效发票信息:

$invoices = $user()->invoices();

然后在视图中将获取到的$invoices循环显示出来:

<table>
    @foreach ($invoices as $invoice)
    <tr>
        <td>{{ $invoice->dateString() }}</td>
        <td>{{ $invoice->dollars() }}</td>
        <td><a href="/order/invoice/{{ $invoice->id }}">下载发票</a></td>
    </tr>
    @endforeach
</table>

我们将这段代码放到上述resources/views/user/service.blade.php之后:

你已经是{{$service['name']}}<br>
@if ($service['type'] == 1)
 <a href="/upgrade">升级为金牌会员</a>
@endif
<div>
    发票信息:
    <table>
         @foreach ($invoices as $invoice)
         <tr>
             <td>{{ $invoice->dateString() }}</td>
             <td>{{ $invoice->dollars() }}</td>
             <td><a href="/user/invoice/{{ $invoice->id }}">下载发票</a></td>
         </tr>
         @endforeach
    </table>
</div>

这样在我们付费成功后,页面显示如下:

最后我们在路由中对点击“下载发票”进行处理:

Route::get('user/invoice/{invoice}', function ($invoiceId) {
    return Auth::user()->downloadInvoice($invoiceId, [
        'vendor'  => 'Laravel Academy',
        'product' => 'Gold Member',
    ]);
});
该代码会将对应发票生成PDF文档并下载。我们点击上述的“下载发票按钮”,下载的PDF发票截图如下:

时间: 2024-09-18 22:32:54

Laravel Cashier例子之付费会员&分期付款&生成发票的相关文章

Laravel Cashier安装配置篇教程详解

0.开始之前 在开始之前我们先理清几个概念. Stripe是一个为个人和公司提供在线支付解决方案的工具,支持Web和移动App. Laravel Cashier为Stripe提供了相应接口以便在Laravel中实现订购支付功能,从而避免让我们编写重复的样板化的代码,真正专注于业务逻辑处理,提高编程效率. 那么,Laravel Cashier到底是怎样的一把利器,下面让我们一一揭晓. 1.安装配置 使用composer安装 我们使用Composer安装Laravel Cashier依赖包,首先将如

微信将推会员制度 付费会员朋可以装修朋友圈

  微博大V@龚文祥 在微博上爆料,微信方面将推出会员制度,目前部分腾讯内部员工已经在内测. 据悉,微信正在内测的会员制度,会分季度与年度会员.用户成为会员之后好友上线可以突破五千,同时付费会员将新增朋友圈装修功能.目前,部分腾讯游戏员工已经参与内测,具体微信会员将如何收费以及具体会有哪些会员功能还暂时不清楚.

135编辑器怎么免费领取付费会员

  如果你要制作微信推广,或者是微信公众号管理人员,经常这款"135编辑器"就不要错过免费领取135编辑器付费会员了.1万多人已免费领取付费会员,你爱在等是什么?跟安下小编一起看看怎么领取吧! 135编辑器怎么免费领取付费会员 135编辑器免费领取付费会员先登录"135编辑器账号",你还没有注册135账号?赶紧注册一个! 请参考教程:135编辑器怎么注册; 第一步:绑定手机号 填写信息 第二步:绑定微信 或者 绑定QQ账号 第三步:免费领取"135编辑器付

阿里巴巴:付费会员激增18万

本报记者 钟慧丽 昨天,阿里巴巴网络有限公司(1688.HK)发布2009年第四季度及全年业绩报告.在宏观经济波动背景下,阿里巴巴延续增长势头,全球注册用户超过 4770万.其中,国内及国际两个交易市场付费会员人数取得增长,截至2009年12月31日,公司共有615212名付费会员, 同比增长42.4%,这意味着,2009年付费会员激增18万余人. 由于付费会员人数的增加,阿里巴巴2009年总营业收入同比增长29%,达到38.75亿元.净利润10.13亿元,同比减少12.3%,主要由于公司为未来

eeee-用Gate仿真自带的例子时,.root文件生成问题。

问题描述 用Gate仿真自带的例子时,.root文件生成问题. 用Gate仿真自带的例子时,.root文件生成问题. 用Gate仿真自带的例子时,.root文件生成问题. 用Gate仿真自带的例子时,.root文件生成问题. 用Gate仿真自带的例子时,.root文件生成问题.用Gate仿真自带的例子时,.root文件生成问题.

root gate ct c-用Gate仿真自带的例子时,.root文件生成问题。

问题描述 用Gate仿真自带的例子时,.root文件生成问题. 大家好, 我是在用gate做一个CT的仿真,仿真一个Gate自带的例子,里面有一堆.mac文件,还有一个.cpp文件,现在是已经用它介绍的命令成功编译了该.cpp文件,生成了可执行文件,但是在执行该可执行文件的时候,提示缺少.root文件,请问如何生成.root文件阿? 解决方案 http://www.docin.com/p-790615680.html

阿里巴巴信用贷款由只面向付费会员开放,开放到向普通会员开放

不需要提供任何担保.抵押,最快一天就能拿到贷款,并且可以随用随借.随借随还.记者昨天获悉,阿里巴巴信用贷款近日由此前只面向付费会员开放,转为面向江浙沪三地所有普通会员开放. 昨天,一则"银行颤抖吧"的微博走红,内容是阿里巴巴集团能够让小企业不用提供任何担保.抵押就把钱贷走.而三年前,马云曾表示,面对小微企业贷款,如果银行不改变,阿里将改变银行.马云会颠覆银行业吗? 据了解,阿里主要为B2B(商业对商业)和B2C(商家对客户)平台即淘宝和天猫的客户提供订单贷款和信用贷款. "我

从网络电话到付费会员 互联网服务模式的困局?

互联网发展至今经历了由免费服务到付费服务的转变,相对的,互联网服务行业仍然处于快速发展时期,基于互联网技术的变革带动了整个行业的发展.到底是付费还是免费,哪种模式可以适应当今行业的发展? 从最初的付费小说阅读到付费视频会员,再到如今各式各样的付费o2o服务模式的探索,互联网服务貌似已经向付费化转变,可是网络电话依然以免费服务作为平 台 的附属功能来招揽客户,偏偏这种方式与传统服务商的利益所背离,其是归于监管还是要进行资质受理我们还不得而知,不过,最终的结局一定是有所指向的. 付费模式在摸索中前进

业内人说:从网络电话到付费会员,互联网服务模式下的困局如何面对?

互联网发展至今经历了由免费服务到付费服务的转变,相对的,互联网服务行业仍然处于快速发展时期,基于互联网技术的变革带动了整个行业的发展.到底是付费还是免费,哪种模式可以适应当今行业的发展? 从最初的付费小说阅读到付费视频会员,再到如今各式各样的付费o2o服务模式的探索,互联网服务貌似已经向付费化转变,可是网络电话依然以免费服务作为平台 的附属功能来招揽客户,偏偏这种方式与传统服务商的利益所背离,其是归于监管还是要进行资质受理我们还不得而知,不过,最终的结局一定是有所指向的. 付费模式在摸索中前进?