Handling File Downloads in AJAX Post Responses
When designing an AJAX application, it's common to handle various response types, including JSON and potentially file attachments. Detecting the response type based on Content-Type and Content-Disposition headers is straightforward. However, triggering a download dialog can pose a challenge.
Fortunately, modern browsers provide a solution through the FileAPI. The following code snippets demonstrate how to implement file downloads in AJAX post requests:
// Using native XMLHttpRequest var xhr = new XMLHttpRequest(); xhr.open('POST', url, true); xhr.responseType = 'blob'; xhr.onload = function () { if (this.status === 200) { // Retrieve the blob and filename from the response var blob = this.response; var filename = ""; var disposition = xhr.getResponseHeader('Content-Disposition'); if (disposition && disposition.indexOf('attachment') !== -1) { filenameRegex = /filename[^;=\n]*=((['"])).*?|[^;\n]*)/; matches = filenameRegex.exec(disposition); if (matches != null && matches[1]) filename = matches[1].replace(/['"]/g, ''); } // Manage file download based on browser capabilities if (typeof window.navigator.msSaveBlob !== 'undefined') { // IE workaround for a known issue window.navigator.msSaveBlob(blob, filename); } else { var URL = window.URL || window.webkitURL; var downloadUrl = URL.createObjectURL(blob); var a = document.createElement("a"); if (a.download !== 'undefined') { a.href = downloadUrl; a.download = filename; document.body.appendChild(a); a.click(); } else { window.location.href = downloadUrl; } setTimeout(function() { URL.revokeObjectURL(downloadUrl); }, 100); // cleanup } } }; xhr.setRequestHeader('Content-type', 'application/x-www-form-urlencoded'); xhr.send($.param(params, true));
If using jQuery.ajax:
$.ajax({ type: "POST", url: url, data: params, xhrFields: { responseType: 'blob' // to avoid binary data being mangled on charset conversion }, success: function(blob, status, xhr) { // Retrieve the blob and filename from the response var filename = ""; var disposition = xhr.getResponseHeader('Content-Disposition'); if (disposition && disposition.indexOf('attachment') !== -1) { filenameRegex = /filename[^;=\n]*=((['"])).*?|[^;\n]*)/; matches = filenameRegex.exec(disposition); if (matches != null && matches[1]) filename = matches[1].replace(/['"]/g, ''); } // Manage file download based on browser capabilities if (typeof window.navigator.msSaveBlob !== 'undefined') { // IE workaround for a known issue window.navigator.msSaveBlob(blob, filename); } else { var URL = window.URL || window.webkitURL; var downloadUrl = URL.createObjectURL(blob); var a = document.createElement("a"); if (a.download !== 'undefined') { a.href = downloadUrl; a.download = filename; document.body.appendChild(a); a.click(); } else { window.location.href = downloadUrl; } setTimeout(function() { URL.revokeObjectURL(downloadUrl); }, 100); // cleanup } } });
By incorporating these techniques, you can ensure that your AJAX post requests can seamlessly handle file attachments and trigger download dialogs for the client.
The above is the detailed content of How Can I Trigger File Downloads in AJAX Post Responses?. For more information, please follow other related articles on the PHP Chinese website!