Commit 7e201b21 authored by Thomas Hamel's avatar Thomas Hamel
Browse files

Sessions : ajout des filtres anneeUniv et type, séances affichées sous forme de résumé dans le tab

parent aa493593
Loading
Loading
Loading
Loading
+5 −0
Changes for module/Formation/src/Formation/Entity/Db/Interfaces/HasTypeInterface.php: 5 added lines, 0 removed lines.
Original line number Diff line number Diff line
@@ -9,6 +9,11 @@ interface HasTypeInterface {
    const TYPE_SPECIFIQUE       = 'S';
    const TYPE_TRANSVERSALE     = 'T';

    const TYPES = [
        self::TYPE_SPECIFIQUE => "Spécifique",
        self::TYPE_TRANSVERSALE => "Transversale",
    ];

    public function getType() : ?string;
    public function setType(?string $type) : HasTypeInterface;

+15 −0
Changes for module/Formation/src/Formation/Entity/Db/Repository/SessionRepository.php: 15 added lines, 0 removed lines.
Original line number Diff line number Diff line
@@ -6,6 +6,7 @@ use Application\Entity\Db\Repository\DefaultEntityRepository;
use Application\QueryBuilder\DefaultQueryBuilder;
use DateTime;
use Doctorant\Entity\Db\Doctorant;
use Doctrine\ORM\Query\Expr\Join;
use Formation\Entity\Db\Etat;
use Formation\Entity\Db\Formation;
use Formation\Entity\Db\Session;
@@ -206,4 +207,18 @@ class SessionRepository extends DefaultEntityRepository

        return $qb->getQuery()->getResult();
    }

    public function fetchDistinctAnneesUnivSessions(string $champ='id', string $ordre='ASC', bool $keep_histo = false) : array
    {
        $qb = $this->createQueryBuilder('session')
            ->distinct()
            ->select("YEAR(seance.debut) as annee")
            ->orderBy("annee", $ordre);

        if (!$keep_histo) $qb = $qb->andWhere('session.histoDestruction IS NULL');

        return array_map(function($value) {
            return current($value);
        }, $qb->getQuery()->getScalarResult());
    }
}
 No newline at end of file
+90 −3
Changes for module/Formation/src/Formation/Service/Session/Search/SessionSearchService.php: 90 added lines, 3 removed lines.
Original line number Diff line number Diff line
@@ -2,6 +2,7 @@

namespace Formation\Service\Session\Search;

use Application\Entity\AnneeUniv;
use Application\QueryBuilder\DefaultQueryBuilder;
use Application\Search\Filter\SearchFilter;
use Application\Search\Filter\SelectSearchFilter;
@@ -9,9 +10,11 @@ use Application\Search\Filter\StrReducedTextSearchFilter;
use Application\Search\Filter\TextSearchFilter;
use Application\Search\SearchService;
use Application\Search\Sorter\SearchSorter;
use Application\Service\AnneeUniv\AnneeUnivServiceAwareTrait;
use Doctrine\ORM\QueryBuilder;
use Formation\Entity\Db\Etat;
use Formation\Entity\Db\Interfaces\HasModaliteInterface;
use Formation\Entity\Db\Interfaces\HasTypeInterface;
use Formation\Entity\Db\Repository\EtatRepositoryAwareTrait;
use Formation\Entity\Db\Repository\FormationRepositoryAwareTrait;
use Formation\Entity\Db\Repository\SessionRepositoryAwareTrait;
@@ -23,6 +26,7 @@ class SessionSearchService extends SearchService
    use FormationRepositoryAwareTrait;
    use EtatRepositoryAwareTrait;
    use SessionRepositoryAwareTrait;
    use AnneeUnivServiceAwareTrait;

    use EtablissementServiceAwareTrait;

@@ -32,6 +36,9 @@ class SessionSearchService extends SearchService
    const NAME_responsable = 'responsable';
    const NAME_site = 'site';
    const NAME_structure = 'structure';
    const NAME_anneeUniv = 'anneeUniv';
    const NAME_type = 'type';


    public function init()
    {
@@ -41,6 +48,8 @@ class SessionSearchService extends SearchService
        $libelleFilter = $this->createLibelleFilter()->setWhereField('formation.libelle');
        $responsableFilter = $this->createResponsableFilter();
        $modaliteFilter = $this->createModaliteFilter();
        $anneeUnivFilter = $this->createAnneeUnivFilter();
        $typeFilter = $this->createTypeFilter();

        $siteFilter->setDataProvider(fn() => $this->etablissementService->getRepository()->findAllEtablissementsInscriptions(true));
        $structureFilter->setDataProvider(fn() => $this->formationRepository->fetchListeStructures());
@@ -50,6 +59,13 @@ class SessionSearchService extends SearchService
            array_map(fn(Etat $e) => $e->getCode(), $etats = $this->etatRepository->findBy([], ['ordre' => 'asc'])),
            $etats
        ));
        $anneeUnivFilter->setDataProvider(function(SelectSearchFilter $filter) {
            return $this->fetchAnneesUniv($filter);
        });
        $typeFilter->setData(HasTypeInterface::TYPES);

        $annee = $this->anneeUnivService->courante();
        $debut = $this->anneeUnivService->computeDateDebut($annee);

        $this->addFilters([
            $siteFilter,
@@ -58,10 +74,12 @@ class SessionSearchService extends SearchService
            $libelleFilter,
            $etatFilter,
            $modaliteFilter,
            $anneeUnivFilter->setDefaultValue($debut->format('Y'))->setAllowsEmptyOption(false),
            $typeFilter
        ]);

        $this->addSorters([
            $this->createLibelleSorter()->setOrderByField('formation.libelle')->setIsDefault(),
            $this->createLibelleSorter(),
            $this->createSiteSorter(),
            $this->createStructureSorter(),
            $this->createResponsableSorter(),
@@ -72,8 +90,12 @@ class SessionSearchService extends SearchService

    public function createQueryBuilder(): QueryBuilder
    {
        // ATTENTION à bien sélectionner les relations utilisées par les filtres/tris et parcourues côté vue.
        return $this->sessionRepository->createQueryBuilder('s');
        $queryBuilder = $this->sessionRepository->createQueryBuilder('s');

        $queryBuilder->select('s');
        $queryBuilder->addOrderBy('CASE WHEN seance.fin IS NULL THEN 1 ELSE 0 END', 'ASC');
        $queryBuilder->addOrderBy('seance.debut', 'DESC');
        return $queryBuilder;
    }

    /********************************** FILTERS ****************************************/
@@ -127,6 +149,37 @@ class SessionSearchService extends SearchService
        return $filter;
    }

    /**
     * @return SelectSearchFilter
     */
    private function createAnneeUnivFilter(): SelectSearchFilter
    {
        $filter = new SelectSearchFilter(
            "An. univ.",
            self::NAME_anneeUniv
        );
        $filter->setQueryBuilderApplier(function(SearchFilter $filter, QueryBuilder $qb, string $alias = 'session') {
            $filterValue = $filter->getValue();
            $annee = $filterValue === 'NULL' ? $this->anneeUnivService->courante() : AnneeUniv::fromPremiereAnnee((int)$filterValue);
            $debut = $this->anneeUnivService->computeDateDebut($annee);
            $fin = $this->anneeUnivService->computeDateFin($annee);
            if ($filterValue === 'NULL') {
                if ($debut !== null && $fin !== null) {
                    $qb->andWhere('seance.debut >= :debut')->setParameter('debut', $debut)
                        ->andWhere('seance.fin <= :fin')->setParameter('fin', $fin);
                }
            } else {
                if ($debut !== null && $fin !== null) {
                    $qb->andWhere('seance.debut >= :debut')->setParameter('debut', $debut)
                        ->andWhere('seance.fin <= :fin')->setParameter('fin', $fin);
                }
            }
        });


        return $filter;
    }

    private function createLibelleFilter(): TextSearchFilter
    {
        $filter = new StrReducedTextSearchFilter("Libellé", self::NAME_libelle);
@@ -135,6 +188,40 @@ class SessionSearchService extends SearchService
        return $filter;
    }

    private function createTypeFilter(): SelectSearchFilter
    {
        $filter = new SelectSearchFilter("Type", self::NAME_type);
        $filter->setQueryBuilderApplier(function(SelectSearchFilter $filter, DefaultQueryBuilder $qb) {
            $qb
                ->andWhere("s.type = :type")
                ->setParameter('type', $filter->getValue());
        });

        return $filter;
    }

    /********************************** FILTERS ****************************************/

    private function fetchAnneesUniv(SelectSearchFilter $filter): array
    {
        $anneeUnivCourante = $this->anneeUnivService->courante();
        $anneeCourante = new \DateTime();
        $anneeCourante = $anneeCourante->format('Y');
        $annees = $this->sessionRepository->fetchDistinctAnneesUnivSessions();

        $anneesUniv = [];
        foreach($annees as $annee){
            if (! is_numeric($annee))  continue;

            if($anneeCourante === $annee){
                if(!in_array($anneeUnivCourante, $anneesUniv)) $anneesUniv[] =  $anneeUnivCourante;
                continue;
            }
            $anneesUniv[$annee] = AnneeUniv::fromPremiereAnnee($annee);
        }

        return $anneesUniv;
    }

    /********************************** SORTERS ****************************************/

+5 −0
Changes for module/Formation/src/Formation/Service/Session/Search/SessionSearchServiceFactory.php: 5 added lines, 0 removed lines.
Original line number Diff line number Diff line
@@ -2,6 +2,7 @@

namespace Formation\Service\Session\Search;

use Application\Service\AnneeUniv\AnneeUnivService;
use Formation\Entity\Db\Etat;
use Formation\Entity\Db\Formation;
use Formation\Entity\Db\Session;
@@ -38,6 +39,10 @@ class SessionSearchServiceFactory implements FactoryInterface
        $etablissementService = $container->get(EtablissementService::class);
        $service->setEtablissementService($etablissementService);

        /** @var AnneeUnivService $anneeUnivService */
        $anneeUnivService = $container->get(AnneeUnivService::class);
        $service->setAnneeUnivService($anneeUnivService);

        return $service;
    }
}
 No newline at end of file
+10 −16
Changes for module/Formation/view/formation/session/recherche/index.phtml: 10 added lines, 16 removed lines.
Original line number Diff line number Diff line
@@ -51,7 +51,7 @@ $canSupprimerSession = $this->isAllowed(SessionPrivileges::getResourceId(Sess
            <th>
                Sessions
            </th>
            <th>
            <th style="max-width: 6rem;">
                <a href="<?php echo $s = $this->sortable(SessionSearchService::NAME_site) ?>"
                   title="<?php echo $this->translate("Établissement organisateur") ?> ">
                    <?php echo $this->translate("Établissement organisateur") ?>*
@@ -78,7 +78,7 @@ $canSupprimerSession = $this->isAllowed(SessionPrivileges::getResourceId(Sess
                    <?php echo $this->translate("État") ?>
                </a> <?php echo $s->icon() ?>
            </th>
            <th>Séances</th>
            <th style="min-width: 14rem;">Séances</th>
            <th style="min-width: 9rem;">Inscriptions</th>
            <th style="min-width: 4rem;">Action</th>
        </tr>
@@ -122,26 +122,20 @@ $canSupprimerSession = $this->isAllowed(SessionPrivileges::getResourceId(Sess
                <td> <?php echo $this->modalite($session); ?> </td>
                <td> <?php echo $this->type($session); ?> </td>
                <td> <?php echo $this->etat($session); ?> </td>
                <td> <!-- Seances ----------------------------------------------------------------------------------------->
                <td style="min-width: 17rem;"> <!-- Seances ----------------------------------------------------------------------------------------->
                    <?php echo count($session->getSeances()); ?>
                    séance<?php if (count($session->getSeances())>1) echo "s"; ?>
                    (<?php echo $session->getDuree(); ?> h.)
                    <br>
                    <strong>Période :</strong>
                    <ul>
                        <?php
                            /** @var Seance[] $seances */
                            $seances = $session->getSeances()->toArray();
                            usort($seances, function (Seance $a, Seance $b) { return $a->getDebut() > $b->getDebut();});
                        ?>
                        <?php foreach ($seances as $seance) : ?>
                        <li>
                                <?php echo $seance->getDebut()->format('d/m/Y'); ?>
                                <?php echo $seance->getDebut()->format('H:i') ; ?>
                                &rightarrow;
                                <?php echo $seance->getFin()->format('H:i') ; ?>
                                -
                                <?php echo $seance->getLieu() ; ?>
                            <?php if ($session->getDateDebut() and $session->getDateFin()) : ?>
                                <?php echo $session->getDateDebut()->format('d/m/Y à H:i'); ?> &rightarrow; <?php echo $session->getDateFin()->format('d/m/Y à H:i'); ?>
                            <?php else : ?>
                                À déterminer
                            <?php endif; ?>
                        </li>
                        <?php endforeach; ?>
                    </ul>
                </td>
                <td> <!-- Inscriptions ------------------------------------------------------------------------------------>