You can not select more than 25 topics Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
 
 

136 lines
4.9 KiB

<?php
namespace App\Console\Commands;
use DB;
use App\Models\Business;
use Illuminate\Console\Command;
use Illuminate\Support\Facades\Cache;
class CostCommand extends Command
{
public const USER_FEE = 400;
public const FILE_FEE = [
200 => 0,
400 => 1000,
800 => 2000,
];
protected $signature = 'cost:work';
protected $description = 'Run the cost worker';
public function __construct()
{
parent::__construct();
}
public function handle()
{
// infinte loop
while (true) {
// to baghali ha
$recorded_month = jdate($business->calculated_at)->format("Y-m-01");
$calculated_at = Cache::get('calculated_at');
if ($calculated_at === null) {
$business = Business::orderBy('calculated_at')->first()->load('users', 'cost');
$calculated_at = $business->calculated_at;
$until_now = jdate()->getMonth() > jdate($business->calculated_at)->getMonth()
? jdate($business->calculated_at)->toCarbon()->setTime("00", "00", "00")
: \Carbon\Carbon::now();
Cache::put('calculated_at', $until_now, 60);
}
// if calculated_at less than an hour stop
if (\Carbon\Carbon::now()->diffInMinutes($until_now) <= 60) {
$this->info('nothing to cost');
continue;
}
try {
DB::beginTransaction();
// business order by last_calculated_at take first
if (!isset($business)) {
$business = Business::orderBy('calculated_at')->first()->load('users', 'cost');
}
$user_fee = enum('business.fee.user');
// get business employee
$users_cost = $business->cost
->where('type', '=', 'users')
->where('fee', '=', $user_fee)
->where('month', '=', $recorded_month)
->where('amount', '=', $business->users->count())
->first();
if ($users_cost === null) {
$business->cost()->create([
'type' => 'users',
'month' => $recorded_month,
'amount' => $business->users->count(),
'fee' => $user_fee,
'duration' => $duration = $until_now->diffInSeconds($calculated_at), // from the created_at time of the newset fifth user
'additional' => $business->users->pluck('id')->toArray(),
]);
} else {
$users_cost->update([
'duration' => $duration = $until_now->diffInMinutes($calculated_at), // last calc - (current month - now else last calc - end of the past month),
'additional' => $business->users->pluck('id')->toArray(),
]);
}
$costs = $user_fee * $duration;
// do the math in php
if (intdiv($business->files_volume, 200) === 0) {
$pads = 0;
} else {
$pads = intdiv($business->files_volume, 200) - 1;
}
$file_fee = enum('business.fee.file');
$files = $business->cost
->where('type', '=', 'files')
->where('fee', '=', $file_fee)
->where('month', '=', $recorded_month)
->where('amount', '=', $business->files_volume)
->first();
if ($files === null) {
$business->cost()->create([
'type' => 'files',
'month' => $recorded_month,
'amount' => $pads,
'fee' => $file_fee,
'duration' => $duration = $until_now->diffInMinutes($calculated_at), // how to determine the file?,
]);
} else {
$files->update([
'duration' => $duration = $until_now->diffInMinutes($calculated_at), // last calc - (current month - now else last calc - end of the past month),,
]);
}
$costs += $file_fee * $duration;
// increment and decrement of wallet in php
// deduct costs from your business wallet
// make sure save the calculated_at
$business->update([
'wallet' => $business->wallet - $costs,
'calculated_at' => \Carbon\Carbon::now(),
]);
DB::commit();
} catch (Throwable $thr) {
DB::rollback();
throw $thr;
continue;
}
}
}
}