Browse Source

add a GET route for pdf downloading

olinox14 1 year ago
parent
commit
ee1e8c3464
2 changed files with 74 additions and 0 deletions
  1. 6 0
      src/ApiResource/CvPdfRequest.php
  2. 68 0
      src/State/Provider/CvPdfRequestProvider.php

+ 6 - 0
src/ApiResource/CvPdfRequest.php

@@ -4,15 +4,21 @@ declare(strict_types=1);
 namespace App\ApiResource;
 
 use ApiPlatform\Metadata\ApiResource;
+use ApiPlatform\Metadata\Get;
 use ApiPlatform\Metadata\Post;
 use App\State\Processor\CvPdfRequestProcessor;
+use App\State\Provider\CvPdfRequestProvider;
 
 #[ApiResource(
     operations: [
+        new Get(
+            uriTemplate: '/download-cv',
+        ),
         new Post(
             uriTemplate: '/download-cv',
         ),
     ],
+    provider: CvPdfRequestProvider::class,
     processor: CvPdfRequestProcessor::class
 )]
 class CvPdfRequest

+ 68 - 0
src/State/Provider/CvPdfRequestProvider.php

@@ -0,0 +1,68 @@
+<?php
+declare(strict_types=1);
+
+namespace App\State\Provider;
+
+use AltchaOrg\Altcha\Altcha;
+use ApiPlatform\Metadata\Get;
+use ApiPlatform\Metadata\Operation;
+use ApiPlatform\State\ProviderInterface;
+use App\ApiResource\CvPdfRequest;
+use Symfony\Component\HttpFoundation\HeaderUtils;
+use Symfony\Component\HttpFoundation\RedirectResponse;
+use Symfony\Component\HttpFoundation\Response;
+use Path\Path;
+
+class CvPdfRequestProvider implements ProviderInterface
+{
+    public function __construct(
+        private readonly string $projectDir,
+        private readonly string $hmacKey
+    )
+    {}
+
+    public function provide(Operation $operation, array $uriVariables = [], array $context = []): Response|RedirectResponse
+    {
+        if (!$operation instanceof Get) {
+            throw new \RuntimeException('not supported', Response::HTTP_METHOD_NOT_ALLOWED);
+        }
+
+        $filters = $context['filters'] ?? [];
+        $altchaPayload = $filters['payload'] ?? null;
+        if ($altchaPayload === null) {
+            throw new \RuntimeException('missing parameter: payload', Response::HTTP_BAD_REQUEST);
+        }
+
+        try {
+            $valid = Altcha::verifySolution(
+                $altchaPayload,
+                $this->hmacKey,
+                true
+            );
+        } catch (\Throwable) {
+            $valid = false;
+        }
+
+        if (!$valid) {
+            throw new \RuntimeException('Invalid payload');
+        }
+
+        $content = (new Path($this->projectDir))
+            ->append('static', 'CV_Olivier_Massot.pdf')
+            ->getContent();
+
+        // Build the response and attach the file to it
+        // @see https://symfony.com/doc/current/components/http_foundation.html#serving-files
+        $response = new Response($content);
+
+        $response->headers->set('Charset', 'UTF-8');
+        $response->headers->set('Access-Control-Expose-Headers', 'Content-Disposition');
+        $response->headers->set('Content-Type', 'application/pdf');
+        $response->headers->set(
+            'Content-Disposition',
+            HeaderUtils::makeDisposition(HeaderUtils::DISPOSITION_ATTACHMENT, 'CV_Olivier_Massot.pdf')
+        );
+
+        return $response;
+    }
+}