adaptations for acl with tasks

This commit is contained in:
2021-10-26 18:05:06 +02:00
parent bae06fcc9c
commit 965ea528e3
22 changed files with 371 additions and 298 deletions

View File

@@ -3,9 +3,12 @@
namespace Chill\TaskBundle\Controller;
use Chill\MainBundle\Entity\Scope;
use Chill\MainBundle\Security\Resolver\CenterResolverDispatcher;
use Chill\MainBundle\Security\Resolver\CenterResolverInterface;
use Chill\PersonBundle\Privacy\PrivacyEvent;
use Psr\Log\LoggerInterface;
use Symfony\Bundle\FrameworkBundle\Controller\AbstractController;
use Symfony\Component\HttpKernel\Exception\BadRequestHttpException;
use Symfony\Component\Routing\Annotation\Route;
use Chill\PersonBundle\Entity\Person;
use Symfony\Component\HttpFoundation\Request;
@@ -24,7 +27,6 @@ use Chill\PersonBundle\Security\Authorization\PersonVoter;
use Chill\PersonBundle\Repository\PersonRepository;
use Chill\TaskBundle\Event\TaskEvent;
use Symfony\Component\EventDispatcher\EventDispatcherInterface;
use Symfony\Component\Translation\TranslatorInterface;
use Chill\TaskBundle\Event\UI\UIEvent;
use Chill\MainBundle\Repository\CenterRepository;
use Chill\MainBundle\Timeline\TimelineBuilder;
@@ -33,6 +35,7 @@ use Chill\PersonBundle\Repository\AccompanyingPeriodRepository;
use Chill\PersonBundle\Security\Authorization\AccompanyingPeriodVoter;
use Doctrine\ORM\EntityManagerInterface;
use Symfony\Component\HttpFoundation\RequestStack;
use Symfony\Contracts\Translation\TranslatorInterface;
use Symfony\Contracts\Translation\TranslatorInterface as TranslationTranslatorInterface;
/**
@@ -40,126 +43,100 @@ use Symfony\Contracts\Translation\TranslatorInterface as TranslationTranslatorIn
*
* @package Chill\TaskBundle\Controller
*/
class SingleTaskController extends AbstractController
final class SingleTaskController extends AbstractController
{
/**
* @var EventDispatcherInterface
*/
protected $eventDispatcher;
/**
*
* @var TimelineBuilder
*/
protected $timelineBuilder;
/**
* @var LoggerInterface
*/
protected $logger;
/**
* @var RequestStack
*/
protected $request;
/**
* SingleTaskController constructor.
*
* @param EventDispatcherInterface $eventDispatcher
*/
private EventDispatcherInterface $eventDispatcher;
private TimelineBuilder $timelineBuilder;
private LoggerInterface $logger;
private CenterResolverDispatcher $centerResolverDispatcher;
private TranslatorInterface $translator;
public function __construct(
CenterResolverDispatcher $centerResolverDispatcher,
TranslatorInterface $translator,
EventDispatcherInterface $eventDispatcher,
TimelineBuilder $timelineBuilder,
LoggerInterface $logger,
RequestStack $requestStack
LoggerInterface $logger
) {
$this->eventDispatcher = $eventDispatcher;
$this->timelineBuilder = $timelineBuilder;
$this->logger = $logger;
$this->request = $requestStack->getCurrentRequest();
$this->translator = $translator;
$this->centerResolverDispatcher = $centerResolverDispatcher;
}
private function getEntityContext()
private function getEntityContext(Request $request)
{
if($this->request->query->has('person_id')){
if ($request->query->has('person_id')) {
return 'person';
} else if ($this->request->query->has('course_id')) {
} else if ($request->query->has('course_id')) {
return 'course';
} else {
return null;
}
}
/**
* @Route(
* "/{_locale}/task/single-task/new",
* name="chill_task_single_task_new"
* )
*/
public function newAction(
TranslationTranslatorInterface $translator
) {
public function newAction(Request $request) {
$task = (new SingleTask())
->setAssignee($this->getUser())
->setType('task_default')
;
$entityType = $this->getEntityContext();
if ($entityType !== null) {
$entityId = $this->request->query->getInt("{$entityType}_id", 0); // sf4 check:
// prevent error: `Argument 2 passed to ::getInt() must be of the type int, null given`
$entityType = $this->getEntityContext($request);
if ($entityId === null) {
return new Response("You must provide a {$entityType}_id", Response::HTTP_BAD_REQUEST);
}
if (NULL === $entityType) {
throw new BadRequestHttpException("You must provide a entity_type");
}
if($entityType === 'person')
{
$entityId = $request->query->getInt("{$entityType}_id", 0);
if ($entityId === null) {
return new BadRequestHttpException("You must provide a {$entityType}_id");
}
switch ($entityType) {
case 'person':
$person = $this->getDoctrine()->getManager()
->getRepository(Person::class)
->find($entityId);
->getRepository(Person::class)
->find($entityId);
if ($person === null) {
$this->createNotFoundException("Invalid person id");
}
$task->setPerson($person);
}
if($entityType === 'course')
{
$task->setPerson($person);
break;
case 'course':
$course = $this->getDoctrine()->getManager()
->getRepository(AccompanyingPeriod::class)
->find($entityId);
->getRepository(AccompanyingPeriod::class)
->find($entityId);
if($course === null) {
if ($course === null) {
$this->createNotFoundException("Invalid accompanying course id");
}
$task->setCourse($course);
}
break;
default:
return new BadRequestHttpException("context with {$entityType} is not supported");
}
//TODO : resolve access rights
// $this->denyAccessUnlessGranted(TaskVoter::CREATE, $task, 'You are not '
// . 'allowed to create this task');
$this->denyAccessUnlessGranted(TaskVoter::CREATE, $task, 'You are not '
. 'allowed to create this task');
$form = $this->setCreateForm($task, new Role(TaskVoter::CREATE));
$form->handleRequest($this->request);
$form->handleRequest($request);
if ($form->isSubmitted()) {
if ($form->isValid()) {
$em = $this->getDoctrine()->getManager();
@@ -169,44 +146,38 @@ class SingleTaskController extends AbstractController
$em->flush();
$this->addFlash('success', $translator->trans("The task is created"));
$this->addFlash('success', $this->translator->trans("The task is created"));
if($entityType === 'person')
{
if ($entityType === 'person') {
return $this->redirectToRoute('chill_task_singletask_list', [
'person_id' => $task->getPerson()->getId()
]);
}
if($entityType === 'course')
{
} elseif ($entityType === 'course') {
return $this->redirectToRoute('chill_task_singletask_courselist', [
'course_id' => $task->getCourse()->getId()
]);
}
} else {
$this->addFlash('error', $translator->trans("This form contains errors"));
$this->addFlash('error', $this->translator->trans("This form contains errors"));
}
}
switch($this->getEntityContext()){
case 'person':
switch ($entityType) {
case 'person':
return $this->render('@ChillTask/SingleTask/Person/new.html.twig', array(
'form' => $form->createView(),
'task' => $task,
'person' => $person,
));
break;
case 'course':
return $this->render('@ChillTask/SingleTask/AccompanyingCourse/new.html.twig', array(
'form' => $form->createView(),
'task' => $task,
'accompanyingCourse' => $course,
));
break;
}
default:
throw new \LogicException("entity context not supported");
}
}
/**
@@ -215,9 +186,9 @@ class SingleTaskController extends AbstractController
* name="chill_task_single_task_show"
* )
*/
public function showAction($id)
public function showAction($id, Request $request)
{
$em = $this->getDoctrine()->getManager();
$task = $em->getRepository(SingleTask::class)->find($id);
@@ -226,7 +197,7 @@ class SingleTaskController extends AbstractController
}
if ($task->getPerson() !== null) {
$personId = $task->getPerson()->getId();
if ($personId === null) {
@@ -250,7 +221,7 @@ class SingleTaskController extends AbstractController
}
if ($task->getCourse() !== null)
if ($task->getCourse() !== null)
{
$courseId = $task->getCourse()->getId();
@@ -274,7 +245,7 @@ class SingleTaskController extends AbstractController
$timeline = $this->timelineBuilder
->getTimelineHTML('task', array('task' => $task));
if($task->getContext() instanceof Person){
return $this->render('@ChillTask/SingleTask/Person/show.html.twig', array(
@@ -299,9 +270,9 @@ class SingleTaskController extends AbstractController
*/
public function editAction(
$id,
TranslationTranslatorInterface $translator
Request $request
) {
$em = $this->getDoctrine()->getManager();
$task = $em->getRepository(SingleTask::class)->find($id);
@@ -339,16 +310,16 @@ class SingleTaskController extends AbstractController
if (!$task) {
throw $this->createNotFoundException('Unable to find Task entity.');
}
$event = (new UIEvent('single-task', $task))
->setForm($this->setCreateForm($task, new Role(TaskVoter::UPDATE)))
;
$this->eventDispatcher->dispatch(UIEvent::EDIT_FORM, $event);
$form = $event->getForm();
$form->handleRequest($this->request);
$form->handleRequest($request);
if ($form->isSubmitted()) {
if ($form->isValid()) {
@@ -357,7 +328,7 @@ class SingleTaskController extends AbstractController
$em->flush();
$this->addFlash('success', $translator
$this->addFlash('success', $this->translator
->trans("The task has been updated"));
if($task->getContext() instanceof Person){
@@ -369,26 +340,26 @@ class SingleTaskController extends AbstractController
$this->eventDispatcher->dispatch(PrivacyEvent::PERSON_PRIVACY_EVENT, $event);
return $this->redirectToRoute(
'chill_task_singletask_list',
$this->request->query->get('list_params', [])
'chill_task_singletask_list',
$request->query->get('list_params', [])
);
} else {
return $this->redirectToRoute(
'chill_task_singletask_courselist',
$this->request->query->get('list_params', [])
'chill_task_singletask_courselist',
$request->query->get('list_params', [])
);
}
} else {
$this->addFlash('error', $translator->trans("This form contains errors"));
$this->addFlash('error', $this->translator->trans("This form contains errors"));
}
}
$this->eventDispatcher->dispatch(UIEvent::EDIT_PAGE, $event);
if ($event->hasResponse()) {
return $event->getResponse();
}
if($task->getContext() instanceof Person){
$event = new PrivacyEvent($person, array(
'element_class' => SingleTask::class,
@@ -420,10 +391,9 @@ class SingleTaskController extends AbstractController
*/
public function deleteAction(
Request $request,
$id,
TranslationTranslatorInterface $translator
$id
) {
$em = $this->getDoctrine()->getManager();
$task = $em->getRepository(SingleTask::class)->find($id);
@@ -471,7 +441,7 @@ class SingleTaskController extends AbstractController
$form->handleRequest($request);
if ($form->isValid()) {
$this->logger->notice("A task has been removed", array(
'by_user' => $this->getUser()->getUsername(),
'task_id' => $task->getId(),
@@ -485,18 +455,18 @@ class SingleTaskController extends AbstractController
$em->remove($task);
$em->flush();
$this->addFlash('success', $translator
$this->addFlash('success', $this->translator
->trans("The task has been successfully removed."));
if($task->getContext() instanceof Person){
return $this->redirect($this->generateUrl(
'chill_task_singletask_list',
'chill_task_singletask_list',
$request->query->get('list_params', [
'person_id' => $person->getId()
])));
} else {
return $this->redirect($this->generateUrl(
'chill_task_singletask_courselist',
'chill_task_singletask_courselist',
$request->query->get('list_params', [
'course_id' => $course->getId()
])));
@@ -528,7 +498,7 @@ class SingleTaskController extends AbstractController
protected function setCreateForm(SingleTask $task, Role $role)
{
$form = $this->createForm(SingleTaskType::class, $task, [
'center' => $task->getCenter(),
'center' => $this->centerResolverDispatcher->resolveCenter($task),
'role' => $role,
]);
@@ -545,12 +515,12 @@ class SingleTaskController extends AbstractController
* name="chill_task_single_my_tasks"
* )
*/
public function myTasksAction(TranslationTranslatorInterface $translator)
public function myTasksAction()
{
return $this->redirectToRoute('chill_task_singletask_list', [
'user_id' => $this->getUser()->getId(),
'hide_form' => true,
'title' => $translator->trans('My tasks')
'title' => $this->translator->trans('My tasks')
]);
}
@@ -575,7 +545,8 @@ class SingleTaskController extends AbstractController
PersonRepository $personRepository,
AccompanyingPeriodRepository $courseRepository,
CenterRepository $centerRepository,
FormFactoryInterface $formFactory
FormFactoryInterface $formFactory,
Request $request
) {
/* @var $viewParams array The parameters for the view */
/* @var $params array The parameters for the query */
@@ -589,9 +560,9 @@ class SingleTaskController extends AbstractController
$viewParams['accompanyingCourse'] = null;
$params['accompanyingCourse'] = null;
if (!empty($this->request->query->get('person_id', NULL))) {
$personId = $this->request->query->getInt('person_id', 0);
if (!empty($request->query->get('person_id', NULL))) {
$personId = $request->query->getInt('person_id', 0);
$person = $personRepository->find($personId);
if ($person === null) {
@@ -603,9 +574,9 @@ class SingleTaskController extends AbstractController
$params['person'] = $person;
}
if (!empty($this->request->query->get('course_id', NULL))) {
$courseId = $this->request->query->getInt('course_id', 0);
if (!empty($request->query->get('course_id', NULL))) {
$courseId = $request->query->getInt('course_id', 0);
$course = $courseRepository->find($courseId);
if ($course === null) {
@@ -616,28 +587,28 @@ class SingleTaskController extends AbstractController
$viewParams['accompanyingCourse'] = $course;
$params['accompanyingCourse'] = $course;
}
if (!empty($this->request->query->get('center_id', NULL))) {
$center = $centerRepository->find($this->request->query->getInt('center_id'));
if (!empty($request->query->get('center_id', NULL))) {
$center = $centerRepository->find($request->query->getInt('center_id'));
if ($center === null) {
throw $this->createNotFoundException('center not found');
}
$params['center'] = $center;
}
if(!empty($this->request->query->get('types', []))) {
$types = $this->request->query->get('types', []);
if(!empty($request->query->get('types', []))) {
$types = $request->query->get('types', []);
if (count($types) > 0) {
$params['types'] = $types;
}
}
if (!empty($this->request->query->get('user_id', null))) {
if ($this->request->query->get('user_id') === '_unassigned') {
if (!empty($request->query->get('user_id', null))) {
if ($request->query->get('user_id') === '_unassigned') {
$params['unassigned'] = true;
} else {
$userId = $this->request->query->getInt('user_id', 0);
$userId = $request->query->getInt('user_id', 0);
$user = $this->getDoctrine()->getManager()
->getRepository(User::class)
->find($userId);
@@ -651,10 +622,10 @@ class SingleTaskController extends AbstractController
}
}
if (!empty($this->request->query->get('scope_id'))) {
if (!empty($request->query->get('scope_id'))) {
$scopeId = $request->query->getInt('scope_id', 0);
$scopeId = $this->request->query->getInt('scope_id', 0);
$scope = $this->getDoctrine()->getManager()
->getRepository(Scope::class)
->find($scopeId);
@@ -668,7 +639,7 @@ class SingleTaskController extends AbstractController
}
$possibleStatuses = \array_merge(SingleTaskRepository::DATE_STATUSES, [ 'closed' ]);
$statuses = $this->request->query->get('status', $possibleStatuses);
$statuses = $request->query->get('status', $possibleStatuses);
$diff = \array_diff($statuses, $possibleStatuses);
if (count($diff) > 0) {
@@ -683,7 +654,7 @@ class SingleTaskController extends AbstractController
$tasks_count = 0;
foreach($statuses as $status) {
if($this->request->query->has('status')
if($request->query->has('status')
&& FALSE === \in_array($status, $statuses)) {
continue;
}
@@ -729,8 +700,8 @@ class SingleTaskController extends AbstractController
'add_type' => true
]);
$form->handleRequest($this->request);
$form->handleRequest($request);
if (isset($person)) {
$event = new PrivacyEvent($person, array(
'element_class' => SingleTask::class,
@@ -738,7 +709,7 @@ class SingleTaskController extends AbstractController
));
$this->eventDispatcher->dispatch(PrivacyEvent::PERSON_PRIVACY_EVENT, $event);
}
return $this->render('@ChillTask/SingleTask/index.html.twig',
array_merge($viewParams, [ 'form' => $form->createView() ]));
}
@@ -747,7 +718,7 @@ class SingleTaskController extends AbstractController
protected function getPersonParam(EntityManagerInterface $em)
{
$person = $em->getRepository(Person::class)
->find($this->request->query->getInt('person_id'))
->find($request->query->getInt('person_id'))
;
if (NULL === $person) {
@@ -763,7 +734,7 @@ class SingleTaskController extends AbstractController
protected function getUserParam(EntityManagerInterface $em)
{
$user = $em->getRepository(User::class)
->find($this->request->query->getInt('user_id'))
->find($request->query->getInt('user_id'))
;
if (NULL === $user) {
@@ -799,16 +770,16 @@ class SingleTaskController extends AbstractController
*/
public function listCourseTasks(
AccompanyingPeriodRepository $courseRepository,
AccompanyingPeriodRepository $courseRepository,
SingleTaskRepository $taskRepository,
FormFactoryInterface $formFactory,
TranslationTranslatorInterface $translator
Request $request
): Response
{
if (!empty($this->request->query->get('course_id', NULL))) {
$courseId = $this->request->query->getInt('course_id', 0);
if (!empty($request->query->get('course_id', NULL))) {
$courseId = $request->query->getInt('course_id', 0);
$course = $courseRepository->find($courseId);
if ($course === null) {
@@ -834,15 +805,15 @@ class SingleTaskController extends AbstractController
'csrf_protection' => false,
'add_type' => true
]);
return $this->render(
'@ChillTask/SingleTask/index.html.twig',
'@ChillTask/SingleTask/index.html.twig',
[
'tasks' => $tasks,
'accompanyingCourse' => $course,
'layout' => '@ChillPerson/AccompanyingCourse/layout.html.twig',
'form' => $form->createView(),
'title' => $translator->trans('Tasks for this accompanying period')
'title' => $this->translator->trans('Tasks for this accompanying period')
]);
}