每天定时执行命令,在命令中同步一张表中的某个字段值的汇总至另一张表中
1、现在场景如下,在一张表中,有一个付款方式的字段,现在有需要,将付款方式定时汇总至另一张表中。为了防止每次定时执行时,重复查询之前的记录,所以需要记录一个上次的执行时间。
2、决定先查询出所有的不重复的付款方式,如果存在上次的执行时间,则加入条件,记录的创建时间小于等于上次的执行时间。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 | /** * Execute the console command. * * @return mixed */ public function handle() { $startTime = time(); $this ->line( '同步付款方式到选项' ); $now = Carbon::now(); // 上一次的执行时间 // $lastTime = Carbon::now(); $builder = Model::query() ->select( 'payment_type' ) ->where( 'table.created_at_gmt' , '<' , $now ) ->distinct(); if (! empty ( $lastTime )) { $builder ->where( 'table.created_at_gmt' , '>=' , $now ); } $paymentTypes = $builder ->pluck( 'payment_type' )->filter()->unique()->toArray(); print_r( $paymentTypes ); exit ; $endTime = time(); Log::info( "同步付款方式到选项; time:" . Carbon::now( 'GMT+8' )->toDateTimeString() . ' 耗时:' . $endTime - $startTime . '秒' ); $this ->line( '同步完成' . ' 耗时:' . $endTime - $startTime . '秒' ); return Command::SUCCESS; } |
3、查看生成的 SQL
1 2 3 4 5 6 | select distinct `payment_type` from ` table ` where ` table `.`created_at_gmt` < '2024-09-12 02:56:29' |
4、打印出 $paymentTypes,结果符合预期。
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 | Array ( [1] => PP [2] => credit [3] => payssion [4] => 网上支付 [5] => 1 [6] => 21 [7] => paypal_cluster_rest [8] => asiabill [9] => nspayment_local [10] => worldpay [11] => paypal_rest [12] => srpay [13] => nspayment [14] => 1000 [15] => worldpay_googlepay ) |
5、先尝试设置当前时间为 6 个月前,最终代码实现如下
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 | private string $cachedLastTimeKey = 'table:sync-payment-type-to-option:last_time' ; /** * Execute the console command. * * @return mixed */ public function handle() { $startTime = time(); $this ->line( '同步付款方式到选项' ); $now = Carbon::now()->subMonths(3); $optionRepository = app(IOptionRepository:: class ); $title = 'payment_types' ; // 选项中的付款方式 $optionPaymentType = $optionRepository ->fetchBy([ 'title' => $title ]); // 上一次的执行时间 $lastTime = Cache::store( 'redis' )->get( $this ->cachedLastTimeKey); $builder = Model::query() ->select( 'payment_type' ) ->where( 'table.created_at_gmt' , '<' , $now ) ->distinct(); if (isset( $lastTime )) { $builder ->where( 'table.created_at_gmt' , '>=' , $lastTime ); } $paymentTypes = $builder ->pluck( 'payment_type' )->filter()->unique()->values()->all(); if (! empty ( $optionPaymentType )) { // 获取两个数组的并集 $optionPaymentTypes = array_values ( array_unique ( array_merge ( $optionPaymentType ->value, $paymentTypes ))); } else { $optionPaymentTypes = $paymentTypes ; } $optionRepository ->updateOrCreateOptionBy([ 'title' => $title ], [ 'value' => $optionPaymentTypes ]); Cache::store( 'redis' )->put( $this ->cachedLastTimeKey, $now ->toDateTimeString()); $endTime = time(); Log::info( "同步付款方式到选项; time:" . Carbon::now( 'GMT+8' )->toDateTimeString() . ' 耗时:' . $endTime - $startTime . '秒' ); $this ->line( '同步完成' . ' 耗时:' . $endTime - $startTime . '秒' ); return Command::SUCCESS; } |
第1次执行同步命令:
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | select * from `options` where `title` = 'payment_types' limit 1; select distinct `payment_type` from ` table ` where ` table `.`created_at_gmt` < '2024-03-12 05:59:02' ; select * from `options` where `title` = 'payment_types' limit 1; insert into `options` (`title`, `value`) values ( 'payment_type' , '[\"PP\",\"credit\",\"payssion\",\"\u7f51\u4e0a\u652f\u4ed8\",\"1\",\"21\",\"paypal_cluster_rest\",\"asiabill\",\"nspayment_local\",\"worldpay\",\"paypal_rest\",\"srpay\",\"nspayment\",\"1000\",\"worldpay_googlepay\"]' ); |
6、再尝试设置当前时间为 3 个月前,第2次执行同步命令,执行的 SQL 如下。符合预期。
1 | $now = Carbon::now()->subMonths(3); |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | select * from `options` where `title` = 'payment_types' limit 1; select distinct `payment_type` from ` table ` where ` table `.`created_at_gmt` < '2024-06-12 06:00:50' and ` table `.`created_at_gmt` >= '2024-03-12 05:59:02' ; select * from `options` where `title` = 'payment_types' limit 1; update `options` set `value` = '[\"PP\",\"credit\",\"payssion\",\"\u7f51\u4e0a\u652f\u4ed8\",\"1\",\"21\",\"paypal_cluster_rest\",\"asiabill\",\"nspayment_local\",\"worldpay\",\"paypal_rest\",\"srpay\",\"nspayment\",\"1000\",\"worldpay_googlepay\"]' where `id` = 75; |
6、再尝试设置当前时间为现在,第3次执行同步命令,执行的 SQL 如下。符合预期。如图1
1 | $now = Carbon::now(); |
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 | select * from `options` where `title` = 'payment_types' limit 1; select distinct `payment_type` from ` table ` where ` table `.`created_at_gmt` < '2024-09-12 06:04:35' and ` table `.`created_at_gmt` >= '2024-06-12 06:00:50' ; select * from `options` where `title` = 'payment_types' limit 1; update `options` set `value` = '[\"PP\",\"credit\",\"payssion\",\"\u7f51\u4e0a\u652f\u4ed8\",\"1\",\"21\",\"paypal_cluster_rest\",\"asiabill\",\"nspayment_local\",\"worldpay\",\"paypal_rest\",\"srpay\",\"nspayment\",\"1000\",\"worldpay_googlepay\",\"paypal\",\"stripe\"]' where `id` = 75; |
近期评论