[IMP] extend wizard to create several users
authorRaphael Collet <rco@openerp.com>
Wed, 27 Apr 2011 10:26:55 +0000 (12:26 +0200)
committerRaphael Collet <rco@openerp.com>
Wed, 27 Apr 2011 10:26:55 +0000 (12:26 +0200)
bzr revid: rco@openerp.com-20110427102655-lxve6401uljqik0k

addons/portal/wizard.py
addons/portal/wizard_view.xml

index 7d91cf5..bed9204 100644 (file)
@@ -45,82 +45,59 @@ def random_password():
 
 
 
-class user_wizard(osv.osv_memory):
+class wizard(osv.osv_memory):
     """
-        A wizard to create a portal user from a res.partner.address.  The use
-        case of the wizard is to provide access to a customer or supplier.
+        A wizard to create portal users from instances of either 'res.partner'
+        or 'res.partner.address'.  The purpose is to provide an OpenERP database
+        access to customers or suppliers.
     """
-    _name = 'res.portal.user_wizard'
-    _description = 'Portal User Wizard'
+    _name = 'res.portal.wizard'
+    _description = 'Portal Wizard'
     
     _columns = {
-        'name': fields.char(size=64, required=True,
-            string='User Name',
-            help="The new user's real name"),
-        'email': fields.char(size=64, required=True,
-            string='E-mail',
-            help="A welcome e-mail will be sent to the new user, "
-                 "with the necessary information to connect to OpenERP"),
-        'lang': fields.selection(_lang_get, required=True,
-            string='Language',
-            help="The language for the user's user interface"),
-        'address_id': fields.many2one('res.partner.address', readonly=True,
-            string='Address'),
         'portal_id': fields.many2one('res.portal', required=True,
             string='Portal',
-            help="The Portal that the new user must belong to"),
+            help="The portal where new users must be added"),
+        'user_ids': fields.one2many('res.portal.wizard.user', 'wizard_id',
+            string='Users'),
     }
-    
-    _constraints = [
-        (lambda self,*args: self._check_email(*args), 'Invalid email address', ['email']),
-        (lambda self,*args: self._check_exist(*args), 'User login already exists', ['email']),
-    ]
 
     def default_get(self, cr, uid, fields, context=None):
-        """ determine default name, email, address_id and lang from the active
-            record """
+        """ determine user configs from the active records """
         # get existing defaults
-        defs = super(user_wizard, self).default_get(cr, uid, fields, context)
+        defs = super(wizard, self).default_get(cr, uid, fields, context)
         
-        # determine a res.partner.address depending on current context
-        address = None
+        # determine relevant res.partner.address(es) depending on context
+        addresses = []
         if context.get('active_model') == 'res.partner.address':
             address_obj = self.pool.get('res.partner.address')
-            address = address_obj.browse(cr, uid, context.get('active_id'), context)
-        
+            address_ids = context.get('active_ids', [])
+            addresses = address_obj.browse(cr, uid, address_ids, context)
         elif context.get('active_model') == 'res.partner':
             partner_obj = self.pool.get('res.partner')
-            partner = partner_obj.browse(cr, uid, context.get('active_id'), context)
-            if partner and partner.address:
-                # take default address if present, or any address otherwise
-                addresses = filter(lambda a: a.type == 'default', partner.address)
-                address = addresses[0] if addresses else partner.address[0]
+            partner_ids = context.get('active_ids', [])
+            partners = partner_obj.browse(cr, uid, partner_ids, context)
+            for p in partners:
+                if p.address:
+                    # take default address if present, or any address otherwise
+                    good = filter(lambda a: a.type == 'default', p.address)
+                    addresses.append(good[0] if good else p.address[0])
         
-        # override name, email, address_id, and lang
-        if address:
-            defs['name'] = address.name
-            defs['email'] = address.email
-            defs['address_id'] = address.id
-            defs['lang'] = address.partner_id and address.partner_id.lang
+        # create user configs based on these addresses
+        defs['user_ids'] = []
+        for address in addresses:
+            user_data = {
+                'name': address.name,
+                'email': address.email,
+                'lang': address.partner_id and address.partner_id.lang,
+                'address_id': address.id,
+            }
+            defs['user_ids'].append(user_data)
         
         return defs
 
-    def _check_email(self, cr, uid, ids):
-        """ check syntax of email address """
-        for wizard in self.browse(cr, uid, ids):
-            if not email_re.match(wizard.email): return False
-        return True
-
-    def _check_exist(self, cr, uid, ids):
-        """ check whether login (email) already in use """
-        user_obj = self.pool.get('res.users')
-        for wizard in self.browse(cr, uid, ids):
-            condition = [('login', '=', wizard.email)]
-            if user_obj.search(cr, ROOT_UID, condition): return False
-        return True
-
     def do_create(self, cr, uid, ids, context=None):
-        """ create a new user in the portal, and notify them by email """
+        """ create new users in portal(s), and notify them by email """
         # we copy the context to change the language for translating emails
         context0 = context or {}
         context = context0.copy()
@@ -130,47 +107,100 @@ class user_wizard(osv.osv_memory):
             raise osv.except_osv(_('Email required'),
                 _('You must have an email address in your User Preferences'
                   ' to send emails.'))
+        email_from = user.user_email
+        company_name = user.company_id.name
         
         portal_obj = self.pool.get('res.portal')
-        for wizard in self.browse(cr, uid, ids, context):
-            # add a new user in wizard.portal_id
-            user_values = {
-                'name': wizard.name,
-                'login': wizard.email,
-                'password': random_password(),
-                'user_email': wizard.email,
-                'address_id': wizard.address_id.id,
-                'context_lang': wizard.lang,
-            }
-            values = {'users': [(0, 0, user_values)]}
-            portal_obj.write(cr, ROOT_UID, [wizard.portal_id.id], values, context0)
-            
-            # send email to new user (translated in language of new user)
-            context['lang'] = user_values['context_lang']
-            user_values['dbname'] = cr.dbname
-            user_values['url'] = "(missing url)"
+        for wiz in self.browse(cr, uid, ids, context):
+            # add new users in portal
+            users_data = [ {
+                    'name': u.name,
+                    'login': u.email,
+                    'password': random_password(),
+                    'user_email': u.email,
+                    'context_lang': u.lang,
+                    'address_id': u.address_id.id,
+                } for u in wiz.user_ids ]
+            portal_obj.write(cr, ROOT_UID, [wiz.portal_id.id],
+                {'users': [(0, 0, data) for data in users_data]}, context0)
             
-            email_to = user_values['user_email']
-            subject = _("Your OpenERP account at %s") % user.company_id.name
-            body = _(
-                "Dear %(name)s,\n\n"
-                "You have been created an OpenERP account at %(url)s.\n\n"
-                "Your login account data is:\n"
-                "Database: %(dbname)s\n"
-                "User:     %(login)s\n"
-                "Password: %(password)s\n\n"
-                "--\n"
-                "OpenERP - Open Source Business Applications\n"
-                "http://www.openerp.com\n"
-                ) % user_values
-            res = email_send(user.user_email, [email_to], subject, body)
-            if not res:
-                logging.getLogger('res.portal.user_wizard').warning(
-                    'Failed to send email from %s to %s', user.user_email, email_to)
-
+            # send email to new users (translated in their language)
+            for data in users_data:
+                context['lang'] = data['context_lang']
+                data['dbname'] = cr.dbname
+                data['url'] = "(missing url)"
+                
+                email_to = data['user_email']
+                subject = _("Your OpenERP account at %s") % company_name
+                body = _(
+                    "Dear %(name)s,\n\n"
+                    "You have been created an OpenERP account at %(url)s.\n\n"
+                    "Your login account data is:\n"
+                    "Database: %(dbname)s\n"
+                    "User:     %(login)s\n"
+                    "Password: %(password)s\n\n"
+                    "--\n"
+                    "OpenERP - Open Source Business Applications\n"
+                    "http://www.openerp.com\n"
+                    ) % data
+                res = email_send(email_from, [email_to], subject, body)
+                if not res:
+                    logging.getLogger('res.portal.wizard').warning(
+                        'Failed to send email from %s to %s', email_from, email_to)
+        
         return {}
 
-user_wizard()
+wizard()
+
+
+
+class wizard_user(osv.osv_memory):
+    """
+        A model to configure users in the portal wizard.
+    """
+    _name = 'res.portal.wizard.user'
+    _description = 'Portal User Config'
+    
+    _columns = {
+        'wizard_id': fields.many2one('res.portal.wizard', required=True,
+            string='Wizard'),
+        'name': fields.char(size=64, required=True,
+            string='User Name',
+            help="The user's real name"),
+        'email': fields.char(size=64, required=True,
+            string='E-mail',
+            help="Will be used as user login.  "  
+                 "Also necessary to send the account information to new users"),
+        'lang': fields.selection(_lang_get, required=True,
+            string='Language',
+            help="The language for the user's user interface"),
+        'address_id': fields.many2one('res.partner.address', required=True,
+            string='Address'),
+        'partner_id': fields.related('address_id', 'partner_id',
+            type='many2one', relation='res.partner', readonly=True,
+            string='Partner'),
+    }
+
+    def _check_email(self, cr, uid, ids):
+        """ check syntax of email address """
+        for wizard in self.browse(cr, uid, ids):
+            if not email_re.match(wizard.email): return False
+        return True
+
+    def _check_exist(self, cr, uid, ids):
+        """ check whether login (email) already in use """
+        user_obj = self.pool.get('res.users')
+        for wizard in self.browse(cr, uid, ids):
+            condition = [('login', '=', wizard.email)]
+            if user_obj.search(cr, ROOT_UID, condition): return False
+        return True
+
+    _constraints = [
+        (_check_email, 'Invalid email address', ['email']),
+        (_check_exist, 'User login already exists', ['email']),
+    ]
+
+wizard_user()
 
 
 
index cefd311..dbc48a6 100644 (file)
@@ -2,40 +2,67 @@
 <openerp>
     <data>
         <!-- wizard action on res.partner -->
-        <act_window id="partner_user_wizard_action"
-            name="Create Portal User"
+        <act_window id="partner_wizard_action"
+            name="Create Portal Users"
             src_model="res.partner"
-            res_model="res.portal.user_wizard"
+            res_model="res.portal.wizard"
             view_type="form" view_mode="form"
             key2="client_action_multi" target="new"/>
 
         <!-- wizard action on res.partner.address -->
-        <act_window id="address_user_wizard_action"
-            name="Create Portal User"
+        <act_window id="address_wizard_action"
+            name="Create Portal Users"
             src_model="res.partner.address"
-            res_model="res.portal.user_wizard"
+            res_model="res.portal.wizard"
             view_type="form" view_mode="form"
             key2="client_action_multi" target="new"/>
 
-        <!-- user_wizard view -->
-        <record id="user_wizard_view" model="ir.ui.view">
-            <field name="name">Create Portal User</field>
-            <field name="model">res.portal.user_wizard</field>
+        <!-- wizard view -->
+        <record id="wizard_view" model="ir.ui.view">
+            <field name="name">Create Portal Users</field>
+            <field name="model">res.portal.wizard</field>
             <field name="type">form</field>
             <field name="arch" type="xml">
-                <form string="Create Portal User">
+                <form string="Create Portal Users">
+                    <field name="portal_id" colspan="4"/>
+                    <field name="user_ids" nolabel="1" colspan="4"/>
+                    <label colspan="2"/>
+                    <button string="Cancel" special="cancel" icon="gtk-cancel"/>
+                    <button string="Create Users" name="do_create" type="object" icon="gtk-ok"/>
+                </form>
+            </field>
+        </record>
+
+        <!-- wizard user list view -->
+        <record id="wizard_user_tree_view" model="ir.ui.view">
+            <field name="name">Portal Users</field>
+            <field name="model">res.portal.wizard.user</field>
+            <field name="type">tree</field>
+            <field name="arch" type="xml">
+                <tree string="Portal Users">
+                    <field name="name"/>
+                    <field name="email"/>
+                    <field name="partner_id"/>
+                </tree>
+            </field>
+        </record>
+
+        <!-- wizard user form view -->
+        <record id="wizard_user_form_view" model="ir.ui.view">
+            <field name="name">Portal User</field>
+            <field name="model">res.portal.wizard.user</field>
+            <field name="type">form</field>
+            <field name="arch" type="xml">
+                <form string="Portal User">
                     <group colspan="2" col="2">
                         <field name="name"/>
                         <field name="email"/>
                         <field name="lang"/>
-                        <field name="address_id"/>
                     </group>
                     <group colspan="2" col="2">
-                        <field name="portal_id"/>
+                        <field name="address_id"/>
+                        <field name="partner_id"/>
                     </group>
-                    <label colspan="2"/>
-                    <button string="Cancel" special="cancel" icon="gtk-cancel"/>
-                    <button string="Create User" name="do_create" type="object" icon="gtk-ok"/>
                 </form>
             </field>
         </record>