Christophe (OpenERP) has proposed merging 
lp:~openerp-dev/openobject-server/trunk-charnosize-chs into 
lp:openobject-server.

Requested reviews:
  OpenERP Core Team (openerp)

For more details, see:
https://code.launchpad.net/~openerp-dev/openobject-server/trunk-charnosize-chs/+merge/127312
-- 
https://code.launchpad.net/~openerp-dev/openobject-server/trunk-charnosize-chs/+merge/127312
Your team OpenERP R&D Team is subscribed to branch 
lp:~openerp-dev/openobject-server/trunk-charnosize-chs.
=== modified file 'openerp/osv/orm.py'
--- openerp/osv/orm.py	2012-09-20 14:55:19 +0000
+++ openerp/osv/orm.py	2012-10-01 15:41:28 +0000
@@ -51,6 +51,7 @@
 import re
 import simplejson
 import time
+import traceback
 import types
 from lxml import etree
 
@@ -371,8 +372,10 @@
                 else:
                     return attr
             else:
-                error_msg = "Field '%s' does not exist in object '%s'" % (name, self) 
+                error_msg = "Field '%s' does not exist in object '%s'" % (name, self)
                 self.__logger.warning(error_msg)
+                if self.__logger.isEnabledFor(logging.DEBUG):
+                    self.__logger.debug(''.join(traceback.format_stack()))
                 raise KeyError(error_msg)
 
             # if the field is a classic one or a many2one, we'll fetch all classic and many2one fields
@@ -709,7 +712,7 @@
 
     def log(self, cr, uid, id, message, secondary=False, context=None):
         return _logger.warning("log() is deprecated. Please use OpenChatter notification system instead of the res.log mechanism.")
-    
+
     def view_init(self, cr, uid, fields_list, context=None):
         """Override this method to do specific things when a view on the object is opened."""
         pass
@@ -899,7 +902,7 @@
                                     # If new class defines a constraint with
                                     # same function name, we let it override
                                     # the old one.
-                                    
+
                                     new[c2] = c
                                     exist = True
                                     break
@@ -1593,7 +1596,7 @@
     def user_has_groups(self, cr, uid, groups, context=None):
         """Return true if the user is at least member of one of the groups
            in groups_str. Typically used to resolve ``groups`` attribute
-           in view and model definitions. 
+           in view and model definitions.
 
            :param str groups: comma-separated list of fully-qualified group
                               external IDs, e.g.: ``base.group_user,base.group_system``
@@ -1636,7 +1639,7 @@
                  the field should be completely removed from the view, as it is
                  completely unavailable for non-members
 
-               :return: True if field should be included in the result of fields_view_get 
+               :return: True if field should be included in the result of fields_view_get
             """
             if node.tag == 'field' and node.get('name') in self._all_columns:
                 column = self._all_columns[node.get('name')].column
@@ -1911,7 +1914,7 @@
     def _get_default_calendar_view(self, cr, user, context=None):
         """ Generates a default calendar view by trying to infer
         calendar fields from a number of pre-set attribute names
-        
+
         :param cr: database cursor
         :param int user: user id
         :param dict context: connection context
@@ -1990,7 +1993,7 @@
 
         def raise_view_error(error_msg, child_view_id):
             view, child_view = self.pool.get('ir.ui.view').browse(cr, user, [view_id, child_view_id], context)
-            error_msg = error_msg % {'parent_xml_id': view.xml_id} 
+            error_msg = error_msg % {'parent_xml_id': view.xml_id}
             raise AttributeError("View definition error for inherited view '%s' on model '%s': %s"
                                  %  (child_view.xml_id, self._name, error_msg))
 
@@ -2026,7 +2029,7 @@
                 if all(node.get(attr) == spec.get(attr) \
                         for attr in spec.attrib
                             if attr not in ('position','version')):
-                    # Version spec should match parent's root element's version 
+                    # Version spec should match parent's root element's version
                     if spec.get('version') and spec.get('version') != source.get('version'):
                         return None
                     return node
@@ -2100,7 +2103,7 @@
                         raise_view_error("Mismatching view API version for element '%s': %r vs %r in parent view '%%(parent_xml_id)s'" % \
                                             (tag, spec.get('version'), source.get('version')), inherit_id)
                     raise_view_error("Element '%s' not found in parent view '%%(parent_xml_id)s'" % tag, inherit_id)
-                    
+
             return source
 
         def apply_view_inheritance(cr, user, source, inherit_id):
@@ -2315,7 +2318,7 @@
                                 or ``'='``.
            :param int limit: optional max number of records to return
            :rtype: list
-           :return: list of pairs ``(id,text_repr)`` for all matching records. 
+           :return: list of pairs ``(id,text_repr)`` for all matching records.
         """
         return self._name_search(cr, user, name, args, operator, context, limit)
 
@@ -2445,7 +2448,7 @@
         # This is useful to implement kanban views for instance, where all columns
         # should be displayed even if they don't contain any record.
 
-        # Grab the list of all groups that should be displayed, including all present groups 
+        # Grab the list of all groups that should be displayed, including all present groups
         present_group_ids = [x[groupby][0] for x in read_group_result if x[groupby]]
         all_groups,folded = self._group_by_full[groupby](self, cr, uid, present_group_ids, domain,
                                                   read_group_order=read_group_order,
@@ -2821,28 +2824,28 @@
 
     def _m2o_fix_foreign_key(self, cr, source_table, source_field, dest_model, ondelete):
         # Find FK constraint(s) currently established for the m2o field,
-        # and see whether they are stale or not 
+        # and see whether they are stale or not
         cr.execute("""SELECT confdeltype as ondelete_rule, conname as constraint_name,
                              cl2.relname as foreign_table
                       FROM pg_constraint as con, pg_class as cl1, pg_class as cl2,
                            pg_attribute as att1, pg_attribute as att2
-                      WHERE con.conrelid = cl1.oid 
-                        AND cl1.relname = %s 
-                        AND con.confrelid = cl2.oid 
-                        AND array_lower(con.conkey, 1) = 1 
-                        AND con.conkey[1] = att1.attnum 
-                        AND att1.attrelid = cl1.oid 
-                        AND att1.attname = %s 
-                        AND array_lower(con.confkey, 1) = 1 
-                        AND con.confkey[1] = att2.attnum 
-                        AND att2.attrelid = cl2.oid 
-                        AND att2.attname = %s 
+                      WHERE con.conrelid = cl1.oid
+                        AND cl1.relname = %s
+                        AND con.confrelid = cl2.oid
+                        AND array_lower(con.conkey, 1) = 1
+                        AND con.conkey[1] = att1.attnum
+                        AND att1.attrelid = cl1.oid
+                        AND att1.attname = %s
+                        AND array_lower(con.confkey, 1) = 1
+                        AND con.confkey[1] = att2.attnum
+                        AND att2.attrelid = cl2.oid
+                        AND att2.attname = %s
                         AND con.contype = 'f'""", (source_table, source_field, 'id'))
         constraints = cr.dictfetchall()
         if constraints:
             if len(constraints) == 1:
                 # Is it the right constraint?
-                cons, = constraints 
+                cons, = constraints
                 if cons['ondelete_rule'] != POSTGRES_CONFDELTYPES.get((ondelete or 'set null').upper(), 'a')\
                     or cons['foreign_table'] != dest_model._table:
                     _schema.debug("Table '%s': dropping obsolete FK constraint: '%s'",
@@ -2964,14 +2967,14 @@
                                 ('numeric', 'float', get_pg_type(f)[1], '::'+get_pg_type(f)[1]),
                                 ('float8', 'float', get_pg_type(f)[1], '::'+get_pg_type(f)[1]),
                             ]
-                            if f_pg_type == 'varchar' and f._type == 'char' and f_pg_size < f.size:
+                            if f_pg_type == 'varchar' and f._type == 'char' and ((f.size is None and f_pg_size) or f_pg_size < f.size):
                                 cr.execute('ALTER TABLE "%s" RENAME COLUMN "%s" TO temp_change_size' % (self._table, k))
                                 cr.execute('ALTER TABLE "%s" ADD COLUMN "%s" %s' % (self._table, k, pg_varchar(f.size)))
                                 cr.execute('UPDATE "%s" SET "%s"=temp_change_size::%s' % (self._table, k, pg_varchar(f.size)))
                                 cr.execute('ALTER TABLE "%s" DROP COLUMN temp_change_size CASCADE' % (self._table,))
                                 cr.commit()
                                 _schema.debug("Table '%s': column '%s' (type varchar) changed size from %s to %s",
-                                    self._table, k, f_pg_size, f.size)
+                                    self._table, k, f_pg_size or 'unlimited', f.size or 'unlimited')
                             for c in casts:
                                 if (f_pg_type==c[0]) and (f._type==c[1]):
                                     if f_pg_type != f_obj_type:
@@ -3204,8 +3207,7 @@
         # attlen is the number of bytes necessary to represent the type when
         # the type has a fixed size. If the type has a varying size attlen is
         # -1 and atttypmod is the size limit + 4, or -1 if there is no limit.
-        # Thus the query can return a negative size for a unlimited varchar.
-        cr.execute("SELECT c.relname,a.attname,a.attlen,a.atttypmod,a.attnotnull,a.atthasdef,t.typname,CASE WHEN a.attlen=-1 THEN a.atttypmod-4 ELSE a.attlen END as size " \
+        cr.execute("SELECT c.relname,a.attname,a.attlen,a.atttypmod,a.attnotnull,a.atthasdef,t.typname,CASE WHEN a.attlen=-1 THEN (CASE WHEN a.atttypmod=-1 THEN 0 ELSE a.atttypmod-4 END) ELSE a.attlen END as size " \
            "FROM pg_class c,pg_attribute a,pg_type t " \
            "WHERE c.relname=%s " \
            "AND c.oid=a.attrelid " \
@@ -3215,7 +3217,7 @@
 
     def _o2m_raise_on_missing_reference(self, cr, f):
         # TODO this check should be a method on fields.one2many.
-        
+
         other = self.pool.get(f._obj)
         if other:
             # TODO the condition could use fields_get_keys().
@@ -3732,7 +3734,7 @@
            the length of `ids`, and raise an appropriate exception if it does not.
         """
         if cr.rowcount != len(ids):
-            # Attempt to distinguish record rule restriction vs deleted records, 
+            # Attempt to distinguish record rule restriction vs deleted records,
             # to provide a more specific error message
             cr.execute('SELECT id FROM ' + self._table + ' WHERE id IN %s', (tuple(ids),))
             if cr.rowcount != len(ids):
@@ -3787,13 +3789,13 @@
                     self._check_record_rules_result_count(cr, uid, sub_ids, operation, context=context)
 
     def _workflow_trigger(self, cr, uid, ids, trigger, context=None):
-        """Call given workflow trigger as a result of a CRUD operation""" 
+        """Call given workflow trigger as a result of a CRUD operation"""
         wf_service = netsvc.LocalService("workflow")
         for res_id in ids:
             getattr(wf_service, trigger)(uid, self._name, res_id, cr)
 
     def _workflow_signal(self, cr, uid, ids, signal, context=None):
-        """Send given workflow signal""" 
+        """Send given workflow signal"""
         wf_service = netsvc.LocalService("workflow")
         for res_id in ids:
             wf_service.trg_validate(uid, self._name, res_id, signal, cr)
@@ -3824,7 +3826,7 @@
         self.check_access_rights(cr, uid, 'unlink')
 
         ir_property = self.pool.get('ir.property')
-        
+
         # Check if the records are used as default properties.
         domain = [('res_id', '=', False),
                   ('value_reference', 'in', ['%s,%s' % (self._name, i) for i in ids]),
@@ -4952,7 +4954,7 @@
 
         :return: map of ids to their fully qualified XML ID,
                  defaulting to an empty string when there's none
-                 (to be usable as a function field), 
+                 (to be usable as a function field),
                  e.g.::
 
                      { 'id': 'module.ext_id',

_______________________________________________
Mailing list: https://launchpad.net/~openerp-dev-gtk
Post to     : [email protected]
Unsubscribe : https://launchpad.net/~openerp-dev-gtk
More help   : https://help.launchpad.net/ListHelp

Reply via email to