<?php
namespace App\Controller\Api\Production;
use DateTime;
use App\Entity\User;
use App\Service\HierarchyService;
use App\Repository\UserRepository;
use App\Repository\ClusterRepository;
use App\Repository\ProductionRepository;
use Doctrine\ORM\EntityManagerInterface;
use App\Repository\PointOfSaleRepository;
use App\Repository\EtatProductionRepository;
use Symfony\Component\HttpFoundation\Request;
use Symfony\Component\Routing\Annotation\Route;
use Symfony\Component\HttpFoundation\JsonResponse;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpKernel\Exception\BadRequestHttpException;
class ProductionsRaccoValidController extends AbstractController
{
private $clusterRepository;
private $productionRepository;
private $pointOfSaleRepository;
private $userRepository;
private $etatRepository;
public function __construct(
ClusterRepository $clusterRepository,
ProductionRepository $productionRepository,
PointOfSaleRepository $pointOfSaleRepository,
UserRepository $userRepository,
EtatProductionRepository $etatRepository
) {
$this->clusterRepository = $clusterRepository;
$this->productionRepository = $productionRepository;
$this->pointOfSaleRepository = $pointOfSaleRepository;
$this->userRepository = $userRepository;
$this->etatRepository = $etatRepository;
}
public function __invoke($annee, $option, Request $request,EntityManagerInterface $entityManager,
HierarchyService $hierarchyService)
{
$pointOfSaleId = $request->query->get('pointOfSaleId', null);
$pointOfSale = null;
if ($pointOfSaleId) {
$pointOfSale = $this->pointOfSaleRepository->find($pointOfSaleId);
if (!$pointOfSale) {
return new JsonResponse('Le point de vente avec cet ID n\'existe pas.');
}
}
if ((strtolower($option) != 'r') && (strtolower($option) != 'v')) {
return new JsonResponse(['error' => 'Vérifier l option de selection'], 404);
}
$codeCluster = $request->query->get('codeCluster', null);
$mois = $request->query->get('mois', null);
$cluster = null;
if ($codeCluster) {
$cluster = $this->clusterRepository->findOneBy(['codeCluster' => $codeCluster]);
if ($cluster == null) {
return new JsonResponse(['error' => 'Aucun cluster avec ce code'], 404);
}
}
$codeInsee = $request->query->get('codeInsee', null);
$organisationId = $request->query->get('organisationId', null);
$etatId=$request->query->get('etatId', 1);
$etat = $this->etatRepository->findOneBy(['id'=>$etatId]);
if ($etat == null) {
return new JsonResponse(['error' => 'Aucune état avec cet ID'], 404);
}
$childs = [];
$user = null;
if ($request->query->get('idUser') != null) {
$user = $entityManager->getRepository(User::class)->find((int)$request->query->get('idUser'));
if (!$user) {
throw new BadRequestHttpException('L\'utilisateur avec cet ID n\'existe pas.');
}
// Récupérer l'hierarchie descendante
if (in_array('ROLE_MANAGER', $user->getRoles()) || in_array('ROLE_DIRECTOR', $user->getRoles())) {
$childs = array_map(fn($p) => (int) $p['id'], $hierarchyService->getHierarchyDescendante($user->getId()));
}
}
$productionsCohorte = $this->productionRepository->getProductionsRaccoValidRate($pointOfSale, $cluster, $mois, $annee, $codeInsee, $etat, $option,$childs,$organisationId);
return new JsonResponse($this->transformResult($productionsCohorte, $option));
}
private function transformResult(array $queryResults, string $option): array
{
$formattedResults = [];
foreach ($queryResults as $row) {
$mois_raccordement = sprintf('%04d-%02d', $row['annee_racc'], $row['mois_racc']);
$mois_validation = sprintf('%04d-%02d', $row['annee_validation'], $row['mois_validation']);
if ($option === "R") {
// Organisation des résultats selon le mois de raccordement
if (!isset($formattedResults[$mois_raccordement])) {
$formattedResults[$mois_raccordement] = [
'mois_raccordement' => $mois_raccordement,
'total_ventes_raccordees' => 0,
'ventes_par_mois_validation' => []
];
}
// Ajout du total des ventes raccordées
$formattedResults[$mois_raccordement]['total_ventes_raccordees'] += $row['total_ventes'];
// Ajout des ventes par mois de validation
if (!isset($formattedResults[$mois_raccordement]['ventes_par_mois_validation'][$mois_validation])) {
$formattedResults[$mois_raccordement]['ventes_par_mois_validation'][$mois_validation] = [
'ventes' => 0,
'pourcentage' => "0%"
];
}
$formattedResults[$mois_raccordement]['ventes_par_mois_validation'][$mois_validation]['ventes'] += $row['total_ventes'];
} elseif ($option === "V") {
// Organisation des résultats selon le mois de validation
if (!isset($formattedResults[$mois_validation])) {
$formattedResults[$mois_validation] = [
'mois_validation' => $mois_validation,
'total_ventes_validees' => 0,
'ventes_par_mois_raccordement' => []
];
}
// Ajout du total des ventes validées
$formattedResults[$mois_validation]['total_ventes_validees'] += $row['total_ventes'];
// Ajout des ventes par mois de raccordement
if (!isset($formattedResults[$mois_validation]['ventes_par_mois_raccordement'][$mois_raccordement])) {
$formattedResults[$mois_validation]['ventes_par_mois_raccordement'][$mois_raccordement] = [
'ventes' => 0,
'pourcentage' => "0%"
];
}
$formattedResults[$mois_validation]['ventes_par_mois_raccordement'][$mois_raccordement]['ventes'] += $row['total_ventes'];
}
}
// Calcul des pourcentages après agrégation
foreach ($formattedResults as &$result) {
if ($option === "R") {
$totalVentes = $result['total_ventes_raccordees'];
foreach ($result['ventes_par_mois_validation'] as &$validation) {
$validation['pourcentage'] = $this->calculerPourcentage($totalVentes, $validation['ventes']) . "%";
}
} elseif ($option === "V") {
$totalVentes = $result['total_ventes_validees'];
foreach ($result['ventes_par_mois_raccordement'] as &$raccordement) {
$raccordement['pourcentage'] = $this->calculerPourcentage($totalVentes, $raccordement['ventes']) . "%";
}
}
}
// Réindexer sous forme de liste
return array_values($formattedResults);
}
// Fonction de calcul de pourcentage
private function calculerPourcentage($total, $ventes)
{
if ($total == 0) {
return 0; // Évite la division par zéro
}
return round(($ventes / $total) * 100);
}
}