1.当购物车提交时,POST传来一个对象{address:2,item:{ {ksu_id:2,count:2},{ksu_id:2,count:2}, }

验证方法:

public function rules()
{
return [
// 判断用户提交的地址 ID 是否存在于数据库并且属于当前用户
// 后面这个条件非常重要,否则恶意用户可以用不同的地址 ID 不断提交订单来遍历出平台所有用户的收货地址
'address_id' => [
'required',
Rule::exists('user_addresses', 'id')->where('user_id', $this->user()->id),
],
'items' => ['required', 'array'],
'items.*.sku_id' => [ // 检查 items 数组下每一个子数组的 sku_id 参数
'required',
function ($attribute, $value, $fail) {
if (!$sku = ProductSku::find($value)) {
return $fail('该商品不存在');
}
if (!$sku->product->on_sale) {
return $fail('该商品未上架');
}
if ($sku->stock === 0) {
return $fail('该商品已售完');
}
// 获取当前索引
preg_match('/items\.(\d+)\.sku_id/', $attribute, $m);
$index = $m[1];
// 根据索引找到用户所提交的购买数量
$amount = $this->input('items')[$index]['amount'];
if ($amount > 0 && $amount > $sku->stock) {
return $fail('该商品库存不足');
}
},
],
'items.*.amount' => ['required', 'integer', 'min:1'],
];
}
}
在检查 sku_id 时我们依然判断了对应 SKU 是否存在、商品是否上架、库存是否充足,因为用户在把商品加入购物车,再到下单时商品的各个状态都可能发生变化。 在检查库存时,我们需要获取用户想要购买的该 SKU 数量,我们可以通过匿名函数的第一个参数 $attribute 来获取当前 SKU 所在的数组索引,比如第一个 SKU 的 $attribute 就是 items.0.sku_id,所以我们采用正则的方式将这个 0 提取出来,$this->input('items')[0]['amount'] 就是用户想购买的数量。 接下来我们来写具体的创建订单逻辑: app/Http/Controllers/OrdersController.php <?php namespace App\Http\Controllers; use App\Http\Requests\OrderRequest;
use App\Models\ProductSku;
use App\Models\UserAddress;
use App\Models\Order;
use Carbon\Carbon; class OrdersController extends Controller
{
public function store(OrderRequest $request)
{
$user = $request->user();
// 开启一个数据库事务
$order = \DB::transaction(function () use ($user, $request) {
$address = UserAddress::find($request->input('address_id'));
// 更新此地址的最后使用时间
$address->update(['last_used_at' => Carbon::now()]);
// 创建一个订单
$order = new Order([
'address' => [ // 将地址信息放入订单中
'address' => $address->full_address,
'zip' => $address->zip,
'contact_name' => $address->contact_name,
'contact_phone' => $address->contact_phone,
],
'remark' => $request->input('remark'),
'total_amount' => 0,
]);
// 订单关联到当前用户
$order->user()->associate($user);
// 写入数据库
$order->save(); $totalAmount = 0;
$items = $request->input('items');
// 遍历用户提交的 SKU
foreach ($items as $data) {
$sku = ProductSku::find($data['sku_id']);
// 创建一个 OrderItem 并直接与当前订单关联
$item = $order->items()->make([
'amount' => $data['amount'],
'price' => $sku->price,
]);
$item->product()->associate($sku->product_id);
$item->productSku()->associate($sku);
$item->save();
$totalAmount += $sku->price * $data['amount'];
} // 更新订单总金额
$order->update(['total_amount' => $totalAmount]); // 将下单的商品从购物车中移除
$skuIds = collect($items)->pluck('sku_id');
$user->cartItems()->whereIn('product_sku_id', $skuIds)->delete(); return $order;
}); return $order;
}

  

Laravel验证问题记录的更多相关文章

  1. Laravel技巧之记录多日志

    相信每个小伙伴在使用laravel的时候都会记录日志.查看日志.那么问题来了,比如我在对接zabbix接口的时候,使用 Log::info() 会让日志全部记录在 storage/logs/larav ...

  2. 关于html以及js相关格式验证的记录

    关于html中禁止输入的一些写法主要是实现实时监听值:      下面的例子实现的事只运行输入数字切小数位数不能超过两位的示例.      1. onkeyup事件是在输的时候在键盘松开的时候进行触发 ...

  3. Linux下部署SSH登录时的二次身份验证环境记录(利用Google Authenticator)

    一般来说,使用ssh远程登录服务器,只需要输入账号和密码,显然这种方式不是很安全.为了安全着想,可以使用GoogleAuthenticator(谷歌身份验证器),以便在账号和密码之间再增加一个验证码, ...

  4. laravel验证规则

    就拿laravel的登入验证来举例: 1.进入login控制器, use AuthenticatesUsers;从这里点进去找到验证规则 //验证protected function validate ...

  5. laravel 验证机制validation

    Laravel 中 validation 验证 返回中文提示 全局设置 自己建一个zn文件夹,然后把en的4个文件全复制过去,修改validation.php的代码为下面的内容,然后在app.php修 ...

  6. laravel开发扩展记录

    whoops 错误提示扩展 whoops 是一个非常优秀的 PHP Debug 扩展,它能够使你在开发中快速定位出错的位置.laravel默认安装.区域 1 -- 是错误异常的简介区域 2 -- 是错 ...

  7. Laravel 验证 教程

    英文源文章: https://www.techiediaries.com/laravel-authentication-tutorial/ 在上一篇教程中,我们已经接触过Laravel,同时介绍了最新 ...

  8. Shiro权限验证代码记录,正确找到shiro框架在什么地方做了权限识别

    权限验证方式的验证代码: org.apache.shiro.web.servlet.AdviceFilter这个类是所有shiro框架提供的默认权限验证实例类的父类 验证代码: public void ...

  9. Yii 中比较常用的rules验证规则记录

    查看代码   打印 01 return array( 02   03     //必须填写 04     array('email, username, password,agree,verifyPa ...

随机推荐

  1. vue2.0 + element-ui2实现分页

    当我们向服务端请求大量数据的时候,并要在页面展示出来,怎么办?这个时候一定会用到分页. 本次所使用的是vue2.0+element-ui2.12实现一个分页功能,element-ui这个组件特别丰富, ...

  2. HTML的多媒体属性

    ㈠什么是多媒体? 多媒体来自多种不同的格式.它可以是听到或看到的任何内容,文字.图片.音乐.音效.录音.电影.动画等等. Web 上的多媒体指的是音效.音乐.视频和动画. 确定媒体类型的最常用的方法是 ...

  3. docker命令集锦

    sudo docker image ls 查看有哪些image镜像sudo docker run hello 运行image 删除全部containerdocker rm $(docker conta ...

  4. Chrome 神器,神奇的技巧

    谷歌开发者工具是前端日常不可缺少的神奇,写布局,找 bug,优化加载速度统统靠他.但是你真的了解他么?这篇文章是专门介绍谷歌浏览器各种好用小技巧的.不是什么长篇大论,旨在提高你的开发效率,早日完工回家 ...

  5. 2018-2019-2 20175215 实验三《敏捷开发与XP实践》实验报告

    一.实验内容与步骤 1.安装.使用alibaba 插件规范代码 在IDEA的setting中找到plugins并搜索alibaba,点击install进行安装 重启IDEA后,在代码中右击点击编码规约 ...

  6. LeetCode 216. 组合总和 III(Combination Sum III)

    题目描述 找出所有相加之和为 n 的 k 个数的组合.组合中只允许含有 1 - 9 的正整数,并且每种组合中不存在重复的数字. 说明: 所有数字都是正整数. 解集不能包含重复的组合. 示例 1: 输入 ...

  7. 一、Git的一些命令操作----创建版本库、增加文件到Git库、时光机穿梭、远程仓库

    具体详细教程请链接:http://www.liaoxuefeng.com/wiki/0013739516305929606dd18361248578c67b8067c8c017b000 我这里只是记录 ...

  8. 【java测试】Junit、Mock+代码覆盖率

    原文见此处 单元测试是编写测试代码,用来检测特定的.明确的.细颗粒的功能.单元测试并不一定保证程序功能是正确的,更不保证整体业务是准备的. 单元测试不仅仅用来保证当前代码的正确性,更重要的是用来保证代 ...

  9. hibernate ifnull

    mysql中sql语句的ifnull函数,在hibernate的hql中可用coalesce代替. 例: mysql的sql:select ifnull(max(sort),0) from table ...

  10. android data binding jetpack IV 绑定一个方法另一种写法和参数传递

    android data binding jetpack VIII BindingConversion android data binding jetpack VII @BindingAdapter ...