From 06abefd576ceac3266e89cb8c3ec750417727c1b Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Julien=20Fastr=C3=A9?= Date: Thu, 19 Aug 2021 23:30:45 +0200 Subject: [PATCH 1/2] add redirection to wopi after doc generation --- .../DocGeneratorTemplateController.php | 45 ++++++++++--------- .../Entity/StoredObject.php | 6 +-- .../Resources/public/chill/js/date.js | 2 +- .../src/Resources/config/routes/routes.php | 2 +- 4 files changed, 30 insertions(+), 25 deletions(-) diff --git a/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php b/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php index 62093c065..a29a07864 100644 --- a/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php +++ b/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php @@ -3,6 +3,8 @@ namespace Chill\DocGeneratorBundle\Controller; use Chill\DocGeneratorBundle\Repository\DocGeneratorTemplateRepository; +use Chill\DocStoreBundle\Entity\StoredObject; +use GuzzleHttp\Exception\TransferException; use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; use Symfony\Component\HttpFoundation\Response; use Symfony\Component\HttpFoundation\JsonResponse; @@ -54,7 +56,7 @@ class DocGeneratorTemplateController extends AbstractController * ) */ public function generateDocFromTemplateAction( - TempUrlOpenstackGenerator $tempUrlGenerator, + \ChampsLibres\AsyncUploaderBundle\TempUrl\TempUrlGeneratorInterface $tempUrlGenerator, DocGeneratorTemplate $template, string $entityClassName, int $entityId): Response { $getUrlGen = $tempUrlGenerator->generate( @@ -84,7 +86,7 @@ class DocGeneratorTemplateController extends AbstractController $fileContent = fopen($tmpfname2, 'r'); // the generated file content - $genDocName = 'doc_'.sprintf( '%010d', rand()).'.docx'; + $genDocName = 'doc_' . sprintf('%010d', rand()) . '.docx'; $getUrlGen = $tempUrlGenerator->generate( 'PUT', @@ -94,25 +96,28 @@ class DocGeneratorTemplateController extends AbstractController $client = new Client(); - $putResponse = $client->request('PUT', $getUrlGen->{'url'}, [ - 'body' => $fileContent - ]); + try { + $putResponse = $client->request('PUT', $getUrlGen->{'url'}, [ + 'body' => $fileContent + ]); - if ($putResponse->getStatusCode() == 201) { - return new JsonResponse( - array( - "msg" => "Document créé", - "id" => $genDocName, - "response" => array( - "reasonPhrase" => $putResponse->getReasonPhrase(), - "statusCode" => $putResponse->getStatusCode()))); + if ($putResponse->getStatusCode() == 201) { + $storedObject = new StoredObject(); + $storedObject + // currently, only docx is supported + ->setType('application/vnd.openxmlformats-officedocument.wordprocessingml.document') + ->setFilename($genDocName); + + $em = $this->getDoctrine()->getManager(); + $em->persist($storedObject); + $em->flush(); + + return $this->redirectToRoute('chill_wopi_file_edit', [ + 'fileId' => $genDocName + ]); + } + } catch (TransferException $e) { + throw $e; } - - return new JsonResponse( - array( - "msg" => "PBM", - "response" => array( - "reasonPhrase" => $putResponse->getReasonPhrase(), - "statusCode" => $putResponse->getStatusCode()))); } } diff --git a/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php b/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php index 538cab28b..019d9a124 100644 --- a/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php +++ b/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php @@ -37,14 +37,14 @@ class StoredObject implements AsyncFileInterface /** * @ORM\Column(type="json_array", name="key") */ - private array $keyInfos; + private array $keyInfos = []; /** * * @var int[] * @ORM\Column(type="json_array", name="iv") */ - private array $iv; + private array $iv = []; /** * @ORM\Column(type="datetime", name="creation_date") @@ -59,7 +59,7 @@ class StoredObject implements AsyncFileInterface /** * @ORM\Column(type="json_array", name="datas") */ - private array $datas; + private array $datas = []; public function __construct() { diff --git a/src/Bundle/ChillMainBundle/Resources/public/chill/js/date.js b/src/Bundle/ChillMainBundle/Resources/public/chill/js/date.js index 44fab8dc2..dfe667536 100644 --- a/src/Bundle/ChillMainBundle/Resources/public/chill/js/date.js +++ b/src/Bundle/ChillMainBundle/Resources/public/chill/js/date.js @@ -94,7 +94,7 @@ const datetimeToISO = (date) => { const intervalDaysToISO = (days) => { if (null === days) { - return 'PD0'; + return 'P0D'; } return `P${days}D`; diff --git a/src/Bundle/ChillWopiBundle/src/Resources/config/routes/routes.php b/src/Bundle/ChillWopiBundle/src/Resources/config/routes/routes.php index e0f3447aa..60bd96bde 100644 --- a/src/Bundle/ChillWopiBundle/src/Resources/config/routes/routes.php +++ b/src/Bundle/ChillWopiBundle/src/Resources/config/routes/routes.php @@ -12,6 +12,6 @@ use Symfony\Component\Routing\Loader\Configurator\RoutingConfigurator; return static function (RoutingConfigurator $routes) { $routes - ->add('testtest', '/edit/{fileId}') + ->add('chill_wopi_file_edit', '/edit/{fileId}') ->controller(Test::class); }; From 7f28effc1e9f4a2279e2b456d701fa0a21a506cd Mon Sep 17 00:00:00 2001 From: =?UTF-8?q?Julien=20Fastr=C3=A9?= Date: Fri, 20 Aug 2021 12:44:15 +0200 Subject: [PATCH 2/2] Associate generate document with evaluation and update UX to go back to documents --- .../DocGeneratorTemplateController.php | 17 +++++- .../Entity/DocGeneratorTemplate.php | 4 +- .../Entity/StoredObject.php | 8 ++- .../AccompanyingPeriodWorkEvaluation.php | 17 ++++++ ...companyingPeriodWorkEvaluationDocument.php | 54 ++++++++++++++++--- .../components/AddEvaluation.vue | 23 ++++++-- .../migrations/Version20210820093927.php | 39 ++++++++++++++ .../migrations/Version20210820100407.php | 29 ++++++++++ 8 files changed, 175 insertions(+), 16 deletions(-) create mode 100644 src/Bundle/ChillPersonBundle/migrations/Version20210820093927.php create mode 100644 src/Bundle/ChillPersonBundle/migrations/Version20210820100407.php diff --git a/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php b/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php index b8f53d1b2..56de44912 100644 --- a/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php +++ b/src/Bundle/ChillDocGeneratorBundle/Controller/DocGeneratorTemplateController.php @@ -4,6 +4,9 @@ namespace Chill\DocGeneratorBundle\Controller; use Chill\DocGeneratorBundle\Repository\DocGeneratorTemplateRepository; use Chill\DocStoreBundle\Entity\StoredObject; +use Chill\PersonBundle\Entity\AccompanyingPeriod\AccompanyingPeriodWorkEvaluation; +use Chill\PersonBundle\Entity\AccompanyingPeriod\AccompanyingPeriodWorkEvaluationDocument; +use Chill\PersonBundle\Entity\SocialWork\Evaluation; use GuzzleHttp\Exception\TransferException; use Symfony\Bundle\FrameworkBundle\Controller\AbstractController; use Symfony\Component\HttpFoundation\Response; @@ -105,14 +108,26 @@ class DocGeneratorTemplateController extends AbstractController ]); if ($putResponse->getStatusCode() == 201) { + $em = $this->getDoctrine()->getManager(); $storedObject = new StoredObject(); $storedObject // currently, only docx is supported ->setType('application/vnd.openxmlformats-officedocument.wordprocessingml.document') ->setFilename($genDocName); - $em = $this->getDoctrine()->getManager(); $em->persist($storedObject); + + // Only for evaluation + if ($entity instanceof AccompanyingPeriodWorkEvaluation) { + $doc = new AccompanyingPeriodWorkEvaluationDocument(); + $doc + ->setStoredObject($storedObject) + ->setTemplate($template) + ; + $entity->addDocument($doc); + $em->persist($doc); + } + $em->flush(); return $this->redirectToRoute('chill_wopi_file_edit', [ diff --git a/src/Bundle/ChillDocGeneratorBundle/Entity/DocGeneratorTemplate.php b/src/Bundle/ChillDocGeneratorBundle/Entity/DocGeneratorTemplate.php index d377773a5..ad8d62056 100644 --- a/src/Bundle/ChillDocGeneratorBundle/Entity/DocGeneratorTemplate.php +++ b/src/Bundle/ChillDocGeneratorBundle/Entity/DocGeneratorTemplate.php @@ -4,11 +4,11 @@ namespace Chill\DocGeneratorBundle\Entity; use Chill\DocGeneratorBundle\Repository\DocGeneratorTemplateRepository; use Doctrine\ORM\Mapping as ORM; +use Symfony\Component\Serializer\Annotation as Serializer; /** * @ORM\Entity * @ORM\Table(name="chill_docgen_template") - */ class DocGeneratorTemplate { @@ -16,11 +16,13 @@ class DocGeneratorTemplate * @ORM\Id * @ORM\GeneratedValue * @ORM\Column(type="integer") + * @Serializer\Groups({"read"}) */ private int $id; /** * @ORM\Column(type="json_array") + * @Serializer\Groups({"read"}) */ private array $name = []; diff --git a/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php b/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php index 019d9a124..9c88e502d 100644 --- a/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php +++ b/src/Bundle/ChillDocStoreBundle/Entity/StoredObject.php @@ -8,12 +8,11 @@ use Doctrine\ORM\Mapping as ORM; use ChampsLibres\AsyncUploaderBundle\Model\AsyncFileInterface; use ChampsLibres\AsyncUploaderBundle\Validator\Constraints\AsyncFileExists; use DateTimeInterface; +use Symfony\Component\Serializer\Annotation as Serializer; /** * Represent a document stored in an object store * - * @author Julien Fastré - * * @ORM\Entity() * @ORM\Table("chill_doc.stored_object") * @AsyncFileExists( @@ -26,11 +25,13 @@ class StoredObject implements AsyncFileInterface * @ORM\Id() * @ORM\GeneratedValue() * @ORM\Column(type="integer") + * @Serializer\Groups({"read"}) */ private $id; /** * @ORM\Column(type="text") + * @Serializer\Groups({"read"}) */ private $filename; @@ -48,16 +49,19 @@ class StoredObject implements AsyncFileInterface /** * @ORM\Column(type="datetime", name="creation_date") + * @Serializer\Groups({"read"}) */ private DateTimeInterface $creationDate; /** * @ORM\Column(type="text", name="type") + * @Serializer\Groups({"read"}) */ private string $type = ''; /** * @ORM\Column(type="json_array", name="datas") + * @Serializer\Groups({"read"}) */ private array $datas = []; diff --git a/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluation.php b/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluation.php index 9c27aeb59..ef5156c4d 100644 --- a/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluation.php +++ b/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluation.php @@ -135,6 +135,7 @@ class AccompanyingPeriodWorkEvaluation implements TrackUpdateInterface, TrackCre * * @Serializer\Groups({"read"}) * @Serializer\Groups({"write"}) + * @Serializer\Groups({"accompanying_period_work_evaluation:create"}) * * @var mixed * @@ -382,6 +383,22 @@ class AccompanyingPeriodWorkEvaluation implements TrackUpdateInterface, TrackCre return $this->documents; } + public function addDocument(AccompanyingPeriodWorkEvaluationDocument $document): self + { + if (!$this->documents->contains($document)) { + $this->documents[] = $document; + $document->setAccompanyingPeriodWorkEvaluation($this); + } + + return $this; + } + + public function removeDocument(AccompanyingPeriodWorkEvaluationDocument $document): self + { + $this->documents->removeElement($document); + return $this; + } + /** * Arbitrary data, used for client * diff --git a/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluationDocument.php b/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluationDocument.php index f61955e1d..eb07cd4d8 100644 --- a/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluationDocument.php +++ b/src/Bundle/ChillPersonBundle/Entity/AccompanyingPeriod/AccompanyingPeriodWorkEvaluationDocument.php @@ -2,6 +2,7 @@ namespace Chill\PersonBundle\Entity\AccompanyingPeriod; +use Chill\DocGeneratorBundle\Entity\DocGeneratorTemplate; use Chill\DocStoreBundle\Entity\StoredObject; use Chill\MainBundle\Doctrine\Model\TrackCreationInterface; use Chill\MainBundle\Doctrine\Model\TrackUpdateInterface; @@ -37,7 +38,7 @@ class AccompanyingPeriodWorkEvaluationDocument implements \Chill\MainBundle\Doct * inversedBy="documents" * ) */ - private ?AccompanyingPeriodWorkEvaluation $accompanyingPeriodWorkEvaluation; + private ?AccompanyingPeriodWorkEvaluation $accompanyingPeriodWorkEvaluation = null; /** * @ORM\ManyToOne( @@ -45,13 +46,13 @@ class AccompanyingPeriodWorkEvaluationDocument implements \Chill\MainBundle\Doct * ) * @Serializer\Groups({"read"}) */ - private ?User $createdBy; + private ?User $createdBy = null; /** * @ORM\Column(type="date_immutable", nullable=true, options={"default": null}) * @Serializer\Groups({"read"}) */ - private ?\DateTimeImmutable $createdAt; + private ?\DateTimeImmutable $createdAt = null; /** * @ORM\ManyToOne( @@ -59,18 +60,29 @@ class AccompanyingPeriodWorkEvaluationDocument implements \Chill\MainBundle\Doct * ) * @Serializer\Groups({"read"}) */ - private ?User $updatedBy; + private ?User $updatedBy = null; /** * @ORM\Column(type="date_immutable", nullable=true, options={"default": null}) * @Serializer\Groups({"read"}) */ - private ?DateTimeImmutable $updatedAt; + private ?\DateTimeImmutable $updatedAt = null; - // TODO: indiquer le document généré par le module "document" - private ?StoredObject $storedObject; + /** + * @ORM\ManyToOne( + * targetEntity=StoredObject::class + * ) + * @Serializer\Groups({"read"}) + */ + private ?StoredObject $storedObject = null; - // TODO: ajouter gabarit + /** + * @ORM\ManyToOne( + * targetEntity=DocGeneratorTemplate::class + * ) + * @Serializer\Groups({"read"}) + */ + private ?DocGeneratorTemplate $template = null; /** * @return AccompanyingPeriodWorkEvaluation|null @@ -86,6 +98,14 @@ class AccompanyingPeriodWorkEvaluationDocument implements \Chill\MainBundle\Doct */ public function setAccompanyingPeriodWorkEvaluation(?AccompanyingPeriodWorkEvaluation $accompanyingPeriodWorkEvaluation): AccompanyingPeriodWorkEvaluationDocument { + // if an evaluation is already associated, we cannot change the association (removing the association, + // by setting a null value, is allowed. + if ($this->accompanyingPeriodWorkEvaluation instanceof AccompanyingPeriodWorkEvaluation + && $accompanyingPeriodWorkEvaluation instanceof AccompanyingPeriodWorkEvaluation) { + if ($this->accompanyingPeriodWorkEvaluation !== $accompanyingPeriodWorkEvaluation) { + throw new \RuntimeException("It is not allowed to change the evaluation for a document"); + } + } $this->accompanyingPeriodWorkEvaluation = $accompanyingPeriodWorkEvaluation; return $this; } @@ -172,4 +192,22 @@ class AccompanyingPeriodWorkEvaluationDocument implements \Chill\MainBundle\Doct return $this->updatedAt; } + /** + * @return DocGeneratorTemplate|null + */ + public function getTemplate(): ?DocGeneratorTemplate + { + return $this->template; + } + + /** + * @param DocGeneratorTemplate|null $template + * @return AccompanyingPeriodWorkEvaluationDocument + */ + public function setTemplate(?DocGeneratorTemplate $template): AccompanyingPeriodWorkEvaluationDocument + { + $this->template = $template; + return $this; + } + } diff --git a/src/Bundle/ChillPersonBundle/Resources/public/vuejs/AccompanyingCourseWorkEdit/components/AddEvaluation.vue b/src/Bundle/ChillPersonBundle/Resources/public/vuejs/AccompanyingCourseWorkEdit/components/AddEvaluation.vue index f7e0902f4..7653365e4 100644 --- a/src/Bundle/ChillPersonBundle/Resources/public/vuejs/AccompanyingCourseWorkEdit/components/AddEvaluation.vue +++ b/src/Bundle/ChillPersonBundle/Resources/public/vuejs/AccompanyingCourseWorkEdit/components/AddEvaluation.vue @@ -19,8 +19,20 @@
{{ $t('warningInterval') }} :
{{ evaluation.warningInterval }}
-
{{ $t('documents') }} :
-
{{ evaluation.documents.length }}
+
@@ -82,7 +94,7 @@ export default { computed: { pickedEvaluations() { return this.$store.state.evaluationsPicked; - } + }, }, methods: { removeEvaluation(e) { @@ -95,7 +107,10 @@ export default { }, submitForm() { this.toggleEditEvaluation(); - } + }, + buildEditLink(storedObject) { + return `/wopi/edit/${storedObject.filename}`; + }, } } diff --git a/src/Bundle/ChillPersonBundle/migrations/Version20210820093927.php b/src/Bundle/ChillPersonBundle/migrations/Version20210820093927.php new file mode 100644 index 000000000..65b07766c --- /dev/null +++ b/src/Bundle/ChillPersonBundle/migrations/Version20210820093927.php @@ -0,0 +1,39 @@ +addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document ADD template_id INT DEFAULT NULL'); + $this->addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document ADD storedObject_id INT DEFAULT NULL'); + $this->addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document ADD CONSTRAINT FK_33EC92296C99C13A FOREIGN KEY (storedObject_id) REFERENCES chill_doc.stored_object (id) NOT DEFERRABLE INITIALLY IMMEDIATE'); + $this->addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document ADD CONSTRAINT FK_33EC92295DA0FB8 FOREIGN KEY (template_id) REFERENCES chill_docgen_template (id) NOT DEFERRABLE INITIALLY IMMEDIATE'); + $this->addSql('CREATE INDEX IDX_33EC92296C99C13A ON chill_person_accompanying_period_work_evaluation_document (storedObject_id)'); + $this->addSql('CREATE INDEX IDX_33EC92295DA0FB8 ON chill_person_accompanying_period_work_evaluation_document (template_id)'); + } + + public function down(Schema $schema): void + { + $this->addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document DROP CONSTRAINT FK_33EC92296C99C13A'); + $this->addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document DROP CONSTRAINT FK_33EC92295DA0FB8'); + $this->addSql('DROP INDEX IDX_33EC92296C99C13A'); + $this->addSql('DROP INDEX IDX_33EC92295DA0FB8'); + $this->addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document DROP template_id'); + $this->addSql('ALTER TABLE chill_person_accompanying_period_work_evaluation_document DROP storedObject_id'); + } +} diff --git a/src/Bundle/ChillPersonBundle/migrations/Version20210820100407.php b/src/Bundle/ChillPersonBundle/migrations/Version20210820100407.php new file mode 100644 index 000000000..fd05a884c --- /dev/null +++ b/src/Bundle/ChillPersonBundle/migrations/Version20210820100407.php @@ -0,0 +1,29 @@ +addSql('CREATE SEQUENCE chill_person_social_work_eval_doc_id_seq INCREMENT BY 1 MINVALUE 1000 START 1000'); + } + + public function down(Schema $schema): void + { + $this->addSql('DROP SEQUENCE chill_person_social_work_eval_doc_id_seq'); + } +}