[Merge]with: lp:openobject-addons

bzr revid: dbr@tinyerp.com-20111221051008-lzmt20sj7lhsqmak
This commit is contained in:
DBR (OpenERP) 2011-12-21 10:40:08 +05:30
commit df46c438f0
51 changed files with 489 additions and 458 deletions

View File

@ -3422,7 +3422,7 @@ class wizard_multi_charts_accounts(osv.osv_memory):
# Create Bank journals
self._create_bank_journals_from_o2m(cr, uid, obj_wizard, company_id, acc_template_ref, context=context)
return True
return {'type' : 'ir.actions.act_window_close'}
def _prepare_bank_journal(self, cr, uid, line, current_num, default_account_id, company_id, context=None):
'''

View File

@ -34,8 +34,11 @@
],
"demo_xml" : [ 'account_asset_demo.xml'
],
'test': ['test/account_asset.yml',
],
'test': [
'test/account_asset_demo.yml',
'test/account_asset.yml',
'test/account_asset_wizard.yml',
],
"update_xml" : [
"security/account_asset_security.xml",
"security/ir.model.access.csv",
@ -45,7 +48,6 @@
"account_asset_view.xml",
"account_asset_invoice_view.xml",
"report/account_asset_report_view.xml",
],
"active": False,
"installable": True,

View File

@ -1,55 +1,35 @@
-
In order to test Account Asset I create Asset and confirm it and check it's Depriciation lines
-
I Create an Asset Category
-
!record {model: account.asset.category, id: account_asset_category_landbuildings0}:
account_asset_id: account.xfa
account_depreciation_id: account.xfa
account_expense_depreciation_id: account.a_expense
journal_id: account.expenses_journal
name: Land & Buildings
-
I Create an Account Asset
-
!record {model: account.asset.asset, id: account_asset_asset_Land0}:
category_id: account_asset_category_landbuildings0
code: land
name: Land
partner_id: base.res_partner_14
purchase_value: 5000.0
state: draft
-
I check Initially that Account Asset is in the "Draft" state
-
!assert {model: account.asset.asset, id: account_asset_asset_Land0}:
- state == 'draft'
-
I Confirm Account Asset using Confirm Asset button
In order to test the process of Account Asset, I perform a action to confirm Account Asset.
-
!python {model: account.asset.asset}: |
self.validate(cr, uid, [ref("account_asset_asset_Land0")])
self.validate(cr, uid, [ref("account_asset_asset_vehicles0")])
-
I check Asset is in running state after pressing Confirm button on asset
I check Asset is now in Open state.
-
!assert {model: account.asset.asset, id: account_asset_asset_Land0}:
!assert {model: account.asset.asset, id: account_asset_asset_vehicles0, severity: error, string: Asset should be in Open state}:
- state == 'open'
-
I Compute Account Asset using Compute button and check the number of depreciation lines created
I compute depreciation lines for asset of CEO's Car .
-
!python {model: account.asset.asset}: |
self.compute_depreciation_board(cr, uid, [ref("account_asset_asset_Land0")])
self.compute_depreciation_board(cr, uid, [ref("account_asset_asset_vehicles0")])
# pressing computation button can be remove if creation of depreciation lines while asset is created
value = self.browse(cr, uid, [ref("account_asset_asset_Land0")])[0]
assert value.method_number == len(value.depreciation_line_ids)
value = self.browse(cr, uid, [ref("account_asset_asset_vehicles0")])[0]
assert value.method_number == len(value.depreciation_line_ids), 'Depreciation lines not created correctly'
-
I Create Account Move using create move button on depreciation lines
I create account move for all depreciation lines.
-
!python {model: account.asset.depreciation.line}: |
ids = self.search(cr, uid, [('asset_id','=',ref('account_asset_asset_Land0'))])
ids = self.search(cr, uid, [('asset_id','=',ref('account_asset_asset_vehicles0'))])
self.create_move(cr, uid, ids)
-
I Check that After creating all the moves of depreciation lines the state is in "Close" state
I check the move line is created.
-
!assert {model: account.asset.asset, id: account_asset_asset_Land0}:
!python {model: account.asset.asset}: |
asset = self.browse(cr, uid, [ref("account_asset_asset_vehicles0")])[0]
assert len(asset.depreciation_line_ids) == len(asset.account_move_line_ids), 'Move lines not created correctly'
-
I Check that After creating all the moves of depreciation lines the state "Close".
-
!assert {model: account.asset.asset, id: account_asset_asset_vehicles0}:
- state == 'close'

View File

@ -0,0 +1,9 @@
-
!record {model: account.asset.category, id: account_asset_category_fixedassets0}:
account_asset_id: account.xfa
-
!record {model: account.asset.asset, id: account_asset_asset_vehicles0}:
category_id: account_asset_category_sale
-
!record {model: account.asset.asset, id: account_asset_asset_vehicles0}:
method_number: 10

View File

@ -0,0 +1,27 @@
-
I create a record to change the duration of asset for calculating depreciation.
-
!record {model: asset.modify, id: asset_modify_number_0, context: "{'active_id': ref('account_asset_asset_office0')}"}:
method_number: 10.0
-
I change the duration.
-
!python {model: asset.modify}: |
context = {"active_id":ref('account_asset_asset_office0')}
self.modify(cr, uid, [ref("asset_modify_number_0")], context=context)
-
I check the proper depreciation lines created.
-
!assert {model: account.asset.asset, id: account_asset.account_asset_asset_office0}:
- method_number == len(depreciation_line_ids) -1
-
I create a period to compute a asset on period.
-
!record {model: asset.depreciation.confirmation.wizard, id: asset_compute_period_0}:
{}
-
I compute a asset on period.
-
!python {model: asset.depreciation.confirmation.wizard}: |
context = {"active_ids": [ref("menu_asset_depreciation_confirmation_wizard")], "active_id":ref('menu_asset_depreciation_confirmation_wizard')}
self.asset_compute(cr, uid, [ref("asset_compute_period_0")], context=context)

View File

@ -57,7 +57,10 @@ Note that if you want to check the followup level for a given partner/account en
'account_followup_data.xml',
],
'demo_xml': [],
'test': ['test/account_followup.yml'],
'test': [
'test/account_followup.yml',
'test/account_followup_report.yml',
],
'installable': True,
'active': False,
'certificate': '0072481076453',

View File

@ -1,91 +1,25 @@
-
In order to test account followup module in OpenERP I create a FollowUp structure
In order to test account followup module in OpenERP, I change the state of invoice to "open".
-
!record {model: res.company, id: ymltest_company_2}:
name: Acme 2
!record {model: account.invoice, id: account.demo_invoice_0}:
check_total: 14.0
-
!record {model: account_followup.followup, id: account_followup_followup_testfollowups0}:
description: First letter after 15 net days, 30 net days and 45 days end of month levels.
company_id: ymltest_company_2
followup_line:
- delay: 15
name: 'level 0: 15 days'
sequence: 0
start: days
description: Dear %(partner_name)s,\n\nException made if there was a mistake
of ours, it seems that the following amount staid unpaid. Please, take appropriate
measures in order to carry out this payment in the next 1 days.\n\nWould your
payment have been carried out after this mail was sent, please consider the
present one as void. Do not hesitate to contact our accounting department at
(+32).10.68.94.39.\n\nBest Regards,\n
- delay: 30
name: 'level1: 30 days'
sequence: 1
start: days
description: Dear %(partner_name)s,\n\nException made if there was a mistake
of ours, it seems that the following amount staid unpaid. Please, take appropriate
measures in order to carry out this payment in the next 2 days.\n\nWould your
payment have been carried out after this mail was sent, please consider the
present one as void. Do not hesitate to contact our accounting department at
(+32).10.68.94.39.\n\nBest Regards,\n
- delay: 45
name: 'level 2: 45 days'
sequence: 2
start: days
description: Dear %(partner_name)s,\n\nException made if there was a mistake
of ours, it seems that the following amount staid unpaid. Please, take appropriate
measures in order to carry out this payment in the next 3 days.\n\nWould your
payment have been carried out after this mail was sent, please consider the
present one as void. Do not hesitate to contact our accounting department at
(+32).10.68.94.39.\n\nBest Regards,
name: My followups
!workflow {model: account.invoice, action: invoice_open, ref: account.demo_invoice_0}
-
I create an invoice
-
!record {model: account.invoice, id: account_invoice_followup}:
account_id: account.a_recv
address_contact_id: base.res_partner_address_3000
address_invoice_id: base.res_partner_address_3000
company_id: base.main_company
currency_id: base.EUR
invoice_line:
- account_id: account.a_sale
name: '[PC1] Basic PC'
price_unit: 450.0
quantity: 1.0
product_id: product.product_product_pc1
uos_id: product.product_uom_unit
journal_id: account.sales_journal
partner_id: base.res_partner_desertic_hispafuentes
reference_type: none
-
I change the state of the invoice using create button
-
!workflow {model: account.invoice, action: invoice_open, ref: account_invoice_followup}
-
I create a send followup record
I create a followup.
-
!record {model: account.followup.print, id: account_followup_print_0}:
date: !eval time.strftime('%Y-%m-%d')
followup_id: account_followup_followup_testfollowups0
{}
-
I Select Followup and clicked on Continue Button
I select the followup to send it to the partner.
-
!python {model: account.followup.print}: |
self.do_continue(cr, uid, [ref("account_followup_print_0")], {"lang": 'en_US',
"active_model": "ir.ui.menu", "active_ids": [ref("account_followup.account_followup_print_menu")],
"tz": False, "active_id": ref("account_followup.account_followup_print_menu"),
})
-
I select partners whom I want to send followups
I select partners whom I want to send followups.
-
!record {model: account.followup.print.all, id: account_followup_print_all_0}:
email_body: 'Date : %(date)s\n\nDear %(partner_name)s,\n\nPlease find in attachment
@ -95,15 +29,12 @@
partner_ids:
- base.res_partner_desertic_hispafuentes
partner_lang: 1
-
I clicked on Print Follow Ups to print Followups reports
I send a followup mail to partner.
-
!python {model: account.followup.print.all}: |
import time
self.do_print(cr, uid, [ref("account_followup_print_all_0")], {"lang": 'en_US',
self.do_mail(cr, uid, [ref("account_followup_print_all_0")], {"lang": 'en_US',
"active_model": "ir.ui.menu", "active_ids": [ref("account_followup.account_followup_print_menu")],
"tz": False, "date": time.strftime('%Y-%m-%d'), "followup_id": ref("account_followup_followup_testfollowups0"), "active_id": ref("account_followup.account_followup_print_menu"),
"company_id": ref('base.main_company'),
"tz": False, "date": time.strftime('%Y-%m-%d'), "followup_id": ref("account_followup.demo_followup1"), "active_id": ref("account_followup.account_followup_print_menu"),
})

View File

@ -0,0 +1,10 @@
-
In order to test the report I print followup report.
-
!python {model: account.followup.print.all}: |
import time
ctx = {'form_view_ref':'account_followup.view_account_followup_print_all', 'followup_id': ref('account_followup.demo_followup1'),'date': time.strftime('%Y-%m-%d'),'model': 'account_followup.followup','active_ids':[ref('account_followup_print_all_0')], 'company_id':ref('base.main_company')}
data_dict = {'email_conf': 1}
from tools import test_reports
test_reports.try_report_action(cr, uid, 'action_account_followup_print_all', context=ctx, wiz_data=data_dict,wiz_buttons=["Print Follow Ups"], our_module='account_followup')

View File

@ -368,8 +368,6 @@ class account_voucher(osv.osv):
line_ids = resolve_o2m_operations(cr, uid, line_pool, line_ids, ["amount"], context)
total = 0.0
total_tax = 0.0
for line in line_ids:
line_amount = 0.0
line_amount = line.get('amount',0.0)
@ -830,8 +828,6 @@ class account_voucher(osv.osv):
:return: mapping between fieldname and value of account move line to create
:rtype: dict
'''
move_line_obj = self.pool.get('account.move.line')
currency_obj = self.pool.get('res.currency')
voucher_brw = self.pool.get('account.voucher').browse(cr,uid,voucher_id,context)
debit = credit = 0.0
# TODO: is there any other alternative then the voucher type ??
@ -870,7 +866,6 @@ class account_voucher(osv.osv):
:return: mapping between fieldname and value of account move to create
:rtype: dict
'''
move_obj = self.pool.get('account.move')
seq_obj = self.pool.get('ir.sequence')
voucher_brw = self.pool.get('account.voucher').browse(cr,uid,voucher_id,context)
if voucher_brw.number:
@ -1119,7 +1114,6 @@ class account_voucher(osv.osv):
:return: mapping between fieldname and value of account move line to create
:rtype: dict
'''
move_line_obj = self.pool.get('account.move.line')
currency_obj = self.pool.get('res.currency')
move_line = {}
@ -1181,9 +1175,6 @@ class account_voucher(osv.osv):
context = {}
move_pool = self.pool.get('account.move')
move_line_pool = self.pool.get('account.move.line')
currency_pool = self.pool.get('res.currency')
tax_obj = self.pool.get('account.tax')
seq_obj = self.pool.get('ir.sequence')
for voucher in self.browse(cr, uid, ids, context=context):
if voucher.move_id:
continue
@ -1213,7 +1204,7 @@ class account_voucher(osv.osv):
# Create the writeoff line if needed
ml_writeoff = self.writeoff_move_line_get(cr, uid, voucher.id, line_total, move_id, name, company_currency, current_currency, context)
if ml_writeoff:
ml_writeoff_id = move_line_pool.create(cr, uid, ml_writeoff, context)
move_line_pool.create(cr, uid, ml_writeoff, context)
# We post the voucher.
self.write(cr, uid, [voucher.id], {
'move_id': move_id,

View File

@ -1,4 +1,5 @@
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
access_audittrail_rule_all_users,audittrail rule all,model_audittrail_rule,base.group_user,1,0,0,0
access_audittrail_rule_all_users,audittrail rule all,model_audittrail_rule,base.group_system,1,1,1,0
access_audittrail_rule_all_access,audittrail rule all,model_audittrail_rule,base.group_erp_manager,1,1,1,0
access_audittrail_log_all_users,audittrail log all,model_audittrail_log,base.group_user,1,0,1,0
access_audittrail_log_line_all_users,audittrail log line all,model_audittrail_log_line,base.group_user,1,0,1,0

1 id name model_id:id group_id:id perm_read perm_write perm_create perm_unlink
2 access_audittrail_rule_all_users audittrail rule all model_audittrail_rule base.group_user base.group_system 1 0 1 0 1 0
3 access_audittrail_rule_all_access audittrail rule all model_audittrail_rule base.group_erp_manager 1 1 1 0
4 access_audittrail_log_all_users audittrail log all model_audittrail_log base.group_user 1 0 1 0
5 access_audittrail_log_line_all_users audittrail log line all model_audittrail_log_line base.group_user 1 0 1 0

View File

@ -38,7 +38,7 @@
<page string="General">
<group colspan="4" col="4">
<group colspan="2" col="4">
<separator string="Communication" colspan="4"/>
<separator string="Personal Information" colspan="4"/>
<field name="mobile"/>
<field name="email" widget="email"/>
<field name="website"/>
@ -52,7 +52,7 @@
<form string="Functions and Addresses">
<field name="location_id"/>
<field name="function" />
<separator string="Communication" colspan="4"/>
<separator string="Professional Info" colspan="4"/>
<field name="phone"/>
<field name="fax"/>
<field name="email" widget="email"/>

View File

@ -123,6 +123,7 @@ Creates a dashboard for CRM that includes:
'test/process/lead2opportunity2win.yml',
'test/process/merge_opportunity.yml',
'test/process/cancel_lead.yml',
'test/process/action_rule.yml',
'test/process/segmentation.yml',
'test/ui/crm_demo.yml',
'test/ui/duplicate_lead.yml',

View File

@ -468,12 +468,10 @@ class crm_case(crm_base):
self._action(cr, uid, cases, state)
return True
#DEAD Code
def remind_partner(self, cr, uid, ids, context=None, attach=False):
return self.remind_user(cr, uid, ids, context, attach,
destination=False)
#DEAD Code
def remind_user(self, cr, uid, ids, context=None, attach=False, destination=True):
mail_message = self.pool.get('mail.message')
for case in self.browse(cr, uid, ids, context=context):

View File

@ -450,7 +450,8 @@
<field name="user_id"/>
<button string="Schedule/Log Call"
name="%(opportunity2phonecall_act)d" icon="terp-call-start" type="action"/>
name="%(opportunity2phonecall_act)d" icon="terp-call-start"
type="action"/>
<field name="planned_revenue"/>
<field name="probability"/>
@ -648,8 +649,8 @@
name="pending"
domain="[('state','=','pending')]"/>
<separator orientation="vertical"/>
<field name="name" string="Opportunity / Customer" filter_domain="['|','|','|',('partner_id','ilike',self),('partner_name','ilike',self),('email_from','ilike',self),('name', 'ilike', self)]"/>
<field name="partner_id" string="Customer / Email" filter_domain="['|','|',('partner_id','ilike',self),('partner_name','ilike',self),('email_from','ilike',self)]"/>
<field name="name" string="Opportunity / Customer"
filter_domain="['|','|','|',('partner_id','ilike',self),('partner_name','ilike',self),('email_from','ilike',self),('name', 'ilike', self)]"/>
<field name="user_id">
<filter icon="terp-personal-"
domain="[('user_id','=', False)]"

View File

@ -118,7 +118,7 @@ class crm_phonecall(crm_base, osv.osv):
"""Resets case as Todo
"""
res = super(crm_phonecall, self).case_reset(cr, uid, ids, args, 'crm.phonecall')
self.write(cr, uid, ids, {'duration': 0.0})
self.write(cr, uid, ids, {'duration': 0.0, 'state':'open'})
return res

View File

@ -0,0 +1,22 @@
-
I create a record rule.
-
!python {model: base.action.rule}: |
modle_id = self.pool.get("ir.model").search(cr, uid, [('name', '=', 'crm.lead')])
from datetime import datetime
new_id = self.create(cr, uid, {'name': 'New Rule', 'model_id': modle_id[0], 'trg_user_id': ref('base.user_root'), 'trg_partner_id': ref('base.res_partner_asus'), 'act_user_id': ref('base.user_demo') })
lead_obj = self.pool.get("crm.lead")
self._check(cr, uid)
-
I create new lead to check record rule.
-
!record {model: crm.lead, id: crm_lead_test_rules_id}:
name: 'Test lead rules'
user_id: base.user_root
partner_id: base.res_partner_asus
-
I check record rule is apply and responsible is changed.
-
!python {model: crm.lead}: |
lead_user = self.browse(cr, uid, ref('crm_lead_test_rules_id'))
assert lead_user.user_id.id == ref('base.user_demo'), "Responsible of lead is not changed."

View File

@ -29,12 +29,12 @@
!assert {model: crm.lead, id: crm.crm_case_itisatelesalescampaign0, string: Lead is in pending state}:
- state == "pending"
-
I Escalate the Lead to Parent Team.
I escalate the lead to parent team.
-
!python {model: crm.lead}: |
self.case_escalate(cr, uid, [ref("crm_case_itisatelesalescampaign0")])
-
I check lead escalate to Parent Team.
I check lead escalate to parent team.
-
!assert {model: crm.lead, id: crm.crm_case_itisatelesalescampaign0, string: Escalate lead to parent team}:
- section_id.name == "Sales Department"

View File

@ -1,5 +1,5 @@
-
Customer interested in our product. so He send request by email to get more details.
Customer interested in our product. so he send request by email to get more details.
-
Mail script will be fetched him request from mail server. so I process that mail after read EML file
-
@ -41,10 +41,12 @@
partner_ids = self.message_partner_by_email(cr, uid, 'Mr. John Right <info@customer.com>')
assert partner_ids.get('partner_id'), "Customer is not found in regular customer list."
-
I convert one phonecall request as a customer and put into regular customer list.
I convert one phonecall request as a customer and put into regular customer list.
-
!python {model: crm.phonecall}: |
self.convert_partner(cr, uid, [ref('crm.crm_case_phone06')], context=context)
!python {model: crm.phonecall2partner}: |
context.update({'active_model': 'crm.phonecall', 'active_ids': [ref("crm.crm_case_phone06")], 'active_id': ref("crm.crm_case_phone06")})
new_id = self.create(cr, uid, {}, context=context)
self.make_partner(cr, uid, [new_id], context=context)
-
I check converted phonecall to partner.
-

View File

@ -6,10 +6,18 @@
!python {model: crm.lead}: |
self.case_open(cr, uid, [ref("crm_case_qrecorp0")])
-
I check lead state is "Open".
I check lead state is "Open".
-
!assert {model: crm.lead, id: crm.crm_case_qrecorp0, string: Lead in open state}:
- state == "open"
-
I create partner from lead.
-
!record {model: crm.lead2partner, id: crm_lead2partner_id1, context: '{"active_model": "crm.lead", "active_ids": [ref("crm_case_qrecorp0")]}'}:
-
!python {model: crm.lead2partner}: |
context.update({'active_model': 'crm.lead', 'active_ids': [ref('crm_case_qrecorp0')], 'active_id': ref('crm_case_qrecorp0')})
self.make_partner(cr, uid ,[ref("crm_lead2partner_id1")], context=context)
-
I convert lead into opportunity for exiting customer.
-
@ -39,13 +47,13 @@
ids = self.search(cr, uid, [('opportunity_id', '=', ref('crm_case_qrecorp0'))])
assert len(ids), 'phonecall is not scheduled'
-
Now I schedule Meeting with Customer.
Now I schedule meeting with customer.
-
!python {model: crm.lead}: |
self.action_makeMeeting(cr, uid, [ref('crm_case_qrecorp0')])
-
After communicated with customer, I put some notes with Contract details.
After communicated with customer, I put some notes with contract details.
-
!python {model: crm.add.note}: |
context.update({'active_model': 'crm.lead', 'active_id': ref('crm_case_qrecorp0')})
@ -57,7 +65,7 @@
!python {model: crm.lead}: |
self.case_mark_won(cr, uid, [ref("crm_case_qrecorp0")])
-
I check details of the opportunity After won the opportunity.
I check details of the opportunity after won the opportunity.
-
!python {model: crm.lead}: |
lead = self.browse(cr, uid, ref('crm_case_qrecorp0'))
@ -72,7 +80,7 @@
id = self.create(cr, uid, {'user_ids': [ref('base.user_root')], 'section_id': ref('crm.section_sales_department')}, context=context)
self.mass_convert(cr, uid, [id], context=context)
-
Now I check First lead converted on opportunity.
Now I check first lead converted on opportunity.
-
!python {model: crm.lead}: |
opp = self.browse(cr, uid, ref('crm_case_employee0'))
@ -81,10 +89,22 @@
assert opp.partner_id.name == "Agrolait", 'Partner missmatch!'
assert opp.stage_id.id == ref("stage_lead1"), 'Stage of probability is incorrect!'
-
Then check for Second lead converted on opportunity.
Then check for second lead converted on opportunity.
-
!python {model: crm.lead}: |
opp = self.browse(cr, uid, ref('crm_case_electonicgoodsdealer0'))
assert opp.name == "Interest in Your New Product", "Opportunity name not correct"
assert opp.type == 'opportunity', 'Lead is not converted to opportunity!'
assert opp.stage_id.id == ref("stage_lead1"), 'Stage of probability is incorrect!'
assert opp.stage_id.id == ref("stage_lead1"), 'Stage of probability is incorrect!'
-
I confirm review needs meeting.
-
!python {model: crm.meeting}: |
context.update({'active_model': 'crm.meeting'})
self.case_open(cr, uid, [ref('crm.crm_case_reviewneeds0')])
-
I invite a user for meeting.
-
!python {model: calendar.attendee}: |
meeting_id = self.create(cr, uid, {'user_id': ref('base.user_root'), 'email': 'user@meeting.com' })
self.do_accept(cr, uid, [meeting_id])

View File

@ -1,5 +1,5 @@
-
I make direct opportunity for Customer.
I make direct opportunity for customer.
-
!python {model: crm.partner2opportunity}: |
context.update({'active_model': 'res.partner', 'active_ids': [ref("base.res_partner_9")]})
@ -13,13 +13,18 @@
res_id = self.create(cr, uid, {'name': "Quoi de prix de votre autre service?", 'partner_id': ref("base.res_partner_9")}, context=context)
self.make_opportunity(cr, uid, [res_id], context=context)
-
Now I merge all opportunities of customer.
Now I merge all opportunities of customer.
-
!python {model: crm.lead}: |
opportunity_ids = self.search(cr, uid, [('partner_id','=', ref("base.res_partner_9"))])
self.merge_opportunity(cr, uid, opportunity_ids, context=context)
context.update({'active_model': 'crm.lead', 'active_ids': opportunity_ids, 'active_id': opportunity_ids[0]})
-
I check for merged opportunities for customer.
!record {model: crm.merge.opportunity, id: opportunity_merge_id }:
-
!python {model: crm.merge.opportunity}: |
self.action_merge(cr, uid, [ref("opportunity_merge_id")], context=context)
-
I check for merged opportunities for customer.
-
!python {model: crm.lead}: |
merge_id = self.search(cr, uid, [('partner_id','=', ref("base.res_partner_9"))])
@ -31,21 +36,51 @@
Now I schedule another phonecall to customer after merged.
-
!python {model: crm.phonecall2phonecall}: |
context.update({'active_model': 'crm.phonecall', 'active_ids': [ref("crm.crm_case_phone06")]})
context.update({'active_model': 'crm.phonecall', 'active_ids': [ref("crm.crm_case_phone06")], 'active_id': ref("crm.crm_case_phone06")})
res_id = self.create(cr, uid, {'name': "vos chances sont fusionnés en un seul"}, context=context)
self.action_schedule(cr, uid, [res_id], context=context)
-
I schedule Meeting on this phonecall.
I schedule meeting on this phonecall.
-
!python {model: crm.phonecall}: |
self.action_make_meeting(cr, uid, [ref("crm.crm_case_phone06")])
-
I setting Phone call to Held (Done).
I set phone call to not held.
-
!python {model: crm.phonecall}: |
self.case_pending(cr, uid, [ref("crm.crm_case_phone06")])
-
I check that the phone call is in 'Not Held' state.
-
!assert {model: crm.phonecall, id: crm.crm_case_phone06, string: Phone call held.}:
- state == "pending"
-
I cancelled the phone call.
-
!python {model: crm.phonecall}: |
self.case_cancel(cr, uid, [ref("crm.crm_case_phone06")])
-
I check that the phone call is in 'Cancelled' state.
-
!assert {model: crm.phonecall, id: crm.crm_case_phone06, string: Phone call is not cancelled.}:
- state == "cancel"
-
I reset the phone call.
-
!python {model: crm.phonecall}: |
self.case_reset(cr, uid, [ref("crm.crm_case_phone06")])
-
I check that the phone call is reset or not.
-
!assert {model: crm.phonecall, id: crm.crm_case_phone06, string: Phone call is not reset.}:
- state == "open"
-
I set phone call to held (done).
-
!python {model: crm.phonecall}: |
self.case_close(cr, uid, [ref("crm.crm_case_phone06")])
-
I check that the phone call is in 'Held' state.
-
!assert {model: crm.phonecall, id: crm.crm_case_phone06, string: Phone call Helded}:
!assert {model: crm.phonecall, id: crm.crm_case_phone06, string: Phone call is not held.}:
- state == "done"

View File

@ -8,7 +8,7 @@
#Todo: Need to check after segmentation started
-
I create rule Segmentation line record for partner .
I create rule segmentation line record for partner .
-
!python {model: crm.segmentation.line}: |
id = self.create(cr, uid, {'name': "OpenERP partners",'expr_value': 25})

View File

@ -601,7 +601,8 @@ class EDIMixin(object):
self._name, external_id, value)
# also need_new_ext_id here, but already been set above
model = self.pool.get(model)
res_id, name = model.name_create(cr, uid, value, context=context)
# should use name_create() but e.g. res.partner won't allow it at the moment
res_id = model.create(cr, uid, {model._rec_name: value}, context=context)
target = model.browse(cr, uid, res_id, context=context)
if need_new_ext_id:
ext_id_members = split_external_id(external_id)

View File

@ -37,7 +37,7 @@ This is the module to manage the accounting chart for France in OpenERP.
Credits: Sistheo Zeekom CrysaLEAD
""",
"depends" : ['base', 'account', 'account_chart', 'base_vat', 'l10n_fr_rib'],
"depends" : ['base_iban', 'account', 'account_chart', 'base_vat', 'l10n_fr_rib'],
"init_xml" : [],
"update_xml" : [
"fr_report_demo.xml",

View File

@ -41,6 +41,7 @@ class report_custom(report_rml):
rml_obj=report_sxw.rml_parse(cr, uid, product_pool._name,context)
rml_obj.localcontext.update({'lang':context.get('lang',False)})
company_currency = user_pool.browse(cr, uid, uid).company_id.currency_id
company_currency_symbol = company_currency.symbol or company_currency.name
def process_bom(bom, currency_id, factor=1):
xml = '<row>'
sum = 0
@ -62,7 +63,7 @@ class report_custom(report_rml):
'uom': prod.uom_po_id.id,
'date': time.strftime('%Y-%m-%d'),
})[pricelist.id]
main_sp_price = """<b>"""+rml_obj.formatLang(price)+' '+ company_currency.symbol+"""</b>\r\n"""
main_sp_price = """<b>"""+rml_obj.formatLang(price)+' '+ (company_currency_symbol)+"""</b>\r\n"""
sum += prod_qtty*price
std_price = product_uom_pool._compute_price(cr, uid, prod.uom_id.id, prod.standard_price, to_uom_id=product_uom.id)
main_strd_price = str(std_price) + '\r\n'
@ -75,11 +76,11 @@ class report_custom(report_rml):
'uom': prod.uom_po_id.id,
'date': time.strftime('%Y-%m-%d'),
})[pricelist.id]
sellers_price += """<i>"""+rml_obj.formatLang(price) +' '+ company_currency.symbol +"""</i>\r\n"""
sellers_price += """<i>"""+rml_obj.formatLang(price) +' '+ (company_currency_symbol) +"""</i>\r\n"""
xml += """<col para='yes'> """+ prod_name +""" </col>
<col para='yes'> """+ main_sp_name + sellers + """ </col>
<col f='yes'>"""+ rml_obj.formatLang(prod_qtty) +' '+ product_uom_name +"""</col>
<col f='yes'>"""+ rml_obj.formatLang(float(main_strd_price)) +' '+ company_currency.symbol +"""</col>
<col f='yes'>"""+ rml_obj.formatLang(float(main_strd_price)) +' '+ (company_currency_symbol) +"""</col>
<col f='yes'>""" + main_sp_price + sellers_price + """</col>'"""
xml += '</row>'
@ -93,9 +94,9 @@ class report_custom(report_rml):
xml = '<row>'
xml += "<col para='yes'>" + to_xml(workcenter.name) + '</col>'
xml += "<col/>"
xml += """<col f='yes'>"""+rml_obj.formatLang(cost_cycle)+' '+ company_currency.symbol + """</col>"""
xml += """<col f='yes'>"""+rml_obj.formatLang(cost_hour)+' '+ company_currency.symbol + """</col>"""
xml += """<col f='yes'>"""+rml_obj.formatLang(cost_hour + cost_cycle)+' '+ company_currency.symbol + """</col>"""
xml += """<col f='yes'>"""+rml_obj.formatLang(cost_cycle)+' '+ (company_currency_symbol) + """</col>"""
xml += """<col f='yes'>"""+rml_obj.formatLang(cost_hour)+' '+ (company_currency_symbol) + """</col>"""
xml += """<col f='yes'>"""+rml_obj.formatLang(cost_hour + cost_cycle)+' '+ (company_currency_symbol) + """</col>"""
xml += '</row>'
return xml, total
@ -159,8 +160,8 @@ class report_custom(report_rml):
<col> """ + _('Total Cost of %s %s') % (str(number), product_uom_name) + """: </col>
<col/>
<col f='yes'/>
<col t='yes'>"""+ rml_obj.formatLang(total_strd, digits=purchase_price_digits) +' '+ company_currency.symbol + """</col>
<col t='yes'>"""+ rml_obj.formatLang(total, digits=purchase_price_digits) +' '+ company_currency.symbol + """</col>
<col t='yes'>"""+ rml_obj.formatLang(total_strd, digits=purchase_price_digits) +' '+ (company_currency_symbol) + """</col>
<col t='yes'>"""+ rml_obj.formatLang(total, digits=purchase_price_digits) +' '+ (company_currency_symbol) + """</col>
</row></lines>'"""
else:
bom = bom_pool.browse(cr, uid, bom_id, context=context)
@ -186,7 +187,7 @@ class report_custom(report_rml):
<col> """ + _('Components Cost of %s %s') % (str(number), product_uom_name) + """: </col>
<col/>
<col t='yes'/>
<col t='yes'>"""+ rml_obj.formatLang(total_strd, digits=purchase_price_digits) +' '+ company_currency.symbol + """</col>
<col t='yes'>"""+ rml_obj.formatLang(total_strd, digits=purchase_price_digits) +' '+ (company_currency_symbol) + """</col>
<col t='yes'></col>
</row></lines>'"""
@ -204,13 +205,13 @@ class report_custom(report_rml):
<col/>
<col/>
<col/>
<col t='yes'>"""+ rml_obj.formatLang(total2, digits=purchase_price_digits) +' '+ company_currency.symbol +"""</col>
<col t='yes'>"""+ rml_obj.formatLang(total2, digits=purchase_price_digits) +' '+ (company_currency_symbol) +"""</col>
</row></lines>'"""
xml += """<lines style='total'> <row>
<col> """ + _('Total Cost of %s %s') % (str(number), product_uom_name) + """: </col>
<col/>
<col t='yes'/>
<col t='yes'>"""+ rml_obj.formatLang(total_strd+total2, digits=purchase_price_digits) +' '+ company_currency.symbol + """</col>
<col t='yes'>"""+ rml_obj.formatLang(total_strd+total2, digits=purchase_price_digits) +' '+ (company_currency_symbol) + """</col>
<col t='yes'></col>
</row></lines>'"""

View File

@ -12,13 +12,14 @@ class plugin_handler(osv.osv_memory):
def _make_url(self, cr, uid, res_id, model, context=None):
"""
@param id: on which document the message is pushed
@param res_id: on which document the message is pushed
@param model: name of the document linked with the mail
@return url
"""
base_url = self.pool.get('ir.config_parameter').get_param(cr, uid, 'web.base.url', default='http://localhost:8069', context=context)
if base_url:
base_url += '/?id=%s&model=%s'%(res_id,model)
user = self.pool.get('res.users').browse(cr, uid, uid, context=context)
base_url += '/web/webclient/login?db=%s&login=%s&key=%s#id=%s&model=%s' % (cr.dbname, user.login, user.password, res_id, model)
return base_url
def is_installed(self, cr, uid):

View File

@ -737,7 +737,6 @@ class product_product(osv.osv):
'expense_pdt': fields.boolean('PoS Cash Output', help="This is a product you can use to take cash from a statement for the point of sale backend, exemple: money lost, transfer to bank, etc."),
'img': fields.binary('Product Image, must be 50x50', help="Use an image size of 50x50."),
'pos_categ_id': fields.many2one('pos.category','PoS Category',
domain="[('type','=','normal')]",
help="If you want to sell this product through the point of sale, select the category it belongs to.")
}
product_product()

View File

@ -82,7 +82,7 @@ class pos_box_out(osv.osv_memory):
stat_done = statement_obj.browse(cr, uid, done_statmt, context=context)
am = 0.0
product = product_obj.browse(cr, uid, data['product_id'], context=context)
acc_id = product.property_account_income
acc_id = product.property_account_income or product.categ_id.property_account_income_categ
if not acc_id:
raise osv.except_osv(_('Error !'), _('please check that account is set to %s')%(product.name))
if not statement_ids:

View File

@ -78,11 +78,12 @@
proc_id = context.get('proc')
proc = self.browse(cr, uid, [proc_id])[0]
assert proc.state == 'ready' or 'exception',"Procurement should be in Ready or Exception state"
-
I compute minimum stock.
-
!python {model: procurement.orderpoint.compute}: |
proc_id = context.get('proc')
context.update({'active_model': 'procurement.order', 'active_id': proc_id})
id = self.create(cr, uid, {'automatic': True}, context)
#self.procure_calculation(cr, uid, [id], context)
#-
# I compute minimum stock.
# [Note. Commented out because it spawns a thread that may query the db after tests have been reverted.]
#-
# !python {model: procurement.orderpoint.compute}: |
# proc_id = context.get('proc')
# context.update({'active_model': 'procurement.order', 'active_id': proc_id})
# id = self.create(cr, uid, {'automatic': True}, context)
# self.procure_calculation(cr, uid, [id], context)

View File

@ -114,13 +114,6 @@ class project(osv.osv):
if task.project_id: result[task.project_id.id] = True
return result.keys()
#dead code
def _get_project_work(self, cr, uid, ids, context=None):
result = {}
for work in self.pool.get('project.task.work').browse(cr, uid, ids, context=context):
if work.task_id and work.task_id.project_id: result[work.task_id.project_id.id] = True
return result.keys()
def unlink(self, cr, uid, ids, *args, **kwargs):
for proj in self.browse(cr, uid, ids):
if proj.tasks:

View File

@ -72,13 +72,7 @@ class project_phase(osv.osv):
if phase['date_start'] and phase['date_end'] and phase['date_start'] > phase['date_end']:
return False
return True
#dead code
def _get_default_uom_id(self, cr, uid):
model_data_obj = self.pool.get('ir.model.data')
model_data_id = model_data_obj._get_id(cr, uid, 'product', 'uom_hour')
return model_data_obj.read(cr, uid, [model_data_id], ['res_id'])[0]['res_id']
#dead code
def _compute_progress(self, cr, uid, ids, field_name, arg, context=None):
res = {}
if not ids:

View File

@ -254,6 +254,7 @@ class project_scrum_task(osv.osv):
for task in line.tasks_id:
result[task.id] = True
return result.keys()
_columns = {
'product_backlog_id': fields.many2one('project.scrum.product.backlog', 'Product Backlog',help="Related product backlog that contains this task. Used in SCRUM methodology"),
'sprint_id': fields.related('product_backlog_id','sprint_id', type='many2one', relation='project.scrum.sprint', string='Sprint',
@ -262,12 +263,7 @@ class project_scrum_task(osv.osv):
'project.scrum.product.backlog': (_get_task, ['sprint_id'], 10)
}),
}
#dead code
def onchange_backlog_id(self, cr, uid, backlog_id=False):
if not backlog_id:
return {}
project_id = self.pool.get('project.scrum.product.backlog').browse(cr, uid, backlog_id).project_id.id
return {'value': {'project_id': project_id}}
project_scrum_task()
class project_scrum_meeting(osv.osv):
@ -292,45 +288,6 @@ class project_scrum_meeting(osv.osv):
_defaults = {
'date' : lambda *a: time.strftime('%Y-%m-%d'),
}
# dead code
def button_send_to_master(self, cr, uid, ids, context=None):
meeting_id = self.browse(cr, uid, ids, context=context)[0]
if meeting_id and meeting_id.sprint_id.scrum_master_id.user_email:
res = self.email_send(cr, uid, ids, meeting_id.sprint_id.scrum_master_id.user_email)
if not res:
raise osv.except_osv(_('Error !'), _('Email notification could not be sent to the scrum master %s') % meeting_id.sprint_id.scrum_master_id.name)
else:
raise osv.except_osv(_('Error !'), _('Please provide email address for scrum master defined on sprint.'))
return True
#dead code
def button_send_product_owner(self, cr, uid, ids, context=None):
if context is None:
context = {}
context.update({'button_send_product_owner': True})
meeting_id = self.browse(cr, uid, ids, context=context)[0]
if meeting_id.sprint_id.product_owner_id.user_email:
res = self.email_send(cr,uid,ids,meeting_id.sprint_id.product_owner_id.user_email)
if not res:
raise osv.except_osv(_('Error !'), _('Email notification could not be sent to the product owner %s') % meeting_id.sprint_id.product_owner_id.name)
else:
raise osv.except_osv(_('Error !'), _('Please provide email address for product owner defined on sprint.'))
return True
#dead code
def email_send(self, cr, uid, ids, email, context=None):
mail_message_obj = self.pool.get('mail.message')
meeting_id = self.browse(cr, uid, ids, context=context)[0]
user = self.pool.get('res.users').browse(cr, uid, uid, context=context)
user_email = user.user_email or tools.config.get('email_from', False)
body = _("Hello %s,\n \nI am sending you Daily Meeting Details of date %s for the Sprint %s\n") %(meeting_id.sprint_id.scrum_master_id.name, meeting_id.date, meeting_id.sprint_id.name)
body += _('\n* Tasks since yesterday:\n_______________________\n%s\n\n* Task for Today:\n_______________________ \n%s\n\n* Blocks encountered:\n_______________________ \n\n%s') %(meeting_id.question_yesterday,meeting_id.question_today, meeting_id.question_blocks or _('No Blocks'))
body += _("\n\nThank you,\n%s") % user.name
sub_name = meeting_id.name or _('Scrum Meeting of %s') % meeting_id.date
flag = mail_message_obj.schedule_with_attach(cr, uid, user_email , [email], sub_name, body, model='project.scrum.meeting', res_id=meeting_id.id, context=context)
if not flag:
return False
return True
project_scrum_meeting()

View File

@ -67,6 +67,7 @@ Dashboard for purchase management that includes:
'test/process/run_scheduler.yml',
'test/process/merge_order.yml',
'test/process/edi_purchase_order.yml',
'test/process/invoice_on_poline.yml',
'test/ui/print_report.yml',
'test/ui/duplicate_order.yml',
'test/ui/delete_order.yml',

View File

@ -35,14 +35,6 @@ from osv.orm import browse_record, browse_null
#
class purchase_order(osv.osv):
def _calc_amount(self, cr, uid, ids, prop, unknow_none, unknow_dict):
res = {}
for order in self.browse(cr, uid, ids):
res[order.id] = 0
for oline in order.order_line:
res[order.id] += oline.price_unit * oline.product_qty
return res
def _amount_all(self, cr, uid, ids, field_name, arg, context=None):
res = {}
cur_obj=self.pool.get('res.currency')
@ -300,25 +292,6 @@ class purchase_order(osv.osv):
for id in ids:
self.write(cr, uid, [id], {'state' : 'confirmed', 'validator' : uid})
return True
# Dead code:
def wkf_warn_buyer(self, cr, uid, ids):
self.write(cr, uid, ids, {'state' : 'wait', 'validator' : uid})
request = pooler.get_pool(cr.dbname).get('res.request')
for po in self.browse(cr, uid, ids):
managers = []
for oline in po.order_line:
manager = oline.product_id.product_manager
if manager and not (manager.id in managers):
managers.append(manager.id)
for manager_id in managers:
request.create(cr, uid,{
'name' : _("Purchase amount over the limit"),
'act_from' : uid,
'act_to' : manager_id,
'body': _('Somebody has just confirmed a purchase with an amount over the defined limit'),
'ref_partner_id': po.partner_id.id,
'ref_doc1': 'purchase.order,%d' % (po.id,),
})
def _prepare_inv_line(self, cr, uid, account_id, order_line, context=None):
"""Collects require data from purchase order line that is used to create invoice line

View File

@ -27,55 +27,7 @@ import pooler
class order(report_sxw.rml_parse):
def __init__(self, cr, uid, name, context):
super(order, self).__init__(cr, uid, name, context=context)
self.localcontext.update({
'time': time,
'get_line_tax': self._get_line_tax,
'get_tax': self._get_tax,
'get_product_code': self._get_product_code,
})
def _get_line_tax(self, line_obj):
self.cr.execute("SELECT tax_id FROM purchase_order_taxe WHERE order_line_id=%s", (line_obj.id))
res = self.cr.fetchall() or None
if not res:
return ""
if isinstance(res, list):
tax_ids = [t[0] for t in res]
else:
tax_ids = res[0]
res = [tax.name for tax in pooler.get_pool(self.cr.dbname).get('account.tax').browse(self.cr, self.uid, tax_ids)]
return ",\n ".join(res)
def _get_tax(self, order_obj):
self.cr.execute("SELECT DISTINCT tax_id FROM purchase_order_taxe, purchase_order_line, purchase_order \
WHERE (purchase_order_line.order_id=purchase_order.id) AND (purchase_order.id=%s)", (order_obj.id))
res = self.cr.fetchall() or None
if not res:
return []
if isinstance(res, list):
tax_ids = [t[0] for t in res]
else:
tax_ids = res[0]
tax_obj = pooler.get_pool(self.cr.dbname).get('account.tax')
res = []
for tax in tax_obj.browse(self.cr, self.uid, tax_ids):
self.cr.execute("SELECT DISTINCT order_line_id FROM purchase_order_line, purchase_order_taxe \
WHERE (purchase_order_taxe.tax_id=%s) AND (purchase_order_line.order_id=%s)", (tax.id, order_obj.id))
lines = self.cr.fetchall() or None
if lines:
if isinstance(lines, list):
line_ids = [l[0] for l in lines]
else:
line_ids = lines[0]
base = 0
for line in pooler.get_pool(self.cr.dbname).get('purchase.order.line').browse(self.cr, self.uid, line_ids):
base += line.price_subtotal
res.append({'code':tax.name,
'base':base,
'amount':base*tax.amount})
return res
def _get_product_code(self, product_id, partner_id):
product_obj=pooler.get_pool(self.cr.dbname).get('product.product')
return product_obj._product_code(self.cr, self.uid, [product_id], name=None, arg=None, context={'partner_id': partner_id})[product_id]
self.localcontext.update({'time': time})
report_sxw.report_sxw('report.purchase.order','purchase.order','addons/purchase/report/order.rml',parser=order)

View File

@ -0,0 +1,27 @@
-
I confirm purchase order which has invoicing control method "Based on Purchase Order Lines".
-
!workflow {model: purchase.order, action: purchase_confirm, ref: order_purchase6}
-
In order to test create invoice for purchase order line.
-
!python {model: purchase.order}: |
invoice_line_obj = self.pool.get('purchase.order.line_invoice')
purchase_order = self.browse(cr, uid, ref("order_purchase6"))
context.update({'active_model': 'purchase.order', 'active_ids': [ref("order_purchase6")]})
for purchase_line in purchase_order.order_line:
invoice_line_obj.makeInvoices(cr, uid, purchase_line.id, context=context)
-
I check the invoice of order.
-
!python {model: purchase.order}: |
purchase_order = self.browse(cr, uid, ref("order_purchase6"))
for purchase_line in purchase_order.order_line:
assert len(purchase_order.invoice_ids) == 1, "Invoice should be generated."
-
I set the default invoicing control method "Based on Purchase Order Lines".
-
!python {model: purchase.config.wizard}: |
new_id = self.create(cr ,uid, {'default_method': 'manual'})
self.execute(cr, uid, [new_id])

View File

@ -41,7 +41,10 @@ that exceeds minimum amount set by configuration wizard.
'purchase_double_validation_installer.xml',
'board_purchase_view.xml'
],
'test': ['test/purchase_double_validation_test.yml'],
'test': [
'test/purchase_double_validation_demo.yml',
'test/purchase_double_validation_test.yml'
],
'demo_xml': [],
'installable': True,
'active': False,

View File

@ -0,0 +1,13 @@
-
!record {model: purchase.order, id: order_purchase11}:
partner_id: base.res_partner_desertic_hispafuentes
order_line:
- product_id: product.product_product_pc4
product_qty: 10
-
!record {model: purchase.order, id: order_purchase12}:
partner_id: base.res_partner_vickingdirect0
order_line:
- product_id: product.product_product_hdd2
product_qty: 10

View File

@ -1,117 +1,36 @@
-
I Create new limit amount from Configure Limit Amount for Purchase wizard.
-
I set new limit amount from Configure Limit Amount for Purchase .
-
!record {model: purchase.double.validation.installer, id: purchase_double_validation_installer_1}:
limit_amount: 3000
-
Then I set the Limit Amount
-
-
!python {model: purchase.double.validation.installer}: |
self.execute(cr, uid, [ref("purchase_double_validation_installer_1")])
-
In order to test the purchase double validation flow,I start by creating a new product 'MOB1'
In order to test the flow, I confirmed the purchase order.
-
!record {model: product.product, id: product_product_mob1}:
categ_id: 'product.product_category_3'
cost_method: standard
mes_type: fixed
name: MOB1
price_margin: 2.0
procure_method: make_to_stock
property_stock_inventory: stock.location_inventory
property_stock_procurement: stock.location_procurement
property_stock_production: stock.location_production
seller_delay: '1'
standard_price: 2000.0
supply_method: buy
type: product
uom_id: product.product_uom_unit
uom_po_id: product.product_uom_unit
volume: 0.0
warranty: 0.0
weight: 0.0
weight_net: 0.0
!workflow {model: purchase.order, action: purchase_confirm, ref: order_purchase11}
-
In order to test the purchase double validation flow,I create a new record where "invoice_method" is From Order.
I check that the order which was initially in the draft state has transmit to confirm state for double validation it should not an Approve state.
-
Test for purchase double validation in which Total > = Limit Amount.
-
I create purchase order for MOB1 for 3 quantity.
-
!record {model: purchase.order, id: purchase_order_po11}:
company_id: base.main_company
date_order: '2011-01-1'
invoice_method: order
location_id: stock.stock_location_stock
order_line:
- date_planned: '2011-01-11'
name: MOB1
price_unit: 2000.0
product_id: 'product_product_mob1'
product_qty: 3.0
product_uom: product.product_uom_unit
state: draft
partner_address_id: base.res_partner_address_7
partner_id: base.res_partner_4
pricelist_id: purchase.list0
-
Initially purchase order is in the draft state.
!assert {model: purchase.order, id: order_purchase11, severity: error, string: Purchase Order should not be in Approved state.}:
- state != 'approved'
-
!assert {model: purchase.order, id: purchase_order_po11}:
- state == 'draft'
I Approved the purchase order.
-
I confirm the purchase order for MOB1.
!workflow {model: purchase.order, action: purchase_approve, ref: order_purchase11}
-
!workflow {model: purchase.order, action: purchase_confirm, ref: purchase_order_po11}
-
I check that the order which was initially in the draft state has transmit to confirm state for double validation.
-
!assert {model: purchase.order, id: purchase_order_po11}:
- state == 'confirmed'
-
I Approved purchase order by Supplier for MOB1.
-
!workflow {model: purchase.order, action: purchase_approve, ref: purchase_order_po11}
-
I check that the order which was initially in the confirmed state has transmit to approved state.
-
!assert {model: purchase.order, id: purchase_order_po11}:
- state == 'approved'
!assert {model: purchase.order, id: order_purchase11, severity: error, string: Purchase Order should be in Approved state.}:
- state == 'approved'
-
Test for purchase double validation in which Total < Limit Amount.
-
I create purchase order for MOB1 for 1 quantity.
-
!record {model: purchase.order, id: purchase_order_po12}:
company_id: base.main_company
date_order: '2011-01-02'
invoice_method: order
location_id: stock.stock_location_stock
order_line:
- date_planned: '2011-01-12'
name: MOB1
price_unit: 2000.0
product_id: 'product_product_mob1'
product_qty: 1.0
product_uom: product.product_uom_unit
state: draft
partner_address_id: base.res_partner_address_7
partner_id: base.res_partner_4
pricelist_id: purchase.list0
-
Initially purchase order is in the draft state.
I confirmed the purchase order of amount of less than Limit amount.
-
!assert {model: purchase.order, id: purchase_order_po12}:
- state == 'draft'
!workflow {model: purchase.order, action: purchase_confirm, ref: order_purchase12}
-
I confirm the purchase order for MOB1.
I check that the order is in approved state.
-
!workflow {model: purchase.order, action: purchase_confirm, ref: purchase_order_po12}
-
I check that the order which was initially in the draft state has transmit to approved state.
-
!assert {model: purchase.order, id: purchase_order_po12}:
!assert {model: purchase.order, id: order_purchase12, severity: error, string: Purchase Order should be in Approved state.}:
- state == 'approved'

View File

@ -45,6 +45,10 @@ It also manages the leaves of every resource.
],
'demo_xml': ['resource_demo.xml'
],
'test': [
'test/resource.yml',
'test/duplicate_resource.yml',
],
'installable': True,
'active': False,
'certificate': '00746371192190459469',

View File

@ -22,7 +22,6 @@
from datetime import datetime, timedelta
import math
from faces import *
from new import classobj
from osv import fields, osv
from tools.translate import _
@ -44,9 +43,12 @@ class resource_calendar(osv.osv):
}
def working_hours_on_day(self, cr, uid, resource_calendar_id, day, context=None):
"""
"""Calculates the Working Total Hours based on Resource Calendar and
given working day (datetime object).
@param resource_calendar_id: resource.calendar browse record
@param day: datetime object
@return: returns the working hours (as float) men should work on the given day if is in the attendance_ids of the resource_calendar_id (i.e if that day is a working day), returns 0.0 otherwise
"""
res = 0.0
@ -56,9 +58,16 @@ class resource_calendar(osv.osv):
return res
def _get_leaves(self, cr, uid, id, resource):
"""Private Method to Calculate resource Leaves days
@param id: resource calendar id
@param resource: resource id for which leaves will ew calculated
@return : returns the list of dates, where resource on leave in
resource.calendar.leaves object (e.g.['%Y-%m-%d', '%Y-%m-%d'])
"""
resource_cal_leaves = self.pool.get('resource.calendar.leaves')
dt_leave = []
resource_leave_ids = resource_cal_leaves.search(cr, uid, [('calendar_id','=',id), '|', ('resource_id','=',False), ('resource_id','=',resource)])
#res_leaves = resource_cal_leaves.read(cr, uid, resource_leave_ids, ['date_from', 'date_to'])
res_leaves = resource_cal_leaves.browse(cr, uid, resource_leave_ids)
@ -73,6 +82,21 @@ class resource_calendar(osv.osv):
return dt_leave
def interval_min_get(self, cr, uid, id, dt_from, hours, resource=False):
"""
Calculates the working Schedule from supplied from date to till hours
will be satisfied based or resource calendar id. If resource is also
given then it will consider the resource leave also and than will
calculates resource working schedule
@param dt_from: datetime object, start of working scheduled
@param hours: float, total number working hours needed scheduled from
start date
@param resource : Optional Resource id, if supplied than resource leaves
will also taken into consideration for calculating working
schedule.
@return : List datetime object of working schedule based on supplies
params
"""
if not id:
td = int(hours)*3
return [(dt_from - timedelta(hours=td), dt_from)]
@ -162,10 +186,32 @@ class resource_calendar(osv.osv):
return results
def interval_get(self, cr, uid, id, dt_from, hours, resource=False, byday=True):
"""Calculates Resource Working Internal Timing Based on Resource Calendar.
@param dt_from: start resource schedule calculation.
@param hours : total number of working hours to be scheduled.
@param resource: optional resource id, If supplied it will take care of
resource leave while scheduling.
@param byday: boolean flag bit enforce day wise scheduling
@return : list of scheduled working timing based on resource calendar.
"""
res = self.interval_get_multi(cr, uid, [(dt_from.strftime('%Y-%m-%d %H:%M:%S'), hours, id)], resource, byday)[(dt_from.strftime('%Y-%m-%d %H:%M:%S'), hours, id)]
return res
def interval_hours_get(self, cr, uid, id, dt_from, dt_to, resource=False):
""" Calculates the Total Working hours based on given start_date to
end_date, If resource id is supplied that it will consider the source
leaves also in calculating the hours.
@param dt_from : date start to calculate hours
@param dt_end : date end to calculate hours
@param resource: optional resource id, If given resource leave will be
considered.
@return : Total number of working hours based dt_from and dt_end and
resource if supplied.
"""
if not id:
return 0.0
dt_leave = self._get_leaves(cr, uid, id, resource)
@ -290,6 +336,7 @@ class resource_resource(osv.osv):
def compute_vacation(self, cr, uid, calendar_id, resource_id=False, resource_calendar=False, context=None):
"""
Compute the vacation from the working calendar of the resource.
@param calendar_id : working calendar of the project
@param resource_id : resource working on phase/task
@param resource_calendar : working calendar of the resource
@ -366,13 +413,6 @@ class resource_resource(osv.osv):
wktime_cal.append((non_working[:-1], time_range))
return wktime_cal
#TODO: Write optimized alogrothem for resource availability. : Method Yet not implemented
def check_availability(self, cr, uid, ids, start, end, context=None):
if context == None:
contex = {}
allocation = {}
return allocation
resource_resource()
class resource_calendar_leaves(osv.osv):

View File

@ -5,73 +5,73 @@
<!-- Example employee -->
<record id="timesheet_group1" model="resource.calendar">
<field name="name">38 Hours/Week</field>
<field name="name">45 Hours/Week</field>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_mon1">
<field name="name">Monday morning</field>
<field name="dayofweek">0</field>
<field name="hour_from">08</field>
<field name="hour_to">12</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_mon2">
<field name="name">Monday evening</field>
<field name="dayofweek">0</field>
<field name="hour_from">13</field>
<field name="hour_to">18</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_tue1">
<field name="name">Tuesday morning</field>
<field name="dayofweek">1</field>
<field name="hour_from">08</field>
<field name="hour_to">12</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_tue2">
<field name="name">Tuesday evening</field>
<field name="dayofweek">1</field>
<field name="hour_from">13</field>
<field name="hour_to">18</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_wed1">
<field name="name">Wednesday morning</field>
<field name="dayofweek">2</field>
<field name="hour_from">08</field>
<field name="hour_to">12</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_wed2">
<field name="name">Wednesday evening</field>
<field name="dayofweek">2</field>
<field name="hour_from">13</field>
<field name="hour_to">18</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_thu1">
<field name="name">Thursday morning</field>
<field name="dayofweek">3</field>
<field name="hour_from">08</field>
<field name="hour_to">12</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_thu2">
<field name="name">Thursday evening</field>
<field name="hour_from">13</field>
<field name="hour_to">18</field>
<field name="dayofweek">3</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_fri1">
<field name="name">Friday morning</field>
<field name="dayofweek">4</field>
<field name="hour_from">08</field>
<field name="hour_to">12</field>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record model="resource.calendar.attendance">
<record model="resource.calendar.attendance" id="calendar_attendance_fri2">
<field name="name">Friday evening</field>
<field name="dayofweek">4</field>
<field name="hour_from">13</field>
@ -79,5 +79,47 @@
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record id="resource_analyst" model="resource.resource">
<field eval="1.0" name="time_efficiency"/>
<field name="user_id" ref="base.user_root"/>
<field name="name">Analyst</field>
<field eval="1" name="active"/>
<field name="calendar_id" ref="timesheet_group1"/>
<field name="resource_type">user</field>
</record>
<record id="resource_designer" model="resource.resource">
<field eval="1.0" name="time_efficiency"/>
<field name="user_id" ref="base.user_demo"/>
<field name="name">Designer</field>
<field eval="1" name="active"/>
<field name="calendar_id" ref="timesheet_group1"/>
<field name="resource_type">user</field>
</record>
<record id="resource_developer" model="resource.resource">
<field eval="1.0" name="time_efficiency"/>
<field name="user_id" ref="base.user_demo"/>
<field name="name">Developer</field>
<field eval="1" name="active"/>
<field name="calendar_id" ref="timesheet_group1"/>
<field name="resource_type">user</field>
</record>
<record id="resource_analyst_leaves_demoleave1" model="resource.calendar.leaves">
<field name="name">2 Hours On Leave</field>
<field name="resource_id" ref="resource_analyst"/>
<field name="date_from" eval="time.strftime('%Y-%m-%d 08:00:00')"/>
<field name="date_to" eval="time.strftime('%Y-%m-%d 11:00:00')"/>
<field name="calendar_id" ref="timesheet_group1"/>
</record>
<record id="resource_dummyleave" model="resource.calendar.leaves">
<field name="name">Dummy Resource Leave</field>
<field name="resource_id" ref="resource_analyst"/>
<field name="date_from" eval="time.strftime('%Y-%m-%d 08:00:00')"/>
<field name="date_to" eval="time.strftime('%Y-%m-%d 11:00:00')"/>
</record>
</data>
</openerp>

View File

@ -0,0 +1,6 @@
-
I duplicate the resource "Analyst"
-
!python {model: resource.resource}: |
copied_id = self.copy(cr, uid, ref("resource_analyst"))
assert copied_id, "Unable to Duplicate Resource"

View File

@ -0,0 +1,59 @@
-
In order to test resource.
-
I assign working calendar '45 Hours/Week' to human resource.
-
!python {model: resource.resource}: |
self.write(cr, uid, [ref('resource_analyst'), ref('resource_designer'), ref('resource_developer')], {'calendar_id' : ref('timesheet_group1'), 'resource_type': 'user'})
-
I had Project of OpenERP Integration of 50 Hours with three human resource assigned on it. I have started project from this week start.
-
First, I generate the resource detail and check the resource Efficiency assigned.
-
!python {model: resource.resource}: |
resources = self.generate_resources(cr, uid, [ref('base.user_root'),ref('base.user_demo')], ref('timesheet_group1'), context)
for resource in resources.values():
assert resource.get('efficiency', 0.0) == 1.0, 'Invalid resource generated.'
-
I check per day work hour availability of the Resource based on Working Calendar Assigned to each resource, for first day of the week.
-
!python {model: resource.resource}: |
calendar_pool = self.pool.get('resource.calendar')
resources = self.browse(cr, uid, [ref('resource_analyst'), ref('resource_designer'), ref('resource_developer')], context)
from datetime import datetime, timedelta
now = datetime.now()
dt = now - timedelta(days=now.weekday())
for resource in resources:
result = calendar_pool.working_hours_on_day(cr, uid, resource.calendar_id, dt, context)
assert result == 9.0, 'Wrong calculation of day work hour availability of the Resource.'
-
Now, resource "Developer" drafted leave on Thursday in this week.
-
!python {model: resource.calendar.leaves}: |
from datetime import datetime,timedelta
now = datetime.now()
dt = (now - timedelta(days=now.weekday()) ) + timedelta(days=3)
self.write(cr, uid, [ref('resource_dummyleave')], {'resource_id': ref('resource_developer'), 'calendar_id': ref('timesheet_group1'), 'date_from': dt.strftime("%Y-%m-%d 09:00:00"), 'date_to': dt.strftime("%Y-%m-%d 18:00:00")})
-
I check Actual working hours on resource 'Developer' from this week
-
!python {model: resource.calendar}: |
from datetime import datetime, timedelta
now = datetime.now()
dt_from = now - timedelta(days=now.weekday())
dt_to = dt_from+ timedelta(days=6)
hours = self.interval_hours_get(cr, uid, ref('timesheet_group1'), dt_from, dt_to, resource=ref('resource_developer'))
assert hours > 27 , 'Invalid Total Week working hour calculated'
-
Project Analysis work is of 20 hours which will start from Week start so i will calculate working schedule for resource Analyst for the same.
-
!python {model: resource.calendar}: |
from datetime import datetime, timedelta
now = datetime.now()
work_intreval = self.interval_min_get(cr, uid, ref('timesheet_group1'), now, 20.0, resource=ref('resource_designer'))
assert len(work_intreval) >= 5, 'Wrong Schedule Calculated'

View File

@ -771,6 +771,11 @@ class sale_order(osv.osv):
self.pool.get('procurement.order').write(cr, uid, [proc_id], {'product_qty': mov.product_qty, 'product_uos_qty': mov.product_uos_qty})
return True
def _get_date_planned(self, cr, uid, order, line, start_date, *args):
date_planned = datetime.strptime(start_date, DEFAULT_SERVER_DATE_FORMAT) + relativedelta(days=line.delay or 0.0)
date_planned = (date_planned - timedelta(days=order.company_id.security_lead)).strftime(DEFAULT_SERVER_DATETIME_FORMAT)
return date_planned
def _create_pickings_and_procurements(self, cr, uid, order, order_lines, picking_id=False, *args):
"""Create the required procurements to supply sale order lines, also connecting
the procurements to appropriate stock moves in order to bring the goods to the
@ -799,8 +804,7 @@ class sale_order(osv.osv):
if line.state == 'done':
continue
date_planned = datetime.strptime(order.date_order, DEFAULT_SERVER_DATE_FORMAT) + relativedelta(days=line.delay or 0.0)
date_planned = (date_planned - timedelta(days=order.company_id.security_lead)).strftime(DEFAULT_SERVER_DATETIME_FORMAT)
date_planned = self._get_date_planned(cr, uid, order, line, order.date_order, *args)
if line.product_id:
if line.product_id.product_tmpl_id.type in ('product', 'consu'):

View File

@ -58,3 +58,4 @@ access_product_pricelist_type_sale_manager,product.pricelist.type salemanager,pr
access_product_pricelist_sale_manager,product.pricelist salemanager,product.model_product_pricelist,base.group_sale_manager,1,1,1,1
access_product_group_res_partner_sale_manager,res_partner group_sale_manager,base.model_res_partner,base.group_sale_manager,1,1,1,0
access_product_pricelist_version_sale_manager,product.pricelist.version sale_manager,product.model_product_pricelist_version,base.group_sale_manager,1,1,1,1
access_account_invoice_report_salesman,account.invoice.report salesman,account.model_account_invoice_report,base.group_sale_salesman,1,0,0,0
1 id name model_id:id group_id:id perm_read perm_write perm_create perm_unlink
58 access_product_pricelist_sale_manager product.pricelist salemanager product.model_product_pricelist base.group_sale_manager 1 1 1 1
59 access_product_group_res_partner_sale_manager res_partner group_sale_manager base.model_res_partner base.group_sale_manager 1 1 1 0
60 access_product_pricelist_version_sale_manager product.pricelist.version sale_manager product.model_product_pricelist_version base.group_sale_manager 1 1 1 1
61 access_account_invoice_report_salesman account.invoice.report salesman account.model_account_invoice_report base.group_sale_salesman 1 0 0 0

View File

@ -1,2 +1,2 @@
id,name,model_id:id,group_id:id,perm_read,perm_write,perm_create,perm_unlink
access_account_invoice_report_salesman,account.invoice.report salesman,account.model_account_invoice_report,base.group_sale_salesman,1,0,0,0

1 id name model_id:id group_id:id perm_read perm_write perm_create perm_unlink
2

View File

@ -9,7 +9,7 @@
<field name="name">sale.order.form.inherit_1</field>
<field name="model">sale.order</field>
<field name="inherit_id" ref="sale.view_order_form"/>
<field name="priority">30</field>
<field name="priority">1000</field>
<field name="type">form</field>
<field name="arch" type="xml">
<xpath expr="/form/notebook/page/field[@name='order_line']" position="replace">

View File

@ -95,10 +95,13 @@ class share_wizard(osv.osv_memory):
# NOTE: take _ids in parameter to allow usage through browse_record objects
base_url = self.pool.get('ir.config_parameter').get_param(cr, uid, 'web.base.url', default='', context=context)
if base_url:
base_url += '/?db=%(dbname)s&login=%(login)s'
base_url += '/web/webclient/login?db=%(dbname)s&login=%(login)s'
extra = context and context.get('share_url_template_extra_arguments')
if extra:
base_url += '&' + '&'.join('%s=%%(%s)s' % (x,x) for x in extra)
hash_ = context and context.get('share_url_template_hash_arguments')
if hash_:
base_url += '#' + '&'.join('%s=%%(%s)s' % (x,x) for x in hash_)
return base_url
def _share_root_url(self, cr, uid, ids, _fieldname, _args, context=None):
@ -156,9 +159,10 @@ class share_wizard(osv.osv_memory):
result = dict.fromkeys(ids, '')
for this in self.browse(cr, uid, ids, context=context):
if this.result_line_ids:
ctx = dict(context, share_url_template_extra_arguments=['key'])
ctx = dict(context, share_url_template_extra_arguments=['key'],
share_url_template_hash_arguments=['action_id'])
user = this.result_line_ids[0]
data = dict(dbname=cr.dbname, login=user.login, key=user.password)
data = dict(dbname=cr.dbname, login=user.login, key=user.password, action_id=this.action_id.id)
result[this.id] = this.share_url_template(context=ctx) % data
return result

View File

@ -169,6 +169,16 @@ function searchmail()
}
function url_for(model, id) {
var base = getWebServerURL(),
db = getDbName(),
login = getusername(),
password = getPassword();
return base + '/web/webclient/login?db='+db+'&login='+login+'&key='+password+'#model='+model+'&id='+id;
}
var openPartnerHandler = {
onResult: function(client, context, result) {
netscape.security.PrivilegeManager.enablePrivilege('UniversalXPConnect UniversalBrowserAccess');
@ -186,15 +196,11 @@ var openPartnerHandler = {
}
if(strlSearchResult=="partner_id"){
partner_id = strlSearchResultValue;
weburl = getWebServerURL();
if (parseInt(partner_id) > 0){
//Encode the url and form an url to have menu in webclient
var encoded = encodeURIComponent("/openerp/form/view?model=res.partner&id="+partner_id)
var t = weburl + "?next=" + encoded
var messenger = Components.classes["@mozilla.org/messenger;1"].createInstance();
messenger = messenger.QueryInterface(Components.interfaces.nsIMessenger);
messenger.launchExternalURL(t);
messenger.launchExternalURL(url_for('res.partner', partner_id));
}
else{
alert("Partner is not Available.");
@ -298,7 +304,6 @@ var listDocumentHandler = {
var res = result.QueryInterface(Components.interfaces.nsISupportsArray);
res_id = res.QueryElementAt(1, Components.interfaces.nsISupportsPRInt32);
model = res.QueryElementAt(0, Components.interfaces.nsISupportsCString);
weburl = getWebServerURL();
if(res_id==0)
{
alert("Document is not available.");
@ -307,11 +312,9 @@ var listDocumentHandler = {
else
{
var encoded = encodeURIComponent("/openerp/form/view?model=" + model +"&id=" + res_id)
var t = weburl + "?next=" + encoded
var messenger = Components.classes["@mozilla.org/messenger;1"].createInstance();
messenger = messenger.QueryInterface(Components.interfaces.nsIMessenger);
messenger.launchExternalURL(t);
messenger.launchExternalURL(url_for(model, res_id));
}
},