diff --git a/config/packages/security.yaml b/config/packages/security.yaml
index 7b38924..1e7714e 100644
--- a/config/packages/security.yaml
+++ b/config/packages/security.yaml
@@ -35,6 +35,7 @@ security:
# Note: Only the *first* access control that matches will be used
access_control:
- { path: ^/task/*, roles: ROLE_USER }
+ - { path: ^/project/*, roles: ROLE_USER }
# - { path: ^/admin, roles: ROLE_ADMIN }
# - { path: ^/profile, roles: ROLE_USER }
diff --git a/src/Controller/ProjectController.php b/src/Controller/ProjectController.php
new file mode 100644
index 0000000..cb3353d
--- /dev/null
+++ b/src/Controller/ProjectController.php
@@ -0,0 +1,124 @@
+security = $security;
+ }
+
+ /**
+ * @Route("/project/list", name="project_list")
+ */
+ public function showPorjects(Request $request): Response
+ {
+ $user = $this->getUser();
+
+ if($this->isGranted('ROLE_ADMIN'))
+ {
+ /** @var $projects */
+ $projects = $this->getDoctrine()->getManager()
+ ->getRepository(Project::class)
+ ->findBy([], []);
+ }
+ else
+ {
+ /** @var $projects */
+ $projects = $this->getDoctrine()->getManager()
+ ->getRepository(Project::class)
+ ->findBy(['author' => $user->getId()]);
+ }
+
+
+
+ return $this->render('project/index.html.twig', [
+ 'projects' => $projects,
+ ]);
+ }
+
+ /**
+ * @Route("/project/create", name="project_create")
+ */
+ public function createProject(Request $request): Response
+ {
+ $project = new Project();
+ $form = $this->createForm(ProjectType::class, $project);
+
+ $form->handleRequest($request);
+ $user = $this->getUser();
+
+
+ if ($form->isSubmitted() && $form->isValid()) {
+
+ $project->setAuthor($user->getId());
+
+ $this->getDoctrine()->getManager()->persist($project);
+ $this->getDoctrine()->getManager()->flush();
+
+ return $this->redirectToRoute('project_list');
+ }
+
+ return $this->render('project/createForm.html.twig', [
+ 'form' => $form->createView(),
+ ]);
+ }
+
+
+ /**
+ * @Route("/project/{id}/", name="project_byId")
+ */
+ public function projectById($id): Response
+ {
+ /** @var Task $project */
+ $project = $this->getDoctrine()->getManager()->find(Project::class, $id);
+
+ if ($project === null) {
+ throw $this->createNotFoundException(sprintf("Project with id %s not found", $id));
+ }
+ $Flag=False;
+ $user = $this->getUser();
+ foreach ($user->getRoles() as $role)
+ {
+ if($role === 'ROLE_ADMIN')
+ {
+ $Flag=True;
+ }
+ }
+
+ if(!$Flag)
+ {
+ if($user->getId() !== $project->getAuthor())
+ {
+ throw $this->createAccessDeniedException();
+ }
+ }
+
+ $tasks = $this->getDoctrine()->getRepository(Task::class)
+ ->findBy(['project' => $id], []);
+
+ return $this->render('project/project.html.twig',[
+ 'id' => $id,
+ 'tasks' => $tasks,
+ ]);
+ }
+}
\ No newline at end of file
diff --git a/src/Controller/TaskController.php b/src/Controller/TaskController.php
index 0d9f9ad..c0549a9 100644
--- a/src/Controller/TaskController.php
+++ b/src/Controller/TaskController.php
@@ -2,6 +2,7 @@
namespace App\Controller;
+use App\Entity\Project;
use App\Entity\Task;
use App\Type\TaskFilterType;
use App\Type\TaskType;
@@ -22,7 +23,11 @@ class TaskController extends AbstractController
public function create(Request $request): Response
{
$task = new Task();
- $form = $this->createForm(TaskType::class, $task);
+ $option = [
+ 'userId' => $this->getUser()->getId(),
+ 'userRole' => $this->getUser()->getRoles(),
+ ];
+ $form = $this->createForm(TaskType::class, $task, $option);
$form->handleRequest($request);
@@ -48,6 +53,20 @@ public function create(Request $request): Response
*/
public function list(Request $request): Response
{
+ $Flag=False;
+ $user = $this->getUser();
+ foreach ($user->getRoles() as $role)
+ {
+ if($role === 'ROLE_ADMIN')
+ {
+ $Flag=True;
+ }
+ }
+ if(!$Flag)
+ {
+ $ids = $this->getProjectID($user->getId());
+ }
+
$taskFilterForm = $this->createForm(TaskFilterType::class);
$taskFilterForm->handleRequest($request);
@@ -58,23 +77,36 @@ public function list(Request $request): Response
if ($filter['isCompleted'] === null) {
unset($filter['isCompleted']);
}
-
+ if(!$Flag)
+ {
+ $filter['project'] = $ids;
+ }
$tasks = $this->getDoctrine()->getRepository(Task::class)
->findBy($filter, [
'dueDate' => 'DESC'
]);
} else {
- /** @var $tasks */
- $tasks = $this->getDoctrine()->getManager()
- ->getRepository(Task::class)
- ->findBy([], [
- 'dueDate' => 'DESC'
- ]);
+ if($Flag)
+ {
+ /** @var $tasks */
+ $tasks = $this->getDoctrine()->getManager()
+ ->getRepository(Task::class)
+ ->findBy([], [
+ 'dueDate' => 'DESC'
+ ]);
+ }
+ else
+ {
+ /** @var $tasks */
+ $tasks = $this->getDoctrine()->getManager()
+ ->getRepository(Task::class)
+ ->findBy(['project' => $ids], [
+ 'dueDate' => 'DESC'
+ ]);
+ }
}
-
-
return $this->render('task/list.html.twig', [
'tasks' => $tasks,
'filterForm' => $taskFilterForm->createView()
@@ -104,4 +136,21 @@ public function complete($id): Response
return $this->redirectToRoute('task_list');
}
+
+ private function getProjectID(int $id)
+ {
+ $returnId = [];
+
+ /** @var $projects */
+ $projects = $this->getDoctrine()->getManager()
+ ->getRepository(Project::class)
+ ->findBy(['author' => $id]);
+
+ foreach ($projects as $project)
+ {
+ array_push($returnId, $project->getId());
+ }
+
+ return $returnId;
+ }
}
\ No newline at end of file
diff --git a/src/Entity/Project.php b/src/Entity/Project.php
new file mode 100644
index 0000000..bd19ac7
--- /dev/null
+++ b/src/Entity/Project.php
@@ -0,0 +1,75 @@
+id;
+ }
+
+ public function getToken(): ?string
+ {
+ return $this->token;
+ }
+
+ public function setToken(string $token): self
+ {
+ $this->token = $token;
+
+ return $this;
+ }
+
+ public function getName(): ?string
+ {
+ return $this->name;
+ }
+
+ public function setName(string $name): self
+ {
+ $this->name = $name;
+
+ return $this;
+ }
+
+ public function getAuthor(): ?int
+ {
+ return $this->author;
+ }
+
+ public function setAuthor(int $author): self
+ {
+ $this->author = $author;
+
+ return $this;
+ }
+}
\ No newline at end of file
diff --git a/src/Entity/Task.php b/src/Entity/Task.php
index 66a4b57..3d67dc5 100644
--- a/src/Entity/Task.php
+++ b/src/Entity/Task.php
@@ -55,6 +55,12 @@ class Task
*/
protected $author;
+ /**
+ * @ORM\ManyToOne(targetEntity="App\Entity\Project", inversedBy="project")
+ * @var Project
+ */
+ protected $project;
+
/**
* Create empty task
*/
@@ -85,6 +91,24 @@ public function getAuthor()
return $this->author;
}
+ /**
+ * Set task Project
+ * @param Project|null $project
+ * @return void
+ */
+ public function setProject(Project $project = null)
+ {
+ $this->project = $project;
+ }
+
+ /**
+ * Return task project
+ * @return Project|null
+ */
+ public function getProject()
+ {
+ return $this->project;
+ }
/**
* @return mixed
diff --git a/src/Repository/ProjectRepository.php b/src/Repository/ProjectRepository.php
new file mode 100644
index 0000000..89a9165
--- /dev/null
+++ b/src/Repository/ProjectRepository.php
@@ -0,0 +1,47 @@
+_em->persist($entity);
+ if ($flush) {
+ $this->_em->flush();
+ }
+ }
+
+ /**
+ * @throws ORMException
+ * @throws OptimisticLockException
+ */
+ public function remove(Project $entity, bool $flush = true): void
+ {
+ $this->_em->remove($entity);
+ if ($flush) {
+ $this->_em->flush();
+ }
+ }
+}
\ No newline at end of file
diff --git a/src/Security/LoginFormAuthenticator.php b/src/Security/LoginFormAuthenticator.php
index eb7b6dd..3bd0209 100644
--- a/src/Security/LoginFormAuthenticator.php
+++ b/src/Security/LoginFormAuthenticator.php
@@ -95,7 +95,7 @@ public function onAuthenticationSuccess(Request $request, TokenInterface $token,
return new RedirectResponse($targetPath);
}
- return new RedirectResponse($this->urlGenerator->generate('task_list'));
+ return new RedirectResponse($this->urlGenerator->generate('project_list'));
}
protected function getLoginUrl()
diff --git a/src/Type/ProjectType.php b/src/Type/ProjectType.php
new file mode 100644
index 0000000..a61bf92
--- /dev/null
+++ b/src/Type/ProjectType.php
@@ -0,0 +1,22 @@
+add('token', TextType::class)
+ ->add('name', TextType::class)
+ ->add('save', SubmitType::class)
+ ;
+ }
+}
\ No newline at end of file
diff --git a/src/Type/TaskType.php b/src/Type/TaskType.php
index 3b58193..839a19f 100644
--- a/src/Type/TaskType.php
+++ b/src/Type/TaskType.php
@@ -2,24 +2,91 @@
namespace App\Type;
+use App\Entity\Project;
+use App\Entity\User;
+use Doctrine\ORM\EntityRepository;
+use Symfony\Bridge\Doctrine\Form\Type\EntityType;
use Symfony\Component\Form\AbstractType;
use Symfony\Component\Form\Extension\Core\Type\DateType;
use Symfony\Component\Form\Extension\Core\Type\SubmitType;
use Symfony\Component\Form\Extension\Core\Type\TextareaType;
use Symfony\Component\Form\Extension\Core\Type\TextType;
use Symfony\Component\Form\FormBuilderInterface;
+use Symfony\Component\OptionsResolver\OptionsResolver;
+use Symfony\Component\Security\Core\User\UserInterface;
class TaskType extends AbstractType
{
+
+ protected $id;
+
+ public function configureOptions(OptionsResolver $resolver): void
+ {
+ $resolver->setDefaults([
+ 'userId' => 0,
+ 'userRole' => []
+ ]);
+
+ // you can also define the allowed types, allowed values and
+ // any other feature supported by the OptionsResolver component
+ $resolver->setAllowedTypes('userId', 'int');
+ $resolver->setAllowedTypes('userRole', 'array');
+ }
+
public function buildForm(FormBuilderInterface $builder, array $options)
{
- $builder
- ->add('name', TextType::class)
- ->add('description', TextareaType::class)
- ->add('dueDate', DateType::class, [
- 'years' => range(2022,2023)
- ])
- ->add('save', SubmitType::class)
- ;
+ $roles = $options['userRole'];
+ $flag = false;
+ foreach ($roles as $role)
+ {
+ if ($role === 'ROLE_ADMIN')
+ {
+ $flag = True;
+ }
+ }
+
+ $this->id = $options['userId'];
+
+ if ($flag)
+ {
+ $builder
+ ->add('name', TextType::class)
+ ->add('description', TextareaType::class)
+ ->add('dueDate', DateType::class, [
+ 'years' => range(2022,2023)
+ ])
+ ->add('project', EntityType::class, [
+ 'class' => Project::class,
+ 'query_builder' => function (EntityRepository $er) {
+ $sql = sprintf('p.author = %d', $this->id);
+ return $er->createQueryBuilder('p')
+ ->orderBy('p.id', 'ASC');
+ },
+ 'choice_label' => 'id',
+ ])
+ ->add('save', SubmitType::class)
+ ;
+ }
+ else
+ {
+ $builder
+ ->add('name', TextType::class)
+ ->add('description', TextareaType::class)
+ ->add('dueDate', DateType::class, [
+ 'years' => range(2022,2023)
+ ])
+ ->add('project', EntityType::class, [
+ 'class' => Project::class,
+ 'query_builder' => function (EntityRepository $er) {
+ $sql = sprintf('p.author = %d', $this->id);
+ return $er->createQueryBuilder('p')
+ ->where($sql)
+ ->orderBy('p.id', 'ASC');
+ },
+ 'choice_label' => 'id',
+ ])
+ ->add('save', SubmitType::class)
+ ;
+ }
}
}
\ No newline at end of file
diff --git a/templates/project/createForm.html.twig b/templates/project/createForm.html.twig
new file mode 100644
index 0000000..fa54bb7
--- /dev/null
+++ b/templates/project/createForm.html.twig
@@ -0,0 +1,16 @@
+{% extends 'base.html.twig' %}
+
+{% block body %}
+
+
+
+
+
+
+ {{ form(form, {'action': path('project_create'), 'method': 'POST'}) }}
+
+
+
+
+
+{% endblock %}
\ No newline at end of file
diff --git a/templates/project/index.html.twig b/templates/project/index.html.twig
new file mode 100644
index 0000000..21c486c
--- /dev/null
+++ b/templates/project/index.html.twig
@@ -0,0 +1,35 @@
+{% extends 'base.html.twig' %}
+
+{% block body %}
+
+
+
+
+
+ {# {{ form(filterForm, {"action" : path('task_list'), "method" : "GET"}) }}#}
+
+
+
+ #
+ Token
+ Name
+
+
+
+ {% for project in projects %}
+
+ <{{ project.id }}
+ {{ project.token }}
+ {{ project.name }}
+
+ {% endfor %}
+
+
+
+
Создать задачу
+
+
+
+
+
+{% endblock %}
\ No newline at end of file
diff --git a/templates/project/project.html.twig b/templates/project/project.html.twig
new file mode 100644
index 0000000..98291aa
--- /dev/null
+++ b/templates/project/project.html.twig
@@ -0,0 +1,46 @@
+{% extends 'base.html.twig' %}
+
+{% block body %}
+
+
+
+
+
+
+
+
+
+
+ #
+ Название
+ Описание
+ Срок выполнения
+ Автор
+ Выполнена
+ Действия
+
+
+
+ {% for task in tasks %}
+
+ {{ task.id }}
+ {{ task.name }}
+ {{ task.description }}
+ {{ task.dueDate|date("d.m.Y") }}
+ {{ task.author }}
+ {{ task.isCompleted ? 'Выполнена' : 'Не выполнена' }}
+
+ {% if (is_granted("complete", task)) %}
+ Сделано
+ {% endif %}
+
+
+ {% endfor %}
+
+
+
+
+
+
+
+{% endblock %}
\ No newline at end of file
diff --git a/templates/security/login.html.twig b/templates/security/login.html.twig
index 7490fa3..db7d331 100644
--- a/templates/security/login.html.twig
+++ b/templates/security/login.html.twig
@@ -16,7 +16,7 @@
Please sign in
Email
-
+
Password
diff --git a/templates/task/list.html.twig b/templates/task/list.html.twig
index 0d50fd4..2759f1b 100644
--- a/templates/task/list.html.twig
+++ b/templates/task/list.html.twig
@@ -38,7 +38,7 @@
- Создать задачу
+ Создать задачу