diff --git a/client/html/post_merge_side.tpl b/client/html/post_merge_side.tpl
index fe705027..a08070f0 100644
--- a/client/html/post_merge_side.tpl
+++ b/client/html/post_merge_side.tpl
@@ -42,6 +42,7 @@
'image/heic': 'HEIC',
'video/webm': 'WEBM',
'video/mp4': 'MPEG-4',
+ 'video/quicktime': 'MOV',
'application/x-shockwave-flash': 'SWF',
}[ctx.post.mimeType] +
' (' +
diff --git a/client/html/post_readonly_sidebar.tpl b/client/html/post_readonly_sidebar.tpl
index 4f18624f..0f93ae3b 100644
--- a/client/html/post_readonly_sidebar.tpl
+++ b/client/html/post_readonly_sidebar.tpl
@@ -15,6 +15,7 @@
'image/heic': 'HEIC',
'video/webm': 'WEBM',
'video/mp4': 'MPEG-4',
+ 'video/quicktime': 'MOV',
'application/x-shockwave-flash': 'SWF',
}[ctx.post.mimeType] %>
diff --git a/client/js/views/post_upload_view.js b/client/js/views/post_upload_view.js
index fc98a19e..4ef4c1ad 100644
--- a/client/js/views/post_upload_view.js
+++ b/client/js/views/post_upload_view.js
@@ -22,6 +22,7 @@ function _mimeTypeToPostType(mimeType) {
"image/heic": "image",
"video/mp4": "video",
"video/webm": "video",
+ "video/quicktime": "video",
}[mimeType] || "unknown"
);
}
@@ -120,6 +121,7 @@ class Url extends Uploadable {
heif: "image/heif",
heic: "image/heic",
mp4: "video/mp4",
+ mov: "video/quicktime",
webm: "video/webm",
};
for (let extension of Object.keys(mime)) {
diff --git a/server/szurubooru/func/mime.py b/server/szurubooru/func/mime.py
index ee10b9db..8fae5679 100644
--- a/server/szurubooru/func/mime.py
+++ b/server/szurubooru/func/mime.py
@@ -39,6 +39,9 @@ def get_mime_type(content: bytes) -> str:
if content[4:12] in (b"ftypisom", b"ftypiso5", b"ftypiso6", b"ftypmp42", b"ftypM4V "):
return "video/mp4"
+ if content[4:12] == b"ftypqt ":
+ return "video/quicktime"
+
return "application/octet-stream"
@@ -54,6 +57,7 @@ def get_extension(mime_type: str) -> Optional[str]:
"image/heif": "heif",
"image/heic": "heic",
"video/mp4": "mp4",
+ "video/quicktime": "mov",
"video/webm": "webm",
"application/octet-stream": "dat",
}
@@ -65,7 +69,12 @@ def is_flash(mime_type: str) -> bool:
def is_video(mime_type: str) -> bool:
- return mime_type.lower() in ("application/ogg", "video/mp4", "video/webm")
+ return mime_type.lower() in (
+ "application/ogg",
+ "video/mp4",
+ "video/quicktime",
+ "video/webm",
+ )
def is_image(mime_type: str) -> bool:
diff --git a/server/szurubooru/tests/assets/mov.mov b/server/szurubooru/tests/assets/mov.mov
new file mode 100644
index 00000000..911ee852
Binary files /dev/null and b/server/szurubooru/tests/assets/mov.mov differ
diff --git a/server/szurubooru/tests/func/test_mime.py b/server/szurubooru/tests/func/test_mime.py
index b33746b4..551ba7c3 100644
--- a/server/szurubooru/tests/func/test_mime.py
+++ b/server/szurubooru/tests/func/test_mime.py
@@ -7,6 +7,7 @@ from szurubooru.func import mime
"input_path,expected_mime_type",
[
("mp4.mp4", "video/mp4"),
+ ("mov.mov", "video/quicktime"),
("webm.webm", "video/webm"),
("flash.swf", "application/x-shockwave-flash"),
("png.png", "image/png"),
@@ -35,6 +36,7 @@ def test_get_mime_type_for_empty_file():
[
("video/mp4", "mp4"),
("video/webm", "webm"),
+ ("video/quicktime", "mov"),
("application/x-shockwave-flash", "swf"),
("image/png", "png"),
("image/jpeg", "jpg"),
@@ -70,6 +72,8 @@ def test_is_flash(input_mime_type, expected_state):
("VIDEO/WEBM", True),
("video/mp4", True),
("VIDEO/MP4", True),
+ ("video/quicktime", True),
+ ("VIDEO/QUICKTIME", True),
("video/anything_else", False),
("application/ogg", True),
("not a video", False),