6
0
Fork 0

管理津贴结算

release
李静 2022-01-15 11:13:47 +08:00
parent 6fa2952467
commit 2884a85cbd
4 changed files with 231 additions and 0 deletions

View File

@ -0,0 +1,158 @@
<?php
namespace App\Console\Commands\Dealer;
use App\Enums\DealerManageSubsidyStatus;
use App\Models\DealerManageSubsidy;
use App\Models\DealerManageSubsidyLog;
use Illuminate\Console\Command;
use Illuminate\Support\Carbon;
use Illuminate\Support\Facades\Cache;
use Illuminate\Support\Facades\DB;
class ManageSubsidySettleCommand extends Command
{
/**
* The name and signature of the console command.
*
* @var string
*/
protected $signature = 'dealer:manage-subsidy-settle
{--force : 是否强制操作运行}';
/**
* The console command description.
*
* @var string
*/
protected $description = '管理津贴结算';
/**
* Execute the console command.
*
* @return int
*/
public function handle()
{
/*
|--------------------------------------------------------------------------
| 管理津贴结算
|--------------------------------------------------------------------------
|
| 管理津贴结算时间为每月的5号和20号。
|
| 5号结算上月20号0点到当月4号23点59分59秒的管理津贴
| 20号结算当月5号0点到19号23点59分59秒的管理津贴
|
*/
$tz = now();
if ($tz->day >= 20) {
$startAt = $tz->copy()->setDay(5)->startOfDay();
$endAt = $tz->copy()->setDay(19)->endOfDay();
} elseif ($tz->day >= 5) {
$startAt = $tz->copy()->subMonthNoOverflow()->set('day', 20)->startOfDay();
$endAt = $tz->copy()->set('day', 4)->endOfDay();
} else {
$startAt = $tz->copy()->subMonthNoOverflow()->setDay(5)->startOfDay();
$endAt = $startAt->copy()->subMonthNoOverflow()->setDay(19)->endOfDay();
}
$head = '【'.$startAt->format('Y/m/d').'-'.$endAt->format('Y/m/d').'】';
// 如果不是强制执行,则需检查是否已结算过
if (! $this->option('force') && Cache::has($this->cacheKey($startAt, $endAt))) {
return $this->warn("{$head}管理津贴已结算");
}
$this->info("{$head}------------[开始]管理津贴结算------------");
if ($this->option('force')) {
$this->info("{$head}正在删除旧数据...");
DealerManageSubsidy::where('start_at', $startAt)->where('end_at', $endAt)->delete();
$this->info("{$head}数据删除成功");
}
$this->info("{$head}数据写入中...");
$this->settle($startAt, $endAt);
$this->info("{$head}写入成功, 总耗时: ".$this->formatDuration($tz->diffInMilliseconds(now(), false)));
$this->info("{$head}------------[结束]管理津贴结算------------".PHP_EOL);
Cache::put($this->cacheKey($startAt, $endAt), 1, 24*3600*22);
return 0;
}
/**
* 管理津贴结算结算
*
* @param \Illuminate\Support\Carbon $startAt
* @param \Illuminate\Support\Carbon $endAt
* @return void
*/
protected function settle(Carbon $startAt, Carbon $endAt): void
{
$subsidies = DealerManageSubsidyLog::select('user_id', DB::raw('sum(total_amount) as total_amount'))
->whereBetween('order_completed_at', [$startAt, $endAt])
->groupBy('user_id')
->get();
$data = [];
$time = now()->toDateTimeString();
foreach ($subsidies as $key => $subsidy) {
if ($key > 0 && $key%500 === 0) {
DealerManageSubsidy::insert($data);
$data = [];
$time = now()->toDateTimeString();
}
$data[] = [
'user_id' => $subsidy->user_id,
'start_at' => $startAt,
'end_at' => $endAt,
'total_amount' => $subsidy->total_amount,
'status' => DealerManageSubsidyStatus::Pending,
'created_at' => $time,
'updated_at' => $time,
];
}
if (count($data) > 0) {
DealerManageSubsidy::insert($data);
}
}
/**
* 生成缓存的 key
*
* @param \Illuminate\Support\Carbon $startAt
* @param \Illuminate\Support\Carbon $endAt
* @return void
*/
protected function cacheKey(Carbon $startAt, Carbon $endAt)
{
$startAt->format('Ymd').'_'.$endAt->format('Ymd').'_dealer_manage_subsidy';
}
/**
* 格式化时间
*
* @param float $milliseconds
* @return string
*/
protected function formatDuration($milliseconds): string
{
if ($milliseconds < 0.01) {
return round($milliseconds * 1000) . 'μs';
} elseif ($milliseconds >= 1000) {
return round($milliseconds / 1000, 2) . 's';
}
return $milliseconds . 'ms';
}
}

View File

@ -0,0 +1,8 @@
<?php
namespace App\Enums;
enum DealerManageSubsidyStatus: int {
case Pending = 0;
case Completed = 5;
}

View File

@ -0,0 +1,25 @@
<?php
namespace App\Models;
use App\Enums\DealerManageSubsidyStatus;
use Illuminate\Database\Eloquent\Model;
class DealerManageSubsidy extends Model
{
protected $casts = [
'start_at' => 'datetime',
'end_at' => 'datetime',
'status' => DealerManageSubsidyStatus::class,
'completed_at' => 'datetime',
];
protected $fillable = [
'user_id',
'total_amount',
'start_at',
'end_at',
'status',
'completed_at',
];
}

View File

@ -0,0 +1,40 @@
<?php
use Illuminate\Database\Migrations\Migration;
use Illuminate\Database\Schema\Blueprint;
use Illuminate\Support\Facades\Schema;
class CreateDealerManageSubsidiesTable extends Migration
{
/**
* Run the migrations.
*
* @return void
*/
public function up()
{
Schema::create('dealer_manage_subsidies', function (Blueprint $table) {
$table->id();
$table->unsignedBigInteger('user_id');
$table->unsignedDecimal('total_amount', 10, 2)->comment('补贴总金额');
$table->timestamp('start_at')->comment('结算开始时间');
$table->timestamp('end_at')->comment('结算结束时间');
$table->tinyInteger('status')->default(0)->comment('状态: 0 待处理, 5 已付款');
$table->timestamp('completed_at')->nullable()->comment('完成时间');
$table->timestamps();
$table->unique(['user_id', 'start_at', 'end_at']);
$table->index(['start_at', 'end_at']);
});
}
/**
* Reverse the migrations.
*
* @return void
*/
public function down()
{
Schema::dropIfExists('dealer_manage_subsidies');
}
}