diff options
| author | Harry (OpenERP) <hmo@tinyerp.com> | 2011-12-14 17:59:24 +0530 |
|---|---|---|
| committer | Harry (OpenERP) <hmo@tinyerp.com> | 2011-12-14 17:59:24 +0530 |
| commit | 092f97b32b35af6a40b9d2ae70c3159da2fb235f (patch) | |
| tree | 2974d3719af9338cd0b1814da900d7e9ca8d4779 /addons/hr | |
| parent | 593f5f571bbc49673975afc405e9345ef3457b92 (diff) | |
| parent | e36dc8c5e3ca3da1474747bae5ec87fea19b23b8 (diff) | |
[MERGE] merged with trunk-development-branch
bzr revid: hmo@tinyerp.com-20111214122924-izzibrz1yz67rt7g
Diffstat (limited to 'addons/hr')
| -rw-r--r-- | addons/hr/__openerp__.py | 7 | ||||
| -rw-r--r-- | addons/hr/hr.py | 26 | ||||
| -rw-r--r-- | addons/hr/hr_board.xml | 12 | ||||
| -rw-r--r-- | addons/hr/hr_department_view.xml | 8 | ||||
| -rw-r--r-- | addons/hr/hr_view.xml | 68 | ||||
| -rw-r--r-- | addons/hr/security/hr_security.xml | 6 | ||||
| -rw-r--r-- | addons/hr/security/ir.model.access.csv | 22 | ||||
| -rw-r--r-- | addons/hr/test/hr_demo.yml | 10 | ||||
| -rw-r--r-- | addons/hr/test/open2recruit2close_job.yml | 38 | ||||
| -rw-r--r-- | addons/hr/test/test_hr.yml | 140 |
10 files changed, 130 insertions, 207 deletions
diff --git a/addons/hr/__openerp__.py b/addons/hr/__openerp__.py index 900c689dfbf..254bb2c28bf 100644 --- a/addons/hr/__openerp__.py +++ b/addons/hr/__openerp__.py @@ -20,7 +20,7 @@ ############################################################################## { - "name": "Human Resources", + "name": "Employee Address Book", "version": "1.1", "author": "OpenERP SA", "category": "Human Resources", @@ -54,7 +54,10 @@ You can manage: 'hr_demo.xml', 'hr_department_demo.xml', ], - 'test': ['test/test_hr.yml'], + 'test': [ + 'test/open2recruit2close_job.yml', + 'test/hr_demo.yml', + ], 'installable': True, 'active': False, 'certificate': '0086710558965', diff --git a/addons/hr/hr.py b/addons/hr/hr.py index f641a425e18..e903f03d974 100644 --- a/addons/hr/hr.py +++ b/addons/hr/hr.py @@ -79,12 +79,28 @@ class hr_job(osv.osv): } return res + def _get_job_position(self, cr, uid, ids, context=None): + res = [] + for employee in self.pool.get('hr.employee').browse(cr, uid, ids, context=context): + if employee.job_id: + res.append(employee.job_id.id) + return res + _name = "hr.job" _description = "Job Description" _columns = { 'name': fields.char('Job Name', size=128, required=True, select=True), - 'expected_employees': fields.function(_no_of_employee, string='Expected Employees', help='Required number of Employees in total for that job.', multi="no_of_employee", store=True), - 'no_of_employee': fields.function(_no_of_employee, string="No of Employee", help='Number of employee with that job.', multi="no_of_employee", store=True), + 'expected_employees': fields.function(_no_of_employee, string='Expected Employees', help='Required number of employees in total for that job.', + store = { + 'hr.job': (lambda self,cr,uid,ids,c=None: ids, ['no_of_recruitment'], 10), + 'hr.employee': (_get_job_position, ['job_id'], 10), + }, + multi='no_of_employee'), + 'no_of_employee': fields.function(_no_of_employee, string="Number of Employees", help='Number of employees with that job.', + store = { + 'hr.employee': (_get_job_position, ['job_id'], 10), + }, + multi='no_of_employee'), 'no_of_recruitment': fields.float('Expected in Recruitment'), 'employee_ids': fields.one2many('hr.employee', 'job_id', 'Employees'), 'description': fields.text('Job Description'), @@ -98,7 +114,7 @@ class hr_job(osv.osv): 'company_id': lambda self,cr,uid,c: self.pool.get('res.company')._company_default_get(cr, uid, 'hr.job', context=c), 'state': 'open', } - + _sql_constraints = [ ('name_company_uniq', 'unique(name, company_id)', 'The name of the job position must be unique per company!'), ] @@ -242,7 +258,7 @@ class res_users(osv.osv): def create(self, cr, uid, data, context=None): user_id = super(res_users, self).create(cr, uid, data, context=context) - + # add shortcut unless 'noshortcut' is True in context if not(context and context.get('noshortcut', False)): data_obj = self.pool.get('ir.model.data') @@ -254,7 +270,7 @@ class res_users(osv.osv): except: # Tolerate a missing shortcut. See product/product.py for similar code. logging.getLogger('orm').debug('Skipped meetings shortcut for user "%s"', data.get('name','<new')) - + return user_id res_users() diff --git a/addons/hr/hr_board.xml b/addons/hr/hr_board.xml index 620f1f51c88..977ca710e52 100644 --- a/addons/hr/hr_board.xml +++ b/addons/hr/hr_board.xml @@ -9,10 +9,8 @@ <field name="arch" type="xml"> <form string="My Board"> <board style="2-1"> - <column> - </column> - <column> - </column> + <column/> + <column/> </board> </form> </field> @@ -39,10 +37,8 @@ <field name="arch" type="xml"> <form string="HR Manager Board"> <board style="2-1"> - <column> - </column> - <column> - </column> + <column/> + <column/> </board> </form> </field> diff --git a/addons/hr/hr_department_view.xml b/addons/hr/hr_department_view.xml index 9fdb64651f5..a48103ad2e0 100644 --- a/addons/hr/hr_department_view.xml +++ b/addons/hr/hr_department_view.xml @@ -19,14 +19,6 @@ <field name="manager_id" select="1"/> <field name="company_id" select="1" widget="selection" groups="base.group_multi_company"/> </group> - <notebook colspan="4" > - <page string="Members"> - <field colspan="4" name="member_ids" nolabel="1"/> - </page> - <page string="Notes"> - <field colspan="4" name="note" nolabel="1"/> - </page> - </notebook> </form> </field> </record> diff --git a/addons/hr/hr_view.xml b/addons/hr/hr_view.xml index c2b0626fab0..f51280f4465 100644 --- a/addons/hr/hr_view.xml +++ b/addons/hr/hr_view.xml @@ -131,45 +131,46 @@ <field name="model">hr.employee</field> <field name="type">kanban</field> <field name="arch" type="xml"> - <kanban default_group_by="department_id"> + <kanban> <field name="color"/> <templates> + <t t-name="employee_details"> + <ul class="oe_kanban_tooltip" t-if="record.job_id.raw_value"> + <li><b>Job:</b> <field name="job_id"/></li> + </ul> + </t> <t t-name="kanban-box"> - <t t-set="color" t-value="kanban_color(record.color.raw_value || record.name.raw_value)"/> - <div t-att-class="color + (record.color.raw_value == 1 ? ' oe_kanban_color_alert' : '')"> + <div t-attf-class="#{kanban_color(record.color.raw_value)}"> <div class="oe_kanban_box oe_kanban_color_border"> - <div class="oe_kanban_box_header oe_kanban_color_bgdark oe_kanban_color_border oe_kanban_draghandle"> - <div class="oe_kanban_title1"><field name="name"/></div> + <div class="oe_kanban_box_header oe_kanban_color_bgdark oe_kanban_color_border oe_kanban_draghandle oe_kanban_title" tooltip="employee_details"> + <field name="name"/> </div> <div class="oe_kanban_box_content oe_kanban_color_bglight oe_kanban_box_show_onclick_trigger oe_kanban_color_border"> - <table class="oe_kanban_table"> - <tr> - <td valign="top" width="22"> - <img t-att-src="kanban_image('hr.employee', 'photo', record.id.value)" width="48"/> - </td> - <td> - <div class="oe_kanban_title2"><field name="job_id"/></div> - <div class="oe_kanban_title3"> - <field name="department_id"/> - <t t-if="record.department_id.raw_value && record.city.raw_value">,</t> - <field name="city"/> - </div> - <div class="oe_kanban_title3"> - <i><field name="work_email"/> - <t t-if="record.work_phone.raw_value && record.work_email.raw_value">,</t> - <field name="work_phone"/></i> - </div> - </td> - </tr> - </table> + <img t-att-src="kanban_image('hr.employee', 'photo', record.id.value)" width="48" style="float: left;"/> + <span t-if="record.parent_id.raw_value" class="oe_kanban_highlight"> + ❖ <field name="parent_id"/> + </span> + <span t-if="record.work_location.raw_value" class="oe_kanban_highlight"> + ✜ <field name="work_location"/> + </span> + <span t-if="record.work_email.raw_value" class="oe_kanban_highlight"> + ✉ <a t-attf-href="mailto:#{record.work_email.value}"><field name="work_email"/></a> + </span> + <span t-if="record.mobile_phone.raw_value" class="oe_kanban_highlight"> + ☎ <field name="mobile_phone"/> + </span> + <span t-if="record.work_phone.raw_value" class="oe_kanban_highlight"> + ☏ <field name="work_phone"/> + </span> + <div class="oe_kanban_clear"/> </div> <div class="oe_kanban_buttons_set oe_kanban_color_border oe_kanban_color_bglight oe_kanban_box_show_onclick"> <div class="oe_kanban_left"> - <a string="Edit" icon="gtk-edit" type="edit"/> + <a string="Edit" icon="gtk-edit" type="edit"/> <a string="Change Color" icon="color-picker" type="color" name="color"/> <a string="Send New Email" name="%(mail.action_email_compose_message_wizard)d" icon="terp-mail-message-new" type="action"/> </div> - <br class="oe_kanban_clear"/> + <div class="oe_kanban_clear"/> </div> </div> </div> @@ -201,21 +202,26 @@ <field name="name">Employees</field> <field name="res_model">hr.employee</field> <field name="view_type">form</field> - <field name="view_mode">tree,form,kanban</field> + <field name="view_mode">kanban,tree,form</field> <field name="domain">[]</field> <field name="context">{"search_default_department_id": department_id,"search_default_active":eval('True')}</field> - <field name="view_id" ref="view_employee_tree"/> + <field name="view_id" eval="False"/> <field name="search_view_id" ref="view_employee_filter"/> <field name="help">Here you can manage your work force by creating employees and assigning them specific properties in the system. Maintain all employee related information and keep track of anything that needs to be recorded for them. The personal information tab will help you maintain their identity data. The Categories tab gives you the opportunity to assign them related employee categories depending on their position and activities within the company. A category can be a seniority level within the company or a department. The Timesheets tab allows to assign them a specific timesheet and analytic journal where they will be able to enter time through the system. In the note tab, you can enter text data that should be recorded for a specific employee.</field> </record> - + + <record id="open_view_employee_list_my_kanban" model="ir.actions.act_window.view"> + <field name="sequence" eval="0"/> + <field name="view_mode">kanban</field> + <field name="act_window_id" ref="open_view_employee_list_my"/> + </record> <record id="open_view_employee_list_my_tree2" model="ir.actions.act_window.view"> <field name="sequence" eval="1"/> <field name="view_mode">tree</field> <field name="view_id" ref="view_employee_tree"/> <field name="act_window_id" ref="open_view_employee_list_my"/> </record> - + <record id="open_view_employee_list_my_form2" model="ir.actions.act_window.view"> <field name="sequence" eval="2"/> <field name="view_mode">form</field> diff --git a/addons/hr/security/hr_security.xml b/addons/hr/security/hr_security.xml index 8e77830184b..e8d1edd3712 100644 --- a/addons/hr/security/hr_security.xml +++ b/addons/hr/security/hr_security.xml @@ -3,11 +3,13 @@ <data noupdate="1"> <record id="base.group_hr_user" model="res.groups"> - <field name="name">Human Resources / HR Officer</field> + <field name="name">HR Officer</field> + <field name="category_id" ref="base.module_category_human_resources"/> <field name="implied_ids" eval="[(4, ref('base.group_user'))]"/> </record> <record id="base.group_hr_manager" model="res.groups"> - <field name="name">Human Resources / HR Manager</field> + <field name="name">HR Manager</field> + <field name="category_id" ref="base.module_category_human_resources"/> <field name="implied_ids" eval="[(4, ref('base.group_hr_user'))]"/> </record> <record id="hr_dept_comp_rule" model="ir.rule"> diff --git a/addons/hr/security/ir.model.access.csv b/addons/hr/security/ir.model.access.csv index 975ed7d4071..2911a49bf53 100644 --- a/addons/hr/security/ir.model.access.csv +++ b/addons/hr/security/ir.model.access.csv @@ -1,11 +1,11 @@ -"id","name","model_id:id","group_id:id","perm_read","perm_write","perm_create","perm_unlink" -"access_hr_employee_category_user","hr.employee.category.user","model_hr_employee_category","base.group_hr_user",1,1,1,1 -"access_hr_employee_category_emp","hr.employee.category.emp","model_hr_employee_category","base.group_user",1,0,0,0 -"access_hr_employee_user","hr.employee user","model_hr_employee","base.group_hr_user",1,1,1,1 -"access_hr_employee_system_user","hr.employee system user","model_hr_employee","base.group_user",1,0,0,0 -"access_hr_employee_resource_user","resource.resource.user","resource.model_resource_resource","base.group_hr_user",1,1,1,1 -"access_hr_department_user","hr.department.user","model_hr_department","base.group_hr_user",1,1,1,1 -"access_hr_department_employee","hr.department.employee","model_hr_department","base.group_user",1,0,0,0 -"access_hr_job_user","hr.job user","model_hr_job","base.group_hr_user",1,1,1,1 -"access_hr_res_partner_address","res.partner.address","base.model_res_partner_address","base.group_hr_manager",1,1,1,1 -"access_ir_property_hr_user","ir_property hr_user","base.model_ir_property","base.group_hr_user",1,1,1,0 +id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
+access_hr_employee_category_user,hr.employee.category.user,model_hr_employee_category,base.group_hr_user,1,1,1,1
+access_hr_employee_category_emp,hr.employee.category.emp,model_hr_employee_category,base.group_user,1,0,0,0
+access_hr_employee_user,hr.employee user,model_hr_employee,base.group_hr_user,1,1,1,1
+access_hr_employee_system_user,hr.employee system user,model_hr_employee,base.group_user,1,0,0,0
+access_hr_employee_resource_user,resource.resource.user,resource.model_resource_resource,base.group_hr_user,1,1,1,1
+access_hr_department_user,hr.department.user,model_hr_department,base.group_hr_user,1,1,1,1
+access_hr_department_employee,hr.department.employee,model_hr_department,base.group_user,1,0,0,0
+access_hr_job_user,hr.job user,model_hr_job,base.group_hr_user,1,1,1,1
+access_hr_res_partner_address,res.partner.address,base.model_res_partner_address,base.group_hr_manager,1,1,1,1
+access_ir_property_hr_user,ir_property hr_user,base.model_ir_property,base.group_hr_user,1,1,1,0
diff --git a/addons/hr/test/hr_demo.yml b/addons/hr/test/hr_demo.yml new file mode 100644 index 00000000000..6dee06d5eb3 --- /dev/null +++ b/addons/hr/test/hr_demo.yml @@ -0,0 +1,10 @@ +- + !record {model: hr.job, id: job_jr_appli, view: False}: + no_of_employee: 0.0 + no_of_recruitment: 5.0 +- + !record {model: hr.employee, id: employee1, view: False}: + address_id: base.main_address + company_id: base.main_company + department_id: dep_technical + user_id: base.user_demo diff --git a/addons/hr/test/open2recruit2close_job.yml b/addons/hr/test/open2recruit2close_job.yml new file mode 100644 index 00000000000..0e618f87a3d --- /dev/null +++ b/addons/hr/test/open2recruit2close_job.yml @@ -0,0 +1,38 @@ +- + In order to test the process of Human Resource Management, I open Job Postion for "Jr. Application Engineer". +- + !python {model: hr.job}: | + self.job_open(cr, uid, [ref('job_jr_appli')]) +- + I check state of Job Position after opening it. +- + !assert {model: hr.job, id: job_jr_appli, string: Job position is in 'open' state and no_of_recruitment = 0}: + - state == 'open' + - no_of_recruitment == 0 +- + Now, Recruitement is started so I start recruitement of Job Postion of "Jr. Application Engineer" Profile. +- + !python {model: hr.job}: | + self.job_recruitement(cr, uid, [ref('job_jr_appli')]) +- + I check 'state' and number of 'Expected in Recruitment' after initiating the recruitment +- + !assert {model: hr.job, id: job_jr_appli, string: Job position is in 'recruit' state and no_of_recruitment = 1.0}: + - state == 'recruit' + - no_of_recruitment == 1.0 +- + I assign the job position to a newly hired employee +- + !python {model: hr.employee}: | + self.write(cr, uid, [ref('employee1')], {'job_id':ref('job_jr_appli')}) +- + Now I don't want to recruit new employee for this position. so I mark it as Old. +- + !python {model: hr.job}: | + self.job_old(cr, uid, [ref('job_jr_appli')]) +- + I check 'state' and number of 'Expected in Recruitment' after closing the Job position. +- + !assert {model: hr.job, id: job_jr_appli, string: Job position is in 'old' state and no_of_recruitment = 0}: + - state == 'old' + - no_of_recruitment == 0 diff --git a/addons/hr/test/test_hr.yml b/addons/hr/test/test_hr.yml deleted file mode 100644 index 0e5ae559416..00000000000 --- a/addons/hr/test/test_hr.yml +++ /dev/null @@ -1,140 +0,0 @@ -- - In order to test hr module in OpenERP, I will create new Employee, Department and Job Position. -- - I create "RD Department" in Department form. -- - !record {model: hr.department, id: hr_department_rd0}: - manager_id: base.user_root - name: 'R & D' -- - Now, I create a new employee Mark Johnson, and select department as RD Department. -- - !record {model: hr.employee, id: hr_employee_mark}: - address_home_id: base.res_partner_address_1 - company_id: base.main_company - gender: male - marital: 'single' - name: Mark Johnson -- - I change the company of the employee. -- - !python {model: hr.employee}: | - res = self.onchange_company(cr, uid, [ref('hr_employee_mark')], ref('base.main_company'), None) - values = dict([('company_id', ref('base.main_company'))] + res['value'].items()) - self.write(cr, uid, [ref('hr_employee_mark')], values, None) -- - I assign department for employee Mark Johnson. -- - !python {model: hr.employee}: | - res = self.onchange_department_id(cr, uid, [ref('hr_employee_mark')], ref('hr_department_rd0'), None) - assert res['value']['parent_id'] - values = dict([('department_id', ref('hr_department_rd0'))] + res['value'].items()) - self.write(cr, uid, [ref('hr_employee_mark')], values, None) -- - Now I create a user for employee Mark Johnson. -- - !record {model: res.users, id: hr_users_markjohnson0}: - context_lang: en_US - groups_id: - - base.group_user - login: markjohnson - name: Mark Johnson - password: markjohnson -- - I assign user to employee Mark Johnson. -- - !python {model: hr.employee}: | - res = self.onchange_user(cr, uid, [ref('hr_employee_mark')], ref('hr_users_markjohnson0'), None) - values = dict([('user_id', ref('hr_users_markjohnson0'))] + res['value'].items()) - self.write(cr, uid, [ref('hr_employee_mark')], values, None) -- - In order to check the wizard Employee Hierarchy , I will create new employee Phil Graves and select Mark Johnson as - Manager. -- - !record {model: hr.employee, id: hr_employee_phil}: - address_home_id: base.res_partner_address_3000 - company_id: base.main_company - gender: male - name: Phil Graves - user_id: base.user_demo - parent_id: 'hr_employee_mark' -- - I fill the Working address for Employee. -- - !python {model: hr.employee}: | - res = self.onchange_address_id(cr, uid, ref('hr_employee_phil'), ref('base.res_partner_address_3000'), None) - assert res['value'] - values = dict([('address_id', ref('base.res_partner_address_3000'))] + res['value'].items()) - self.write(cr, uid, [ref('hr_employee_phil')], values, None) -- - I will open up form view of Mark Johnson and test the wizard Employee Hierarchy so it display the employee - hierarchy starting from Mark Johnson. - -- - I will create new Job Position. I will check successful creation of new Job Position by adding the information. -- - !record {model: hr.job, id: hr_job_jea0}: - department_id: 'hr_department_rd0' - description: 'Position of Junior Application Engineer' - expected_employees: 5 - name: 'JAE' -- - I check that Employee form is in "Open" state. -- - !assert {model: hr.job, id: hr_job_jea0}: - - state == 'open' -- - I create Employee for job position. -- - !record {model: hr.job, id: hr_job_jea0}: - employee_ids: - - address_home_id: base.res_partner_address_1 - name: Manuel Lehba - department_id: 'hr_department_rd0' - gender: male - parent_id: 'hr_employee_mark' -- - I check that "Number of Employees" field have some value. -- - !assert {model: hr.job, id: hr_job_jea0}: - - no_of_employee != False -- - As more requirements on the said job position are come, I increase the number of expected employees. -- - !python {model: hr.job}: | - res = self.on_change_expected_employee(cr, uid, [ref('hr_job_jea0')], 6, 3, None) - assert res['value']['expected_employees'] - values = dict([('expected_employees', ref('hr_job_jea0'))] + res['value'].items()) - self.write(cr, uid, [ref('hr_job_jea0')], values, None) -- - I open the job position for recruitment. -- - !python {model: hr.job}: | - self.job_recruitement(cr, uid, [ref('hr_job_jea0')]) -- - I assign the job position to employee and mark the position. -- - !python {model: hr.job}: | - self.job_open(cr, uid, [ref('hr_job_jea0')]) -- - Now the process is over so I don't want to use this position. I mark it as Old. -- - !python {model: hr.job}: | - self.job_old(cr, uid, [ref('hr_job_jea0')]) -- - I create a parent category for the new recruited employees who are Freshers. -- - !record {model: hr.employee.category, id: hr_employee_category_fresher0}: - name: Fresher -- - I create another category for Junior Level freshers. -- - !record {model: hr.employee.category, id: hr_employee_category_juniorlevel0}: - name: Junior Level - parent_id: hr_employee_category_fresher0 -- - I open the tree view of Categories and see the categories in a hierarchical manner. -- - !python {model: hr.employee.category}: | - res = self.name_get(cr, uid, [ref('hr_employee_category_juniorlevel0')], None) - assert res |
