Add S3KeyCleaner (#348)
This commit is contained in:
54
app/Service/Storage/S3KeyCleaner.php
Normal file
54
app/Service/Storage/S3KeyCleaner.php
Normal file
@@ -0,0 +1,54 @@
|
||||
<?php
|
||||
|
||||
namespace App\Service\Storage;
|
||||
|
||||
class S3KeyCleaner
|
||||
{
|
||||
public static function sanitize($objectKey, $separator = '-')
|
||||
{
|
||||
return (new self())->sanitizeS3Key($objectKey, $separator);
|
||||
}
|
||||
|
||||
public function replaceLatinCharacters($value)
|
||||
{
|
||||
// Load the latin map
|
||||
$latinMap = json_decode(\File::get(resource_path('data/latin-map.json')), true);
|
||||
|
||||
$result = '';
|
||||
$length = mb_strlen($value);
|
||||
for ($i = 0; $i < $length; $i++) {
|
||||
$char = mb_substr($value, $i, 1);
|
||||
$result .= array_key_exists($char, $latinMap) ? $latinMap[$char] : $char;
|
||||
}
|
||||
return $result;
|
||||
}
|
||||
|
||||
private function removeIllegalCharacters($value)
|
||||
{
|
||||
$SAFE_CHARACTERS = '/[^0-9a-zA-Z! _\\.\\*\'\\(\\)\\-\\/]/';
|
||||
return preg_replace($SAFE_CHARACTERS, '', $value);
|
||||
}
|
||||
|
||||
private function isValidSeparator($separator)
|
||||
{
|
||||
$SAFE_CHARACTERS = '/[^0-9a-zA-Z! _\\.\\*\'\\(\\)\\-\\/]/';
|
||||
return $separator && !preg_match($SAFE_CHARACTERS, $separator);
|
||||
}
|
||||
|
||||
public function sanitizeS3Key($objectKey, $separator = '-')
|
||||
{
|
||||
if (!$this->isValidSeparator($separator)) {
|
||||
throw new \Exception("${separator} is not a valid separator");
|
||||
}
|
||||
|
||||
if (!$objectKey || (!is_string($objectKey) && !is_numeric($objectKey))) {
|
||||
throw new \Exception("Expected non-empty string or number, got ${objectKey}");
|
||||
}
|
||||
|
||||
if (is_numeric($objectKey)) {
|
||||
return strval($objectKey);
|
||||
}
|
||||
|
||||
return str_replace(' ', $separator, $this->removeIllegalCharacters($this->replaceLatinCharacters(trim($objectKey))));
|
||||
}
|
||||
}
|
||||
@@ -30,10 +30,10 @@ class StorageFileNameParser
|
||||
public function getMovedFileName(): ?string
|
||||
{
|
||||
if ($this->fileName && $this->extension) {
|
||||
$fileName = substr($this->fileName, 0, 50).'_'.$this->uuid.'.'.$this->extension;
|
||||
$fileName = substr($this->fileName, 0, 50) . '_' . $this->uuid . '.' . $this->extension;
|
||||
$fileName = preg_replace('#\p{C}+#u', '', $fileName); // avoid CorruptedPathDetected exceptions
|
||||
|
||||
return mb_convert_encoding($fileName, 'UTF-8', 'UTF-8');
|
||||
return S3KeyCleaner::sanitize($fileName);
|
||||
}
|
||||
|
||||
return $this->uuid;
|
||||
@@ -47,13 +47,15 @@ class StorageFileNameParser
|
||||
return;
|
||||
}
|
||||
|
||||
if (! str_contains($fileName, '_')) {
|
||||
if (!str_contains($fileName, '_')) {
|
||||
return;
|
||||
}
|
||||
|
||||
$candidateString = substr($fileName, strrpos($fileName, '_') + 1);
|
||||
if (! str_contains($candidateString, '.')
|
||||
|| ! Str::isUuid(substr($candidateString, 0, strpos($candidateString, '.')))) {
|
||||
if (
|
||||
!str_contains($candidateString, '.')
|
||||
|| !Str::isUuid(substr($candidateString, 0, strpos($candidateString, '.')))
|
||||
) {
|
||||
return;
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user