[IMP] get export to work correctly with Session.get_file (so the user really downloads a file each time)

bzr revid: xmo@openerp.com-20110830110204-lf3qi2r5ck8avcs9
This commit is contained in:
Xavier Morel 2011-08-30 13:02:04 +02:00
parent 8448cdc63d
commit c326d6942c
3 changed files with 64 additions and 32 deletions

View File

@ -1112,7 +1112,7 @@ def export_xls(fieldnames, table):
data = fp.read()
fp.close()
#return data.decode('ISO-8859-1')
return base64.b64encode(data)
return data
class Export(View):
_cp_path = "/base/export"
@ -1238,19 +1238,30 @@ class Export(View):
return _fields
return rec(fields)
@openerpweb.jsonrequest
def export_data(self, req, model, fields, ids, domain, import_compat=False, export_format="csv", context=None):
@openerpweb.httprequest
def export_data(self, req, data, token):
model, fields, ids, domain, import_compat, export_format = \
operator.itemgetter('model', 'fields', 'ids', 'domain',
'import_compat', 'export_format')(
simplejson.loads(data))
context = req.session.eval_context(req.context)
modle_obj = req.session.model(model)
ids = ids or modle_obj.search(domain, context=context)
Model = req.session.model(model)
ids = ids or Model.search(domain, context=context)
field = fields.keys()
result = modle_obj.export_data(ids, field , context).get('datas',[])
result = Model.export_data(ids, field, context).get('datas',[])
if not import_compat:
field = [val.strip() for val in fields.values()]
req.httpresponse.headers['Content-Disposition'] = \
'attachment; filename="%s.%s"' % (model, export_format)
req.httpresponse.cookie['fileToken'] = int(token)
req.httpresponse.cookie['fileToken']['path'] = '/'
if export_format == 'xls':
req.httpresponse.headers['Content-Type'] = 'application/vnd.mx-excel'
return export_xls(field, result)
else:
req.httpresponse.headers['Content-Type'] = 'text/csv;charset=utf8'
return export_csv(field, result)

View File

@ -627,7 +627,9 @@ openerp.base.Session = openerp.base.CallbackEnabled.extend( /** @lends openerp.b
* "known" type (e.g. text/plain, or for some browsers application/json
*
* @param {Object} options
* @param {HTMLFormElement} options.form the form to submit in order to fetch the file
* @param {String} [options.url] used to dynamically create a form
* @param {Object} [options.data] data to add to the form submission. If can be used without a form, in which case a form is created from scratch. Otherwise, added to form data
* @param {HTMLFormElement} [options.form] the form to submit in order to fetch the file
* @param {Function} [options.success] callback in case of download success
* @param {Function} [options.error] callback in case of request error, provided with the error body
* @param {Function} [options.complete] called after both ``success`` and ``error` callbacks have executed
@ -640,25 +642,46 @@ openerp.base.Session = openerp.base.CallbackEnabled.extend( /** @lends openerp.b
// http://geekswithblogs.net/GruffCode/archive/2010/10/28/detecting-the-file-download-dialog-in-the-browser.aspx
var timer, token = new Date().getTime(),
cookie_name = 'fileToken', cookie_length = cookie_name.length,
self = this, CHECK_INTERVAL = 100, id = _.uniqueId('get_file_frame'),
$token = $('<input type="hidden" name="token" value="' + token +'">');
CHECK_INTERVAL = 1000, id = _.uniqueId('get_file_frame'),
remove_form = false;
var $form, $form_data = $('<div>');
var complete = function () {
if (options.complete) { options.complete(); }
clearTimeout(timer);
$token.remove();
$form_data.remove();
$target.remove();
if (remove_form && $form) { $form.remove(); }
};
var $target = $('<iframe style="display: none;">')
.attr({id: id, name: id})
.appendTo(document.body)
.load(function () {
if (options.error) {
options.error(this.contentDocument.body)
}
if (options.error) { options.error(this.contentDocument.body); }
complete();
});
$(options.form)
.append($token)
if (options.form) {
$form = $(options.form);
} else {
remove_form = true;
$form = $('<form>', {
action: options.url,
method: 'POST'
}).appendTo(document.body);
}
_(_.extend({}, options.data || {},
{session_id: this.session_id, token: token}))
.each(function (value, key) {
$('<input type="hidden" name="' + key + '">')
.val(value)
.appendTo($form_data);
});
$form
.append($form_data)
.attr('target', id)
.get(0).submit();

View File

@ -373,10 +373,10 @@ openerp.base.DataExport = openerp.base.Dialog.extend({
return export_field;
},
on_click_export_data: function() {
var self = this;
$.blockUI(this.$element);
var export_field = {};
var flag = true;
self.$element.find("#fields_list option").each(function() {
this.$element.find("#fields_list option").each(function() {
export_field[$(this).val()] = $(this).text();
flag = false;
});
@ -385,22 +385,20 @@ openerp.base.DataExport = openerp.base.Dialog.extend({
return;
}
var import_comp = self.$element.find("#import_compat option:selected").val(),
export_format = self.$element.find("#export_format").val();
var import_comp = this.$element.find("#import_compat option:selected").val(),
export_format = this.$element.find("#export_format").val();
self.rpc("/base/export/export_data", {
model: self.dataset.model,
fields: export_field,
ids: self.dataset.ids,
domain: self.dataset.domain,
import_compat: parseInt(import_comp),
export_format: export_format
}, function(data) {
var mime = export_format === 'csv'
? 'text/csv;charset=utf8'
: 'application/vnd.mx-excel;base64';
window.location = 'data:' + mime + ',' + data;
self.close();
this.session.get_file({
url: '/base/export/export_data',
data: {data: JSON.stringify({
model: this.dataset.model,
fields: export_field,
ids: this.dataset.ids,
domain: this.dataset.domain,
import_compat: parseInt(import_comp),
export_format: export_format
})},
complete: $.unblockUI
});
},
close: function() {