在 Laravel 9 中,基于 Spatie\QueryBuilder\QueryBuilder 来生成查询 SQL,同一字段可支持:partial、exact
1、参考:在 Laravel 9 中,在异步队列中复用 Spatie\QueryBuilder\QueryBuilder 来生成查询 SQL
/** * 查询生成器 * @param array $criteria * @return QueryBuilder */ public function QueryBuilder(array $criteria): QueryBuilder { return QueryBuilder::for(OrderShippingLog::class, new Request($criteria)) ->allowedFilters([ AllowedFilter::exact('shop_plat_id'), AllowedFilter::exact('shop_id'), AllowedFilter::exact('logistic_channel_id'), AllowedFilter::exact('logistic_company_id'), AllowedFilter::exact('operated_source'), AllowedFilter::exact('plat_order_no'), AllowedFilter::exact('logistic_freight_no'), AllowedFilter::exact('logistic_freight_transfer_no'), AllowedFilter::exact('logistic_freight_inner_no'), AllowedFilter::exact('logistic_virtual_number'), AllowedFilter::exact('shipping_type'), AllowedFilter::exact('shipping_status'), AllowedFilter::scope('shipping_at_gmt_start'), AllowedFilter::scope('shipping_at_gmt_end'), AllowedFilter::scope('operated_at_gmt_start'), AllowedFilter::scope('operated_at_gmt_end'), ]) ->with('shopPlat:id,title') ->with('shop:id,title') ->with('order.orderItemLogisticsFeatures') ->with('order.urgentType:id,title,color') ->with('logisticChannel:id,title') ->with('operatorUser:id,name,number') ->defaultSort('-id'); }
2、现在的实现方案,针对某一个字段,只能够使用一种过滤器,或者 partial ,或者 exact。参考:在 Yii 2.0 中,实现过滤器的请求参数形式。
{ "filter": { "plat_order_no": [ "GM20240202055938", "GM20240131081251" ] }, "sort": "-operated_at_gmt", "per_page": 20, "page": 1 }
{ "filter": { "plat_order_no": [ "like": [ "GM20240202055938", "GM20240131081251" ] ] }, "sort": "-operated_at_gmt", "per_page": 20, "page": 1 }
3、针对需要 单个模糊检索,多个精确检索 的字段,决定验证其类型为数组,然后判断数组元素的数量,如果大于 1 ,则精确检索,否则,模糊检索。最终实现如下。
$validator = Validator::make( $params, [ 'filter.plat_order_no' => 'array', 'filter.plat_order_no.*' => 'max:100', ], [ 'filter.plat_order_no.array' => '原订单的平台订单号必须是数组', 'filter.plat_order_no.*.max' => '原订单的平台订单号最大长度是100', ] ); if ($validator->stopOnFirstFailure()->fails()) { throw new BusinessException(BusinessException::MODULE_ORDER, $validator->getMessageBag()->first()); } return $validator;
// 单个模糊检索,多个精确检索:订单号、交易号、退货单号、退货快递单号、货运单号、商品SKU // 键为请求参数,值为 SQL 查询字段 $fields = [ 'plat_order_no' => 'plat_order_no', ]; foreach ($fields as $key => $field) { if (isset($criteria['filter'][$key])) { if (count($criteria['filter'][$key]) > 1) { // 多个精确检索 $allowedFilters[] = AllowedFilter::exact($field); } else { // 单个模糊检索 $allowedFilters[] = AllowedFilter::partial($field); } if ($key != $field) { $criteria['filter'][$field] = $criteria['filter'][$key]; unset($criteria['filter'][$key]); } } } $builder = QueryBuilder::for(ReturnOrder::class, new Request($criteria)) ->select('return_orders.*') ->allowedFilters($allowedFilters) ->defaultSort('-id');
近期评论