use DataUploadEvent fields rather than required metadata

This commit is contained in:
Shish 2023-02-22 23:37:37 +00:00
parent cfa7434d8d
commit 36951db563
19 changed files with 83 additions and 180 deletions

View file

@ -313,43 +313,20 @@ abstract class DataHandlerExtension extends Extension
if (is_null($existing)) {
throw new UploadException("Post to replace does not exist!");
}
if ($existing->hash === $event->metadata['hash']) {
if ($existing->hash === $event->hash) {
throw new UploadException("The uploaded post is the same as the one to replace.");
}
// even more hax..
$event->metadata['tags'] = $existing->get_tag_list();
$image = $this->create_image_from_data(warehouse_path(Image::IMAGE_DIR, $event->metadata['hash']), $event->metadata);
if (is_null($image)) {
throw new UploadException("Data handler failed to create post object from data");
}
if (empty($image->get_mime())) {
throw new UploadException("Unable to determine MIME for ". $event->tmpname);
}
try {
send_event(new MediaCheckPropertiesEvent($image));
} catch (MediaException $e) {
throw new UploadException("Unable to scan media properties: ".$e->getMessage());
}
$image = $this->create_image_from_data(warehouse_path(Image::IMAGE_DIR, $event->hash), $event->metadata);
send_event(new ImageReplaceEvent($event->replace_id, $image));
$_id = $event->replace_id;
assert(!is_null($_id));
$event->image_id = $_id;
} else {
$image = $this->create_image_from_data(warehouse_path(Image::IMAGE_DIR, $event->hash), $event->metadata);
if (is_null($image)) {
throw new UploadException("Data handler failed to create post object from data");
}
if (empty($image->get_mime())) {
throw new UploadException("Unable to determine MIME for ". $event->tmpname);
}
try {
send_event(new MediaCheckPropertiesEvent($image));
} catch (MediaException $e) {
throw new UploadException("Unable to scan media properties: ".$e->getMessage());
}
$iae = send_event(new ImageAdditionEvent($image));
$event->image_id = $iae->image->id;
$event->merged = $iae->merged;
@ -402,7 +379,7 @@ abstract class DataHandlerExtension extends Extension
public function onMediaCheckProperties(MediaCheckPropertiesEvent $event)
{
if ($this->supported_mime($event->mime)) {
if ($this->supported_mime($event->image->get_mime())) {
$this->media_check_properties($event);
}
}
@ -411,19 +388,23 @@ abstract class DataHandlerExtension extends Extension
{
$image = new Image();
$image->filesize = $metadata['size'];
$image->hash = $metadata['hash'];
assert(is_readable($filename));
$image->filesize = filesize($filename);
$image->hash = md5_file($filename);
$image->filename = (($pos = strpos($metadata['filename'], '?')) !== false) ? substr($metadata['filename'], 0, $pos) : $metadata['filename'];
if (array_key_exists("extension", $metadata)) {
$image->set_mime(MimeType::get_for_file($filename, $metadata["extension"]));
} else {
$image->set_mime(MimeType::get_for_file($filename));
}
$image->set_mime(MimeType::get_for_file($filename, get_file_ext($metadata["filename"]) ?? null));
$image->tag_array = is_array($metadata['tags']) ? $metadata['tags'] : Tag::explode($metadata['tags']);
$image->source = $metadata['source'];
if (empty($image->get_mime())) {
throw new UploadException("Unable to determine MIME for $filename");
}
try {
send_event(new MediaCheckPropertiesEvent($image));
} catch (MediaException $e) {
throw new UploadException("Unable to scan media properties $filename / $image->filename / $image->hash: ".$e->getMessage());
}
return $image;
}

View file

@ -39,22 +39,18 @@ function add_dir(string $base): array
/**
* Sends a DataUploadEvent for a file.
*/
function add_image(string $tmpname, string $filename, string $tags): int
function add_image(string $tmpname, string $filename, string $tags, ?string $source=null): DataUploadEvent
{
assert(file_exists($tmpname));
$pathinfo = pathinfo($filename);
$metadata = [];
$metadata['filename'] = $pathinfo['basename'];
if (array_key_exists('extension', $pathinfo)) {
$metadata['extension'] = $pathinfo['extension'];
return send_event(new DataUploadEvent($tmpname, [
'filename' => pathinfo($filename, PATHINFO_BASENAME),
'tags' => Tag::explode($tags),
'source' => $source,
]));
}
$metadata['tags'] = Tag::explode($tags);
$metadata['source'] = null;
$due = send_event(new DataUploadEvent($tmpname, $metadata));
return $due->image_id;
function get_file_ext(string $filename): ?string
{
return pathinfo($filename)['extension'] ?? null;
}
/**

View file

@ -50,17 +50,7 @@ class BulkAddCSV extends Extension
*/
private function add_image(string $tmpname, string $filename, string $tags, string $source, string $rating, string $thumbfile)
{
assert(file_exists($tmpname));
$pathinfo = pathinfo($filename);
$metadata = [];
$metadata['filename'] = $pathinfo['basename'];
if (array_key_exists('extension', $pathinfo)) {
$metadata['extension'] = $pathinfo['extension'];
}
$metadata['tags'] = Tag::explode($tags);
$metadata['source'] = $source;
$event = send_event(new DataUploadEvent($tmpname, $metadata));
$event = add_image($tmpname, $filename, $tags, $source);
if ($event->image_id == -1) {
throw new UploadException("File type not recognised");
} else {
@ -105,12 +95,11 @@ class BulkAddCSV extends Extension
$source = $csvdata[2];
$rating = $csvdata[3];
$thumbfile = $csvdata[4];
$pathinfo = pathinfo($fullpath);
$shortpath = $pathinfo["basename"];
$shortpath = pathinfo($fullpath, PATHINFO_BASENAME);
$list .= "<br>".html_escape("$shortpath (".str_replace(" ", ", ", $tags).")... ");
if (file_exists($csvdata[0]) && is_file($csvdata[0])) {
try {
$this->add_image($fullpath, $pathinfo["basename"], $tags, $source, $rating, $thumbfile);
$this->add_image($fullpath, $shortpath, $tags, $source, $rating, $thumbfile);
$list .= "ok\n";
} catch (\Exception $ex) {
$list .= "failed:<br>". $ex->getMessage();

View file

@ -52,7 +52,7 @@ class BulkImportExport extends DataHandlerExtension
file_put_contents($tmpfile, $stream);
$id = add_image($tmpfile, $item->filename, Tag::implode($item->tags));
$id = add_image($tmpfile, $item->filename, Tag::implode($item->tags))->image_id;
if ($id==-1) {
throw new SCoreException("Unable to import file $item->hash");

View file

@ -466,29 +466,11 @@ class CronUploader extends Extension
*/
private function add_image(string $tmpname, string $filename, string $tags): DataUploadEvent
{
assert(file_exists($tmpname));
$tagArray = Tag::explode($tags);
if (count($tagArray) == 0) {
$tagArray[] = "tagme";
}
$pathinfo = pathinfo($filename);
$metadata = [];
$metadata ['filename'] = $pathinfo ['basename'];
if (array_key_exists('extension', $pathinfo)) {
$metadata ['extension'] = $pathinfo ['extension'];
}
$metadata ['tags'] = $tagArray;
$metadata ['source'] = null;
$event = send_event(new DataUploadEvent($tmpname, $metadata));
$event = add_image($tmpname, $filename, $tags, null);
// Generate info message
if ($event->image_id == -1) {
if (array_key_exists("mime", $event->metadata)) {
throw new UploadException("File type not recognised (".$event->metadata["mime"]."). Filename: {$filename}");
}
throw new UploadException("File type not recognised. Filename: {$filename}");
throw new UploadException("File type not recognised (".$event->mime."). Filename: {$filename}");
} elseif ($event->merged === true) {
$infomsg = "Post merged. ID: {$event->image_id} - Filename: {$filename}";
} else {
@ -529,14 +511,12 @@ class CronUploader extends Extension
$ite = new \RecursiveDirectoryIterator($base, \FilesystemIterator::SKIP_DOTS);
foreach (new \RecursiveIteratorIterator($ite) as $fullpath => $cur) {
if (!is_link($fullpath) && !is_dir($fullpath) && !$this->is_skippable_file($fullpath)) {
$pathinfo = pathinfo($fullpath);
$relativePath = substr($fullpath, strlen($base));
$tags = path_to_tags($relativePath);
yield [
0 => $fullpath,
1 => $pathinfo ["basename"],
1 => pathinfo($fullpath, PATHINFO_BASENAME),
2 => $tags
];
}

View file

@ -336,22 +336,13 @@ class DanbooruApi extends Extension
return;
}
// Fire off an event which should process the new file and add it to the db
$fileinfo = pathinfo($filename);
$metadata = [];
$metadata['filename'] = $fileinfo['basename'];
if (array_key_exists('extension', $fileinfo)) {
$metadata['extension'] = $fileinfo['extension'];
}
$metadata['tags'] = $posttags;
$metadata['source'] = $source;
//log_debug("danbooru_api","========== NEW($filename) =========");
//log_debug("danbooru_api", "upload($filename): fileinfo(".var_export($fileinfo,TRUE)."), metadata(".var_export($metadata,TRUE).")...");
try {
$nevent = new DataUploadEvent($file, $metadata);
// Fire off an event which should process the new file and add it to the db
$nevent = add_image($file, $filename, $posttags, $source);
//log_debug("danbooru_api", "send_event(".var_export($nevent,TRUE).")");
send_event($nevent);
// If it went ok, grab the id for the newly uploaded image and pass it in the header
$newimg = Image::by_hash($hash); // FIXME: Unsupported file doesn't throw an error?
$newid = make_link("post/view/" . $newimg->id);

View file

@ -14,8 +14,7 @@ class EmoticonListTheme extends Themelet
$html .= "<table><tr>";
$n = 1;
foreach ($list as $item) {
$pathinfo = pathinfo($item);
$name = $pathinfo["filename"];
$name = pathinfo($item, PATHINFO_FILENAME);
$html .= "<td><img alt='$name' src='$data_href/$item'> :$name:</td>";
if ($n++ % 3 == 0) {
$html .= "</tr><tr>";

View file

@ -15,7 +15,7 @@ class CBZFileHandler extends DataHandlerExtension
$event->image->audio = false;
$event->image->image = false;
$tmp = $this->get_representative_image($event->file_name);
$tmp = $this->get_representative_image($event->image->get_image_filename());
$info = getimagesize($tmp);
if ($info) {
$event->image->width = $info[0];

View file

@ -14,7 +14,7 @@ class FlashFileHandler extends DataHandlerExtension
$event->image->video = true;
$event->image->image = false;
$info = getimagesize($event->file_name);
$info = getimagesize($event->image->get_image_filename());
if ($info) {
$event->image->width = $info[0];
$event->image->height = $info[1];

View file

@ -13,9 +13,9 @@ class IcoFileHandler extends DataHandlerExtension
$event->image->lossless = true;
$event->image->video = false;
$event->image->audio = false;
$event->image->image = ($event->mime!= MimeType::ANI);
$event->image->image = ($event->image->get_mime() != MimeType::ANI);
$fp = fopen($event->file_name, "r");
$fp = fopen($event->image->get_image_filename(), "r");
try {
unpack("Snull/Stype/Scount", fread($fp, 6));
$subheader = unpack("Cwidth/Cheight/Ccolours/Cnull/Splanes/Sbpp/Lsize/loffset", fread($fp, 16));

View file

@ -10,14 +10,17 @@ class PixelFileHandler extends DataHandlerExtension
protected function media_check_properties(MediaCheckPropertiesEvent $event): void
{
$event->image->lossless = Media::is_lossless($event->file_name, $event->mime);
$filename = $event->image->get_image_filename();
$mime = $event->image->get_mime();
$event->image->lossless = Media::is_lossless($filename, $mime);
$event->image->audio = false;
switch ($event->mime) {
switch ($mime) {
case MimeType::GIF:
$event->image->video = MimeType::is_animated_gif($event->file_name);
$event->image->video = MimeType::is_animated_gif($filename);
break;
case MimeType::WEBP:
$event->image->video = MimeType::is_animated_webp($event->file_name);
$event->image->video = MimeType::is_animated_webp($filename);
break;
default:
$event->image->video = false;
@ -25,7 +28,7 @@ class PixelFileHandler extends DataHandlerExtension
}
$event->image->image = !$event->image->video;
$info = getimagesize($event->file_name);
$info = getimagesize($event->image->get_image_filename());
if ($info) {
$event->image->width = $info[0];
$event->image->height = $info[1];

View file

@ -39,7 +39,7 @@ class SVGFileHandler extends DataHandlerExtension
$event->image->audio = false;
$event->image->image = true;
$msp = new MiniSVGParser($event->file_name);
$msp = new MiniSVGParser($event->image->get_image_filename());
$event->image->width = $msp->width;
$event->image->height = $msp->height;
}
@ -50,6 +50,7 @@ class SVGFileHandler extends DataHandlerExtension
$sanitizer->removeRemoteReferences(true);
$dirtySVG = file_get_contents($event->tmpname);
$cleanSVG = $sanitizer->sanitize($dirtySVG);
$event->hash = md5($cleanSVG);
file_put_contents(warehouse_path(Image::IMAGE_DIR, $event->hash), $cleanSVG);
}

View file

@ -18,7 +18,7 @@ class SVGFileHandlerTest extends ShimmiePHPUnitTestCase
# FIXME: test that it gets displayed properly
}
public function testAbuiveSVG()
public function testAbusiveSVG()
{
$this->log_in_as_user();
$image_id = $this->post_image("tests/alert.svg", "something");

View file

@ -64,7 +64,7 @@ class VideoFileHandler extends DataHandlerExtension
$event->image->video = true;
$event->image->image = false;
try {
$data = Media::get_ffprobe_data($event->file_name);
$data = Media::get_ffprobe_data($event->image->get_image_filename());
if (is_array($data)) {
if (array_key_exists("streams", $data)) {

View file

@ -55,15 +55,8 @@ class MediaResizeEvent extends Event
class MediaCheckPropertiesEvent extends Event
{
public Image $image;
public string $file_name;
public string $mime;
public function __construct(Image $image)
public function __construct(public Image $image)
{
parent::__construct();
$this->image = $image;
$this->file_name = warehouse_path(Image::IMAGE_DIR, $image->hash);
$this->mime = strtolower($image->get_mime());
}
}

View file

@ -168,20 +168,18 @@ class TranscodeImage extends Extension
global $config;
if ($config->get_bool(TranscodeConfig::UPLOAD) == true) {
$mime = strtolower($event->mime);
if ($mime===MimeType::GIF&&MimeType::is_animated_gif($event->tmpname)) {
if ($event->mime === MimeType::GIF&&MimeType::is_animated_gif($event->tmpname)) {
return;
}
if (in_array($mime, array_values(self::INPUT_MIMES))) {
$target_mime = self::get_mapping($mime);
if (in_array($event->mime, array_values(self::INPUT_MIMES))) {
$target_mime = self::get_mapping($event->mime);
if (empty($target_mime)) {
return;
}
try {
$new_image = $this->transcode_image($event->tmpname, $mime, $target_mime);
$event->set_mime($target_mime);
$event->set_tmpname($new_image);
$new_image = $this->transcode_image($event->tmpname, $event->mime, $target_mime);
$event->set_tmpname($new_image, $target_mime);
} catch (\Exception $e) {
log_error("transcode", "Error while performing upload transcode: ".$e->getMessage());
// We don't want to interfere with the upload process,

View file

@ -85,8 +85,7 @@ class TranscodeVideo extends Extension
// }
// try {
// $new_image = $this->transcode_image($event->tmpname, $ext, $target_format);
// $event->set_mime(Media::determine_ext($target_format));
// $event->set_tmpname($new_image);
// $event->set_tmpname($new_image, Media::determine_ext($target_format));
// } catch (Exception $e) {
// log_error("transcode_video", "Error while performing upload transcode: ".$e->getMessage());
// // We don't want to interfere with the upload process,

View file

@ -11,63 +11,46 @@ require_once "config.php";
*/
class DataUploadEvent extends Event
{
public string $tmpname;
public array $metadata;
public string $hash;
public string $mime = "";
public string $mime;
public int $size;
public int $image_id = -1;
public ?int $replace_id = null;
public bool $handled = false;
public bool $merged = false;
/**
* Some data is being uploaded.
* This should be caught by a file handler.
* $metadata should contain at least "filename", "extension", "tags" and "source".
*/
public function __construct(string $tmpname, array $metadata, ?int $replace_id = null)
{
public function __construct(
public string $tmpname,
public array $metadata,
public ?int $replace_id = null
) {
parent::__construct();
assert(file_exists($tmpname));
$this->set_tmpname($tmpname);
assert(is_string($metadata["filename"]));
assert(is_array($metadata["tags"]));
assert(is_string($metadata["source"]) || is_null($metadata["source"]));
// DB limits to 255 char filenames
$metadata['filename'] = substr($metadata['filename'], 0, 255);
$this->metadata = $metadata;
$this->replace_id = $replace_id;
$this->set_tmpname($tmpname);
if (array_key_exists("extension", $metadata)) {
$mime = MimeType::get_for_file($tmpname, $metadata["extension"]);
} else {
$mime = MimeType::get_for_file($tmpname);
}
if (empty($mime)) {
throw new UploadException("Could not determine mime type for file " . $metadata["filename"]);
}
$this->set_mime($mime);
}
public function set_mime(String $mime)
{
$this->mime = strtolower($mime);
$this->metadata["mime"] = $this->mime;
}
public function set_tmpname(String $tmpname)
public function set_tmpname(string $tmpname, ?string $mime=null)
{
assert(is_readable($tmpname));
$this->tmpname = $tmpname;
$this->metadata['hash'] = md5_file($tmpname);
$this->metadata['size'] = filesize($tmpname);
// useful for most file handlers, so pull directly into fields
$this->hash = $this->metadata['hash'];
$this->hash = md5_file($tmpname);
$this->size = filesize($tmpname);
$mime = $mime ?? MimeType::get_for_file($tmpname, get_file_ext($this->metadata["filename"]) ?? null);
if (empty($mime)) {
throw new UploadException("Could not determine mime type");
}
$this->mime = strtolower($mime);
}
}
@ -162,8 +145,8 @@ class Upload extends Extension
if ($this->is_full) {
throw new UploadException("Upload failed; disk nearly full");
}
if (filesize($event->tmpname) > $config->get_int(UploadConfig::SIZE)) {
$size = to_shorthand_int(filesize($event->tmpname));
if ($event->size > $config->get_int(UploadConfig::SIZE)) {
$size = to_shorthand_int($event->size);
$limit = to_shorthand_int($config->get_int(UploadConfig::SIZE));
throw new UploadException("File too large ($size > $limit)");
}
@ -343,22 +326,15 @@ class Upload extends Extension
throw new UploadException($this->upload_error_message($file['error'][$i]));
}
$pathinfo = pathinfo($file['name'][$i]);
$metadata = [];
$metadata['filename'] = $pathinfo['basename'];
$metadata['extension'] = $pathinfo['extension'] ?? "";
$metadata['mime'] = MimeType::get_for_file($file['tmp_name'][$i], $metadata['extension']);
if (empty($metadata['mime'])) {
throw new UploadException("Unable to determine MIME for file " . $metadata['filename']);
}
$metadata['filename'] = pathinfo($file['name'][$i], PATHINFO_BASENAME);
$metadata['tags'] = $tags;
$metadata['source'] = $source;
$event = new DataUploadEvent($file['tmp_name'][$i], $metadata, $replace_id);
send_event($event);
if ($event->image_id == -1) {
throw new UploadException("MIME type not supported: " . $metadata['mime']);
throw new UploadException("MIME type not supported: " . $event->mime);
}
$image_ids[] = $event->image_id;
$page->add_http_header("X-Shimmie-Post-ID: " . $event->image_id);
@ -404,12 +380,10 @@ class Upload extends Extension
$h_filename = ($s_filename ? preg_replace('/^.*filename="([^ ]+)"/i', '$1', $s_filename) : null);
$filename = $h_filename ?: basename($url);
$pathinfo = pathinfo($url);
$metadata = [];
$metadata['filename'] = $filename;
$metadata['tags'] = $tags;
$metadata['source'] = (($url == $source) && !$config->get_bool(UploadConfig::TLSOURCE) ? "" : $source);
$metadata['extension'] = $pathinfo['extension'] ?? "";
if ($user->can(Permissions::EDIT_IMAGE_LOCK) && !empty($_GET['locked'])) {
$metadata['locked'] = bool_escape($_GET['locked']) ? "on" : "";
}
@ -422,7 +396,7 @@ class Upload extends Extension
$event = new DataUploadEvent($tmp_filename, $metadata, $replace_id);
send_event($event);
if ($event->image_id == -1) {
throw new UploadException("File type not supported: " . $metadata['extension']);
throw new UploadException("File type not supported: " . $event->mime);
}
$image_ids[] = $event->image_id;
} catch (UploadException $ex) {

View file

@ -250,7 +250,6 @@ abstract class ShimmiePHPUnitTestCase extends TestCase
{
$dae = send_event(new DataUploadEvent($filename, [
"filename" => $filename,
"extension" => pathinfo($filename, PATHINFO_EXTENSION),
"tags" => Tag::explode($tags),
"source" => null,
]));