154 lines
5.2 KiB
PHP
154 lines
5.2 KiB
PHP
<?php
|
|
|
|
namespace App\Http\Controllers\Bo;
|
|
|
|
use App\Http\Controllers\Controller;
|
|
use App\Http\Resources\InstantWinResource;
|
|
use App\Models\InstantWin;
|
|
use App\Models\Prize;
|
|
use App\Models\Settings;
|
|
use Illuminate\Http\JsonResponse;
|
|
use Illuminate\Support\Carbon;
|
|
use Illuminate\Support\Facades\DB;
|
|
|
|
class InstantWinController extends Controller
|
|
{
|
|
/**
|
|
* View Instant gagnants page
|
|
*
|
|
* @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory
|
|
*/
|
|
public function index()
|
|
{
|
|
// * Can generate only if there are none already generate and prizes on database
|
|
$canGenerate = InstantWin::count() ? false : (Prize::sum('quantity') ? true : false);
|
|
|
|
$instantWin = InstantWin::orderBy('appear_date')->get();
|
|
|
|
return view('bo.instant-win.index', [
|
|
'can_generate' => $canGenerate,
|
|
'instant_win' => new InstantWinResource($instantWin)
|
|
]);
|
|
}
|
|
|
|
/**
|
|
* Generate Instant wins
|
|
*
|
|
* @return \Illuminate\Http\JsonResponse
|
|
*/
|
|
public function instantWinGenerate(): JsonResponse
|
|
{
|
|
/** @var \App\Models\Settings $settings */
|
|
$settings = app(Settings::class);
|
|
|
|
/** @var \Illuminate\Support\Carbon $start_date */
|
|
$start_date = $settings->start_date;
|
|
/** @var \Illuminate\Support\Carbon $end_date */
|
|
$end_date = $settings->end_date;
|
|
|
|
$lots = Prize::orderBy('id')->get();
|
|
|
|
/** @var \Illuminate\Support\Collection $daterange all days of the game period */
|
|
$daterange = collect($start_date->range($end_date)->toArray());
|
|
/** @var \Illuminate\Support\Collection $dateGlobal all randomized instant wins */
|
|
$dateGlobal = collect();
|
|
/** @var \Illuminate\Support\Collection $lotsGlobal All randomized lots */
|
|
$lotsGlobal = collect();
|
|
|
|
// * Assign Lots on collection
|
|
foreach ($lots as $lot) {
|
|
for ($i = $lot->quantity; $i > 0; $i--) {
|
|
$lotsGlobal->push($lot);
|
|
}
|
|
}
|
|
|
|
$daysRunningGame = clone $daterange;
|
|
|
|
// * Create Instant wins on collection
|
|
for ($i = $lotsGlobal->count(); $i > 0; $i--) {
|
|
// * Get each day once then randomize
|
|
if ($daysRunningGame->count()) {
|
|
/** @var Carbon $dateTime */
|
|
$dateTime = $daysRunningGame->shift();
|
|
} else {
|
|
/** @var Carbon $dateTime */
|
|
$dateTime = $daterange->random();
|
|
}
|
|
// * If end of loop and there are less lots then days
|
|
if ($i === 1 and $lotsGlobal->count() < $daysRunningGame->count()) {
|
|
// * Make the last instant win on the last day
|
|
/** @var Carbon $dateTime */
|
|
$dateTime = $daterange->random();
|
|
}
|
|
$dateGlobal->push(Carbon::parse(sprintf(
|
|
'%s %s',
|
|
$dateTime->format('Y-m-d'),
|
|
$this->getRandomWiningHour()
|
|
)));
|
|
}//end for
|
|
|
|
// * Sort dates
|
|
$dateGlobal = $dateGlobal->sortBy(function (Carbon $date) {
|
|
return $date->getTimestamp();
|
|
});
|
|
|
|
// * Reserve big prize (the first should be ID 1) and last Instant win for the end
|
|
/** @var \App\Models\Prize $bigPrize */
|
|
$bigPrize = $lotsGlobal->shift();
|
|
/** @var Carbon $lastInstantWin */
|
|
$lastInstantWin = $dateGlobal->pop();
|
|
|
|
// * Shuffle Instant wins
|
|
// ! Initialize mt rand seed !!
|
|
\mt_srand();
|
|
$lotsGlobal = $lotsGlobal->shuffle(\mt_rand(0, 99999));
|
|
|
|
// * Shuffle Lots
|
|
// ! Initialize mt rand seed !!
|
|
\mt_srand();
|
|
$dateGlobal = $dateGlobal->shuffle(\mt_rand(0, 99999));
|
|
|
|
// ! Return empty if no prizes are available
|
|
if (!$bigPrize) {
|
|
return \response()->json();
|
|
}
|
|
|
|
$instantWinsLots = $dateGlobal->map(function (Carbon $instantWinDate) use ($lotsGlobal) {
|
|
return [
|
|
'date' => $instantWinDate,
|
|
'lot' => $lotsGlobal->shift()
|
|
];
|
|
});
|
|
|
|
// * Save Instant wins
|
|
DB::transaction(function () use ($instantWinsLots, $lastInstantWin, $bigPrize) {
|
|
$instantWinsLots->map(function (array $instantWinLot) {
|
|
$instantWin = new InstantWin();
|
|
$instantWin->appear_date = $instantWinLot['date'];
|
|
$instantWin->prize()->associate($instantWinLot['lot']);
|
|
$instantWin->saveOrFail();
|
|
});
|
|
|
|
// * Insert last Instant win (big prize)
|
|
$instantWin = new InstantWin();
|
|
$instantWin->appear_date = $lastInstantWin;
|
|
$instantWin->prize()->associate($bigPrize);
|
|
$instantWin->saveOrFail();
|
|
});
|
|
|
|
return \response()->json(new InstantWinResource(InstantWin::orderBy('appear_date')->get()));
|
|
}
|
|
|
|
/**
|
|
* Generate a random hour between 06:00 and 22:59
|
|
*
|
|
* @return string
|
|
*/
|
|
private function getRandomWiningHour(): string
|
|
{
|
|
// ! Initialize mt rand seed !!
|
|
\mt_srand();
|
|
return Carbon::parse('22:59')
|
|
->subMinutes(\mt_rand(0, (23 - 6) * 60 - 1))->format('H:i');
|
|
}
|
|
}
|