ldc-gen-game-web/app/Http/Controllers/EnterCodeController.php
Noah Lancien 949b7ca13e phpcs
2023-08-24 12:59:51 +00:00

291 lines
10 KiB
PHP

<?php
namespace App\Http\Controllers;
use App\Http\Requests\ParticipateRequest;
use App\Mail\CourrierArcadiaError;
use App\Mail\NotifAdmin;
use App\Mail\NotifWinAdmin;
use App\Mail\PrizeWon;
use App\Mail\ReductionWon;
use App\Models\BannedIp;
use App\Models\InstantWin;
use App\Models\Participation;
use App\Models\Reduction;
use LDCWeb\MesBR;
use App\Models\Settings;
use Illuminate\Http\Request;
use Illuminate\Support\Facades\Auth;
use Illuminate\Support\Facades\Mail;
class EnterCodeController extends Controller
{
/**
*
* @var \LDCCRM\ApiV1
*/
private $apiCrm;
/**
* EnterCodeController
*/
public function __construct()
{
$this->apiCrm = new \LDCCRM\ApiV1(config('crm.endpoint'), config('crm.token'));
}
/**
* Show enter code form
*
* @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory
*/
public function index()
{
$nbParticipations = Participation::where('user_id', Auth::user()->id)->count();
$settings = app(Settings::class)->select('use_ean_codes', 'nb_participation_player')->first();
if ($nbParticipations >= $settings->nb_participation_player) {
return view('front.basic.participation-exhausted', compact('settings'));
}
return view('front.basic.enter-code', compact('settings'));
}
/**
* Participate Method
*
* @param ParticipateRequest $request
* @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory
*/
public function participate(ParticipateRequest $request)
{
// Récupération des données à utilisées.
/** @var \App\Models\Settings $settings */
$settings = app(Settings::class);
// * Cas IP bannie.
$ipBanned = BannedIp::where('ip', app('clientIp'))->first() === null ? 0 : 1;
if ($ipBanned) {
return view('front.basic.participation-exhausted', compact('settings'));
}
// * Cas nombre de participation maximale atteint.
$nbParticipations = Participation::where('user_id', auth()->user()->id)->count();
if ($nbParticipations >= $settings->nb_participation_player) {
return view('front.basic.participation-exhausted', compact('settings'));
}
// * Tous les cas "bloquants" sont passé, l'utilisateur participe à partir d'ici.
$participation = new Participation();
$participation->user_id = auth()->user()->id;
$participation->code_unique_id = $request->code->id;
$participation->code_ean_id = $request->code_ean ? $request->code_ean->id : null;
$participation->ip = app('clientIp');
$participation->save();
// * Gestion des instants gagnants.
$userAlreadyWon = Participation::has('instantWin')
->whereHas('user', function ($q) {
$q->whereId(auth()->user()->id);
})->first();
// * Si l'utilisateur actuel à déjà gagné un gros lot, pas d'instant gagnant.
if ($userAlreadyWon) {
return $this->serveCouponWin($settings, $participation);
}
$instantWin = InstantWin::where([['appear_date', '<', now()], ['won', 0]])
->orderBy('appear_date', 'ASC')->first();
if ($instantWin) {
// Ici si fail car unique dupliqué catch.
try {
// Gain d'un gros lot.
return $this->instantWin($settings, $request, $participation, $instantWin);
} catch (\ErrorException $e) {
// Unbind instant gagnant.
$participation->instantWin()->delete();
// phpcs:ignore
// TODO: si erreur il faut envoyer un mail à equipe.web@ldc.fr.
} //end try
}
return $this->serveCouponWin($settings, $participation);
}
/**
* Handle instant wins
*
* @param Settings $settings
* @param Request $request
* @param Participation $participation
* @param InstantWin|null $instantWin
* @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory
*/
private function instantWin(Settings $settings, Request $request, Participation &$participation, $instantWin)
{
$instantWin->won = true;
// Should save now to prevent next player win on the same winning moment.
$instantWin->save();
$participation->instantWin()->save($instantWin);
// Envoi du courrier Arcadia.
if (
$instantWin->prize->arcadia_operation_code !== 0 &&
$instantWin->prize->arcadia_support_code !== 0
) {
$crmId = auth()->user()->crm_id;
$fields = [
'root' => [
[
'fieldName' => 'order_date',
'fieldValue' => date('d/m/Y')
],
[
'fieldName' => 'operation',
'fieldValue' => $instantWin->prize->arcadia_operation_code
]
],
'orderLine' => [
[
'fieldName' => 'code_unique',
'fieldValue' => $request->serial
],
[
'fieldName' => 'support_code',
'fieldValue' => $instantWin->prize->arcadia_support_code
],
[
'fieldName' => 'label_type_support',
'fieldValue' => 'Gain du lot : ' . $instantWin->prize->label_one
]
]
];
if ($settings->use_ean_codes === 1) {
$codeEan = $request->code_ean;
$fields['orderLine'][] = [
'fieldName' => 'code_on_pack',
'fieldValue' => "$codeEan->code"
];
}
$arcadiaMail = $this->apiCrm->ArcadiaOutgoingMail($crmId, $fields, 'game');
if ($arcadiaMail->status === 'KO') {
Mail::to(config('mail.MAIL_ADMIN'))->send(new CourrierArcadiaError(auth()->user()));
}
} //end if
Mail::to(auth()->user()->email)->send(new PrizeWon(auth()->user(), $instantWin->prize, $settings));
$mails = json_decode($settings->notification_emails);
foreach ($mails as $mail) {
Mail::to($mail->email)->send(new NotifWinAdmin($settings, $participation));
}
$participation->save();
return view("front.basic." . $instantWin->prize->gainView->file_name, compact('settings'))
->with('prize', $instantWin->prize);
}
/**
* Détermine si un BR doit être servi
* renvoi la vue de gain BR ou la vue "Perdu"
*
* @param Settings $settings
* @param Participation $participation
* @return \Illuminate\Contracts\View\View|\Illuminate\Contracts\View\Factory
*/
private function serveCouponWin(Settings $settings, Participation $participation)
{
// Si le jeu est 100% gagnant.
if ($settings->reductions_activated === 1) {
$coupon = $this->getRandomCoupon($settings);
$crmCoupon = $this->updateCoupon($settings, $coupon->web_coupon_identifiant, $participation);
if (!$crmCoupon) {
$participation->delete();
return back()->withErrors("Une erreur est survenue, merci de réessayez ultérieurement.");
}
Mail::to(Auth::user()->email)->send(new ReductionWon(Auth::user(), $coupon, $settings, $crmCoupon));
return view('front.basic.reduction', compact('crmCoupon', 'coupon'));
} else {
return view('front.basic.loose');
}
}
/**
* Get a random coupon
*
* @param Settings $settings
* @return mixed
*/
private function getRandomCoupon(Settings $settings)
{
$webCoupons = json_decode($settings->web_coupons);
if (count($webCoupons) > 1) {
$lots = [];
foreach ($webCoupons as $webCoupon) {
$lots[] = $webCoupon;
}
foreach ($lots as $lot) {
for ($i = 0; $i < $lot->percentage; $i++) {
$tmp[] = $lot;
}
}
shuffle($tmp);
return $tmp[0];
} else {
return $webCoupons[0];
}
}
/**
* Update a coupon
*
* @param Settings $settings
* @param mixed $coupon
* @param Participation $participation
* @return \App\Models\Reduction|null
*/
private function updateCoupon(Settings $settings, mixed $coupon, Participation $participation)
{
$reduction = null;
$mesBR = new MesBR(config('mesbr.endpoint'), $settings->reductions_site, $settings->reductions_campaign);
$crmUser = $this->apiCrm->getCustomer(Auth::user()->crm_id);
if ($crmUser->status === 'OK') {
$mesBR->updateContact($crmUser->user);
$result = $mesBR->updatePanier($crmUser->user, $coupon);
if ($result["status"] === "OK") {
$reduction = new Reduction();
$reduction->link = $result["link"];
$reduction->verification = $result["verif"];
$reduction->basket_id = $result["basketId"];
$reduction->save();
$participation->reduction_id = $reduction->id;
$participation->save();
} else {
Mail::to(config('mail.MAIL_ADMIN'))
->send(new NotifAdmin(\sprintf(
'MESBR : Une erreur est survenue. Code : %s Message : %s',
$result["code"],
$result["message"]
)));
}
} //end if
return $reduction;
}
/**
* Undocumented function
*
* @return \Illuminate\Http\Response
*/
public function formWinningProof()
{
$participation = Participation::where([
['user_id', Auth::user()->id],
['sticker', null],
['ticket', null],
['barcode', null]
])->has('instantWin')->first();
if ($participation) {
return view('front.basic.winning-proof', compact('participation'));
}
return redirect()->route('home');
}
}