Skip to content

Instantly share code, notes, and snippets.

@Jako
Last active November 3, 2024 15:47
Show Gist options
  • Save Jako/befda58500189c12b5a8ecdfb19201bf to your computer and use it in GitHub Desktop.
Save Jako/befda58500189c12b5a8ecdfb19201bf to your computer and use it in GitHub Desktop.
ExtJS download utility
// This utility method allows downloading files with a failure and a success callback.
// It uses the following setting in the fields property:
//
// Key | Default | Description
// ------- | ------------------------- | -----------
// url | MODx.config.connector_url | The connector url
// timeout | 30 | Set a polling timeout
// debug | false | Log the polling in the console
// params | {} | Additional params for the connector url
// success | null | Callback called after a successful download,
// failure | null | Callback called after a failed download
// To use the success callback, the download processor has to set a cookie i.e. by:
// if ($this->getProperty('cookieName')) {
// setcookie($this->getProperty('cookieName'), 'true', time() + 10, '/');
// }
Packagename.util.FileDownload = function (fields) {
if (!Ext.isObject(fields)) {
return;
}
let me = this;
me.clearCookie = function () {
Ext.util.Cookies.set(cookieName, null, new Date("January 1, 1970"), '/');
Ext.util.Cookies.clear(cookieName, '/');
}
me.randomHex = function (len) {
const hex = '0123456789ABCDEF';
let output = '';
for (let i = 0; i < len; ++i) {
output += hex.charAt(Math.floor(Math.random() * hex.length));
}
return output;
}
me.isFinished = function (successCallback, failureCallback) {
// Check if file is started downloading
if (Ext.util.Cookies.get(cookieName) && Ext.util.Cookies.get(cookieName) === 'true') {
me.clearCookie();
if (typeof successCallback === 'function') {
successCallback({success: true, message: _('packagename.file_msg_download_success')});
}
return;
}
// Check for error / IF any error happens the frame will have content
try {
var response = frame.dom.contentDocument.body.innerHTML;
if (response.length > 0) {
let result = Ext.decode(frame.dom.contentDocument.body.innerHTML);
result = (result) ? result : {success: false, message: _('packagename.file_msg_download_error')};
me.failure(failureCallback, result);
frame.dom.contentDocument.body.innerHTML = "";
return;
}
} catch (e) {
me.failure(failureCallback, {success: false, message: MODx.util.safeHtml(response)});
return;
}
if (polling) {
if (debug) {
console.log('polling ' + polling);
}
// Download is not finished. Check again in 100 milliseconds.
window.setTimeout(function () {
polling--;
me.isFinished(successCallback, failureCallback);
}, 100);
} else {
// Polling timeout with no fileDownload cookie set
me.failure(failureCallback, {success: false, message: _('packagename.file_msg_download_timeout')});
}
};
me.failure = function (failureCallback, result) {
me.clearCookie();
if (failureCallback) {
failureCallback(result);
}
}
const cookieName = 'fileDownload' + me.randomHex(16),
ident = fields.ident || 'filedownload-' + Ext.id(),
url = fields.url || MODx.config.connector_url,
debug = fields.debug || false;
let params = fields.params || {},
polling = fields.timeout * 10 || 300,
successCallback = fields.success || null,
failureCallback = fields.failure || null,
body = Ext.getBody();
let frame = body.createChild({
tag: 'iframe',
cls: 'x-hidden',
id: ident + '-iframe',
name: ident + '-iframe',
}),
form = body.createChild({
tag: 'form',
cls: 'x-hidden',
id: ident + '-form',
action: url,
target: ident + '-iframe',
method: 'post',
});
params.HTTP_MODAUTH = MODx.siteId;
if (typeof successCallback === 'function') {
params.cookieName = cookieName;
} else {
polling = 0;
}
Ext.iterate(params, function (name, value) {
let textarea = form.createChild({
tag: 'textarea',
cls: 'x-hidden',
id: ident + '-' + name,
name: name
});
textarea.dom.innerText = value;
});
form.dom.submit();
if (successCallback || failureCallback) {
me.isFinished(successCallback, failureCallback);
}
};
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment