diff options
| author | niv-openerp <nicolas.vanhoren@openerp.com> | 2013-06-10 17:45:14 +0200 |
|---|---|---|
| committer | niv-openerp <nicolas.vanhoren@openerp.com> | 2013-06-10 17:45:14 +0200 |
| commit | a94bbf8e5e3aafb236a059f82b855d16dc033d9e (patch) | |
| tree | 0b3f2cfa795a23150a10d561996052a023fd48f5 /addons/web | |
| parent | 901ba0cba5ea8413ea5cb64974ce8fc973093105 (diff) | |
| parent | 02aa3f211471a55fd956027a84b6baca1272ffa1 (diff) | |
[FIX] Merge fix in saas1 for the problem that made the server crash when install a db
bzr revid: nicolas.vanhoren@openerp.com-20130610144915-0nj8vpk7n84ocj3f
bzr revid: nicolas.vanhoren@openerp.com-20130610150657-3xddn91gm0iq0ubp
bzr revid: nicolas.vanhoren@openerp.com-20130610154514-oee6s4f9g17bx63z
Diffstat (limited to 'addons/web')
| -rw-r--r-- | addons/web/__openerp__.py | 4 | ||||
| -rw-r--r-- | addons/web/controllers/main.py | 32 | ||||
| -rw-r--r-- | addons/web/http.py | 21 | ||||
| -rw-r--r-- | addons/web/static/src/js/chrome.js | 43 | ||||
| -rw-r--r-- | addons/web/static/src/js/corelib.js | 3 | ||||
| -rw-r--r-- | addons/web/static/src/js/view_form.js | 19 | ||||
| -rw-r--r-- | addons/web/static/src/js/views.js | 9 |
7 files changed, 104 insertions, 27 deletions
diff --git a/addons/web/__openerp__.py b/addons/web/__openerp__.py index 269aa13d58e..48903312b44 100644 --- a/addons/web/__openerp__.py +++ b/addons/web/__openerp__.py @@ -1,7 +1,7 @@ { 'name': 'Web', 'category': 'Hidden', - 'version': '7.0.1.0', + 'version': '1.0', 'description': """ OpenERP Web core module. @@ -13,6 +13,7 @@ This module provides the core of the OpenERP Web Client. 'auto_install': True, 'post_load': 'wsgi_postload', 'js' : [ + "static/src/fixbind.js", "static/lib/datejs/globalization/en-US.js", "static/lib/datejs/core.js", "static/lib/datejs/parser.js", @@ -76,6 +77,7 @@ This module provides the core of the OpenERP Web Client. "static/test/class.js", "static/test/registry.js", "static/test/form.js", + "static/test/data.js", "static/test/list-utils.js", "static/test/formats.js", "static/test/rpc.js", diff --git a/addons/web/controllers/main.py b/addons/web/controllers/main.py index b7071eff9e2..8683ef177bc 100644 --- a/addons/web/controllers/main.py +++ b/addons/web/controllers/main.py @@ -310,7 +310,7 @@ def fs2web(path): """convert FS path into web path""" return '/'.join(path.split(os.path.sep)) -def manifest_glob(extension, addons=None, db=None): +def manifest_glob(extension, addons=None, db=None, include_remotes=False): if addons is None: addons = module_boot(db=db) else: @@ -324,8 +324,12 @@ def manifest_glob(extension, addons=None, db=None): addons_path = os.path.join(manifest['addons_path'], '')[:-1] globlist = manifest.get(extension, []) for pattern in globlist: - for path in glob.glob(os.path.normpath(os.path.join(addons_path, addon, pattern))): - r.append((path, fs2web(path[len(addons_path):]))) + if pattern.startswith(('http://', 'https://', '//')): + if include_remotes: + r.append((None, pattern)) + else: + for path in glob.glob(os.path.normpath(os.path.join(addons_path, addon, pattern))): + r.append((path, fs2web(path[len(addons_path):]))) return r def manifest_list(extension, mods=None, db=None): @@ -333,14 +337,16 @@ def manifest_list(extension, mods=None, db=None): mods: a comma separated string listing modules db: a database name (return all installed modules in that database) """ + files = manifest_glob(extension, addons=mods, db=db, include_remotes=True) if not req.debug: path = '/web/webclient/' + extension if mods is not None: path += '?' + urllib.urlencode({'mods': mods}) elif db: path += '?' + urllib.urlencode({'db': db}) - return [path] - files = manifest_glob(extension, addons=mods, db=db) + + remotes = [wp for fp, wp in files if fp is None] + return [path] + remotes return [wp for _fp, wp in files] def get_last_modified(files): @@ -1204,19 +1210,19 @@ class Binary(openerpweb.Controller): headers = [('Content-Type', 'image/png')] etag = req.httprequest.headers.get('If-None-Match') hashed_session = hashlib.md5(req.session_id).hexdigest() + retag = hashed_session id = None if not id else simplejson.loads(id) if type(id) is list: id = id[0] # m2o - if etag: - if not id and hashed_session == etag: - return werkzeug.wrappers.Response(status=304) - else: - date = Model.read([id], [last_update], req.context)[0].get(last_update) - if hashlib.md5(date).hexdigest() == etag: + try: + if etag: + if not id and hashed_session == etag: return werkzeug.wrappers.Response(status=304) + else: + date = Model.read([id], [last_update], req.context)[0].get(last_update) + if hashlib.md5(date).hexdigest() == etag: + return werkzeug.wrappers.Response(status=304) - retag = hashed_session - try: if not id: res = Model.default_get([field], req.context).get(field) image_base64 = res diff --git a/addons/web/http.py b/addons/web/http.py index 67d71ac7d37..2dc41c8cad9 100644 --- a/addons/web/http.py +++ b/addons/web/http.py @@ -121,6 +121,13 @@ class WebRequest(object): # we use _ as seprator where RFC2616 uses '-' self.lang = lang.replace('-', '_') + @contextlib.contextmanager + def registry_cr(self): + dbname = self.session._db or openerp.addons.web.controllers.main.db_monodb(self) + registry = openerp.modules.registry.RegistryManager.get(dbname.lower()) + with registry.cursor() as cr: + yield (registry, cr) + def reject_nonliteral(dct): if '__ref' in dct: raise ValueError( @@ -298,6 +305,8 @@ class HttpRequest(WebRequest): #_logger.debug("%s --> %s.%s %r", self.httprequest.method, method.im_class.__name__, method.__name__, akw) try: r = method(**self.params) + except werkzeug.exceptions.HTTPException, e: + r = e except Exception, e: _logger.exception("An exception occured during an http request") se = serialize_exception(e) @@ -307,11 +316,13 @@ class HttpRequest(WebRequest): 'data': se } r = werkzeug.exceptions.InternalServerError(cgi.escape(simplejson.dumps(error))) - if self.debug or 1: - if isinstance(r, (werkzeug.wrappers.BaseResponse, werkzeug.exceptions.HTTPException)): - _logger.debug('<-- %s', r) - else: - _logger.debug("<-- size: %s", len(r)) + else: + if not r: + r = werkzeug.wrappers.Response(status=204) # no content + if isinstance(r, (werkzeug.wrappers.BaseResponse, werkzeug.exceptions.HTTPException)): + _logger.debug('<-- %s', r) + else: + _logger.debug("<-- size: %s", len(r)) return r def make_response(self, data, headers=None, cookies=None): diff --git a/addons/web/static/src/js/chrome.js b/addons/web/static/src/js/chrome.js index f357f6ac2e6..884dc41a9f9 100644 --- a/addons/web/static/src/js/chrome.js +++ b/addons/web/static/src/js/chrome.js @@ -913,9 +913,7 @@ instance.web.Menu = instance.web.Widget.extend({ self.reflow(); // launch the fetch of needaction counters, asynchronous if (!_.isEmpty(menu_data.all_menu_ids)) { - this.rpc("/web/menu/load_needaction", {menu_ids: menu_data.all_menu_ids}).done(function(r) { - self.on_needaction_loaded(r); - }); + this.do_load_needaction(menu_data.all_menu_ids); } }); var lazyreflow = _.debounce(this.reflow.bind(this), 200); @@ -941,7 +939,7 @@ instance.web.Menu = instance.web.Widget.extend({ this.data = {data: data}; this.renderElement(); this.$secondary_menus.html(QWeb.render("Menu.secondary", { widget : this })); - this.$el.on('click', 'a[data-menu]', this.on_menu_click); + this.$el.on('click', 'a[data-menu]', this.on_top_menu_click); // Hide second level submenus this.$secondary_menus.find('.oe_menu_toggler').siblings('.oe_secondary_submenu').hide(); if (self.current_menu) { @@ -950,6 +948,16 @@ instance.web.Menu = instance.web.Widget.extend({ this.trigger('menu_loaded', data); this.has_been_loaded.resolve(); }, + do_load_needaction: function (menu_ids) { + var self = this; + menu_ids = _.reject(menu_ids, _.isEmpty); + if (_.isEmpty(menu_ids)) { + return $.when(); + } + return this.rpc("/web/menu/load_needaction", {'menu_ids': menu_ids}).done(function(r) { + self.on_needaction_loaded(r); + }); + }, on_needaction_loaded: function(data) { var self = this; this.needaction_data = data; @@ -1081,11 +1089,38 @@ instance.web.Menu = instance.web.Widget.extend({ } this.open_menu(id); }, + do_reload_needaction: function () { + var self = this; + if (self.current_menu) { + self.do_load_needaction([self.current_menu]).then(function () { + self.trigger("need_action_reloaded"); + }); + } + }, /** * Jquery event handler for menu click * * @param {Event} ev the jquery event */ + on_top_menu_click: function(ev) { + var self = this; + var id = $(ev.currentTarget).data('menu'); + var menu_ids = [id]; + var menu = _.filter(this.data.data.children, function (menu) {return menu.id == id;})[0]; + function add_menu_ids (menu) { + if (menu.children) { + _.each(menu.children, function (menu) { + menu_ids.push(menu.id); + add_menu_ids(menu); + }); + } + }; + add_menu_ids(menu); + self.do_load_needaction(menu_ids).then(function () { + self.trigger("need_action_reloaded"); + }); + this.on_menu_click(ev); + }, on_menu_click: function(ev) { ev.preventDefault(); var needaction = $(ev.target).is('div.oe_menu_counter'); diff --git a/addons/web/static/src/js/corelib.js b/addons/web/static/src/js/corelib.js index c4bb81117f8..116ddf2e8c2 100644 --- a/addons/web/static/src/js/corelib.js +++ b/addons/web/static/src/js/corelib.js @@ -1144,7 +1144,8 @@ instance.web.JsonRPC = instance.web.Class.extend(instance.web.PropertiesMixin, { } qs = '?' + $.param(params); } - return this.prefix + path + qs; + var prefix = _.any(['http://', 'https://', '//'], _.bind(_.str.startsWith, null, path)) ? '' : this.prefix; + return prefix + path + qs; }, }); diff --git a/addons/web/static/src/js/view_form.js b/addons/web/static/src/js/view_form.js index 6a1dc019f95..32e86d69bed 100644 --- a/addons/web/static/src/js/view_form.js +++ b/addons/web/static/src/js/view_form.js @@ -91,6 +91,7 @@ instance.web.FormView = instance.web.View.extend(instance.web.form.FieldManagerM init: function(parent, dataset, view_id, options) { var self = this; this._super(parent); + this.ViewManager = parent; this.set_default_options(options); this.dataset = dataset; this.model = dataset.model; @@ -720,6 +721,8 @@ instance.web.FormView = instance.web.View.extend(instance.web.form.FieldManagerM return this.save().done(function(result) { self.trigger("save", result); self.to_view_mode(); + }).then(function(result) { + self.ViewManager.ActionManager.__parentedParent.menu.do_reload_needaction(); }); }, on_button_cancel: function(event) { @@ -2901,7 +2904,7 @@ instance.web.form.FieldRadio = instance.web.form.AbstractField.extend(instance.w var domain = instance.web.pyeval.eval('domain', this.build_domain()) || []; if (! _.isEqual(self.domain, domain)) { self.domain = domain; - var ds = new instance.web.DataSet(self, self.field.relation); + var ds = new instance.web.DataSetStatic(self, self.field.relation, self.build_context()); ds.call('search', [self.domain]) .then(function (records) { ds.name_get(records).then(function (records) { @@ -3151,6 +3154,7 @@ instance.web.form.FieldMany2One = instance.web.form.AbstractField.extend(instanc instance.web.form.CompletionFieldMixin.init.call(this); this.set({'value': false}); this.display_value = {}; + this.display_value_backup = {}; this.last_search = []; this.floating = false; this.current_display = null; @@ -3234,6 +3238,7 @@ instance.web.form.FieldMany2One = instance.web.form.AbstractField.extend(instanc ); pop.on('write_completed', self, function(){ self.display_value = {}; + self.display_value_backup = {}; self.render_value(); self.focus(); }); @@ -3284,6 +3289,7 @@ instance.web.form.FieldMany2One = instance.web.form.AbstractField.extend(instanc if (self.last_search.length > 0) { if (self.last_search[0][0] != self.get("value")) { self.display_value = {}; + self.display_value_backup = {}; self.display_value["" + self.last_search[0][0]] = self.last_search[0][1]; self.reinit_value(self.last_search[0][0]); } else { @@ -3349,6 +3355,7 @@ instance.web.form.FieldMany2One = instance.web.form.AbstractField.extend(instanc var item = ui.item; if (item.id) { self.display_value = {}; + self.display_value_backup = {}; self.display_value["" + item.id] = item.name; self.reinit_value(item.id); } else if (item.action) { @@ -3394,6 +3401,11 @@ instance.web.form.FieldMany2One = instance.web.form.AbstractField.extend(instanc this.alive(dataset.name_get([self.get("value")])).done(function(data) { self.display_value["" + self.get("value")] = data[0][1]; self.render_value(true); + }).fail( function (data, event) { + // avoid displaying crash errors as many2One should be name_get compliant + event.preventDefault(); + self.display_value["" + self.get("value")] = self.display_value_backup["" + self.get("value")]; + self.render_value(true); }); } }, @@ -3437,9 +3449,13 @@ instance.web.form.FieldMany2One = instance.web.form.AbstractField.extend(instanc var self = this; if (value_ instanceof Array) { this.display_value = {}; + this.display_value_backup = {} if (! this.options.always_reload) { this.display_value["" + value_[0]] = value_[1]; } + else { + this.display_value_backup["" + value_[0]] = value_[1]; + } value_ = value_[0]; } value_ = value_ || false; @@ -3450,6 +3466,7 @@ instance.web.form.FieldMany2One = instance.web.form.AbstractField.extend(instanc }, add_id: function(id) { this.display_value = {}; + this.display_value_backup = {}; this.reinit_value(id); }, is_false: function() { diff --git a/addons/web/static/src/js/views.js b/addons/web/static/src/js/views.js index 0737281e199..fdb2eeee329 100644 --- a/addons/web/static/src/js/views.js +++ b/addons/web/static/src/js/views.js @@ -522,6 +522,7 @@ instance.web.ViewManager = instance.web.Widget.extend({ return x; } }); + this.ActionManager = parent; this.views = {}; this.flags = flags || {}; this.registry = instance.web.views; @@ -1253,6 +1254,7 @@ instance.web.View = instance.web.Widget.extend({ view_type: undefined, init: function(parent, dataset, view_id, options) { this._super(parent); + this.ViewManager = parent; this.dataset = dataset; this.view_id = view_id; this.set_default_options(options); @@ -1324,7 +1326,6 @@ instance.web.View = instance.web.Widget.extend({ } }; var context = new instance.web.CompoundContext(dataset.get_context(), action_data.context || {}); - var handler = function (action) { if (action && action.constructor == Object) { var ncontext = new instance.web.CompoundContext(context); @@ -1361,7 +1362,11 @@ instance.web.View = instance.web.Widget.extend({ } } args.push(context); - return dataset.call_button(action_data.name, args).then(handler); + return dataset.call_button(action_data.name, args).then(handler).then(function () { + if (self.ViewManager.ActionManager) { + self.ViewManager.ActionManager.__parentedParent.menu.do_reload_needaction(); + } + }); } else if (action_data.type=="action") { return this.rpc('/web/action/load', { action_id: action_data.name, |
