FIX: catch all server-side error when uploading a file

UX: always show a message to the user whenever an error happens on the server when uploading a file
This commit is contained in:
Régis Hanol 2017-12-27 16:33:25 +01:00
parent 805d1c25d3
commit f5e170c6b5
6 changed files with 34 additions and 28 deletions

View File

@ -493,7 +493,7 @@ export default Ember.Component.extend({
this._xhr = null; this._xhr = null;
if (!userCancelled) { if (!userCancelled) {
displayErrorForUpload(data.jqXHR.responseJSON); displayErrorForUpload(data);
} }
}); });

View File

@ -334,27 +334,27 @@ export function getUploadMarkdown(upload) {
} }
export function displayErrorForUpload(data) { export function displayErrorForUpload(data) {
// deal with meaningful errors first
if (data.jqXHR) { if (data.jqXHR) {
switch (data.jqXHR.status) { switch (data.jqXHR.status) {
// cancelled by the user // cancelled by the user
case 0: return; case 0:
return;
// entity too large, usually returned from the web server // entity too large, usually returned from the web server
case 413: case 413:
var type = uploadTypeFromFileName(data.files[0].name); const type = uploadTypeFromFileName(data.files[0].name);
var maxSizeKB = Discourse.SiteSettings['max_' + type + '_size_kb']; const max_size_kb = Discourse.SiteSettings[`max_${type}_size_kb`];
bootbox.alert(I18n.t('post.errors.file_too_large', { max_size_kb: maxSizeKB })); bootbox.alert(I18n.t('post.errors.file_too_large', { max_size_kb }));
return; return;
// the error message is provided by the server // the error message is provided by the server
case 422: case 422:
if (data.jqXHR.responseJSON.message) { if (data.jqXHR.responseJSON.message) {
bootbox.alert(data.jqXHR.responseJSON.message); bootbox.alert(data.jqXHR.responseJSON.message);
} else { } else {
bootbox.alert(data.jqXHR.responseJSON.join("\n")); bootbox.alert(data.jqXHR.responseJSON.join("\n"));
} }
return; return;
} }
} else if (data.errors && data.errors.length > 0) { } else if (data.errors && data.errors.length > 0) {
bootbox.alert(data.errors.join("\n")); bootbox.alert(data.errors.join("\n"));

View File

@ -56,7 +56,7 @@ export default Em.Mixin.create({
}); });
$upload.on("fileuploadfail", (e, data) => { $upload.on("fileuploadfail", (e, data) => {
displayErrorForUpload(data.jqXHR.responseJSON); displayErrorForUpload(data);
reset(); reset();
}); });
}.on("didInsertElement"), }.on("didInsertElement"),

View File

@ -26,17 +26,22 @@ class UploadsController < ApplicationController
# note, atm hijack is processed in its own context and has not access to controller # note, atm hijack is processed in its own context and has not access to controller
# longer term we may change this # longer term we may change this
hijack do hijack do
info = UploadsController.create_upload( begin
current_user: me, info = UploadsController.create_upload(
file: file, current_user: me,
url: url, file: file,
type: type, url: url,
for_private_message: for_private_message, type: type,
pasted: pasted, for_private_message: for_private_message,
is_api: is_api, pasted: pasted,
retain_hours: retain_hours is_api: is_api,
) retain_hours: retain_hours
render json: UploadsController.serialize_upload(info), status: Upload === info ? 200 : 422 )
rescue => e
render json: failed_json.merge(message: e.message&.split("\n")&.first), status: 422
else
render json: UploadsController.serialize_upload(info), status: Upload === info ? 200 : 422
end
end end
end end

View File

@ -2873,6 +2873,7 @@ en:
store_failure: "Failed to store upload #%{upload_id} for user #%{user_id}." store_failure: "Failed to store upload #%{upload_id} for user #%{user_id}."
file_missing: "Sorry, you must provide a file to upload." file_missing: "Sorry, you must provide a file to upload."
empty: "Sorry, but the file you provided is empty." empty: "Sorry, but the file you provided is empty."
png_to_jpg_conversion_failure_message: "An error happened when converting from PNG to JPG."
attachments: attachments:
too_large: "Sorry, the file you are trying to upload is too big (maximum size is %{max_size_kb}KB)." too_large: "Sorry, the file you are trying to upload is too big (maximum size is %{max_size_kb}KB)."
images: images:

View File

@ -163,7 +163,7 @@ class UploadCreator
command << '-debug' << 'all' if debug command << '-debug' << 'all' if debug
command << output_file.path command << output_file.path
Discourse::Utils.execute_command(*command, failure_message: "failed to convert png to jpg") Discourse::Utils.execute_command(*command, failure_message: I18n.t("upload.png_to_jpg_conversion_failure_message"))
end end
def should_downsize? def should_downsize?