mirror of
https://gitlab.com/Chill-Projet/chill-bundles.git
synced 2025-06-07 18:44:08 +00:00
fix: SA: Fix many critical rules.
SA stands for Static Analysis.
This commit is contained in:
parent
db2010082a
commit
5432242376
@ -90,51 +90,21 @@ parameters:
|
|||||||
count: 1
|
count: 1
|
||||||
path: src/Bundle/ChillTaskBundle/Controller/TaskController.php
|
path: src/Bundle/ChillTaskBundle/Controller/TaskController.php
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Undefined variable\\: \\$id$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillFamilyMembersBundle/Controller/FamilyMemberController.php
|
|
||||||
|
|
||||||
-
|
-
|
||||||
message: "#^Call to an undefined method Chill\\\\MainBundle\\\\CRUD\\\\Controller\\\\AbstractCRUDController\\:\\:getRoleFor\\(\\)\\.$#"
|
message: "#^Call to an undefined method Chill\\\\MainBundle\\\\CRUD\\\\Controller\\\\AbstractCRUDController\\:\\:getRoleFor\\(\\)\\.$#"
|
||||||
count: 1
|
count: 1
|
||||||
path: src/Bundle/ChillMainBundle/CRUD/Controller/AbstractCRUDController.php
|
path: src/Bundle/ChillMainBundle/CRUD/Controller/AbstractCRUDController.php
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Call to an undefined method Chill\\\\MainBundle\\\\Command\\\\ChillImportUsersCommand\\:\\:tempOutput\\(\\)\\.$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillMainBundle/Command/ChillImportUsersCommand.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\MainBundle\\\\Controller\\\\AdminCountryCRUDController\\:\\:\\$paginatorFactory\\.$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillMainBundle/Controller/AdminCountryCRUDController.php
|
|
||||||
|
|
||||||
-
|
-
|
||||||
message: "#^Call to an undefined method Chill\\\\MainBundle\\\\Controller\\\\UserController\\:\\:createEditForm\\(\\)\\.$#"
|
message: "#^Call to an undefined method Chill\\\\MainBundle\\\\Controller\\\\UserController\\:\\:createEditForm\\(\\)\\.$#"
|
||||||
count: 1
|
count: 1
|
||||||
path: src/Bundle/ChillMainBundle/Controller/UserController.php
|
path: src/Bundle/ChillMainBundle/Controller/UserController.php
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\MainBundle\\\\Entity\\\\RoleScope\\:\\:\\$new\\.$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillMainBundle/Entity/RoleScope.php
|
|
||||||
|
|
||||||
-
|
-
|
||||||
message: "#^Undefined variable\\: \\$current$#"
|
message: "#^Undefined variable\\: \\$current$#"
|
||||||
count: 1
|
count: 1
|
||||||
path: src/Bundle/ChillMainBundle/Pagination/PageGenerator.php
|
path: src/Bundle/ChillMainBundle/Pagination/PageGenerator.php
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\MainBundle\\\\Routing\\\\MenuComposer\\:\\:\\$routeCollection\\.$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillMainBundle/Routing/MenuComposer.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\MainBundle\\\\Search\\\\SearchApiResult\\:\\:\\$relevance\\.$#"
|
|
||||||
count: 2
|
|
||||||
path: src/Bundle/ChillMainBundle/Search/SearchApiResult.php
|
|
||||||
|
|
||||||
-
|
-
|
||||||
message: "#^Call to an undefined method Chill\\\\MainBundle\\\\Security\\\\Authorization\\\\AbstractChillVoter\\:\\:getSupportedAttributes\\(\\)\\.$#"
|
message: "#^Call to an undefined method Chill\\\\MainBundle\\\\Security\\\\Authorization\\\\AbstractChillVoter\\:\\:getSupportedAttributes\\(\\)\\.$#"
|
||||||
count: 1
|
count: 1
|
||||||
@ -155,46 +125,6 @@ parameters:
|
|||||||
count: 3
|
count: 3
|
||||||
path: src/Bundle/ChillPersonBundle/Controller/PersonController.php
|
path: src/Bundle/ChillPersonBundle/Controller/PersonController.php
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\PersonBundle\\\\Controller\\\\TimelinePersonController\\:\\:\\$authorizationHelper\\.$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillPersonBundle/Controller/TimelinePersonController.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\PersonBundle\\\\DataFixtures\\\\ORM\\\\LoadHousehold\\:\\:\\$personIds\\.$#"
|
|
||||||
count: 2
|
|
||||||
path: src/Bundle/ChillPersonBundle/DataFixtures/ORM/LoadHousehold.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\PersonBundle\\\\Form\\\\CreationPersonType\\:\\:\\$centerTransformer\\.$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillPersonBundle/Form/CreationPersonType.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\ReportBundle\\\\Timeline\\\\TimelineReportProvider\\:\\:\\$security\\.$#"
|
|
||||||
count: 4
|
|
||||||
path: src/Bundle/ChillReportBundle/Timeline/TimelineReportProvider.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\AsideActivityBundle\\\\Entity\\\\AsideActivityCategory\\:\\:\\$oldParent\\.$#"
|
|
||||||
count: 2
|
|
||||||
path: src/Bundle/ChillAsideActivityBundle/src/Entity/AsideActivityCategory.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\AsideActivityBundle\\\\Form\\\\AsideActivityCategoryType\\:\\:\\$categoryRender\\.$#"
|
|
||||||
count: 2
|
|
||||||
path: src/Bundle/ChillAsideActivityBundle/src/Form/AsideActivityCategoryType.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\AsideActivityBundle\\\\Form\\\\AsideActivityFormType\\:\\:\\$translatableStringHelper\\.$#"
|
|
||||||
count: 1
|
|
||||||
path: src/Bundle/ChillAsideActivityBundle/src/Form/AsideActivityFormType.php
|
|
||||||
|
|
||||||
-
|
|
||||||
message: "#^Access to an undefined property Chill\\\\CalendarBundle\\\\DataFixtures\\\\ORM\\\\LoadCalendarRange\\:\\:\\$userRepository\\.$#"
|
|
||||||
count: 2
|
|
||||||
path: src/Bundle/ChillCalendarBundle/DataFixtures/ORM/LoadCalendarRange.php
|
|
||||||
|
|
||||||
-
|
-
|
||||||
message: "#^Call to an undefined method Chill\\\\ThirdPartyBundle\\\\Form\\\\Type\\\\PickThirdPartyTypeCategoryType\\:\\:transform\\(\\)\\.$#"
|
message: "#^Call to an undefined method Chill\\\\ThirdPartyBundle\\\\Form\\\\Type\\\\PickThirdPartyTypeCategoryType\\:\\:transform\\(\\)\\.$#"
|
||||||
count: 1
|
count: 1
|
||||||
|
@ -44,13 +44,15 @@ class AsideActivityCategory
|
|||||||
* @ORM\ManyToOne(targetEntity=AsideActivityCategory::class, inversedBy="children")
|
* @ORM\ManyToOne(targetEntity=AsideActivityCategory::class, inversedBy="children")
|
||||||
* @ORM\JoinColumn(nullable=true)
|
* @ORM\JoinColumn(nullable=true)
|
||||||
*/
|
*/
|
||||||
private $parent;
|
private AsideActivityCategory $parent;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @ORM\OneToMany(targetEntity=AsideActivityCategory::class, mappedBy="parent")
|
* @ORM\OneToMany(targetEntity=AsideActivityCategory::class, mappedBy="parent")
|
||||||
*/
|
*/
|
||||||
private $children;
|
private $children;
|
||||||
|
|
||||||
|
private AsideActivityCategory $oldParent;
|
||||||
|
|
||||||
public function __construct()
|
public function __construct()
|
||||||
{
|
{
|
||||||
$this->children = new ArrayCollection();
|
$this->children = new ArrayCollection();
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\AsideActivityBundle\Form;
|
namespace Chill\AsideActivityBundle\Form;
|
||||||
|
|
||||||
use Chill\AsideActivityBundle\Entity\AsideActivityCategory;
|
use Chill\AsideActivityBundle\Entity\AsideActivityCategory;
|
||||||
@ -14,12 +16,11 @@ use Symfony\Component\Form\FormBuilderInterface;
|
|||||||
|
|
||||||
final class AsideActivityCategoryType extends AbstractType
|
final class AsideActivityCategoryType extends AbstractType
|
||||||
{
|
{
|
||||||
|
private CategoryRender $categoryRender;
|
||||||
|
|
||||||
protected $translatableStringHelper;
|
public function __construct(
|
||||||
|
CategoryRender $categoryRender
|
||||||
public function __construct(TranslatableStringHelper $translatableStringHelper, CategoryRender $categoryRender)
|
) {
|
||||||
{
|
|
||||||
$this->translatableStringHelper = $translatableStringHelper;
|
|
||||||
$this->categoryRender = $categoryRender;
|
$this->categoryRender = $categoryRender;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -25,18 +25,16 @@ use Symfony\Component\Templating\EngineInterface;
|
|||||||
|
|
||||||
final class AsideActivityFormType extends AbstractType
|
final class AsideActivityFormType extends AbstractType
|
||||||
{
|
{
|
||||||
protected array $timeChoices;
|
private array $timeChoices;
|
||||||
private TokenStorageInterface $storage;
|
private TokenStorageInterface $storage;
|
||||||
private CategoryRender $categoryRender;
|
private CategoryRender $categoryRender;
|
||||||
|
|
||||||
public function __construct (
|
public function __construct (
|
||||||
TranslatableStringHelper $translatableStringHelper,
|
|
||||||
ParameterBagInterface $parameterBag,
|
ParameterBagInterface $parameterBag,
|
||||||
TokenStorageInterface $storage,
|
TokenStorageInterface $storage,
|
||||||
CategoryRender $categoryRender
|
CategoryRender $categoryRender
|
||||||
){
|
){
|
||||||
$this->timeChoices = $parameterBag->get('chill_aside_activity.form.time_duration');
|
$this->timeChoices = $parameterBag->get('chill_aside_activity.form.time_duration');
|
||||||
$this->translatableStringHelper = $translatableStringHelper;
|
|
||||||
$this->storage = $storage;
|
$this->storage = $storage;
|
||||||
$this->categoryRender = $categoryRender;
|
$this->categoryRender = $categoryRender;
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\CalendarBundle\DataFixtures\ORM;
|
namespace Chill\CalendarBundle\DataFixtures\ORM;
|
||||||
|
|
||||||
use Chill\CalendarBundle\Entity\CalendarRange;
|
use Chill\CalendarBundle\Entity\CalendarRange;
|
||||||
@ -15,6 +17,10 @@ use Doctrine\Persistence\ObjectManager;
|
|||||||
|
|
||||||
class LoadCalendarRange extends Fixture implements FixtureGroupInterface, OrderedFixtureInterface
|
class LoadCalendarRange extends Fixture implements FixtureGroupInterface, OrderedFixtureInterface
|
||||||
{
|
{
|
||||||
|
private UserRepository $userRepository;
|
||||||
|
|
||||||
|
public static array $references = [];
|
||||||
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
UserRepository $userRepository
|
UserRepository $userRepository
|
||||||
) {
|
) {
|
||||||
@ -31,8 +37,6 @@ class LoadCalendarRange extends Fixture implements FixtureGroupInterface, Ordere
|
|||||||
return ['calendar'];
|
return ['calendar'];
|
||||||
}
|
}
|
||||||
|
|
||||||
public static $references = [];
|
|
||||||
|
|
||||||
public function load(ObjectManager $manager): void
|
public function load(ObjectManager $manager): void
|
||||||
{
|
{
|
||||||
$arr = range(-50, 50);
|
$arr = range(-50, 50);
|
||||||
|
@ -3,7 +3,6 @@
|
|||||||
namespace Chill\AMLI\FamilyMembersBundle\Controller;
|
namespace Chill\AMLI\FamilyMembersBundle\Controller;
|
||||||
|
|
||||||
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
|
use Symfony\Bundle\FrameworkBundle\Controller\Controller;
|
||||||
use Sensio\Bundle\FrameworkExtraBundle\Configuration\Route;
|
|
||||||
use Chill\PersonBundle\Entity\Person;
|
use Chill\PersonBundle\Entity\Person;
|
||||||
use Symfony\Component\HttpFoundation\Request;
|
use Symfony\Component\HttpFoundation\Request;
|
||||||
use Doctrine\ORM\EntityManagerInterface;
|
use Doctrine\ORM\EntityManagerInterface;
|
||||||
@ -13,27 +12,16 @@ use Chill\AMLI\FamilyMembersBundle\Form\FamilyMemberType;
|
|||||||
use Symfony\Component\Form\Extension\Core\Type\SubmitType;
|
use Symfony\Component\Form\Extension\Core\Type\SubmitType;
|
||||||
use Symfony\Component\Translation\TranslatorInterface;
|
use Symfony\Component\Translation\TranslatorInterface;
|
||||||
use Psr\Log\LoggerInterface;
|
use Psr\Log\LoggerInterface;
|
||||||
|
use Symfony\Component\Routing\Annotation\Route;
|
||||||
|
|
||||||
class FamilyMemberController extends Controller
|
class FamilyMemberController extends Controller
|
||||||
{
|
{
|
||||||
/**
|
protected EntityManagerInterface $em;
|
||||||
*
|
|
||||||
* @var EntityManagerInterface
|
protected TranslatorInterface $translator;
|
||||||
*/
|
|
||||||
protected $em;
|
protected LoggerInterface $chillMainLogger;
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var TranslatorInterface
|
|
||||||
*/
|
|
||||||
protected $translator;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var LoggerInterface
|
|
||||||
*/
|
|
||||||
protected $chillMainLogger;
|
|
||||||
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
EntityManagerInterface $em,
|
EntityManagerInterface $em,
|
||||||
TranslatorInterface $translator,
|
TranslatorInterface $translator,
|
||||||
@ -44,7 +32,7 @@ class FamilyMemberController extends Controller
|
|||||||
$this->chillMainLogger = $chillMainLogger;
|
$this->chillMainLogger = $chillMainLogger;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @Route(
|
* @Route(
|
||||||
* "{_locale}/family-members/family-members/by-person/{id}",
|
* "{_locale}/family-members/family-members/by-person/{id}",
|
||||||
@ -54,11 +42,11 @@ class FamilyMemberController extends Controller
|
|||||||
public function indexAction(Person $person)
|
public function indexAction(Person $person)
|
||||||
{
|
{
|
||||||
$this->denyAccessUnlessGranted(FamilyMemberVoter::SHOW, $person);
|
$this->denyAccessUnlessGranted(FamilyMemberVoter::SHOW, $person);
|
||||||
|
|
||||||
$familyMembers = $this->em
|
$familyMembers = $this->em
|
||||||
->getRepository(FamilyMember::class)
|
->getRepository(FamilyMember::class)
|
||||||
->findByPerson($person);
|
->findByPerson($person);
|
||||||
|
|
||||||
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:index.html.twig', array(
|
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:index.html.twig', array(
|
||||||
'person' => $person,
|
'person' => $person,
|
||||||
'familyMembers' => $familyMembers
|
'familyMembers' => $familyMembers
|
||||||
@ -76,26 +64,26 @@ class FamilyMemberController extends Controller
|
|||||||
$familyMember = (new FamilyMember())
|
$familyMember = (new FamilyMember())
|
||||||
->setPerson($person)
|
->setPerson($person)
|
||||||
;
|
;
|
||||||
|
|
||||||
$this->denyAccessUnlessGranted(FamilyMemberVoter::CREATE, $familyMember);
|
$this->denyAccessUnlessGranted(FamilyMemberVoter::CREATE, $familyMember);
|
||||||
|
|
||||||
$form = $this->createForm(FamilyMemberType::class, $familyMember);
|
$form = $this->createForm(FamilyMemberType::class, $familyMember);
|
||||||
$form->add('submit', SubmitType::class);
|
$form->add('submit', SubmitType::class);
|
||||||
|
|
||||||
$form->handleRequest($request);
|
$form->handleRequest($request);
|
||||||
|
|
||||||
if ($form->isSubmitted() and $form->isValid()) {
|
if ($form->isSubmitted() and $form->isValid()) {
|
||||||
$em = $this->getDoctrine()->getManager();
|
$em = $this->getDoctrine()->getManager();
|
||||||
$em->persist($familyMember);
|
$em->persist($familyMember);
|
||||||
$em->flush();
|
$em->flush();
|
||||||
|
|
||||||
$this->addFlash('success', $this->translator->trans('Family member created'));
|
$this->addFlash('success', $this->translator->trans('Family member created'));
|
||||||
|
|
||||||
return $this->redirectToRoute('chill_family_members_family_members_index', [
|
return $this->redirectToRoute('chill_family_members_family_members_index', [
|
||||||
'id' => $person->getId()
|
'id' => $person->getId()
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:new.html.twig', array(
|
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:new.html.twig', array(
|
||||||
'form' => $form->createView(),
|
'form' => $form->createView(),
|
||||||
'person' => $person
|
'person' => $person
|
||||||
@ -111,37 +99,37 @@ class FamilyMemberController extends Controller
|
|||||||
public function editAction(FamilyMember $familyMember, Request $request)
|
public function editAction(FamilyMember $familyMember, Request $request)
|
||||||
{
|
{
|
||||||
$this->denyAccessUnlessGranted(FamilyMemberVoter::UPDATE, $familyMember);
|
$this->denyAccessUnlessGranted(FamilyMemberVoter::UPDATE, $familyMember);
|
||||||
|
|
||||||
$form = $this->createForm(FamilyMemberType::class, $familyMember);
|
$form = $this->createForm(FamilyMemberType::class, $familyMember);
|
||||||
$form->add('submit', SubmitType::class);
|
$form->add('submit', SubmitType::class);
|
||||||
|
|
||||||
$form->handleRequest($request);
|
$form->handleRequest($request);
|
||||||
|
|
||||||
if ($form->isSubmitted() and $form->isValid()) {
|
if ($form->isSubmitted() and $form->isValid()) {
|
||||||
$em = $this->getDoctrine()->getManager();
|
$em = $this->getDoctrine()->getManager();
|
||||||
$em->flush();
|
$em->flush();
|
||||||
|
|
||||||
$this->addFlash('success', $this->translator->trans('Family member updated'));
|
$this->addFlash('success', $this->translator->trans('Family member updated'));
|
||||||
|
|
||||||
return $this->redirectToRoute('chill_family_members_family_members_index', [
|
return $this->redirectToRoute('chill_family_members_family_members_index', [
|
||||||
'id' => $familyMember->getPerson()->getId()
|
'id' => $familyMember->getPerson()->getId()
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:edit.html.twig', array(
|
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:edit.html.twig', array(
|
||||||
'familyMember' => $familyMember,
|
'familyMember' => $familyMember,
|
||||||
'form' => $form->createView(),
|
'form' => $form->createView(),
|
||||||
'person' => $familyMember->getPerson()
|
'person' => $familyMember->getPerson()
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* @Route(
|
* @Route(
|
||||||
* "{_locale}/family-members/family-members/{id}/delete",
|
* "{_locale}/family-members/family-members/{id}/delete",
|
||||||
* name="chill_family_members_family_members_delete"
|
* name="chill_family_members_family_members_delete"
|
||||||
* )
|
* )
|
||||||
*
|
*
|
||||||
* @param FamilyMember $familyMember
|
* @param FamilyMember $familyMember
|
||||||
* @param Request $request
|
* @param Request $request
|
||||||
* @return \Symfony\Component\BrowserKit\Response
|
* @return \Symfony\Component\BrowserKit\Response
|
||||||
@ -183,7 +171,7 @@ class FamilyMemberController extends Controller
|
|||||||
'delete_form' => $form->createView()
|
'delete_form' => $form->createView()
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @Route(
|
* @Route(
|
||||||
* "{_locale}/family-members/family-members/{id}/view",
|
* "{_locale}/family-members/family-members/{id}/view",
|
||||||
@ -193,12 +181,12 @@ class FamilyMemberController extends Controller
|
|||||||
public function viewAction(FamilyMember $familyMember)
|
public function viewAction(FamilyMember $familyMember)
|
||||||
{
|
{
|
||||||
$this->denyAccessUnlessGranted(FamilyMemberVoter::SHOW, $familyMember);
|
$this->denyAccessUnlessGranted(FamilyMemberVoter::SHOW, $familyMember);
|
||||||
|
|
||||||
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:view.html.twig', array(
|
return $this->render('ChillAMLIFamilyMembersBundle:FamilyMember:view.html.twig', array(
|
||||||
'familyMember' => $familyMember
|
'familyMember' => $familyMember
|
||||||
));
|
));
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Creates a form to delete a help request entity by id.
|
* Creates a form to delete a help request entity by id.
|
||||||
*
|
*
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\MainBundle\CRUD\Controller;
|
namespace Chill\MainBundle\CRUD\Controller;
|
||||||
|
|
||||||
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
|
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
|
||||||
@ -14,31 +16,28 @@ use Symfony\Component\EventDispatcher\EventDispatcherInterface;
|
|||||||
use Symfony\Component\Serializer\SerializerInterface;
|
use Symfony\Component\Serializer\SerializerInterface;
|
||||||
use Symfony\Component\Translation\TranslatorInterface;
|
use Symfony\Component\Translation\TranslatorInterface;
|
||||||
|
|
||||||
class AbstractCRUDController extends AbstractController
|
abstract class AbstractCRUDController extends AbstractController
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
* The crud configuration
|
* The crud configuration
|
||||||
*
|
*
|
||||||
* This configuration si defined by `chill_main['crud']` or `chill_main['apis']`
|
* This configuration si defined by `chill_main['crud']` or `chill_main['apis']`
|
||||||
*
|
|
||||||
* @var array
|
|
||||||
*/
|
*/
|
||||||
protected array $crudConfig = [];
|
protected array $crudConfig = [];
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* get the instance of the entity with the given id
|
* get the instance of the entity with the given id
|
||||||
*
|
*
|
||||||
* @param string $id
|
|
||||||
* @return object
|
|
||||||
* @throw Symfony\Component\HttpKernel\Exception\NotFoundHttpException if the object is not found
|
* @throw Symfony\Component\HttpKernel\Exception\NotFoundHttpException if the object is not found
|
||||||
*/
|
*/
|
||||||
protected function getEntity($action, $id, Request $request): object
|
protected function getEntity($action, string $id, Request $request): object
|
||||||
{
|
{
|
||||||
$e = $this->getDoctrine()
|
$e = $this
|
||||||
|
->getDoctrine()
|
||||||
->getRepository($this->getEntityClass())
|
->getRepository($this->getEntityClass())
|
||||||
->find($id);
|
->find($id);
|
||||||
|
|
||||||
if (NULL === $e) {
|
if (null === $e) {
|
||||||
throw $this->createNotFoundException(sprintf("The object %s for id %s is not found", $this->getEntityClass(), $id));
|
throw $this->createNotFoundException(sprintf("The object %s for id %s is not found", $this->getEntityClass(), $id));
|
||||||
}
|
}
|
||||||
|
|
||||||
@ -47,61 +46,50 @@ class AbstractCRUDController extends AbstractController
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* Create an entity.
|
* Create an entity.
|
||||||
*
|
*
|
||||||
* @param string $action
|
|
||||||
* @param Request $request
|
|
||||||
* @return object
|
* @return object
|
||||||
*/
|
*/
|
||||||
protected function createEntity(string $action, Request $request): object
|
protected function createEntity(string $action, Request $request): object
|
||||||
{
|
{
|
||||||
$type = $this->getEntityClass();
|
return $this->getEntityClass();
|
||||||
|
|
||||||
return new $type;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Count the number of entities
|
* Count the number of entities
|
||||||
*
|
*
|
||||||
* By default, count all entities. You can customize the query by
|
* By default, count all entities. You can customize the query by
|
||||||
* using the method `customizeQuery`.
|
* using the method `customizeQuery`.
|
||||||
*
|
|
||||||
* @param string $action
|
|
||||||
* @param Request $request
|
|
||||||
* @return int
|
|
||||||
*/
|
*/
|
||||||
protected function countEntities(string $action, Request $request, $_format): int
|
protected function countEntities(string $action, Request $request, $_format): int
|
||||||
{
|
{
|
||||||
return $this->buildQueryEntities($action, $request)
|
return $this->buildQueryEntities($action, $request)
|
||||||
->select('COUNT(e)')
|
->select('COUNT(e)')
|
||||||
->getQuery()
|
->getQuery()
|
||||||
->getSingleScalarResult()
|
->getSingleScalarResult();
|
||||||
;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Query the entity.
|
* Query the entity.
|
||||||
*
|
*
|
||||||
* By default, get all entities. You can customize the query by using the
|
* By default, get all entities. You can customize the query by using the
|
||||||
* method `customizeQuery`.
|
* method `customizeQuery`.
|
||||||
*
|
*
|
||||||
* The method `orderEntity` is called internally to order entities.
|
* The method `orderEntity` is called internally to order entities.
|
||||||
*
|
*
|
||||||
* It returns, by default, a query builder.
|
* It returns, by default, a query builder.
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
protected function queryEntities(string $action, Request $request, string $_format, PaginatorInterface $paginator)
|
protected function queryEntities(string $action, Request $request, string $_format, PaginatorInterface $paginator)
|
||||||
{
|
{
|
||||||
$query = $this->buildQueryEntities($action, $request)
|
$query = $this->buildQueryEntities($action, $request)
|
||||||
->setFirstResult($paginator->getCurrentPage()->getFirstItemNumber())
|
->setFirstResult($paginator->getCurrentPage()->getFirstItemNumber())
|
||||||
->setMaxResults($paginator->getItemsPerPage());
|
->setMaxResults($paginator->getItemsPerPage());
|
||||||
|
|
||||||
// allow to order queries and return the new query
|
// allow to order queries and return the new query
|
||||||
return $this->orderQuery($action, $query, $request, $paginator, $_format);
|
return $this->orderQuery($action, $query, $request, $paginator, $_format);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Add ordering fields in the query build by self::queryEntities
|
* Add ordering fields in the query build by self::queryEntities
|
||||||
*
|
|
||||||
*/
|
*/
|
||||||
protected function orderQuery(string $action, $query, Request $request, PaginatorInterface $paginator, $_format)
|
protected function orderQuery(string $action, $query, Request $request, PaginatorInterface $paginator, $_format)
|
||||||
{
|
{
|
||||||
@ -112,14 +100,12 @@ class AbstractCRUDController extends AbstractController
|
|||||||
* Build the base query for listing all entities.
|
* Build the base query for listing all entities.
|
||||||
*
|
*
|
||||||
* This method is used internally by `countEntities` `queryEntities`
|
* This method is used internally by `countEntities` `queryEntities`
|
||||||
*
|
*
|
||||||
* This base query does not contains any `WHERE` or `SELECT` clauses. You
|
* This base query does not contains any `WHERE` or `SELECT` clauses. You
|
||||||
* can add some by using the method `customizeQuery`.
|
* can add some by using the method `customizeQuery`.
|
||||||
*
|
*
|
||||||
* The alias for the entity is "e".
|
* The alias for the entity is "e".
|
||||||
*
|
*
|
||||||
* @param string $action
|
|
||||||
* @param Request $request
|
|
||||||
* @return QueryBuilder
|
* @return QueryBuilder
|
||||||
*/
|
*/
|
||||||
protected function buildQueryEntities(string $action, Request $request)
|
protected function buildQueryEntities(string $action, Request $request)
|
||||||
@ -127,8 +113,7 @@ class AbstractCRUDController extends AbstractController
|
|||||||
$qb = $this->getDoctrine()->getManager()
|
$qb = $this->getDoctrine()->getManager()
|
||||||
->createQueryBuilder()
|
->createQueryBuilder()
|
||||||
->select('e')
|
->select('e')
|
||||||
->from($this->getEntityClass(), 'e')
|
->from($this->getEntityClass(), 'e');
|
||||||
;
|
|
||||||
|
|
||||||
$this->customizeQuery($action, $request, $qb);
|
$this->customizeQuery($action, $request, $qb);
|
||||||
|
|
||||||
@ -138,55 +123,55 @@ class AbstractCRUDController extends AbstractController
|
|||||||
protected function customizeQuery(string $action, Request $request, $query): void {}
|
protected function customizeQuery(string $action, Request $request, $query): void {}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the result of the query
|
* Get the result of the query.
|
||||||
*/
|
*/
|
||||||
protected function getQueryResult(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator, $query)
|
protected function getQueryResult(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator, $query)
|
||||||
{
|
{
|
||||||
return $query->getQuery()->getResult();
|
return $query->getQuery()->getResult();
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function onPreIndex(string $action, Request $request, string $_format): ?Response
|
protected function onPreIndex(string $action, Request $request, string $_format): ?Response
|
||||||
{
|
{
|
||||||
return null;
|
|
||||||
}
|
|
||||||
|
|
||||||
/**
|
|
||||||
* method used by indexAction
|
|
||||||
*/
|
|
||||||
protected function onPreIndexBuildQuery(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator): ?Response
|
|
||||||
{
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* method used by indexAction
|
* Method used by indexAction.
|
||||||
|
*/
|
||||||
|
protected function onPreIndexBuildQuery(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator): ?Response
|
||||||
|
{
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Method used by indexAction.
|
||||||
*/
|
*/
|
||||||
protected function onPostIndexBuildQuery(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator, $query): ?Response
|
protected function onPostIndexBuildQuery(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator, $query): ?Response
|
||||||
{
|
{
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* method used by indexAction
|
* Method used by indexAction.
|
||||||
*/
|
*/
|
||||||
protected function onPostIndexFetchQuery(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator, $entities): ?Response
|
protected function onPostIndexFetchQuery(string $action, Request $request, string $_format, int $totalItems, PaginatorInterface $paginator, $entities): ?Response
|
||||||
{
|
{
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Get the complete FQDN of the class
|
* Get the FQDN of the class.
|
||||||
*
|
*
|
||||||
* @return string the complete fqdn of the class
|
* @return string The FQDN of the class
|
||||||
*/
|
*/
|
||||||
protected function getEntityClass(): string
|
protected function getEntityClass(): string
|
||||||
{
|
{
|
||||||
return $this->crudConfig['class'];
|
return $this->crudConfig['class'];
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* called on post fetch entity
|
* Called on post fetch entity.
|
||||||
*/
|
*/
|
||||||
protected function onPostFetchEntity(string $action, Request $request, $entity, $_format): ?Response
|
protected function onPostFetchEntity(string $action, Request $request, $entity, $_format): ?Response
|
||||||
{
|
{
|
||||||
@ -194,7 +179,7 @@ class AbstractCRUDController extends AbstractController
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Called on post check ACL
|
* Called on post check ACL.
|
||||||
*/
|
*/
|
||||||
protected function onPostCheckACL(string $action, Request $request, string $_format, $entity): ?Response
|
protected function onPostCheckACL(string $action, Request $request, string $_format, $entity): ?Response
|
||||||
{
|
{
|
||||||
@ -203,23 +188,23 @@ class AbstractCRUDController extends AbstractController
|
|||||||
|
|
||||||
/**
|
/**
|
||||||
* check the acl. Called by every action.
|
* check the acl. Called by every action.
|
||||||
*
|
*
|
||||||
* By default, check the role given by `getRoleFor` for the value given in
|
* By default, check the role given by `getRoleFor` for the value given in
|
||||||
* $entity.
|
* $entity.
|
||||||
*
|
*
|
||||||
* Throw an \Symfony\Component\Security\Core\Exception\AccessDeniedHttpException
|
* Throw an \Symfony\Component\Security\Core\Exception\AccessDeniedHttpException
|
||||||
* if not accessible.
|
* if not accessible.
|
||||||
*
|
*
|
||||||
* @throws \Symfony\Component\Security\Core\Exception\AccessDeniedHttpException
|
* @throws \Symfony\Component\Security\Core\Exception\AccessDeniedHttpException
|
||||||
*/
|
*/
|
||||||
protected function checkACL(string $action, Request $request, string $_format, $entity = null)
|
protected function checkACL(string $action, Request $request, string $_format, $entity = null)
|
||||||
{
|
{
|
||||||
|
// @TODO: Implements abstract getRoleFor method or do it in the interface.
|
||||||
$this->denyAccessUnlessGranted($this->getRoleFor($action, $request, $entity, $_format), $entity);
|
$this->denyAccessUnlessGranted($this->getRoleFor($action, $request, $entity, $_format), $entity);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
* @return string The crud name.
|
||||||
* @return string the crud name
|
|
||||||
*/
|
*/
|
||||||
protected function getCrudName(): string
|
protected function getCrudName(): string
|
||||||
{
|
{
|
||||||
@ -230,7 +215,7 @@ class AbstractCRUDController extends AbstractController
|
|||||||
{
|
{
|
||||||
return $this->crudConfig['actions'][$action];
|
return $this->crudConfig['actions'][$action];
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Set the crud configuration
|
* Set the crud configuration
|
||||||
*
|
*
|
||||||
@ -241,9 +226,6 @@ class AbstractCRUDController extends AbstractController
|
|||||||
$this->crudConfig = $config;
|
$this->crudConfig = $config;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @return PaginatorFactory
|
|
||||||
*/
|
|
||||||
protected function getPaginatorFactory(): PaginatorFactory
|
protected function getPaginatorFactory(): PaginatorFactory
|
||||||
{
|
{
|
||||||
return $this->container->get('chill_main.paginator_factory');
|
return $this->container->get('chill_main.paginator_factory');
|
||||||
@ -254,9 +236,6 @@ class AbstractCRUDController extends AbstractController
|
|||||||
return $this->get('validator');
|
return $this->get('validator');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
* @return array
|
|
||||||
*/
|
|
||||||
public static function getSubscribedServices(): array
|
public static function getSubscribedServices(): array
|
||||||
{
|
{
|
||||||
return \array_merge(
|
return \array_merge(
|
||||||
|
@ -1,7 +1,10 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\MainBundle\Command;
|
namespace Chill\MainBundle\Command;
|
||||||
|
|
||||||
|
use Chill\MainBundle\Repository\UserRepository;
|
||||||
use Symfony\Component\Console\Command\Command;
|
use Symfony\Component\Console\Command\Command;
|
||||||
use Symfony\Component\Console\Input\InputArgument;
|
use Symfony\Component\Console\Input\InputArgument;
|
||||||
use Symfony\Component\Console\Input\InputInterface;
|
use Symfony\Component\Console\Input\InputInterface;
|
||||||
@ -23,82 +26,35 @@ use League\Csv\Writer;
|
|||||||
|
|
||||||
class ChillImportUsersCommand extends Command
|
class ChillImportUsersCommand extends Command
|
||||||
{
|
{
|
||||||
|
protected EntityManagerInterface $em;
|
||||||
/**
|
|
||||||
*
|
protected ValidatorInterface $validator;
|
||||||
* @var EntityManagerInterface
|
|
||||||
*/
|
protected LoggerInterface $logger;
|
||||||
protected $em;
|
|
||||||
|
protected UserPasswordEncoderInterface $passwordEncoder;
|
||||||
/**
|
|
||||||
*
|
protected UserRepository $userRepository;
|
||||||
* @var ValidatorInterface
|
|
||||||
*/
|
protected bool $doChanges = true;
|
||||||
protected $validator;
|
|
||||||
|
protected OutputInterface $tempOutput;
|
||||||
/**
|
|
||||||
*
|
protected InputInterface $tempInput;
|
||||||
* @var LoggerInterface
|
|
||||||
*/
|
|
||||||
protected $logger;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var UserPasswordEncoderInterface
|
|
||||||
*/
|
|
||||||
protected $passwordEncoder;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var \Chill\MainBundle\Repository\UserRepository
|
|
||||||
*/
|
|
||||||
protected $userRepository;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var bool
|
|
||||||
*/
|
|
||||||
protected $doChanges = true;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var OutputInterface
|
|
||||||
*/
|
|
||||||
protected $tempOutput;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var InputInterface
|
|
||||||
*/
|
|
||||||
protected $tempInput;
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Centers and aliases.
|
* Centers and aliases.
|
||||||
*
|
*
|
||||||
* key are aliases, values are an array of centers
|
* key are aliases, values are an array of centers
|
||||||
*
|
|
||||||
* @var array
|
|
||||||
*/
|
*/
|
||||||
protected $centers = [];
|
protected array $centers;
|
||||||
|
|
||||||
/**
|
protected array $permissionGroups;
|
||||||
*
|
|
||||||
* @var array
|
protected array $groupCenters;
|
||||||
*/
|
|
||||||
protected $permissionGroups = [];
|
protected Writer $output;
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var array
|
|
||||||
*/
|
|
||||||
protected $groupCenters = [];
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var Writer
|
|
||||||
*/
|
|
||||||
protected $output = null;
|
|
||||||
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
EntityManagerInterface $em,
|
EntityManagerInterface $em,
|
||||||
LoggerInterface $logger,
|
LoggerInterface $logger,
|
||||||
@ -109,15 +65,12 @@ class ChillImportUsersCommand extends Command
|
|||||||
$this->passwordEncoder = $passwordEncoder;
|
$this->passwordEncoder = $passwordEncoder;
|
||||||
$this->validator = $validator;
|
$this->validator = $validator;
|
||||||
$this->logger = $logger;
|
$this->logger = $logger;
|
||||||
|
|
||||||
|
|
||||||
$this->userRepository = $em->getRepository(User::class);
|
$this->userRepository = $em->getRepository(User::class);
|
||||||
|
|
||||||
parent::__construct('chill:main:import-users');
|
parent::__construct('chill:main:import-users');
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
protected function configure()
|
protected function configure()
|
||||||
{
|
{
|
||||||
$this
|
$this
|
||||||
@ -126,25 +79,24 @@ class ChillImportUsersCommand extends Command
|
|||||||
->addArgument('csvfile', InputArgument::REQUIRED, 'Path to the csv file. Columns are: `username`, `email`, `center` (can contain alias), `permission group`')
|
->addArgument('csvfile', InputArgument::REQUIRED, 'Path to the csv file. Columns are: `username`, `email`, `center` (can contain alias), `permission group`')
|
||||||
->addOption('grouping-centers', null, InputOption::VALUE_OPTIONAL, 'Path to a csv file to aggregate multiple centers into a single alias')
|
->addOption('grouping-centers', null, InputOption::VALUE_OPTIONAL, 'Path to a csv file to aggregate multiple centers into a single alias')
|
||||||
->addOption('dry-run', null, InputOption::VALUE_NONE, 'Do not commit the changes')
|
->addOption('dry-run', null, InputOption::VALUE_NONE, 'Do not commit the changes')
|
||||||
->addOption('csv-dump', null, InputOption::VALUE_REQUIRED, 'A path to dump a summary of the created file')
|
->addOption('csv-dump', null, InputOption::VALUE_REQUIRED, 'A path to dump a summary of the created file');
|
||||||
;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function execute(InputInterface $input, OutputInterface $output)
|
protected function execute(InputInterface $input, OutputInterface $output)
|
||||||
{
|
{
|
||||||
$this->tempOutput = $output;
|
$this->tempOutput = $output;
|
||||||
$this->tempInput = $input;
|
$this->tempInput = $input;
|
||||||
|
|
||||||
if ($input->getOption('dry-run')) {
|
if ($input->getOption('dry-run')) {
|
||||||
$this->doChanges = false;
|
$this->doChanges = false;
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->prepareWriter();
|
$this->prepareWriter();
|
||||||
|
|
||||||
if ($input->hasOption('grouping-centers')) {
|
if ($input->hasOption('grouping-centers')) {
|
||||||
$this->prepareGroupingCenters();
|
$this->prepareGroupingCenters();
|
||||||
}
|
}
|
||||||
|
|
||||||
try {
|
try {
|
||||||
$this->loadUsers();
|
$this->loadUsers();
|
||||||
}
|
}
|
||||||
@ -152,19 +104,19 @@ class ChillImportUsersCommand extends Command
|
|||||||
throw $e;
|
throw $e;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function prepareWriter()
|
protected function prepareWriter()
|
||||||
{
|
{
|
||||||
$this->output = $output = Writer::createFromPath($this->tempInput
|
$this->output = $output = Writer::createFromPath($this->tempInput
|
||||||
->getOption('csv-dump'), 'a+');
|
->getOption('csv-dump'), 'a+');
|
||||||
|
|
||||||
$output->insertOne([
|
$output->insertOne([
|
||||||
'email',
|
'email',
|
||||||
'username',
|
'username',
|
||||||
'id'
|
'id'
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function appendUserToFile(User $user)
|
protected function appendUserToFile(User $user)
|
||||||
{
|
{
|
||||||
$this->output->insertOne( [
|
$this->output->insertOne( [
|
||||||
@ -173,35 +125,35 @@ class ChillImportUsersCommand extends Command
|
|||||||
$user->getId()
|
$user->getId()
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function loadUsers()
|
protected function loadUsers()
|
||||||
{
|
{
|
||||||
$reader = Reader::createFromPath($this->tempInput->getArgument('csvfile'));
|
$reader = Reader::createFromPath($this->tempInput->getArgument('csvfile'));
|
||||||
$reader->setHeaderOffset(0);
|
$reader->setHeaderOffset(0);
|
||||||
|
|
||||||
foreach ($reader->getRecords() as $line => $r) {
|
foreach ($reader->getRecords() as $line => $r) {
|
||||||
$this->logger->debug("starting handling new line", [
|
$this->logger->debug("starting handling new line", [
|
||||||
'line' => $line
|
'line' => $line
|
||||||
]);
|
]);
|
||||||
|
|
||||||
if ($this->doesUserExists($r)) {
|
if ($this->doesUserExists($r)) {
|
||||||
$this->tempOutput->writeln(sprintf("User with username '%s' already "
|
$this->tempOutput->writeln(sprintf("User with username '%s' already "
|
||||||
. "exists, skipping", $r["username"]));
|
. "exists, skipping", $r["username"]));
|
||||||
|
|
||||||
$this->logger->info("One user already exists, skipping creation", [
|
$this->logger->info("One user already exists, skipping creation", [
|
||||||
'username_in_file' => $r['username'],
|
'username_in_file' => $r['username'],
|
||||||
'email_in_file' => $r['email'],
|
'email_in_file' => $r['email'],
|
||||||
'line' => $line
|
'line' => $line
|
||||||
]);
|
]);
|
||||||
|
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
|
|
||||||
$user = $this->createUser($line, $r);
|
$user = $this->createUser($line, $r);
|
||||||
$this->appendUserToFile($user);
|
$this->appendUserToFile($user);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function doesUserExists($data)
|
protected function doesUserExists($data)
|
||||||
{
|
{
|
||||||
if ($this->userRepository->countByUsernameOrEmail($data['username']) > 0) {
|
if ($this->userRepository->countByUsernameOrEmail($data['username']) > 0) {
|
||||||
@ -211,10 +163,10 @@ class ChillImportUsersCommand extends Command
|
|||||||
if ($this->userRepository->countByUsernameOrEmail($data['email']) > 0) {
|
if ($this->userRepository->countByUsernameOrEmail($data['email']) > 0) {
|
||||||
return true;
|
return true;
|
||||||
}
|
}
|
||||||
|
|
||||||
return false;
|
return false;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function createUser($offset, $data)
|
protected function createUser($offset, $data)
|
||||||
{
|
{
|
||||||
$user = new User();
|
$user = new User();
|
||||||
@ -222,41 +174,41 @@ class ChillImportUsersCommand extends Command
|
|||||||
->setEmail(\trim($data['email']))
|
->setEmail(\trim($data['email']))
|
||||||
->setUsername(\trim($data['username']))
|
->setUsername(\trim($data['username']))
|
||||||
->setEnabled(true)
|
->setEnabled(true)
|
||||||
->setPassword($this->passwordEncoder->encodePassword($user,
|
->setPassword($this->passwordEncoder->encodePassword($user,
|
||||||
\bin2hex(\random_bytes(32))))
|
\bin2hex(\random_bytes(32))))
|
||||||
;
|
;
|
||||||
|
|
||||||
$errors = $this->validator->validate($user);
|
$errors = $this->validator->validate($user);
|
||||||
|
|
||||||
if ($errors->count() > 0) {
|
if ($errors->count() > 0) {
|
||||||
$errorMessages = $this->concatenateViolations($errors);
|
$errorMessages = $this->concatenateViolations($errors);
|
||||||
|
|
||||||
$this->tempOutput->writeln(sprintf("%d errors found with user with username \"%s\" at line %d", $errors->count(), $data['username'], $offset));
|
$this->tempOutput->writeln(sprintf("%d errors found with user with username \"%s\" at line %d", $errors->count(), $data['username'], $offset));
|
||||||
$this->tempOutput->writeln($errorMessages);
|
$this->tempOutput->writeln($errorMessages);
|
||||||
|
|
||||||
throw new \RuntimeException("Found errors while creating an user. "
|
throw new \RuntimeException("Found errors while creating an user. "
|
||||||
. "Watch messages in command output");
|
. "Watch messages in command output");
|
||||||
}
|
}
|
||||||
|
|
||||||
$pgs = $this->getPermissionGroup($data['permission group']);
|
$pgs = $this->getPermissionGroup($data['permission group']);
|
||||||
$centers = $this->getCenters($data['center']);
|
$centers = $this->getCenters($data['center']);
|
||||||
|
|
||||||
foreach($pgs as $pg) {
|
foreach($pgs as $pg) {
|
||||||
foreach ($centers as $center) {
|
foreach ($centers as $center) {
|
||||||
$groupcenter = $this->createOrGetGroupCenter($center, $pg);
|
$groupcenter = $this->createOrGetGroupCenter($center, $pg);
|
||||||
|
|
||||||
if (FALSE === $user->getGroupCenters()->contains($groupcenter)) {
|
if (FALSE === $user->getGroupCenters()->contains($groupcenter)) {
|
||||||
$user->addGroupCenter($groupcenter);
|
$user->addGroupCenter($groupcenter);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if ($this->doChanges) {
|
if ($this->doChanges) {
|
||||||
$this->em->persist($user);
|
$this->em->persist($user);
|
||||||
$this->em->flush();
|
$this->em->flush();
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->logger->notice("Create user", [
|
$this->logger->notice("Create user", [
|
||||||
'username' => $user->getUsername(),
|
'username' => $user->getUsername(),
|
||||||
'id' => $user->getId(),
|
'id' => $user->getId(),
|
||||||
@ -265,65 +217,58 @@ class ChillImportUsersCommand extends Command
|
|||||||
|
|
||||||
return $user;
|
return $user;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function getPermissionGroup($alias)
|
protected function getPermissionGroup($alias)
|
||||||
{
|
{
|
||||||
if (\array_key_exists($alias, $this->permissionGroups)) {
|
if (\array_key_exists($alias, $this->permissionGroups)) {
|
||||||
return $this->permissionGroups[$alias];
|
return $this->permissionGroups[$alias];
|
||||||
}
|
}
|
||||||
|
|
||||||
$permissionGroupsByName = [];
|
$permissionGroupsByName = [];
|
||||||
|
|
||||||
foreach($this->em->getRepository(PermissionsGroup::class)
|
foreach($this->em->getRepository(PermissionsGroup::class)
|
||||||
->findAll() as $permissionGroup) {
|
->findAll() as $permissionGroup) {
|
||||||
$permissionGroupsByName[$permissionGroup->getName()] = $permissionGroup;
|
$permissionGroupsByName[$permissionGroup->getName()] = $permissionGroup;
|
||||||
}
|
}
|
||||||
|
|
||||||
if (count($permissionGroupsByName) === 0) {
|
if (count($permissionGroupsByName) === 0) {
|
||||||
throw new \RuntimeException("no permission groups found. Create them "
|
throw new \RuntimeException("no permission groups found. Create them "
|
||||||
. "before importing users");
|
. "before importing users");
|
||||||
}
|
}
|
||||||
|
|
||||||
$question = new ChoiceQuestion("To which permission groups associate with \"$alias\" ?",
|
$question = new ChoiceQuestion("To which permission groups associate with \"$alias\" ?",
|
||||||
\array_keys($permissionGroupsByName));
|
\array_keys($permissionGroupsByName));
|
||||||
$question
|
$question
|
||||||
->setMultiselect(true)
|
->setMultiselect(true)
|
||||||
->setAutocompleterValues(\array_keys($permissionGroupsByName))
|
->setAutocompleterValues(\array_keys($permissionGroupsByName))
|
||||||
->setNormalizer(function($value) {
|
->setNormalizer(function($value) {
|
||||||
if (NULL === $value) { return ''; }
|
if (NULL === $value) { return ''; }
|
||||||
|
|
||||||
return \trim($value);
|
return \trim($value);
|
||||||
})
|
})
|
||||||
;
|
;
|
||||||
$helper = $this->getHelper('question');
|
$helper = $this->getHelper('question');
|
||||||
|
|
||||||
$keys = $helper->ask($this->tempInput, $this->tempOutput, $question);
|
$keys = $helper->ask($this->tempInput, $this->tempOutput, $question);
|
||||||
|
|
||||||
$this->tempOutput->writeln("You have chosen ".\implode(", ", $keys));
|
$this->tempOutput->writeln("You have chosen ".\implode(", ", $keys));
|
||||||
|
|
||||||
if ($helper->ask($this->tempInput, $this->tempOutput,
|
if ($helper->ask($this->tempInput, $this->tempOutput,
|
||||||
new ConfirmationQuestion("Are you sure ?", true))) {
|
new ConfirmationQuestion("Are you sure ?", true))) {
|
||||||
|
|
||||||
foreach ($keys as $key) {
|
foreach ($keys as $key) {
|
||||||
$this->permissionGroups[$alias][] = $permissionGroupsByName[$key];
|
$this->permissionGroups[$alias][] = $permissionGroupsByName[$key];
|
||||||
}
|
}
|
||||||
|
|
||||||
return $this->permissionGroups[$alias];
|
return $this->permissionGroups[$alias];
|
||||||
} else {
|
|
||||||
$this->logger->error("Error while responding to a a question");
|
|
||||||
|
|
||||||
$this->tempOutput("Ok, I accept, but I do not know what to do. Please try again.");
|
|
||||||
|
|
||||||
throw new \RuntimeException("Error while responding to a question");
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
$this->logger->error('Error while responding to a a question');
|
||||||
|
$this->tempOutput->writeln('Ok, I accept, but I do not know what to do. Please try again.');
|
||||||
|
|
||||||
|
throw new \RuntimeException('Error while responding to a question');
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @param Center $center
|
|
||||||
* @param \Chill\MainBundle\Command\PermissionGroup $pg
|
|
||||||
* @return GroupCenter
|
|
||||||
*/
|
|
||||||
protected function createOrGetGroupCenter(Center $center, PermissionsGroup $pg): GroupCenter
|
protected function createOrGetGroupCenter(Center $center, PermissionsGroup $pg): GroupCenter
|
||||||
{
|
{
|
||||||
if (\array_key_exists($center->getId(), $this->groupCenters)) {
|
if (\array_key_exists($center->getId(), $this->groupCenters)) {
|
||||||
@ -331,36 +276,36 @@ class ChillImportUsersCommand extends Command
|
|||||||
return $this->groupCenters[$center->getId()][$pg->getId()];
|
return $this->groupCenters[$center->getId()][$pg->getId()];
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
$repository = $this->em->getRepository(GroupCenter::class);
|
$repository = $this->em->getRepository(GroupCenter::class);
|
||||||
|
|
||||||
$groupCenter = $repository->findOneBy(array(
|
$groupCenter = $repository->findOneBy(array(
|
||||||
'center' => $center,
|
'center' => $center,
|
||||||
'permissionsGroup' => $pg
|
'permissionsGroup' => $pg
|
||||||
));
|
));
|
||||||
|
|
||||||
if ($groupCenter === NULL) {
|
if ($groupCenter === NULL) {
|
||||||
$groupCenter = new GroupCenter();
|
$groupCenter = new GroupCenter();
|
||||||
$groupCenter
|
$groupCenter
|
||||||
->setCenter($center)
|
->setCenter($center)
|
||||||
->setPermissionsGroup($pg)
|
->setPermissionsGroup($pg)
|
||||||
;
|
;
|
||||||
|
|
||||||
$this->em->persist($groupCenter);
|
$this->em->persist($groupCenter);
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->groupCenters[$center->getId()][$pg->getId()] = $groupCenter;
|
$this->groupCenters[$center->getId()][$pg->getId()] = $groupCenter;
|
||||||
|
|
||||||
return $groupCenter;
|
return $groupCenter;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function prepareGroupingCenters()
|
protected function prepareGroupingCenters()
|
||||||
{
|
{
|
||||||
$reader = Reader::createFromPath($this->tempInput->getOption('grouping-centers'));
|
$reader = Reader::createFromPath($this->tempInput->getOption('grouping-centers'));
|
||||||
$reader->setHeaderOffset(0);
|
$reader->setHeaderOffset(0);
|
||||||
|
|
||||||
foreach ($reader->getRecords() as $r) {
|
foreach ($reader->getRecords() as $r) {
|
||||||
$this->centers[$r['alias']] =
|
$this->centers[$r['alias']] =
|
||||||
\array_merge(
|
\array_merge(
|
||||||
$this->centers[$r['alias']] ?? [],
|
$this->centers[$r['alias']] ?? [],
|
||||||
$this->getCenters($r['center']
|
$this->getCenters($r['center']
|
||||||
@ -368,18 +313,18 @@ class ChillImportUsersCommand extends Command
|
|||||||
);
|
);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* return a list of centers matching the name of alias.
|
* return a list of centers matching the name of alias.
|
||||||
*
|
*
|
||||||
* If the name match one center, this center is returned in an array.
|
* If the name match one center, this center is returned in an array.
|
||||||
*
|
*
|
||||||
* If the name match an alias, the centers corresponding to the alias are
|
* If the name match an alias, the centers corresponding to the alias are
|
||||||
* returned in an array.
|
* returned in an array.
|
||||||
*
|
*
|
||||||
* If the center is not found or alias is not created, a new center is created
|
* If the center is not found or alias is not created, a new center is created
|
||||||
* and suggested to user
|
* and suggested to user
|
||||||
*
|
*
|
||||||
* @param string $name the name of the center or the alias regrouping center
|
* @param string $name the name of the center or the alias regrouping center
|
||||||
* @return Center[]
|
* @return Center[]
|
||||||
*/
|
*/
|
||||||
@ -387,62 +332,62 @@ class ChillImportUsersCommand extends Command
|
|||||||
{
|
{
|
||||||
// sanitize
|
// sanitize
|
||||||
$name = \trim($name);
|
$name = \trim($name);
|
||||||
|
|
||||||
if (\array_key_exists($name, $this->centers)) {
|
if (\array_key_exists($name, $this->centers)) {
|
||||||
return $this->centers[$name];
|
return $this->centers[$name];
|
||||||
}
|
}
|
||||||
|
|
||||||
// search for a center with given name
|
// search for a center with given name
|
||||||
$center = $this->em->getRepository(Center::class)
|
$center = $this->em->getRepository(Center::class)
|
||||||
->findOneByName($name);
|
->findOneByName($name);
|
||||||
|
|
||||||
if ($center instanceof Center) {
|
if ($center instanceof Center) {
|
||||||
$this->centers[$name] = [$center];
|
$this->centers[$name] = [$center];
|
||||||
|
|
||||||
return $this->centers[$name];
|
return $this->centers[$name];
|
||||||
}
|
}
|
||||||
|
|
||||||
// suggest and create
|
// suggest and create
|
||||||
$center = (new Center())
|
$center = (new Center())
|
||||||
->setName($name);
|
->setName($name);
|
||||||
|
|
||||||
$this->tempOutput->writeln("Center with name \"$name\" not found.");
|
$this->tempOutput->writeln("Center with name \"$name\" not found.");
|
||||||
$qFormatter = $this->getHelper('question');
|
$qFormatter = $this->getHelper('question');
|
||||||
$question = new ConfirmationQuestion("Create a center with name \"$name\" ?", true);
|
$question = new ConfirmationQuestion("Create a center with name \"$name\" ?", true);
|
||||||
|
|
||||||
if ($qFormatter->ask($this->tempInput, $this->tempOutput, $question)) {
|
if ($qFormatter->ask($this->tempInput, $this->tempOutput, $question)) {
|
||||||
$this->centers[$name] = [ $center ];
|
$this->centers[$name] = [ $center ];
|
||||||
|
|
||||||
$errors = $this->validator->validate($center);
|
$errors = $this->validator->validate($center);
|
||||||
|
|
||||||
if ($errors->count() > 0) {
|
if ($errors->count() > 0) {
|
||||||
$errorMessages = $this->concatenateViolations($errors);
|
$errorMessages = $this->concatenateViolations($errors);
|
||||||
|
|
||||||
$this->tempOutput->writeln(sprintf("%d errors found with center with name \"%s\"", $errors->count(), $name));
|
$this->tempOutput->writeln(sprintf("%d errors found with center with name \"%s\"", $errors->count(), $name));
|
||||||
$this->tempOutput->writeln($errorMessages);
|
$this->tempOutput->writeln($errorMessages);
|
||||||
|
|
||||||
throw new \RuntimeException("Found errors while creating one center. "
|
throw new \RuntimeException("Found errors while creating one center. "
|
||||||
. "Watch messages in command output");
|
. "Watch messages in command output");
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->em->persist($center);
|
$this->em->persist($center);
|
||||||
|
|
||||||
return $this->centers[$name];
|
return $this->centers[$name];
|
||||||
}
|
}
|
||||||
|
|
||||||
return null;
|
return null;
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function concatenateViolations(ConstraintViolationListInterface $list)
|
protected function concatenateViolations(ConstraintViolationListInterface $list)
|
||||||
{
|
{
|
||||||
$str = [];
|
$str = [];
|
||||||
|
|
||||||
foreach ($list as $e) {
|
foreach ($list as $e) {
|
||||||
/* @var $e \Symfony\Component\Validator\ConstraintViolationInterface */
|
/* @var $e \Symfony\Component\Validator\ConstraintViolationInterface */
|
||||||
$str[] = $e->getMessage();
|
$str[] = $e->getMessage();
|
||||||
}
|
}
|
||||||
|
|
||||||
return \implode(";", $str);
|
return \implode(";", $str);
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -1,20 +1,12 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\MainBundle\Controller;
|
namespace Chill\MainBundle\Controller;
|
||||||
|
|
||||||
use Chill\MainBundle\CRUD\Controller\CRUDController;
|
use Chill\MainBundle\CRUD\Controller\CRUDController;
|
||||||
use Chill\MainBundle\Entity\Country;
|
|
||||||
use Chill\MainBundle\Pagination\PaginatorFactory;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
*
|
|
||||||
*/
|
|
||||||
class AdminCountryCRUDController extends CRUDController
|
class AdminCountryCRUDController extends CRUDController
|
||||||
{
|
{
|
||||||
|
|
||||||
function __construct(PaginatorFactory $paginator)
|
|
||||||
{
|
|
||||||
$this->paginatorFactory = $paginator;
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
@ -136,20 +136,17 @@ class UserController extends CRUDController
|
|||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
private function createEditPasswordForm(User $user): FormInterface
|
||||||
*
|
|
||||||
*
|
|
||||||
* @param User $user
|
|
||||||
* @return \Symfony\Component\Form\Form
|
|
||||||
*/
|
|
||||||
private function createEditPasswordForm(User $user)
|
|
||||||
{
|
{
|
||||||
return $this->createForm(UserPasswordType::class, null, array(
|
return $this->createForm(
|
||||||
'user' => $user
|
UserPasswordType::class,
|
||||||
))
|
null,
|
||||||
|
[
|
||||||
|
'user' => $user
|
||||||
|
]
|
||||||
|
)
|
||||||
->add('submit', SubmitType::class, array('label' => 'Change password'))
|
->add('submit', SubmitType::class, array('label' => 'Change password'))
|
||||||
->remove('actual_password')
|
->remove('actual_password');
|
||||||
;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
|
@ -1,23 +1,5 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/*
|
|
||||||
* Chill is a suite of a modules, Chill is a software for social workers
|
|
||||||
* Copyright (C) 2014, Champs Libres Cooperative SCRLFS, <http://www.champs-libres.coop>
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU Affero General Public License as
|
|
||||||
* published by the Free Software Foundation, either version 3 of the
|
|
||||||
* License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU Affero General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Affero General Public License
|
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Chill\MainBundle\Entity;
|
namespace Chill\MainBundle\Entity;
|
||||||
|
|
||||||
use Doctrine\ORM\Mapping as ORM;
|
use Doctrine\ORM\Mapping as ORM;
|
||||||
@ -28,38 +10,30 @@ use Doctrine\Common\Collections\ArrayCollection;
|
|||||||
* @ORM\Entity
|
* @ORM\Entity
|
||||||
* @ORM\Table(name="role_scopes")
|
* @ORM\Table(name="role_scopes")
|
||||||
* @ORM\Cache(usage="NONSTRICT_READ_WRITE", region="acl_cache_region")
|
* @ORM\Cache(usage="NONSTRICT_READ_WRITE", region="acl_cache_region")
|
||||||
*
|
|
||||||
* @author Julien Fastré <julien.fastre@champs-libres.coop>
|
|
||||||
*/
|
*/
|
||||||
class RoleScope
|
class RoleScope
|
||||||
{
|
{
|
||||||
/**
|
/**
|
||||||
* @var integer
|
|
||||||
*
|
|
||||||
* @ORM\Id
|
* @ORM\Id
|
||||||
* @ORM\Column(name="id", type="integer")
|
* @ORM\Column(name="id", type="integer")
|
||||||
* @ORM\GeneratedValue(strategy="AUTO")
|
* @ORM\GeneratedValue(strategy="AUTO")
|
||||||
*/
|
*/
|
||||||
private $id;
|
private int $id;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var string
|
|
||||||
*
|
|
||||||
* @ORM\Column(type="string", length=255)
|
* @ORM\Column(type="string", length=255)
|
||||||
*/
|
*/
|
||||||
private $role;
|
private string $role;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var Scope
|
|
||||||
*
|
|
||||||
* @ORM\ManyToOne(
|
* @ORM\ManyToOne(
|
||||||
* targetEntity="Chill\MainBundle\Entity\Scope",
|
* targetEntity="Chill\MainBundle\Entity\Scope",
|
||||||
* inversedBy="roleScopes")
|
* inversedBy="roleScopes")
|
||||||
* @ORM\JoinColumn(nullable=true, name="scope_id")
|
* @ORM\JoinColumn(nullable=true, name="scope_id")
|
||||||
* @ORM\Cache(usage="NONSTRICT_READ_WRITE")
|
* @ORM\Cache(usage="NONSTRICT_READ_WRITE")
|
||||||
*/
|
*/
|
||||||
private $scope;
|
private Scope $scope;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @var Collection
|
* @var Collection
|
||||||
*
|
*
|
||||||
@ -68,16 +42,14 @@ class RoleScope
|
|||||||
* mappedBy="roleScopes")
|
* mappedBy="roleScopes")
|
||||||
*/
|
*/
|
||||||
private $permissionsGroups;
|
private $permissionsGroups;
|
||||||
|
|
||||||
|
private bool $new;
|
||||||
/**
|
|
||||||
* RoleScope constructor.
|
|
||||||
*/
|
|
||||||
public function __construct() {
|
public function __construct() {
|
||||||
$this->new = true;
|
$this->new = true;
|
||||||
$this->permissionsGroups = new ArrayCollection();
|
$this->permissionsGroups = new ArrayCollection();
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @return int
|
* @return int
|
||||||
*/
|
*/
|
||||||
@ -101,7 +73,7 @@ class RoleScope
|
|||||||
{
|
{
|
||||||
return $this->scope;
|
return $this->scope;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @param type $role
|
* @param type $role
|
||||||
* @return RoleScope
|
* @return RoleScope
|
||||||
@ -120,7 +92,7 @@ class RoleScope
|
|||||||
public function setScope(Scope $scope = null)
|
public function setScope(Scope $scope = null)
|
||||||
{
|
{
|
||||||
$this->scope = $scope;
|
$this->scope = $scope;
|
||||||
|
|
||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,50 +1,23 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/*
|
declare(strict_types=1);
|
||||||
* Chill is a software for social workers
|
|
||||||
* Copyright (C) 2016 Champs-Libres Coopérative <info@champs-libres.coop>
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU Affero General Public License as published by
|
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
|
||||||
* (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU Affero General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Affero General Public License
|
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Chill\MainBundle\Pagination;
|
namespace Chill\MainBundle\Pagination;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* PageGenerator associated with a Paginator
|
* PageGenerator associated with a Paginator.
|
||||||
*
|
|
||||||
* @author Julien Fastré <julien.fastre@champs-libres.coop>
|
|
||||||
* @author Champs Libres <info@champs-libres.coop>
|
|
||||||
*/
|
*/
|
||||||
class PageGenerator implements \Iterator
|
class PageGenerator implements \Iterator
|
||||||
{
|
{
|
||||||
/**
|
protected Paginator $paginator;
|
||||||
*
|
|
||||||
* @var Paginator
|
protected int $current = 1;
|
||||||
*/
|
|
||||||
protected $paginator;
|
public function __construct(Paginator $paginator)
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var int
|
|
||||||
*/
|
|
||||||
protected $current = 1;
|
|
||||||
|
|
||||||
public function __construct(Paginator $paginator)
|
|
||||||
{
|
{
|
||||||
$this->paginator = $paginator;;
|
$this->paginator = $paginator;;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function current()
|
public function current()
|
||||||
{
|
{
|
||||||
return $this->paginator->getPage($current);
|
return $this->paginator->getPage($current);
|
||||||
@ -67,7 +40,7 @@ class PageGenerator implements \Iterator
|
|||||||
|
|
||||||
public function valid()
|
public function valid()
|
||||||
{
|
{
|
||||||
return $this->current > 0
|
return $this->current > 0
|
||||||
&& $this->current <= $this->paginator->countPages();
|
&& $this->current <= $this->paginator->countPages();
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\MainBundle\Routing;
|
namespace Chill\MainBundle\Routing;
|
||||||
|
|
||||||
use Symfony\Component\Routing\RouteCollection;
|
use Symfony\Component\Routing\RouteCollection;
|
||||||
@ -8,43 +10,28 @@ use Knp\Menu\FactoryInterface;
|
|||||||
use Knp\Menu\ItemInterface;
|
use Knp\Menu\ItemInterface;
|
||||||
use Symfony\Component\Translation\TranslatorInterface;
|
use Symfony\Component\Translation\TranslatorInterface;
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* This class permit to build menu from the routing information
|
* This class permit to build menu from the routing information
|
||||||
* stored in each bundle.
|
* stored in each bundle.
|
||||||
*
|
*
|
||||||
* how to must come here FIXME
|
* how to must come here FIXME
|
||||||
*
|
*
|
||||||
* @author julien
|
* @author julien
|
||||||
*/
|
*/
|
||||||
class MenuComposer
|
class MenuComposer
|
||||||
{
|
{
|
||||||
|
|
||||||
/**
|
private RouterInterface $router;
|
||||||
*
|
|
||||||
* @var RouterInterface
|
private FactoryInterface $menuFactory;
|
||||||
*/
|
|
||||||
private $router;
|
private TranslatorInterface $translator;
|
||||||
|
|
||||||
/**
|
private array $localMenuBuilders = [];
|
||||||
*
|
|
||||||
* @var FactoryInterface
|
private RouteCollection $routeCollection;
|
||||||
*/
|
|
||||||
private $menuFactory;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var TranslatorInterface
|
|
||||||
*/
|
|
||||||
private $translator;
|
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var
|
|
||||||
*/
|
|
||||||
private $localMenuBuilders = [];
|
|
||||||
|
|
||||||
|
|
||||||
function __construct(
|
function __construct(
|
||||||
RouterInterface $router,
|
RouterInterface $router,
|
||||||
FactoryInterface $menuFactory,
|
FactoryInterface $menuFactory,
|
||||||
@ -60,7 +47,7 @@ class MenuComposer
|
|||||||
* This function is needed for testing purpose: routeCollection is not
|
* This function is needed for testing purpose: routeCollection is not
|
||||||
* available as a service (RouterInterface is provided as a service and
|
* available as a service (RouterInterface is provided as a service and
|
||||||
* added to this class as paramater in __construct)
|
* added to this class as paramater in __construct)
|
||||||
*
|
*
|
||||||
* @param RouteCollection $routeCollection
|
* @param RouteCollection $routeCollection
|
||||||
*/
|
*/
|
||||||
public function setRouteCollection(RouteCollection $routeCollection)
|
public function setRouteCollection(RouteCollection $routeCollection)
|
||||||
@ -71,7 +58,7 @@ class MenuComposer
|
|||||||
/**
|
/**
|
||||||
* Return an array of routes added to $menuId,
|
* Return an array of routes added to $menuId,
|
||||||
* The array is aimed to build route with MenuTwig
|
* The array is aimed to build route with MenuTwig
|
||||||
*
|
*
|
||||||
* @param string $menuId
|
* @param string $menuId
|
||||||
* @param array $parameters see https://redmine.champs-libres.coop/issues/179
|
* @param array $parameters see https://redmine.champs-libres.coop/issues/179
|
||||||
* @return array
|
* @return array
|
||||||
@ -83,7 +70,7 @@ class MenuComposer
|
|||||||
|
|
||||||
foreach ($routeCollection->all() as $routeKey => $route) {
|
foreach ($routeCollection->all() as $routeKey => $route) {
|
||||||
if ($route->hasOption('menus')) {
|
if ($route->hasOption('menus')) {
|
||||||
|
|
||||||
if (array_key_exists($menuId, $route->getOption('menus'))) {
|
if (array_key_exists($menuId, $route->getOption('menus'))) {
|
||||||
$route = $route->getOption('menus')[$menuId];
|
$route = $route->getOption('menus')[$menuId];
|
||||||
|
|
||||||
@ -101,12 +88,12 @@ class MenuComposer
|
|||||||
|
|
||||||
return $routes;
|
return $routes;
|
||||||
}
|
}
|
||||||
|
|
||||||
public function getMenuFor($menuId, array $parameters = array())
|
public function getMenuFor($menuId, array $parameters = array())
|
||||||
{
|
{
|
||||||
$routes = $this->getRoutesFor($menuId, $parameters);
|
$routes = $this->getRoutesFor($menuId, $parameters);
|
||||||
$menu = $this->menuFactory->createItem($menuId);
|
$menu = $this->menuFactory->createItem($menuId);
|
||||||
|
|
||||||
// build menu from routes
|
// build menu from routes
|
||||||
foreach ($routes as $order => $route) {
|
foreach ($routes as $order => $route) {
|
||||||
$menu->addChild($this->translator->trans($route['label']), [
|
$menu->addChild($this->translator->trans($route['label']), [
|
||||||
@ -121,24 +108,24 @@ class MenuComposer
|
|||||||
])
|
])
|
||||||
;
|
;
|
||||||
}
|
}
|
||||||
|
|
||||||
if ($this->hasLocalMenuBuilder($menuId)) {
|
if ($this->hasLocalMenuBuilder($menuId)) {
|
||||||
foreach ($this->localMenuBuilders[$menuId] as $builder) {
|
foreach ($this->localMenuBuilders[$menuId] as $builder) {
|
||||||
/* @var $builder LocalMenuBuilderInterface */
|
/* @var $builder LocalMenuBuilderInterface */
|
||||||
$builder->buildMenu($menuId, $menu, $parameters['args']);
|
$builder->buildMenu($menuId, $menu, $parameters['args']);
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->reorderMenu($menu);
|
$this->reorderMenu($menu);
|
||||||
|
|
||||||
return $menu;
|
return $menu;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* recursive function to resolve the order of a array of routes.
|
* recursive function to resolve the order of a array of routes.
|
||||||
* If the order chosen in routing.yml is already in used, find the
|
* If the order chosen in routing.yml is already in used, find the
|
||||||
* first next order available.
|
* first next order available.
|
||||||
*
|
*
|
||||||
* @param array $routes the routes previously added
|
* @param array $routes the routes previously added
|
||||||
* @param int $order
|
* @param int $order
|
||||||
* @return int
|
* @return int
|
||||||
@ -151,41 +138,41 @@ class MenuComposer
|
|||||||
return $order;
|
return $order;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
private function reorderMenu(ItemInterface $menu)
|
private function reorderMenu(ItemInterface $menu)
|
||||||
{
|
{
|
||||||
$ordered = [];
|
$ordered = [];
|
||||||
$unordered = [];
|
$unordered = [];
|
||||||
|
|
||||||
foreach ($menu->getChildren() as $name => $item) {
|
foreach ($menu->getChildren() as $name => $item) {
|
||||||
$order = $item->getExtra('order');
|
$order = $item->getExtra('order');
|
||||||
|
|
||||||
if ($order !== null) {
|
if ($order !== null) {
|
||||||
$ordered[$this->resolveOrder($ordered, $order)] = $name;
|
$ordered[$this->resolveOrder($ordered, $order)] = $name;
|
||||||
} else {
|
} else {
|
||||||
$unordered = $name;
|
$unordered = $name;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
ksort($ordered);
|
ksort($ordered);
|
||||||
|
|
||||||
$menus = \array_merge(\array_values($ordered), $unordered);
|
$menus = \array_merge(\array_values($ordered), $unordered);
|
||||||
$menu->reorderChildren($menus);
|
$menu->reorderChildren($menus);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public function addLocalMenuBuilder(LocalMenuBuilderInterface $menuBuilder, $menuId)
|
public function addLocalMenuBuilder(LocalMenuBuilderInterface $menuBuilder, $menuId)
|
||||||
{
|
{
|
||||||
$this->localMenuBuilders[$menuId][] = $menuBuilder;
|
$this->localMenuBuilders[$menuId][] = $menuBuilder;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Return true if the menu has at least one builder.
|
* Return true if the menu has at least one builder.
|
||||||
*
|
*
|
||||||
* This function is a helper to determine if the method `getMenuFor`
|
* This function is a helper to determine if the method `getMenuFor`
|
||||||
* should be used, or `getRouteFor`. The method `getMenuFor` should be used
|
* should be used, or `getRouteFor`. The method `getMenuFor` should be used
|
||||||
* if the result is true (it **does** exists at least one menu builder.
|
* if the result is true (it **does** exists at least one menu builder.
|
||||||
*
|
*
|
||||||
* @param string $menuId
|
* @param string $menuId
|
||||||
* @return bool
|
* @return bool
|
||||||
*/
|
*/
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\MainBundle\Search;
|
namespace Chill\MainBundle\Search;
|
||||||
|
|
||||||
use Symfony\Component\Serializer\Annotation as Serializer;
|
use Symfony\Component\Serializer\Annotation as Serializer;
|
||||||
@ -10,6 +12,8 @@ class SearchApiResult
|
|||||||
|
|
||||||
private $result;
|
private $result;
|
||||||
|
|
||||||
|
private float $relevance;
|
||||||
|
|
||||||
public function __construct(float $relevance)
|
public function __construct(float $relevance)
|
||||||
{
|
{
|
||||||
$this->relevance = $relevance;
|
$this->relevance = $relevance;
|
||||||
@ -20,7 +24,7 @@ class SearchApiResult
|
|||||||
$this->result = $result;
|
$this->result = $result;
|
||||||
|
|
||||||
return $this;
|
return $this;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* @Serializer\Groups({"read"})
|
* @Serializer\Groups({"read"})
|
||||||
|
@ -1,34 +1,17 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/*
|
declare(strict_types=1);
|
||||||
* Copyright (C) 2015 Julien Fastré <julien.fastre@champs-libres.coop>
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU Affero General Public License as published by
|
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
|
||||||
* (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU Affero General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Affero General Public License
|
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Chill\MainBundle\Security\Authorization;
|
namespace Chill\MainBundle\Security\Authorization;
|
||||||
|
|
||||||
use Symfony\Component\Security\Core\Authorization\Voter\Voter;
|
use Symfony\Component\Security\Core\Authorization\Voter\Voter;
|
||||||
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
|
use Symfony\Component\Security\Core\Authentication\Token\TokenInterface;
|
||||||
|
use Symfony\Component\Security\Core\User\UserInterface;
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Voter for Chill software.
|
* Voter for Chill software.
|
||||||
*
|
*
|
||||||
* This abstract Voter provide generic methods to handle object specific to Chill
|
* This abstract Voter provide generic methods to handle object specific to Chill
|
||||||
*
|
|
||||||
*
|
|
||||||
* @author Julien Fastré <julien.fastre@champs-libres.coop>
|
|
||||||
*/
|
*/
|
||||||
abstract class AbstractChillVoter extends Voter implements ChillVoterInterface
|
abstract class AbstractChillVoter extends Voter implements ChillVoterInterface
|
||||||
{
|
{
|
||||||
@ -39,6 +22,8 @@ abstract class AbstractChillVoter extends Voter implements ChillVoterInterface
|
|||||||
. 'getSupportedAttributes and getSupportedClasses methods.',
|
. 'getSupportedAttributes and getSupportedClasses methods.',
|
||||||
E_USER_DEPRECATED);
|
E_USER_DEPRECATED);
|
||||||
|
|
||||||
|
// @TODO: getSupportedAttributes() should be created in here and made abstract or in ChillVoterInterface.
|
||||||
|
// @TODO: getSupportedClasses() should be created in here and made abstract or in ChillVoterInterface.
|
||||||
return \in_array($attribute, $this->getSupportedAttributes($attribute))
|
return \in_array($attribute, $this->getSupportedAttributes($attribute))
|
||||||
&& \in_array(\get_class($subject), $this->getSupportedClasses());
|
&& \in_array(\get_class($subject), $this->getSupportedClasses());
|
||||||
}
|
}
|
||||||
@ -49,7 +34,7 @@ abstract class AbstractChillVoter extends Voter implements ChillVoterInterface
|
|||||||
. 'methods introduced by Symfony 3.0, and do not rely on '
|
. 'methods introduced by Symfony 3.0, and do not rely on '
|
||||||
. 'isGranted method', E_USER_DEPRECATED);
|
. 'isGranted method', E_USER_DEPRECATED);
|
||||||
|
|
||||||
|
// @TODO: isGranted() should be created in here and made abstract or in ChillVoterInterface.
|
||||||
return $this->isGranted($attribute, $subject, $token->getUser());
|
return $this->isGranted($attribute, $subject, $token->getUser());
|
||||||
}
|
}
|
||||||
|
|
||||||
}
|
}
|
||||||
|
@ -1,87 +1,62 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/*
|
declare(strict_types=1);
|
||||||
* Copyright (C) 2015 Champs-Libres Coopérative <info@champs-libres.coop>
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU Affero General Public License as published by
|
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
|
||||||
* (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU Affero General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Affero General Public License
|
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Chill\PersonBundle\Controller;
|
namespace Chill\PersonBundle\Controller;
|
||||||
|
|
||||||
|
use Chill\MainBundle\Security\Authorization\AuthorizationHelperInterface;
|
||||||
|
use Chill\PersonBundle\Entity\Person;
|
||||||
use Chill\PersonBundle\Privacy\PrivacyEvent;
|
use Chill\PersonBundle\Privacy\PrivacyEvent;
|
||||||
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
|
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
|
||||||
use Symfony\Component\EventDispatcher\EventDispatcherInterface;
|
use Symfony\Component\EventDispatcher\EventDispatcherInterface;
|
||||||
use Symfony\Component\HttpFoundation\Response;
|
|
||||||
use Symfony\Component\HttpFoundation\Request;
|
use Symfony\Component\HttpFoundation\Request;
|
||||||
use Chill\MainBundle\Timeline\TimelineBuilder;
|
use Chill\MainBundle\Timeline\TimelineBuilder;
|
||||||
use Chill\MainBundle\Pagination\PaginatorFactory;
|
use Chill\MainBundle\Pagination\PaginatorFactory;
|
||||||
use Chill\PersonBundle\Security\Authorization\PersonVoter;
|
use Chill\PersonBundle\Security\Authorization\PersonVoter;
|
||||||
use Chill\MainBundle\Security\Authorization\AuthorizationHelper;
|
|
||||||
use Symfony\Component\Security\Core\Role\Role;
|
|
||||||
|
|
||||||
class TimelinePersonController extends AbstractController
|
class TimelinePersonController extends AbstractController
|
||||||
{
|
{
|
||||||
|
|
||||||
protected EventDispatcherInterface $eventDispatcher;
|
protected EventDispatcherInterface $eventDispatcher;
|
||||||
|
|
||||||
protected TimelineBuilder $timelineBuilder;
|
protected TimelineBuilder $timelineBuilder;
|
||||||
|
|
||||||
protected PaginatorFactory $paginatorFactory;
|
protected PaginatorFactory $paginatorFactory;
|
||||||
|
|
||||||
/**
|
|
||||||
* TimelinePersonController constructor.
|
|
||||||
*
|
|
||||||
* @param EventDispatcherInterface $eventDispatcher
|
|
||||||
*/
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
EventDispatcherInterface $eventDispatcher,
|
EventDispatcherInterface $eventDispatcher,
|
||||||
TimelineBuilder $timelineBuilder,
|
TimelineBuilder $timelineBuilder,
|
||||||
PaginatorFactory $paginatorFactory,
|
PaginatorFactory $paginatorFactory
|
||||||
AuthorizationHelper $authorizationHelper
|
|
||||||
) {
|
) {
|
||||||
$this->eventDispatcher = $eventDispatcher;
|
$this->eventDispatcher = $eventDispatcher;
|
||||||
$this->timelineBuilder = $timelineBuilder;
|
$this->timelineBuilder = $timelineBuilder;
|
||||||
$this->paginatorFactory = $paginatorFactory;
|
$this->paginatorFactory = $paginatorFactory;
|
||||||
$this->authorizationHelper = $authorizationHelper;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public function personAction(Request $request, $person_id)
|
public function personAction(Request $request, $person_id)
|
||||||
{
|
{
|
||||||
$person = $this->getDoctrine()
|
$person = $this->getDoctrine()
|
||||||
->getRepository('ChillPersonBundle:Person')
|
->getRepository(Person::class)
|
||||||
->find($person_id);
|
->find($person_id);
|
||||||
|
|
||||||
if ($person === NULL) {
|
if ($person === NULL) {
|
||||||
throw $this->createNotFoundException();
|
throw $this->createNotFoundException();
|
||||||
}
|
}
|
||||||
|
|
||||||
$this->denyAccessUnlessGranted(PersonVoter::SEE, $person);
|
$this->denyAccessUnlessGranted(PersonVoter::SEE, $person);
|
||||||
|
|
||||||
$nbItems = $this->timelineBuilder->countItems('person',
|
$nbItems = $this->timelineBuilder->countItems('person',
|
||||||
[ 'person' => $person ]
|
[ 'person' => $person ]
|
||||||
);
|
);
|
||||||
|
|
||||||
$paginator = $this->paginatorFactory->create($nbItems);
|
$paginator = $this->paginatorFactory->create($nbItems);
|
||||||
|
|
||||||
$event = new PrivacyEvent($person, array('action' => 'timeline'));
|
$event = new PrivacyEvent($person, array('action' => 'timeline'));
|
||||||
$this->eventDispatcher->dispatch(PrivacyEvent::PERSON_PRIVACY_EVENT, $event);
|
$this->eventDispatcher->dispatch(PrivacyEvent::PERSON_PRIVACY_EVENT, $event);
|
||||||
|
|
||||||
return $this->render('ChillPersonBundle:Timeline:index.html.twig', array
|
return $this->render('ChillPersonBundle:Timeline:index.html.twig', array
|
||||||
(
|
(
|
||||||
'timeline' => $this->timelineBuilder->getTimelineHTML(
|
'timeline' => $this->timelineBuilder->getTimelineHTML(
|
||||||
'person',
|
'person',
|
||||||
array('person' => $person),
|
array('person' => $person),
|
||||||
$paginator->getCurrentPage()->getFirstItemNumber(),
|
$paginator->getCurrentPage()->getFirstItemNumber(),
|
||||||
$paginator->getItemsPerPage()
|
$paginator->getItemsPerPage()
|
||||||
|
@ -1,5 +1,7 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
|
declare(strict_types=1);
|
||||||
|
|
||||||
namespace Chill\PersonBundle\DataFixtures\ORM;
|
namespace Chill\PersonBundle\DataFixtures\ORM;
|
||||||
|
|
||||||
use Chill\PersonBundle\Entity\Person;
|
use Chill\PersonBundle\Entity\Person;
|
||||||
@ -24,6 +26,8 @@ class LoadHousehold extends Fixture implements DependentFixtureInterface
|
|||||||
|
|
||||||
private CONST NUMBER_OF_HOUSEHOLD = 10;
|
private CONST NUMBER_OF_HOUSEHOLD = 10;
|
||||||
|
|
||||||
|
private array $personIds;
|
||||||
|
|
||||||
public function __construct(MembersEditorFactory $editorFactory, EntityManagerInterface $em)
|
public function __construct(MembersEditorFactory $editorFactory, EntityManagerInterface $em)
|
||||||
{
|
{
|
||||||
$this->editorFactory = $editorFactory;
|
$this->editorFactory = $editorFactory;
|
||||||
@ -149,14 +153,14 @@ class LoadHousehold extends Fixture implements DependentFixtureInterface
|
|||||||
|
|
||||||
private function preparePersonIds()
|
private function preparePersonIds()
|
||||||
{
|
{
|
||||||
|
// @TODO: Remove this and make this service stateless
|
||||||
$this->personIds = $this->em
|
$this->personIds = $this->em
|
||||||
->createQuery('SELECT p.id FROM '.Person::class.' p '.
|
->createQuery('SELECT p.id FROM '.Person::class.' p '.
|
||||||
'JOIN p.center c '.
|
'JOIN p.center c '.
|
||||||
'WHERE c.name = :center '
|
'WHERE c.name = :center '
|
||||||
)
|
)
|
||||||
->setParameter('center', 'Center A')
|
->setParameter('center', 'Center A')
|
||||||
->getScalarResult()
|
->getScalarResult();
|
||||||
;
|
|
||||||
|
|
||||||
\shuffle($this->personIds);
|
\shuffle($this->personIds);
|
||||||
}
|
}
|
||||||
@ -169,9 +173,7 @@ class LoadHousehold extends Fixture implements DependentFixtureInterface
|
|||||||
|
|
||||||
for ($i=0; $i < $nb; $i++) {
|
for ($i=0; $i < $nb; $i++) {
|
||||||
$personId = \array_pop($this->personIds)['id'];
|
$personId = \array_pop($this->personIds)['id'];
|
||||||
$persons[] = $this->em->getRepository(Person::class)
|
$persons[] = $this->em->getRepository(Person::class)->find($personId);
|
||||||
->find($personId)
|
|
||||||
;
|
|
||||||
}
|
}
|
||||||
|
|
||||||
return $persons;
|
return $persons;
|
||||||
|
@ -1,28 +1,10 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/*
|
declare(strict_types=1);
|
||||||
* Chill is a software for social workers
|
|
||||||
*
|
|
||||||
* Copyright (C) 2014, Champs Libres Cooperative SCRLFS, <http://www.champs-libres.coop>
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU Affero General Public License as
|
|
||||||
* published by the Free Software Foundation, either version 3 of the
|
|
||||||
* License, or (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU Affero General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Affero General Public License
|
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Chill\PersonBundle\Form;
|
namespace Chill\PersonBundle\Form;
|
||||||
|
|
||||||
use Chill\MainBundle\Form\Event\CustomizeFormEvent;
|
use Chill\MainBundle\Form\Event\CustomizeFormEvent;
|
||||||
use Chill\MainBundle\Repository\CenterRepository;
|
|
||||||
use Chill\PersonBundle\Entity\Person;
|
use Chill\PersonBundle\Entity\Person;
|
||||||
use Chill\PersonBundle\Security\Authorization\PersonVoter;
|
use Chill\PersonBundle\Security\Authorization\PersonVoter;
|
||||||
use Symfony\Component\DependencyInjection\ParameterBag\ParameterBagInterface;
|
use Symfony\Component\DependencyInjection\ParameterBag\ParameterBagInterface;
|
||||||
@ -30,12 +12,9 @@ use Symfony\Component\EventDispatcher\EventDispatcherInterface;
|
|||||||
use Symfony\Component\Form\AbstractType;
|
use Symfony\Component\Form\AbstractType;
|
||||||
use Symfony\Component\Form\FormBuilderInterface;
|
use Symfony\Component\Form\FormBuilderInterface;
|
||||||
use Symfony\Component\OptionsResolver\OptionsResolver;
|
use Symfony\Component\OptionsResolver\OptionsResolver;
|
||||||
use Symfony\Component\Form\Extension\Core\DataTransformer\DateTimeToStringTransformer;
|
|
||||||
use Symfony\Component\Form\Extension\Core\Type\HiddenType;
|
|
||||||
use Chill\MainBundle\Form\Type\ChillDateType;
|
use Chill\MainBundle\Form\Type\ChillDateType;
|
||||||
use Chill\MainBundle\Form\Type\PickCenterType;
|
use Chill\MainBundle\Form\Type\PickCenterType;
|
||||||
use Chill\PersonBundle\Form\Type\GenderType;
|
use Chill\PersonBundle\Form\Type\GenderType;
|
||||||
use Chill\MainBundle\Form\Type\DataTransformer\CenterTransformer;
|
|
||||||
use Chill\PersonBundle\Config\ConfigPersonAltNamesHelper;
|
use Chill\PersonBundle\Config\ConfigPersonAltNamesHelper;
|
||||||
use Chill\PersonBundle\Form\Type\PersonAltNameType;
|
use Chill\PersonBundle\Form\Type\PersonAltNameType;
|
||||||
|
|
||||||
@ -43,27 +22,19 @@ final class CreationPersonType extends AbstractType
|
|||||||
{
|
{
|
||||||
// TODO: This is only used in test.
|
// TODO: This is only used in test.
|
||||||
// TODO: See if this is still valid and update accordingly.
|
// TODO: See if this is still valid and update accordingly.
|
||||||
const NAME = 'chill_personbundle_person_creation';
|
public const NAME = 'chill_personbundle_person_creation';
|
||||||
|
|
||||||
private CenterRepository $centerRepository;
|
private ConfigPersonAltNamesHelper $configPersonAltNamesHelper;
|
||||||
|
|
||||||
/**
|
|
||||||
*
|
|
||||||
* @var ConfigPersonAltNamesHelper
|
|
||||||
*/
|
|
||||||
protected $configPersonAltNamesHelper;
|
|
||||||
|
|
||||||
private EventDispatcherInterface $dispatcher;
|
private EventDispatcherInterface $dispatcher;
|
||||||
|
|
||||||
private bool $askCenters;
|
private bool $askCenters;
|
||||||
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
CenterRepository $centerRepository,
|
|
||||||
ConfigPersonAltNamesHelper $configPersonAltNamesHelper,
|
ConfigPersonAltNamesHelper $configPersonAltNamesHelper,
|
||||||
EventDispatcherInterface $dispatcher,
|
EventDispatcherInterface $dispatcher,
|
||||||
ParameterBagInterface $parameterBag
|
ParameterBagInterface $parameterBag
|
||||||
) {
|
) {
|
||||||
$this->centerTransformer = $centerRepository;
|
|
||||||
$this->configPersonAltNamesHelper = $configPersonAltNamesHelper;
|
$this->configPersonAltNamesHelper = $configPersonAltNamesHelper;
|
||||||
$this->dispatcher = $dispatcher;
|
$this->dispatcher = $dispatcher;
|
||||||
$this->askCenters = $parameterBag->get('chill_main')['acl']['form_show_centers'];
|
$this->askCenters = $parameterBag->get('chill_main')['acl']['form_show_centers'];
|
||||||
|
@ -1,22 +1,6 @@
|
|||||||
<?php
|
<?php
|
||||||
|
|
||||||
/*
|
declare(strict_types=1);
|
||||||
* Chill is a software for social workers
|
|
||||||
* Copyright (C) 2015 Champs Libres <info@champs-libres.coop>
|
|
||||||
*
|
|
||||||
* This program is free software: you can redistribute it and/or modify
|
|
||||||
* it under the terms of the GNU Affero General Public License as published by
|
|
||||||
* the Free Software Foundation, either version 3 of the License, or
|
|
||||||
* (at your option) any later version.
|
|
||||||
*
|
|
||||||
* This program is distributed in the hope that it will be useful,
|
|
||||||
* but WITHOUT ANY WARRANTY; without even the implied warranty of
|
|
||||||
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
|
|
||||||
* GNU Affero General Public License for more details.
|
|
||||||
*
|
|
||||||
* You should have received a copy of the GNU Affero General Public License
|
|
||||||
* along with this program. If not, see <http://www.gnu.org/licenses/>.
|
|
||||||
*/
|
|
||||||
|
|
||||||
namespace Chill\ReportBundle\Timeline;
|
namespace Chill\ReportBundle\Timeline;
|
||||||
|
|
||||||
@ -38,38 +22,39 @@ use Chill\MainBundle\Timeline\TimelineSingleQuery;
|
|||||||
*/
|
*/
|
||||||
class TimelineReportProvider implements TimelineProviderInterface
|
class TimelineReportProvider implements TimelineProviderInterface
|
||||||
{
|
{
|
||||||
|
|
||||||
protected EntityManager $em;
|
protected EntityManager $em;
|
||||||
|
|
||||||
protected AuthorizationHelper $helper;
|
protected AuthorizationHelper $helper;
|
||||||
|
|
||||||
protected CustomFieldsHelper $customFieldsHelper;
|
protected CustomFieldsHelper $customFieldsHelper;
|
||||||
|
|
||||||
protected $showEmptyValues;
|
protected bool $showEmptyValues;
|
||||||
|
|
||||||
|
private Security $security;
|
||||||
|
|
||||||
public function __construct(
|
public function __construct(
|
||||||
EntityManager $em,
|
EntityManager $em,
|
||||||
AuthorizationHelper $helper,
|
AuthorizationHelper $helper,
|
||||||
Security $security,
|
Security $security,
|
||||||
CustomFieldsHelper $customFieldsHelper,
|
CustomFieldsHelper $customFieldsHelper,
|
||||||
$showEmptyValues
|
$showEmptyValues
|
||||||
)
|
) {
|
||||||
{
|
|
||||||
$this->em = $em;
|
$this->em = $em;
|
||||||
$this->helper = $helper;
|
$this->helper = $helper;
|
||||||
$this->security = $security;
|
$this->security = $security;
|
||||||
$this->customFieldsHelper = $customFieldsHelper;
|
$this->customFieldsHelper = $customFieldsHelper;
|
||||||
$this->showEmptyValues = $showEmptyValues;
|
$this->showEmptyValues = $showEmptyValues;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* {@inheritDoc}
|
* {@inheritDoc}
|
||||||
*/
|
*/
|
||||||
public function fetchQuery($context, array $args)
|
public function fetchQuery($context, array $args)
|
||||||
{
|
{
|
||||||
$this->checkContext($context);
|
$this->checkContext($context);
|
||||||
|
|
||||||
$report = $this->em->getClassMetadata(Report::class);
|
$report = $this->em->getClassMetadata(Report::class);
|
||||||
[$where, $parameters] = $this->getWhereClause($context, $args);
|
[$where, $parameters] = $this->getWhereClause($context, $args);
|
||||||
|
|
||||||
@ -84,7 +69,7 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
'parameters' => $parameters
|
'parameters' => $parameters
|
||||||
]);
|
]);
|
||||||
}
|
}
|
||||||
|
|
||||||
private function getWhereClause(string $context, array $args): array
|
private function getWhereClause(string $context, array $args): array
|
||||||
{
|
{
|
||||||
switch ($context) {
|
switch ($context) {
|
||||||
@ -102,7 +87,7 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
$report = $this->em->getClassMetadata(Report::class);
|
$report = $this->em->getClassMetadata(Report::class);
|
||||||
$person = $this->em->getClassMetadata(Person::class);
|
$person = $this->em->getClassMetadata(Person::class);
|
||||||
$role = new Role('CHILL_REPORT_SEE');
|
$role = new Role('CHILL_REPORT_SEE');
|
||||||
$reachableCenters = $this->helper->getReachableCenters($this->security->getUser(),
|
$reachableCenters = $this->helper->getReachableCenters($this->security->getUser(),
|
||||||
$role);
|
$role);
|
||||||
$reportPersonId = $report->getAssociationMapping('person')['joinColumns'][0]['name'];
|
$reportPersonId = $report->getAssociationMapping('person')['joinColumns'][0]['name'];
|
||||||
$reportScopeId = $report->getAssociationMapping('scope')['joinColumns'][0]['name'];
|
$reportScopeId = $report->getAssociationMapping('scope')['joinColumns'][0]['name'];
|
||||||
@ -123,13 +108,13 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
// add the center id to the parameters
|
// add the center id to the parameters
|
||||||
$parameters[] = $center->getId();
|
$parameters[] = $center->getId();
|
||||||
// loop over scopes
|
// loop over scopes
|
||||||
$scopeIds = [];
|
$scopeIds = [];
|
||||||
foreach ($this->helper->getReachableScopes($this->security->getUser(),
|
foreach ($this->helper->getReachableScopes($this->security->getUser(),
|
||||||
$role, $center) as $scope) {
|
$role, $center) as $scope) {
|
||||||
if (\in_array($scope->getId(), $scopeIds)) {
|
if (\in_array($scope->getId(), $scopeIds)) {
|
||||||
continue;
|
continue;
|
||||||
}
|
}
|
||||||
$scopeIds[] = $scope->getId();
|
$scopeIds[] = $scope->getId();
|
||||||
}
|
}
|
||||||
@ -173,7 +158,7 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
// this is the final clause that we are going to fill
|
// this is the final clause that we are going to fill
|
||||||
$clause = "{report}.{person_id} = ? AND {report}.{scopes_id} IN ({scopes_ids})";
|
$clause = "{report}.{person_id} = ? AND {report}.{scopes_id} IN ({scopes_ids})";
|
||||||
// iterate over reachable scopes
|
// iterate over reachable scopes
|
||||||
$scopes = $this->helper->getReachableScopes($this->security->getUser(), $role,
|
$scopes = $this->helper->getReachableScopes($this->security->getUser(), $role,
|
||||||
$args['person']->getCenter());
|
$args['person']->getCenter());
|
||||||
|
|
||||||
foreach ($scopes as $scope) {
|
foreach ($scopes as $scope) {
|
||||||
@ -194,16 +179,16 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
$clause,
|
$clause,
|
||||||
[
|
[
|
||||||
'{report}' => $report->getTableName(),
|
'{report}' => $report->getTableName(),
|
||||||
'{person_id}' => $reportPersonId,
|
'{person_id}' => $reportPersonId,
|
||||||
'{scopes_id}' => $reportScopeId,
|
'{scopes_id}' => $reportScopeId,
|
||||||
'{scopes_ids}' => \implode(', ',
|
'{scopes_ids}' => \implode(', ',
|
||||||
\array_fill(0, \count($parameters)-1, '?'))
|
\array_fill(0, \count($parameters)-1, '?'))
|
||||||
]
|
]
|
||||||
),
|
),
|
||||||
$parameters
|
$parameters
|
||||||
];
|
];
|
||||||
}
|
}
|
||||||
|
|
||||||
private function getFromClause(string $context): string
|
private function getFromClause(string $context): string
|
||||||
{
|
{
|
||||||
$report = $this->em->getClassMetadata(Report::class);
|
$report = $this->em->getClassMetadata(Report::class);
|
||||||
@ -229,30 +214,30 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* {@inheritDoc}
|
* {@inheritDoc}
|
||||||
*/
|
*/
|
||||||
public function getEntities(array $ids)
|
public function getEntities(array $ids)
|
||||||
{
|
{
|
||||||
$reports = $this->em->getRepository('ChillReportBundle:Report')
|
$reports = $this->em->getRepository('ChillReportBundle:Report')
|
||||||
->findBy(array('id' => $ids));
|
->findBy(array('id' => $ids));
|
||||||
|
|
||||||
$result = array();
|
$result = array();
|
||||||
foreach($reports as $report) {
|
foreach($reports as $report) {
|
||||||
$result[$report->getId()] = $report;
|
$result[$report->getId()] = $report;
|
||||||
}
|
}
|
||||||
|
|
||||||
return $result;
|
return $result;
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* {@inheritDoc}
|
* {@inheritDoc}
|
||||||
*/
|
*/
|
||||||
public function getEntityTemplate($entity, $context, array $args)
|
public function getEntityTemplate($entity, $context, array $args)
|
||||||
{
|
{
|
||||||
$this->checkContext($context);
|
$this->checkContext($context);
|
||||||
|
|
||||||
return array(
|
return array(
|
||||||
'template' => 'ChillReportBundle:Timeline:report.html.twig',
|
'template' => 'ChillReportBundle:Timeline:report.html.twig',
|
||||||
'template_data' => array(
|
'template_data' => array(
|
||||||
@ -262,19 +247,19 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
)
|
)
|
||||||
);
|
);
|
||||||
}
|
}
|
||||||
|
|
||||||
protected function getFieldsToRender(Report $entity, $context, array $args = array())
|
protected function getFieldsToRender(Report $entity, $context, array $args = array())
|
||||||
{
|
{
|
||||||
//gather all custom fields which should appears in summary
|
//gather all custom fields which should appears in summary
|
||||||
$gatheredFields = array();
|
$gatheredFields = array();
|
||||||
|
|
||||||
if (array_key_exists('summary_fields', $entity->getCFGroup()->getOptions())) {
|
if (array_key_exists('summary_fields', $entity->getCFGroup()->getOptions())) {
|
||||||
// keep in memory title
|
// keep in memory title
|
||||||
$title = null;
|
$title = null;
|
||||||
$subtitle = null;
|
$subtitle = null;
|
||||||
|
|
||||||
foreach ($entity->getCFGroup()->getCustomFields() as $customField) {
|
foreach ($entity->getCFGroup()->getCustomFields() as $customField) {
|
||||||
if (in_array($customField->getSlug(),
|
if (in_array($customField->getSlug(),
|
||||||
$entity->getCFGroup()->getOptions()['summary_fields'])) {
|
$entity->getCFGroup()->getOptions()['summary_fields'])) {
|
||||||
// if we do not want to show empty values
|
// if we do not want to show empty values
|
||||||
if ($this->showEmptyValues === false) {
|
if ($this->showEmptyValues === false) {
|
||||||
@ -304,23 +289,23 @@ class TimelineReportProvider implements TimelineProviderInterface
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
return $gatheredFields;
|
return $gatheredFields;
|
||||||
|
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
*
|
*
|
||||||
* {@inheritDoc}
|
* {@inheritDoc}
|
||||||
*/
|
*/
|
||||||
public function supportsType($type)
|
public function supportsType($type)
|
||||||
{
|
{
|
||||||
return $type === 'report';
|
return $type === 'report';
|
||||||
}
|
}
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* check if the context is supported
|
* check if the context is supported
|
||||||
*
|
*
|
||||||
* @param string $context
|
* @param string $context
|
||||||
* @throws \LogicException if the context is not supported
|
* @throws \LogicException if the context is not supported
|
||||||
*/
|
*/
|
||||||
|
Loading…
x
Reference in New Issue
Block a user