[ADD] doc: new documentation, with training tutorials, and new scaffolding
[odoo/odoo.git] / openerp / tools / convert.py
index d55ba52..84e7490 100644 (file)
@@ -212,18 +212,10 @@ def _eval_xml(self, node, pool, cr, uid, idref, context=None):
             if t=='tuple':
                 return tuple(res)
             return res
-    elif node.tag == "getitem":
-        for n in node:
-            res=_eval_xml(self,n,pool,cr,uid,idref)
-        if not res:
-            raise LookupError
-        elif node.get('type') in ("int", "list"):
-            return res[int(node.get('index'))]
-        else:
-            return res[node.get('index','').encode("utf8")]
     elif node.tag == "function":
         args = []
         a_eval = node.get('eval','')
+        # FIXME: should probably be exclusive
         if a_eval:
             idref['ref'] = lambda x: self.id_get(cr, x)
             args = unsafe_eval(a_eval, idref)
@@ -231,8 +223,8 @@ def _eval_xml(self, node, pool, cr, uid, idref, context=None):
             return_val = _eval_xml(self,n, pool, cr, uid, idref, context)
             if return_val is not None:
                 args.append(return_val)
-        model = pool[node.get('model','')]
-        method = node.get('name','')
+        model = pool[node.get('model', '')]
+        method = node.get('name')
         res = getattr(model, method)(cr, uid, *args)
         return res
     elif node.tag == "test":
@@ -298,9 +290,9 @@ form: module.record_id""" % (xml_id,)
             _logger.error('id: %s is to long (max: 64)', id)
 
     def _tag_delete(self, cr, rec, data_node=None):
-        d_model = rec.get("model",'')
+        d_model = rec.get("model")
         d_search = rec.get("search",'').encode('utf-8')
-        d_id = rec.get("id",'')
+        d_id = rec.get("id")
         ids = []
 
         if d_search:
@@ -385,40 +377,6 @@ form: module.record_id""" % (xml_id,)
         _eval_xml(self,rec, self.pool, cr, uid, self.idref, context=context)
         return
 
-    def _tag_wizard(self, cr, rec, data_node=None):
-        string = rec.get("string",'').encode('utf8')
-        model = rec.get("model",'').encode('utf8')
-        name = rec.get("name",'').encode('utf8')
-        xml_id = rec.get('id','').encode('utf8')
-        self._test_xml_id(xml_id)
-        multi = rec.get('multi','') and eval(rec.get('multi','False'))
-        res = {'name': string, 'wiz_name': name, 'multi': multi, 'model': model}
-
-        if rec.get('groups'):
-            g_names = rec.get('groups','').split(',')
-            groups_value = []
-            for group in g_names:
-                if group.startswith('-'):
-                    group_id = self.id_get(cr, group[1:])
-                    groups_value.append((3, group_id))
-                else:
-                    group_id = self.id_get(cr, group)
-                    groups_value.append((4, group_id))
-            res['groups_id'] = groups_value
-
-        id = self.pool['ir.model.data']._update(cr, self.uid, "ir.actions.wizard", self.module, res, xml_id, noupdate=self.isnoupdate(data_node), mode=self.mode)
-        self.idref[xml_id] = int(id)
-        # ir_set
-        if (not rec.get('menu') or eval(rec.get('menu','False'))) and id:
-            keyword = str(rec.get('keyword','') or 'client_action_multi')
-            value = 'ir.actions.wizard,'+str(id)
-            replace = rec.get("replace",'') or True
-            self.pool['ir.model.data'].ir_set(cr, self.uid, 'action', keyword, string, [model], value, replace=replace, isobject=True, xml_id=xml_id)
-        elif self.mode=='update' and (rec.get('menu') and eval(rec.get('menu','False'))==False):
-            # Special check for wizard having attribute menu=False on update
-            value = 'ir.actions.wizard,'+str(id)
-            self._remove_ir_values(cr, string, value, model)
-
     def _tag_url(self, cr, rec, data_node=None):
         url = rec.get("url",'').encode('utf8')
         target = rec.get("target",'').encode('utf8')
@@ -552,8 +510,8 @@ form: module.record_id""" % (xml_id,)
     def _tag_workflow(self, cr, rec, data_node=None):
         if self.isnoupdate(data_node) and self.mode != 'init':
             return
-        model = str(rec.get('model',''))
-        w_ref = rec.get('ref','')
+        model = rec.get('model').encode('ascii')
+        w_ref = rec.get('ref')
         if w_ref:
             id = self.id_get(cr, w_ref)
         else:
@@ -565,9 +523,8 @@ form: module.record_id""" % (xml_id,)
             id = _eval_xml(self, rec[0], self.pool, cr, self.uid, self.idref)
 
         uid = self.get_uid(cr, self.uid, data_node, rec)
-        openerp.workflow.trg_validate(uid, model,
-            id,
-            str(rec.get('action','')), cr)
+        openerp.workflow.trg_validate(
+            uid, model, id, rec.get('action').encode('ascii'), cr)
 
     #
     # Support two types of notation:
@@ -623,47 +580,12 @@ form: module.record_id""" % (xml_id,)
             a_action = rec.get('action','').encode('utf8')
 
             # determine the type of action
-            a_type, a_id = self.model_id_get(cr, a_action)
-            a_type = a_type.split('.')[-1] # keep only type part
-
-            icons = {
-                "act_window": 'STOCK_NEW',
-                "report.xml": 'STOCK_PASTE',
-                "wizard": 'STOCK_EXECUTE',
-                "url": 'STOCK_JUMP_TO',
-                "client": 'STOCK_EXECUTE',
-                "server": 'STOCK_EXECUTE',
-            }
-            values['icon'] = icons.get(a_type,'STOCK_NEW')
-
-            if a_type=='act_window':
-                cr.execute('select view_type,view_mode,name,view_id,target from ir_act_window where id=%s', (int(a_id),))
-                rrres = cr.fetchone()
-                assert rrres, "No window action defined for this id %s !\n" \
-                    "Verify that this is a window action or add a type argument." % (a_action,)
-                action_type,action_mode,action_name,view_id,target = rrres
-                if view_id:
-                    view_arch = self.pool['ir.ui.view'].read(cr, 1, [view_id], ['arch'])
-                    action_mode = etree.fromstring(view_arch[0]['arch'].encode('utf8')).tag
-                cr.execute('SELECT view_mode FROM ir_act_window_view WHERE act_window_id=%s ORDER BY sequence LIMIT 1', (int(a_id),))
-                if cr.rowcount:
-                    action_mode, = cr.fetchone()
-                if action_type=='tree':
-                    values['icon'] = 'STOCK_INDENT'
-                elif action_mode and action_mode.startswith(('tree','kanban','gantt')):
-                    values['icon'] = 'STOCK_JUSTIFY_FILL'
-                elif action_mode and action_mode.startswith('graph'):
-                    values['icon'] = 'terp-graph'
-                elif action_mode and action_mode.startswith('calendar'):
-                    values['icon'] = 'terp-calendar'
-                if target=='new':
-                    values['icon'] = 'STOCK_EXECUTE'
-                if not values.get('name', False):
-                    values['name'] = action_name
-
-            elif a_type in ['wizard', 'url', 'client', 'server'] and not values.get('name'):
-                a_table = 'ir_act_%s' % a_type
-                cr.execute('select name from %s where id=%%s' % a_table, (int(a_id),))
+            action_type, action_id = self.model_id_get(cr, a_action)
+            action_type = action_type.split('.')[-1] # keep only type part
+
+            if not values.get('name') and action_type in ('act_window', 'wizard', 'url', 'client', 'server'):
+                a_table = 'ir_act_%s' % action_type.replace('act_', '')
+                cr.execute('select name from "%s" where id=%%s' % a_table, (int(action_id),))
                 resw = cr.fetchone()
                 if resw:
                     values['name'] = resw[0]
@@ -674,12 +596,6 @@ form: module.record_id""" % (xml_id,)
 
         if rec.get('sequence'):
             values['sequence'] = int(rec.get('sequence'))
-        if rec.get('icon'):
-            values['icon'] = str(rec.get('icon'))
-        if rec.get('web_icon'):
-            values['web_icon'] = "%s,%s" %(self.module, str(rec.get('web_icon')))
-        if rec.get('web_icon_hover'):
-            values['web_icon_hover'] = "%s,%s" %(self.module, str(rec.get('web_icon_hover')))
 
         if rec.get('groups'):
             g_names = rec.get('groups','').split(',')
@@ -699,7 +615,7 @@ form: module.record_id""" % (xml_id,)
             self.idref[rec_id] = int(pid)
 
         if rec.get('action') and pid:
-            action = "ir.actions.%s,%d" % (a_type, a_id)
+            action = "ir.actions.%s,%d" % (action_type, action_id)
             self.pool['ir.model.data'].ir_set(cr, self.uid, 'action', 'tree_but_open', 'Menuitem', [('ir.ui.menu', int(pid))], action, True, True, xml_id=rec_id)
         return 'ir.ui.menu', pid
 
@@ -782,45 +698,40 @@ form: module.record_id""" % (xml_id,)
         # opt-out using @noupdate="1". A second check will be performed in
         # ir.model.data#_update() using the record's ir.model.data `noupdate` field.
         if self.isnoupdate(data_node) and self.mode != 'init':
-            # check if the xml record has an id string
-            if rec_id:
-                if '.' in rec_id:
-                    module,rec_id2 = rec_id.split('.')
-                else:
-                    module = self.module
-                    rec_id2 = rec_id
-                id = self.pool['ir.model.data']._update_dummy(cr, self.uid, rec_model, module, rec_id2)
-                # check if the resource already existed at the last update
-                if id:
-                    # if it existed, we don't update the data, but we need to
-                    # know the id of the existing record anyway
-                    self.idref[rec_id] = int(id)
-                    return None
-                else:
-                    # if the resource didn't exist
-                    if not self.nodeattr2bool(rec, 'forcecreate', True):
-                        # we don't want to create it, so we skip it
-                        return None
-                    # else, we let the record to be created
+            # check if the xml record has no id, skip
+            if not rec_id:
+                return None
 
+            if '.' in rec_id:
+                module,rec_id2 = rec_id.split('.')
             else:
-                # otherwise it is skipped
+                module = self.module
+                rec_id2 = rec_id
+            id = self.pool['ir.model.data']._update_dummy(cr, self.uid, rec_model, module, rec_id2)
+            if id:
+                # if the resource already exists, don't update it but store
+                # its database id (can be useful)
+                self.idref[rec_id] = int(id)
+                return None
+            elif not self.nodeattr2bool(rec, 'forcecreate', True):
+                # if it doesn't exist and we shouldn't create it, skip it
                 return None
+            # else create it normally
+
         res = {}
         for field in rec.findall('./field'):
-#TODO: most of this code is duplicated above (in _eval_xml)...
-            f_name = field.get("name",'').encode('utf-8')
+            #TODO: most of this code is duplicated above (in _eval_xml)...
+            f_name = field.get("name").encode('utf-8')
             f_ref = field.get("ref",'').encode('utf-8')
             f_search = field.get("search",'').encode('utf-8')
             f_model = field.get("model",'').encode('utf-8')
-            if not f_model and model._all_columns.get(f_name,False):
+            if not f_model and model._all_columns.get(f_name):
                 f_model = model._all_columns[f_name].column._obj
             f_use = field.get("use",'').encode('utf-8') or 'id'
             f_val = False
 
             if f_search:
                 q = unsafe_eval(f_search, self.idref)
-                field = []
                 assert f_model, 'Define an attribute model="..." in your .XML file !'
                 f_obj = self.pool[f_model]
                 # browse the objects searched
@@ -835,15 +746,12 @@ form: module.record_id""" % (xml_id,)
                     # take the first element of the search
                     f_val = s[0][f_use]
             elif f_ref:
-                if f_ref=="null":
-                    f_val = False
+                if f_name in model._all_columns \
+                          and model._all_columns[f_name].column._type == 'reference':
+                    val = self.model_id_get(cr, f_ref)
+                    f_val = val[0] + ',' + str(val[1])
                 else:
-                    if f_name in model._all_columns \
-                              and model._all_columns[f_name].column._type == 'reference':
-                        val = self.model_id_get(cr, f_ref)
-                        f_val = val[0] + ',' + str(val[1])
-                    else:
-                        f_val = self.id_get(cr, f_ref)
+                    f_val = self.id_get(cr, f_ref)
             else:
                 f_val = _eval_xml(self,field, self.pool, cr, self.uid, self.idref)
                 if f_name in model._all_columns:
@@ -855,7 +763,7 @@ form: module.record_id""" % (xml_id,)
         id = self.pool['ir.model.data']._update(cr, self.uid, rec_model, self.module, res, rec_id or False, not self.isnoupdate(data_node), noupdate=self.isnoupdate(data_node), mode=self.mode, context=rec_context )
         if rec_id:
             self.idref[rec_id] = int(id)
-        if config.get('import_partial', False):
+        if config.get('import_partial'):
             cr.commit()
         return rec_model, id
 
@@ -954,18 +862,18 @@ form: module.record_id""" % (xml_id,)
         self.assertion_report = report
         self.noupdate = noupdate
         self._tags = {
-            'menuitem': self._tag_menuitem,
             'record': self._tag_record,
-            'template': self._tag_template,
-            'assert': self._tag_assert,
-            'report': self._tag_report,
-            'wizard': self._tag_wizard,
             'delete': self._tag_delete,
-            'ir_set': self._tag_ir_set,
             'function': self._tag_function,
+            'menuitem': self._tag_menuitem,
+            'template': self._tag_template,
             'workflow': self._tag_workflow,
+            'report': self._tag_report,
+
+            'ir_set': self._tag_ir_set,
             'act_window': self._tag_act_window,
-            'url': self._tag_url
+            'url': self._tag_url,
+            'assert': self._tag_assert,
         }
 
 def convert_file(cr, module, filename, idref, mode='update', noupdate=False, kind=None, report=None, pathname=None):