Skip to content

Commit f9f1a54

Browse files
committed
Allow SVG in jury test case visualization
1 parent 379abdc commit f9f1a54

File tree

4 files changed

+37
-11
lines changed

4 files changed

+37
-11
lines changed

webapp/src/Controller/Jury/ProblemController.php

Lines changed: 20 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -605,16 +605,26 @@ public function testcasesAction(Request $request, int $probId): Response
605605
}
606606
$content = file_get_contents($file->getRealPath());
607607
if ($type === 'image') {
608-
$imageType = Utils::getImageType($content, $error);
609-
if ($imageType === false) {
610-
$this->addFlash('danger', sprintf('image: %s', $error));
611-
return $this->redirectToRoute('jury_problem_testcases', ['probId' => $probId]);
612-
}
613-
$thumb = Utils::getImageThumb($content, $thumbnailSize,
614-
$this->dj->getDomjudgeTmpDir(), $error);
615-
if ($thumb === false) {
616-
$this->addFlash('danger', sprintf('image: %s', $error));
617-
return $this->redirectToRoute('jury_problem_testcases', ['probId' => $probId]);
608+
if (mime_content_type($file->getRealPath()) === 'image/svg+xml') {
609+
$content = Utils::sanitizeSvg($content);
610+
if ($content === false) {
611+
$this->addFlash('danger', sprintf('image: %s', $error));
612+
return $this->redirectToRoute('jury_problem_testcases', ['probId' => $probId]);
613+
}
614+
$thumb = $content;
615+
$imageType = 'svg';
616+
} else {
617+
$imageType = Utils::getImageType($content, $error);
618+
if ($imageType === false) {
619+
$this->addFlash('danger', sprintf('image: %s', $error));
620+
return $this->redirectToRoute('jury_problem_testcases', ['probId' => $probId]);
621+
}
622+
$thumb = Utils::getImageThumb($content, $thumbnailSize,
623+
$this->dj->getDomjudgeTmpDir(), $error);
624+
if ($thumb === false) {
625+
$this->addFlash('danger', sprintf('image: %s', $error));
626+
return $this->redirectToRoute('jury_problem_testcases', ['probId' => $probId]);
627+
}
618628
}
619629

620630
$testcase->setImageType($imageType);

webapp/src/Service/DOMJudgeService.php

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -85,6 +85,12 @@ class DOMJudgeService
8585
'image/svg+xml' => 'svg',
8686
];
8787

88+
final public const EXTENSION_TO_MIMETYPE = [
89+
'png' => 'image/png',
90+
'jpg' => 'image/jpeg',
91+
'svg' => 'image/svg+xml',
92+
];
93+
8894
public function __construct(
8995
protected readonly EntityManagerInterface $em,
9096
protected readonly LoggerInterface $logger,

webapp/src/Service/ImportProblemService.php

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -427,6 +427,15 @@ public function importZippedProblem(
427427
break;
428428
}
429429
}
430+
// Handle SVG differently, as a lot of the above concepts do not make sense in this context.
431+
$imageFileName = $baseFileName . '.svg';
432+
if (($imageFile = $zip->getFromName($imageFileName)) !== false) {
433+
if (($imageFile = Utils::sanitizeSvg($imageFile)) === false) {
434+
$messages['warning'][] = sprintf("Contents of '%s' is not safe.", $imageFileName);
435+
}
436+
$imageType = 'svg';
437+
$imageThumb = $imageFile;
438+
}
430439

431440
if (str_contains($testInput, "\r")) {
432441
$messages['warning'][] = "Testcase file '$baseFileName.in' contains Windows newlines.";

webapp/templates/jury/submission.html.twig

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -742,7 +742,8 @@
742742
<span style="float:right; border: 3px solid #438ec3; margin: 5px; padding: 5px;">
743743
{% set imgUrl = path('jury_problem_testcase_fetch', {'probId': submission.problem.probid, 'rank': run.rank, 'type': 'image'}) %}
744744
<a href="{{ imgUrl }}">
745-
<img src="data:image/{{ run.imageType }};base64,{{ runsOutput[runIdx].image_thumb | base64 }}"/>
745+
{% set EXTENSION_TO_MIMETYPE = constant('App\\Service\\DOMJudgeService::EXTENSION_TO_MIMETYPE') %}
746+
<img src="data:{{ EXTENSION_TO_MIMETYPE[run.imageType] }};base64,{{ runsOutput[runIdx].image_thumb | base64 }}"/>
746747
</a>
747748
</span>
748749
{% endif %}

0 commit comments

Comments
 (0)