From 37b87eb284c08530457d93c611eba582fd4fa82a Mon Sep 17 00:00:00 2001 From: Johannes Meyer Date: Mon, 20 Jul 2015 10:52:28 +0200 Subject: [PATCH] js: Add fallback in case XHR file uploads are not possible refs #8758 --- public/js/icinga/events.js | 11 +++++++++++ public/js/icinga/loader.js | 29 +++++++++++++++++++++++++++++ 2 files changed, 40 insertions(+) diff --git a/public/js/icinga/events.js b/public/js/icinga/events.js index 51f9846f9..a1048095b 100644 --- a/public/js/icinga/events.js +++ b/public/js/icinga/events.js @@ -269,6 +269,17 @@ url = icinga.utils.addUrlParams(url, dataObj); } else { if (encoding === 'multipart/form-data') { + if (typeof window.FormData === 'undefined') { + icinga.loader.submitFormToIframe($form, url, $target); + + // Disable all form controls to prevent resubmission as early as possible. + // (This relies on native form submission, so using setTimeout is the only possible solution) + setTimeout(function () { + $form.find(':input:not(:disabled)').prop('disabled', true); + }, 0); + return true; + } + data = new window.FormData($form[0]); } else { data = $form.serializeArray(); diff --git a/public/js/icinga/loader.js b/public/js/icinga/loader.js index 5677eb629..3a3e1a4bf 100644 --- a/public/js/icinga/loader.js +++ b/public/js/icinga/loader.js @@ -140,6 +140,35 @@ return req; }, + /** + * Mimic XHR form submission by using an iframe + * + * @param {object} $form The form being submitted + * @param {string} action The form's action URL + * @param {object} $target The target container + */ + submitFormToIframe: function ($form, action, $target) { + var self = this; + + $form.prop('action', self.icinga.utils.addUrlParams(action, { + '_disableLayout': true + })); + $form.prop('target', 'fileupload-frame-target'); + $('#fileupload-frame-target').on('load', function (event) { + var $frame = $(event.target); + + // Fetch the frame's new content, paste it into the target.. + self.renderContentToContainer( + $frame.contents().find('body').html(), + $target, + 'replace' + ); + $frame.prop('src', 'about:blank'); // ..and clear the frame's dom + + $frame.off('load'); // Unbind the event as it's set on demand + }); + }, + /** * Create an URL relative to the Icinga base Url, still unused *