- Define default users preferences
+ Define Users's Preferences
- Specify default values. This will set the default values for each new user, each user is free to change his own preferences.
+ This will set the default preferences for all users. After this, each user will be able to update his own preferences.
@@ -148,6 +142,7 @@
+ once
@@ -156,14 +151,13 @@
ir.actions.act_windowres.usersform
- form
-
+ tree,form
+ 1000
- done
@@ -182,7 +176,7 @@
Specify Your Terminology
- Based on the industry needs you can use this wizard to change the terminologies for Partners.
+ You can use this wizard to change the terminologies for customers in the whole application.
@@ -208,6 +202,7 @@
+ once
@@ -225,21 +220,6 @@
1
-
-
- Upload Your Company Logo
- ir.actions.act_window
- res.company
-
- form
- form
- {'res_id': user.company_id.id}
-
-
-
-
- done
-
diff --git a/addons/base_synchro/i18n/zh_TW.po b/addons/base_synchro/i18n/zh_TW.po
new file mode 100644
index 00000000000..a4fc9db7d81
--- /dev/null
+++ b/addons/base_synchro/i18n/zh_TW.po
@@ -0,0 +1,289 @@
+# Chinese (Traditional) translation for openobject-addons
+# Copyright (c) 2011 Rosetta Contributors and Canonical Ltd 2011
+# This file is distributed under the same license as the openobject-addons package.
+# FIRST AUTHOR , 2011.
+#
+msgid ""
+msgstr ""
+"Project-Id-Version: openobject-addons\n"
+"Report-Msgid-Bugs-To: FULL NAME \n"
+"POT-Creation-Date: 2011-01-11 11:14+0000\n"
+"PO-Revision-Date: 2011-09-27 14:38+0000\n"
+"Last-Translator: FULL NAME \n"
+"Language-Team: Chinese (Traditional) \n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:20+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
+
+#. module: base_synchro
+#: model:ir.actions.act_window,name:base_synchro.action_view_base_synchro
+msgid "Base Synchronization"
+msgstr "基礎同步化"
+
+#. module: base_synchro
+#: field:base.synchro.server,server_db:0
+msgid "Server Database"
+msgstr "伺服器資料庫"
+
+#. module: base_synchro
+#: view:base.synchro.server:0
+#: model:ir.model,name:base_synchro.model_base_synchro_server
+msgid "Synchronized server"
+msgstr "同步化伺服器"
+
+#. module: base_synchro
+#: field:base.synchro.obj.avoid,name:0
+msgid "Field Name"
+msgstr "欄位名稱"
+
+#. module: base_synchro
+#: field:base.synchro.obj,synchronize_date:0
+msgid "Latest Synchronization"
+msgstr "最新同步化"
+
+#. module: base_synchro
+#: field:base.synchro,user_id:0
+msgid "Send Result To"
+msgstr "將結果發送至"
+
+#. module: base_synchro
+#: model:ir.model,name:base_synchro.model_base_synchro_obj_avoid
+msgid "Fields to not synchronize"
+msgstr "不同步化之欄位"
+
+#. module: base_synchro
+#: view:base.synchro:0
+msgid "_Close"
+msgstr "關閉(_C)"
+
+#. module: base_synchro
+#: view:base.synchro:0
+msgid "Transfer Data To Server"
+msgstr "將資料轉至伺服器"
+
+#. module: base_synchro
+#: model:ir.model,name:base_synchro.model_base_synchro_obj
+msgid "Register Class"
+msgstr ""
+
+#. module: base_synchro
+#: view:base.synchro.obj:0
+#: model:ir.actions.act_window,name:base_synchro.action_transfer_tree
+#: model:ir.ui.menu,name:base_synchro.transfer_menu_id
+msgid "Synchronized objects"
+msgstr "同步化物件"
+
+#. module: base_synchro
+#: field:base.synchro.server,obj_ids:0
+msgid "Models"
+msgstr "模型"
+
+#. module: base_synchro
+#: field:base.synchro.obj.avoid,obj_id:0
+#: view:base.synchro.obj.line:0
+#: field:base.synchro.obj.line,obj_id:0
+msgid "Object"
+msgstr "物件"
+
+#. module: base_synchro
+#: field:base.synchro.server,login:0
+msgid "User Name"
+msgstr ""
+
+#. module: base_synchro
+#: view:base.synchro.obj:0
+#: view:base.synchro.obj.line:0
+msgid "Group By"
+msgstr ""
+
+#. module: base_synchro
+#: selection:base.synchro.obj,action:0
+msgid "Upload"
+msgstr "上載"
+
+#. module: base_synchro
+#: view:base.synchro.obj:0
+msgid "Latest synchronization"
+msgstr "最新同步化"
+
+#. module: base_synchro
+#: model:ir.module.module,description:base_synchro.module_meta_information
+msgid "Synchronization with all objects."
+msgstr "與所有物件同步化。"
+
+#. module: base_synchro
+#: view:base.synchro.obj.line:0
+#: field:base.synchro.obj.line,name:0
+msgid "Date"
+msgstr "日期"
+
+#. module: base_synchro
+#: field:base.synchro.server,password:0
+msgid "Password"
+msgstr "密碼"
+
+#. module: base_synchro
+#: field:base.synchro.obj,avoid_ids:0
+msgid "Fields Not Sync."
+msgstr "無同步化欄位"
+
+#. module: base_synchro
+#: selection:base.synchro.obj,action:0
+msgid "Both"
+msgstr "兩者"
+
+#. module: base_synchro
+#: field:base.synchro.obj,name:0
+msgid "Name"
+msgstr "名稱"
+
+#. module: base_synchro
+#: view:base.synchro.obj:0
+msgid "Fields"
+msgstr "欄位"
+
+#. module: base_synchro
+#: view:base.synchro.obj.line:0
+msgid "Transfered Ids Details"
+msgstr "已傳送 Ids 詳情"
+
+#. module: base_synchro
+#: field:base.synchro.obj,action:0
+msgid "Synchronisation direction"
+msgstr "同步化方向"
+
+#. module: base_synchro
+#: field:base.synchro.obj,server_id:0
+msgid "Server"
+msgstr "伺服器"
+
+#. module: base_synchro
+#: model:ir.actions.act_window,name:base_synchro.action_base_synchro_obj_line_tree
+#: model:ir.model,name:base_synchro.model_base_synchro_obj_line
+#: model:ir.ui.menu,name:base_synchro.menu_action_base_synchro_obj_line_tree
+msgid "Synchronized instances"
+msgstr ""
+
+#. module: base_synchro
+#: field:base.synchro.obj,active:0
+msgid "Active"
+msgstr "作用中"
+
+#. module: base_synchro
+#: view:base.synchro.obj:0
+#: field:base.synchro.obj,model_id:0
+msgid "Object to synchronize"
+msgstr "要同步化物件"
+
+#. module: base_synchro
+#: model:ir.module.module,shortdesc:base_synchro.module_meta_information
+msgid "Base Synchro"
+msgstr ""
+
+#. module: base_synchro
+#: model:ir.actions.act_window,name:base_synchro.action_base_synchro_server_tree
+#: model:ir.ui.menu,name:base_synchro.synchro_server_tree_menu_id
+msgid "Servers to be synchronized"
+msgstr "要同步化伺服器"
+
+#. module: base_synchro
+#: view:base.synchro.obj:0
+msgid "Transfer Details"
+msgstr "傳送詳情"
+
+#. module: base_synchro
+#: field:base.synchro.obj.line,remote_id:0
+msgid "Remote Id"
+msgstr "遠端 Id"
+
+#. module: base_synchro
+#: field:base.synchro.obj,line_id:0
+msgid "Ids Affected"
+msgstr "受影響 Ids"
+
+#. module: base_synchro
+#: model:ir.ui.menu,name:base_synchro.next_id_63
+msgid "History"
+msgstr "歷史紀錄"
+
+#. module: base_synchro
+#: model:ir.ui.menu,name:base_synchro.next_id_62
+#: model:ir.ui.menu,name:base_synchro.synch_config
+msgid "Synchronization"
+msgstr "同步化"
+
+#. module: base_synchro
+#: field:base.synchro.obj,domain:0
+msgid "Domain"
+msgstr "領域"
+
+#. module: base_synchro
+#: view:base.synchro:0
+msgid "_Synchronize"
+msgstr "同步化(_S)"
+
+#. module: base_synchro
+#: view:base.synchro:0
+msgid "OK"
+msgstr ""
+
+#. module: base_synchro
+#: field:base.synchro.server,name:0
+msgid "Server name"
+msgstr "伺服器名稱"
+
+#. module: base_synchro
+#: field:base.synchro.obj,sequence:0
+msgid "Sequence"
+msgstr "次序"
+
+#. module: base_synchro
+#: view:base.synchro:0
+msgid ""
+"The synchronisation has been started.You will receive a request when it's "
+"done."
+msgstr "同步化已開始。完成時會收到要求。"
+
+#. module: base_synchro
+#: field:base.synchro.server,server_port:0
+msgid "Server Port"
+msgstr "伺服器連接埠"
+
+#. module: base_synchro
+#: model:ir.ui.menu,name:base_synchro.menu_action_view_base_synchro
+msgid "Synchronize objects"
+msgstr "同步化物件"
+
+#. module: base_synchro
+#: view:base.synchro:0
+msgid "Synchronization Complited!"
+msgstr "同步化完成!"
+
+#. module: base_synchro
+#: model:ir.model,name:base_synchro.model_base_synchro
+msgid "base.synchro"
+msgstr ""
+
+#. module: base_synchro
+#: field:base.synchro.obj.line,local_id:0
+msgid "Local Id"
+msgstr "本機 Id"
+
+#. module: base_synchro
+#: model:ir.actions.act_window,name:base_synchro.actions_regclass_tree
+#: model:ir.actions.act_window,name:base_synchro.actions_transfer_line_form
+msgid "Filters"
+msgstr ""
+
+#. module: base_synchro
+#: selection:base.synchro.obj,action:0
+msgid "Download"
+msgstr "下載"
+
+#. module: base_synchro
+#: field:base.synchro,server_url:0
+#: field:base.synchro.server,server_url:0
+msgid "Server URL"
+msgstr "伺服器 URL"
diff --git a/addons/base_tools/i18n/zh_TW.po b/addons/base_tools/i18n/zh_TW.po
new file mode 100644
index 00000000000..b38f10132cf
--- /dev/null
+++ b/addons/base_tools/i18n/zh_TW.po
@@ -0,0 +1,32 @@
+# Chinese (Traditional) translation for openobject-addons
+# Copyright (c) 2011 Rosetta Contributors and Canonical Ltd 2011
+# This file is distributed under the same license as the openobject-addons package.
+# FIRST AUTHOR , 2011.
+#
+msgid ""
+msgstr ""
+"Project-Id-Version: openobject-addons\n"
+"Report-Msgid-Bugs-To: FULL NAME \n"
+"POT-Creation-Date: 2011-01-11 11:14+0000\n"
+"PO-Revision-Date: 2011-09-27 14:45+0000\n"
+"Last-Translator: FULL NAME \n"
+"Language-Team: Chinese (Traditional) \n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:20+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
+
+#. module: base_tools
+#: model:ir.module.module,shortdesc:base_tools.module_meta_information
+msgid "Common base for tools modules"
+msgstr "工具模組共同基礎"
+
+#. module: base_tools
+#: model:ir.module.module,description:base_tools.module_meta_information
+msgid ""
+"\n"
+" "
+msgstr ""
+"\n"
+" "
diff --git a/addons/board/board_administration_view.xml b/addons/board/board_administration_view.xml
index 29146ad53ad..9e22dbd3fb6 100644
--- a/addons/board/board_administration_view.xml
+++ b/addons/board/board_administration_view.xml
@@ -139,13 +139,11 @@
-
-
+
+
-
-
-
+
diff --git a/addons/crm/crm.py b/addons/crm/crm.py
index 512192ddce7..bf30cac58fb 100644
--- a/addons/crm/crm.py
+++ b/addons/crm/crm.py
@@ -71,6 +71,7 @@ class crm_case_stage(osv.osv):
'on_change': fields.boolean('Change Probability Automatically', help="Setting this stage will change the probability automatically on the opportunity."),
'requirements': fields.text('Requirements'),
'section_ids':fields.many2many('crm.case.section', 'section_stage_rel', 'stage_id', 'section_id', 'Sections'),
+ 'case_default': fields.boolean('Common to All Teams', help="If you check this field, this stage will be proposed by default on each sales team. It will not assign this stage to existing teams."),
}
_defaults = {
@@ -106,10 +107,14 @@ class crm_case_section(osv.osv):
'working_hours': fields.float('Working Hours', digits=(16,2 )),
'stage_ids': fields.many2many('crm.case.stage', 'section_stage_rel', 'section_id', 'stage_id', 'Stages'),
}
+ def _get_stage_common(self, cr, uid, context):
+ ids = self.pool.get('crm.case.stage').search(cr, uid, [('case_default','=',1)], context=context)
+ return ids
_defaults = {
'active': lambda *a: 1,
'allow_unlink': lambda *a: 1,
+ 'stage_ids': _get_stage_common
}
_sql_constraints = [
@@ -381,7 +386,7 @@ class crm_case(crm_base):
default.update({ 'date_closed': False, })
if self._columns.get('date_open'):
default.update({ 'date_open': False })
- return super(osv.osv, self).copy(cr, uid, id, default, context=context)
+ return super(crm_case, self).copy(cr, uid, id, default, context=context)
def case_open(self, cr, uid, ids, *args):
diff --git a/addons/crm/crm_installer_view.xml b/addons/crm/crm_installer_view.xml
index 782083e4669..b840b609c61 100644
--- a/addons/crm/crm_installer_view.xml
+++ b/addons/crm/crm_installer_view.xml
@@ -48,6 +48,7 @@
crm.case.stageformtree,form
+ {'default_case_default': 1}Stages will allow salesmen to easily track how a specific opportunity is positioned in the sales cycle. In order to efficiently manage your sales pipeline, it's important to define conditions to go to the next step. Example: to set an opportunity as 'Qualified', you must set the "Expected Revenue" and the "Expected Closing Date." You should also have a look at the tooltip of the field "Change Probability Automatically".
@@ -56,7 +57,7 @@
- 10
+ 9
diff --git a/addons/crm/crm_lead_data.xml b/addons/crm/crm_lead_data.xml
index 0c7215c09eb..aaa00307bfe 100644
--- a/addons/crm/crm_lead_data.xml
+++ b/addons/crm/crm_lead_data.xml
@@ -5,31 +5,37 @@
Lost
+ New
+ Qualification
+ Proposition
+ Negotiation
+ Won
+
diff --git a/addons/crm/crm_lead_menu.xml b/addons/crm/crm_lead_menu.xml
index 0d13911a5fe..9b0581844a5 100644
--- a/addons/crm/crm_lead_menu.xml
+++ b/addons/crm/crm_lead_menu.xml
@@ -9,7 +9,7 @@
['|', ('type','=','lead'), ('type','=',False)]
- {'search_default_current':1, 'default_type': 'lead', 'search_default_section_id': section_id, 'stage_type': 'lead'}
+ {'search_default_new':1, 'default_type': 'lead', 'search_default_section_id': section_id, 'stage_type': 'lead'}Leads allow you to manage and keep track of all initial contacts with a prospect or partner showing interest in your products or services. A lead is usually the first step in your sales cycle. Once qualified, a lead may be converted into a business opportunity, while creating the related partner for further detailed tracking of any linked activities. You can import a database of prospects, keep track of your business cards or integrate your website's contact form with the OpenERP Leads. Leads can be connected to the email gateway: new emails may create leads, each of them automatically gets the history of the conversation with the prospect.
@@ -62,7 +62,7 @@
crm.leadtree,form,graph,calendar,kanban[('type','=','opportunity')]
- {'search_default_user_id':uid,'search_default_current':1, 'search_default_section_id':section_id, 'stage_type': 'opportunity', 'default_type': 'opportunity'}
+ {'search_default_user_id':uid,'search_default_new':1, 'search_default_open':1, 'search_default_section_id':section_id, 'stage_type': 'opportunity', 'default_type': 'opportunity'}With opportunities you can manage and keep track of your sales pipeline by creating specific customer- or prospect-related sales documents to follow up potential sales. Information such as expected revenue, opportunity stage, expected closing date, communication history and much more can be stored. Opportunities can be connected to the email gateway: new emails may create opportunities, each of them automatically gets the history of the conversation with the customer.
diff --git a/addons/crm/crm_lead_view.xml b/addons/crm/crm_lead_view.xml
index 12a3428236d..42587eea2b0 100644
--- a/addons/crm/crm_lead_view.xml
+++ b/addons/crm/crm_lead_view.xml
@@ -372,13 +372,15 @@
@@ -675,13 +677,15 @@
diff --git a/addons/crm/crm_view.xml b/addons/crm/crm_view.xml
index c7038958126..fc01cfd5a05 100644
--- a/addons/crm/crm_view.xml
+++ b/addons/crm/crm_view.xml
@@ -64,11 +64,11 @@
-
+
-
+
@@ -154,12 +154,12 @@
-
-
-
-
-
+
+
+
+
+
@@ -230,7 +230,7 @@
-
+
@@ -382,7 +382,6 @@
@@ -396,7 +395,7 @@
-
+
diff --git a/addons/crm/i18n/zh_TW.po b/addons/crm/i18n/zh_TW.po
index 896a92d76a0..cb7df534f37 100644
--- a/addons/crm/i18n/zh_TW.po
+++ b/addons/crm/i18n/zh_TW.po
@@ -7,14 +7,14 @@ msgstr ""
"Project-Id-Version: OpenERP Server 5.0.4\n"
"Report-Msgid-Bugs-To: support@openerp.com\n"
"POT-Creation-Date: 2011-01-11 11:15+0000\n"
-"PO-Revision-Date: 2011-01-27 05:08+0000\n"
+"PO-Revision-Date: 2011-09-27 07:26+0000\n"
"Last-Translator: Walter Cheuk \n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
-"X-Launchpad-Export-Date: 2011-09-05 05:08+0000\n"
-"X-Generator: Launchpad (build 13830)\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:19+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
#. module: crm
#: view:crm.lead.report:0
@@ -78,7 +78,7 @@ msgstr "今日"
#. module: crm
#: view:crm.merge.opportunity:0
msgid "Select Opportunities"
-msgstr "選取機會"
+msgstr "選擇機會"
#. module: crm
#: view:crm.meeting:0
@@ -184,7 +184,7 @@ msgstr "搜尋機會"
#, python-format
msgid ""
"Opportunity must have Partner assigned before merging with other Opportunity."
-msgstr "機會要先安排伙伴才可合併。"
+msgstr "機會要先安排伙伴才可與其他機會合併。"
#. module: crm
#: code:addons/crm/wizard/crm_merge_opportunities.py:46
@@ -249,7 +249,7 @@ msgstr ""
#: view:res.partner:0
#, python-format
msgid "Phone Call"
-msgstr "打電話"
+msgstr "致電"
#. module: crm
#: field:crm.lead,optout:0
@@ -260,7 +260,7 @@ msgstr ""
#: code:addons/crm/crm_opportunity.py:108
#, python-format
msgid "The opportunity '%s' has been marked as lost."
-msgstr ""
+msgstr "「%s」機會已標為丟失。"
#. module: crm
#: model:ir.actions.act_window,help:crm.action_report_crm_lead
@@ -309,7 +309,7 @@ msgid ""
"If you select Merge with existing Opportunity, the lead details(with the "
"communication history) will be merged with existing Opportunity of Selected "
"partner."
-msgstr ""
+msgstr "如選擇與現有機會合併,潛在客戶之詳情(包括通訊記錄)會與選取之伙伴的現有機會合併。"
#. module: crm
#: selection:crm.meeting,class:0
@@ -389,7 +389,7 @@ msgstr ""
#. module: crm
#: model:process.transition,name:crm.process_transition_opportunitymeeting0
msgid "Opportunity Meeting"
-msgstr ""
+msgstr "商機會談"
#. module: crm
#: help:crm.lead.report,delay_close:0
@@ -400,7 +400,7 @@ msgstr ""
#. module: crm
#: model:process.node,note:crm.process_node_opportunities0
msgid "When a real project/opportunity is detected"
-msgstr ""
+msgstr "當偵測到真正專案/機會"
#. module: crm
#: field:crm.installer,crm_fundraising:0
@@ -446,7 +446,7 @@ msgstr ""
#. module: crm
#: model:ir.model,name:crm.model_crm_lead2opportunity_action
msgid "Convert/Merge Opportunity"
-msgstr ""
+msgstr "轉變/合併機會"
#. module: crm
#: field:crm.lead,write_date:0
@@ -457,7 +457,7 @@ msgstr "更新日期"
#: view:crm.lead2opportunity.action:0
#: field:crm.lead2opportunity.action,name:0
msgid "Select Action"
-msgstr ""
+msgstr "選擇動作"
#. module: crm
#: field:base.action.rule,trg_categ_id:0
@@ -475,7 +475,7 @@ msgstr "分類"
#. module: crm
#: view:crm.lead.report:0
msgid "#Opportunities"
-msgstr ""
+msgstr "#機會"
#. module: crm
#: model:crm.case.resource.type,name:crm.type_oppor2
@@ -495,7 +495,7 @@ msgstr ""
#. module: crm
#: view:crm.lead.report:0
msgid "Opportunity Analysis"
-msgstr ""
+msgstr "機會分析"
#. module: crm
#: help:crm.meeting,location:0
@@ -525,7 +525,7 @@ msgstr ""
#. module: crm
#: model:process.transition,note:crm.process_transition_opportunitymeeting0
msgid "Normal or phone meeting for opportunity"
-msgstr ""
+msgstr "與機會的正常或電話會談"
#. module: crm
#: model:process.node,note:crm.process_node_leads0
@@ -544,7 +544,7 @@ msgstr ""
#: model:ir.actions.act_window,name:crm.crm_partner2opportunity
#, python-format
msgid "Create Opportunity"
-msgstr ""
+msgstr "建立機會"
#. module: crm
#: view:crm.installer:0
@@ -631,7 +631,7 @@ msgstr "滿意度調查"
msgid ""
"Thick this box if you want that on escalation, the responsible of this sale "
"team automatically becomes responsible of the lead/opportunity escaladed"
-msgstr ""
+msgstr "如想提升注意級別,勾選此項;此銷售隊伍之負責人會自動成為已提升注意潛在客戶/機會之負責人"
#. module: crm
#: help:crm.installer,outlook:0
@@ -671,7 +671,7 @@ msgstr ""
#. module: crm
#: view:crm.phonecall.report:0
msgid "#Phone calls"
-msgstr ""
+msgstr "致電數"
#. module: crm
#: help:crm.segmentation,categ_id:0
@@ -691,7 +691,7 @@ msgid ""
"The channels represent the different communication "
"modes available with the customer. With each commercial opportunity, you can "
"indicate the canall which is this opportunity source."
-msgstr ""
+msgstr "渠道代表該顧客之不同通訊模式。對於每個商機,您可指明此機會來源之管道。"
#. module: crm
#: code:addons/crm/crm_meeting.py:93
@@ -720,7 +720,7 @@ msgstr ""
#. module: crm
#: view:res.users:0
msgid "Current Activity"
-msgstr "目前活動"
+msgstr "當前動態"
#. module: crm
#: help:crm.meeting,exrule:0
@@ -835,7 +835,7 @@ msgstr "停止處理"
#. module: crm
#: view:crm.phonecall:0
msgid "Search Phonecalls"
-msgstr ""
+msgstr "搜尋致電"
#. module: crm
#: view:crm.lead2opportunity.partner:0
@@ -953,7 +953,7 @@ msgstr ""
#. module: crm
#: view:crm.phonecall2opportunity:0
msgid "Convert To Opportunity "
-msgstr ""
+msgstr "轉變為機會 "
#. module: crm
#: help:crm.case.stage,sequence:0
@@ -1016,7 +1016,7 @@ msgstr "三月"
#: code:addons/crm/crm_lead.py:230
#, python-format
msgid "The opportunity '%s' has been closed."
-msgstr ""
+msgstr "「%s」機會已結束。"
#. module: crm
#: field:crm.lead,day_open:0
@@ -1033,7 +1033,7 @@ msgstr "將時間顯示為"
#: view:crm.phonecall2partner:0
#, python-format
msgid "Create Partner"
-msgstr ""
+msgstr "建立伙伴"
#. module: crm
#: selection:crm.segmentation.line,expr_operator:0
@@ -1056,7 +1056,7 @@ msgstr ""
#, python-format
msgid ""
"There are no other 'Open' or 'Pending' Opportunities for the partner '%s'."
-msgstr ""
+msgstr "「%s」伙伴並無「開放」或「待處理」之機會。"
#. module: crm
#: view:crm.lead:0
@@ -1105,7 +1105,7 @@ msgstr ""
#: field:crm.meeting,date_action_next:0
#: field:crm.phonecall,date_action_next:0
msgid "Next Action"
-msgstr ""
+msgstr "下個動作"
#. module: crm
#: field:crm.meeting,end_date:0
@@ -1128,7 +1128,7 @@ msgstr ""
#: code:addons/crm/wizard/crm_phonecall_to_opportunity.py:57
#, python-format
msgid "Closed/Cancelled Phone Call Could not convert into Opportunity"
-msgstr ""
+msgstr "已結束/已取消之致電不能轉為機會"
#. module: crm
#: view:crm.segmentation:0
@@ -1353,7 +1353,7 @@ msgstr "已處理最大伙伴ID"
#: model:ir.actions.act_window,name:crm.action_report_crm_phonecall
#: model:ir.ui.menu,name:crm.menu_report_crm_phonecalls_tree
msgid "Phone Calls Analysis"
-msgstr ""
+msgstr "致電分析"
#. module: crm
#: field:crm.lead.report,opening_date:0
@@ -1493,7 +1493,7 @@ msgstr ""
#. module: crm
#: field:crm.phonecall2opportunity,name:0
msgid "Opportunity Summary"
-msgstr ""
+msgstr "機會摘要"
#. module: crm
#: view:crm.phonecall.report:0
@@ -1584,7 +1584,7 @@ msgstr ""
#. module: crm
#: model:ir.model,name:crm.model_crm_merge_opportunity
msgid "Merge two Opportunities"
-msgstr ""
+msgstr "合併兩個機會"
#. module: crm
#: selection:crm.meeting,end_type:0
@@ -1611,7 +1611,7 @@ msgstr ""
#. module: crm
#: model:ir.actions.act_window,name:crm.crm_phonecall_categ_action
msgid "Phonecall Categories"
-msgstr ""
+msgstr "致電分類"
#. module: crm
#: view:crm.meeting:0
@@ -1804,7 +1804,7 @@ msgstr "上級團隊"
#. module: crm
#: field:crm.lead,date_action:0
msgid "Next Action Date"
-msgstr ""
+msgstr "下個動作日期"
#. module: crm
#: selection:crm.segmentation,state:0
@@ -1850,7 +1850,7 @@ msgstr ""
#: view:crm.phonecall.report:0
#: model:ir.actions.act_window,name:crm.act_crm_opportunity_crm_phonecall_new
msgid "Phone calls"
-msgstr ""
+msgstr "致電"
#. module: crm
#: view:crm.lead:0
@@ -2070,7 +2070,7 @@ msgstr ""
#. module: crm
#: model:process.node,note:crm.process_node_meeting0
msgid "Schedule a normal or phone meeting"
-msgstr ""
+msgstr "安排正常或電話會談"
#. module: crm
#: code:addons/crm/crm.py:375
@@ -2331,7 +2331,7 @@ msgstr ""
#: model:ir.ui.menu,name:crm.menu_crm_case_phone
#: view:res.partner:0
msgid "Phone Calls"
-msgstr ""
+msgstr "致電"
#. module: crm
#: help:crm.lead.report,delay_open:0
@@ -2358,7 +2358,7 @@ msgstr "活躍"
#: code:addons/crm/crm_lead.py:306
#, python-format
msgid "The stage of opportunity '%s' has been changed to '%s'."
-msgstr ""
+msgstr "機會階段已由「%s」變為「%s」。"
#. module: crm
#: code:addons/crm/crm_lead.py:282
@@ -2414,7 +2414,7 @@ msgstr ""
#: field:crm.lead2partner,action:0
#: field:crm.phonecall2partner,action:0
msgid "Action"
-msgstr ""
+msgstr "動作"
#. module: crm
#: field:crm.installer,crm_claim:0
@@ -2544,7 +2544,7 @@ msgstr ""
#: view:board.board:0
#: model:ir.actions.act_window,name:crm.act_my_oppor
msgid "My Open Opportunities"
-msgstr ""
+msgstr "我的開放機會"
#. module: crm
#: model:ir.actions.act_window,name:crm.open_board_statistical_dash
@@ -2585,7 +2585,7 @@ msgstr "會議類型"
#: code:addons/crm/wizard/crm_lead_to_opportunity.py:314
#, python-format
msgid "Merge with Existing Opportunity"
-msgstr "與既有機會合併"
+msgstr "與現有機會合併"
#. module: crm
#: help:crm.lead,state:0
@@ -2714,7 +2714,7 @@ msgstr ""
#: field:crm.meeting,date_action_last:0
#: field:crm.phonecall,date_action_last:0
msgid "Last Action"
-msgstr ""
+msgstr "最後動作"
#. module: crm
#: field:crm.meeting,duration:0
@@ -3485,7 +3485,7 @@ msgstr "各階段機會"
#. module: crm
#: model:ir.actions.act_window,name:crm.crm_case_categ_phone_create_partner
msgid "Schedule Phone Call"
-msgstr ""
+msgstr "安排致電"
#. module: crm
#: selection:crm.lead.report,month:0
@@ -3564,7 +3564,7 @@ msgstr ""
#: code:addons/crm/wizard/crm_merge_opportunities.py:100
#, python-format
msgid "Merged into Opportunity: %s"
-msgstr "合併至機會:%s"
+msgstr "已合併至機會: %s"
#. module: crm
#: code:addons/crm/crm.py:347
@@ -3584,7 +3584,7 @@ msgstr "分類化"
#. module: crm
#: model:ir.model,name:crm.model_base_action_rule
msgid "Action Rules"
-msgstr ""
+msgstr "動作規則"
#. module: crm
#: field:crm.meeting,rrule_type:0
@@ -3594,7 +3594,7 @@ msgstr ""
#. module: crm
#: field:crm.meeting,phonecall_id:0
msgid "Phonecall"
-msgstr ""
+msgstr "致電"
#. module: crm
#: selection:crm.meeting,week_list:0
@@ -3763,7 +3763,7 @@ msgstr ""
#. module: crm
#: selection:crm.lead2opportunity.action,name:0
msgid "Merge with existing Opportunity"
-msgstr ""
+msgstr "與現有機會合併"
#. module: crm
#: field:crm.meeting,select1:0
@@ -3816,7 +3816,7 @@ msgstr ""
#. module: crm
#: field:res.partner,phonecall_ids:0
msgid "Phonecalls"
-msgstr ""
+msgstr "致電"
#. module: crm
#: view:crm.lead.report:0
diff --git a/addons/crm/test/test_crm_lead.yml b/addons/crm/test/test_crm_lead.yml
index 6a954939e04..5e9b7a5cfca 100644
--- a/addons/crm/test/test_crm_lead.yml
+++ b/addons/crm/test/test_crm_lead.yml
@@ -92,7 +92,6 @@
-
!record {model: crm.lead2opportunity.partner, id: crm_lead2opportunity_partner_create_1}:
action: 'exist'
- name: 'existing partner'
-
Then, Click on "Create Opportunity" button.
-
@@ -104,7 +103,6 @@
-
!record {model: crm.lead2opportunity.partner, id: crm_lead2opportunity_partner_create_2}:
action: 'nothing'
- name: 'Do not link to a partner'
-
Then, Click on "Create Opportunity" button.
-
diff --git a/addons/crm/wizard/crm_lead_to_opportunity.py b/addons/crm/wizard/crm_lead_to_opportunity.py
index 8200dbd1675..87ab9229d26 100644
--- a/addons/crm/wizard/crm_lead_to_opportunity.py
+++ b/addons/crm/wizard/crm_lead_to_opportunity.py
@@ -37,7 +37,7 @@ class crm_lead2opportunity_partner(osv.osv_memory):
('nothing', 'Do not link to a partner')], \
'Action', required=True),
'name': fields.selection([('convert', 'Convert to Opportunity'), ('merge', 'Merge with existing Opportunity')],'Select Action', required=True),
- 'opportunity_ids': fields.many2many('crm.lead', 'merge_opportunity_rel', 'merge_id', 'opportunity_id', 'Opportunities', domain=[('type', '=', 'opportunity')]),
+ 'opportunity_ids': fields.many2many('crm.lead', string='Opportunities', domain=[('type', '=', 'opportunity')]),
}
def default_get(self, cr, uid, fields, context=None):
@@ -236,7 +236,7 @@ class crm_lead2opportunity_mass_convert(osv.osv_memory):
_columns = {
- 'user_ids': fields.many2many('res.users', 'mass_convert_rel', 'user_id', 'wizard_id', 'Salesmans'),
+ 'user_ids': fields.many2many('res.users', string='Salesmans'),
'section_id': fields.many2one('crm.case.section', 'Sales Team'),
}
diff --git a/addons/crm/wizard/crm_merge_opportunities.py b/addons/crm/wizard/crm_merge_opportunities.py
index d2d46749746..f092d6ad0b6 100644
--- a/addons/crm/wizard/crm_merge_opportunities.py
+++ b/addons/crm/wizard/crm_merge_opportunities.py
@@ -142,7 +142,7 @@ class crm_merge_opportunity(osv.osv_memory):
count+=1
for history in opp.message_ids:
- message_obj.write(cr, uid, history.id, {'res_id': first_opportunity.id, 'name' : _("From %s : %s") % (opp.name, history.name) }, context=context)
+ message_obj.write(cr, uid, history.id, {'res_id': first_opportunity.id, 'subject' : _("From %s : %s") % (opp.name, history.subject) }, context=context)
#Notification about loss of information
details = []
diff --git a/addons/crm_partner_assign/test/test_crm_partner_assign.yml b/addons/crm_partner_assign/test/test_crm_partner_assign.yml
index b214f535275..359fa8454f6 100644
--- a/addons/crm_partner_assign/test/test_crm_partner_assign.yml
+++ b/addons/crm_partner_assign/test/test_crm_partner_assign.yml
@@ -108,6 +108,7 @@
'email_to': 'info@axelor.com',
'email_from': 'Administrator ',
'reply_to': 'sales_openerp@openerp.com',
+ 'state': 'draft',
'history': 'latest',
}
ids = self.create(cr, uid, vals, context={'active_id': ref('crm_lead_questionnaireonopenerp0'), 'active_model': 'crm.lead'})
diff --git a/addons/crm_partner_assign/wizard/crm_forward_to_partner_view.xml b/addons/crm_partner_assign/wizard/crm_forward_to_partner_view.xml
index d3ecddb1aa3..8bdb03cf962 100644
--- a/addons/crm_partner_assign/wizard/crm_forward_to_partner_view.xml
+++ b/addons/crm_partner_assign/wizard/crm_forward_to_partner_view.xml
@@ -25,7 +25,6 @@
-
diff --git a/addons/crm_profiling/crm_profiling.py b/addons/crm_profiling/crm_profiling.py
index 90dc0818743..59137966da0 100644
--- a/addons/crm_profiling/crm_profiling.py
+++ b/addons/crm_profiling/crm_profiling.py
@@ -264,7 +264,7 @@ class crm_segmentation(osv.osv):
}
_constraints = [
- (orm.orm._check_recursion, 'Error ! You can not create recursive profiles.', ['parent_id'])
+ (osv.osv._check_recursion, 'Error ! You can not create recursive profiles.', ['parent_id'])
]
def process_continue(self, cr, uid, ids, start=False):
diff --git a/addons/decimal_precision/i18n/zh_TW.po b/addons/decimal_precision/i18n/zh_TW.po
new file mode 100644
index 00000000000..0350112585d
--- /dev/null
+++ b/addons/decimal_precision/i18n/zh_TW.po
@@ -0,0 +1,72 @@
+# Chinese (Traditional) translation for openobject-addons
+# Copyright (c) 2011 Rosetta Contributors and Canonical Ltd 2011
+# This file is distributed under the same license as the openobject-addons package.
+# FIRST AUTHOR , 2011.
+#
+msgid ""
+msgstr ""
+"Project-Id-Version: openobject-addons\n"
+"Report-Msgid-Bugs-To: FULL NAME \n"
+"POT-Creation-Date: 2011-01-11 11:15+0000\n"
+"PO-Revision-Date: 2011-09-27 08:06+0000\n"
+"Last-Translator: FULL NAME \n"
+"Language-Team: Chinese (Traditional) \n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:20+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
+
+#. module: decimal_precision
+#: field:decimal.precision,digits:0
+msgid "Digits"
+msgstr "數字"
+
+#. module: decimal_precision
+#: view:decimal.precision:0
+msgid "Decimal Precision"
+msgstr "小數精確度"
+
+#. module: decimal_precision
+#: model:ir.actions.act_window,name:decimal_precision.action_decimal_precision_form
+#: model:ir.ui.menu,name:decimal_precision.menu_decimal_precision_form
+msgid "Decimal Accuracy Definitions"
+msgstr ""
+
+#. module: decimal_precision
+#: model:ir.module.module,description:decimal_precision.module_meta_information
+msgid ""
+"\n"
+"This module allows to configure the price accuracy you need for different "
+"kind\n"
+"of usage: accounting, sales, purchases, ...\n"
+"\n"
+"The decimal precision is configured per company.\n"
+msgstr ""
+"\n"
+"此模組讓您為會計、銷售、採購...等不同用途設定價錢準確度。\n"
+"\n"
+"每間公司之小數精確度可以不同。\n"
+
+#. module: decimal_precision
+#: field:decimal.precision,name:0
+msgid "Usage"
+msgstr "用途"
+
+#. module: decimal_precision
+#: sql_constraint:decimal.precision:0
+msgid "Only one value can be defined for each given usage!"
+msgstr "每種用途只可定義一個值!"
+
+#. module: decimal_precision
+#: model:ir.module.module,shortdesc:decimal_precision.module_meta_information
+msgid "Decimal Precision Configuration"
+msgstr "小數精確度設定"
+
+#. module: decimal_precision
+#: model:ir.model,name:decimal_precision.model_decimal_precision
+msgid "decimal.precision"
+msgstr ""
+
+#~ msgid "Decimal Accuracy"
+#~ msgstr "小數準確度"
diff --git a/addons/delivery/delivery.py b/addons/delivery/delivery.py
index 94a21289925..cac4c20c288 100644
--- a/addons/delivery/delivery.py
+++ b/addons/delivery/delivery.py
@@ -61,16 +61,16 @@ class delivery_carrier(osv.osv):
return res
_columns = {
- 'name': fields.char('Carrier', size=64, required=True),
- 'partner_id': fields.many2one('res.partner', 'Carrier Partner', required=True),
+ 'name': fields.char('Delivery Method', size=64, required=True),
+ 'partner_id': fields.many2one('res.partner', 'Transport Company', required=True, help="The partner that is doing the delivery service."),
'product_id': fields.many2one('product.product', 'Delivery Product', required=True),
'grids_id': fields.one2many('delivery.grid', 'carrier_id', 'Delivery Grids'),
'price' : fields.function(get_price, string='Price'),
'active': fields.boolean('Active', help="If the active field is set to False, it will allow you to hide the delivery carrier without removing it."),
- 'normal_price': fields.float('Normal Price'),
- 'free_if_more_than': fields.boolean('Free If More Than'),
- 'amount': fields.float('Amount'),
- 'use_detailed_pricelist': fields.boolean('Use Detailed Pricelist'),
+ 'normal_price': fields.float('Normal Price', help="Keep empty if the pricing depends on the advanced pricing per destination"),
+ 'free_if_more_than': fields.boolean('Free If More Than', help="If the order is more expensive than a certain amount, the customer can benefit from a free shipping"),
+ 'amount': fields.float('Amount', help="Amount of the order to benefit from a free shipping, expressed in the company currency"),
+ 'use_detailed_pricelist': fields.boolean('Advanced Pricing per Destination', help="Check this box if you want to manage delivery prices that depends on the destination, the weight, the total of the order, etc."),
'pricelist_ids': fields.one2many('delivery.grid', 'carrier_id', 'Advanced Pricing'),
}
@@ -103,25 +103,32 @@ class delivery_carrier(osv.osv):
grid_line_pool = self.pool.get('delivery.grid.line')
grid_pool = self.pool.get('delivery.grid')
for record in self.browse(cr, uid, ids, context=context):
- grid_id = grid_pool.search(cr, uid, [('carrier_id', '=', record.id)], context=context)
+ grid_id = grid_pool.search(cr, uid, [('carrier_id', '=', record.id),('sequence','=',9999)], context=context)
+
+ if grid_id and not (record.normal_price or record.free_if_more_than):
+ grid_pool.unlink(cr, uid, grid_id, context=context)
+
+ if not (record.normal_price or record.free_if_more_than):
+ continue
+
if not grid_id:
record_data = {
- 'name': vals.get('name', False),
+ 'name': record.name,
'carrier_id': record.id,
- 'seqeunce': 10,
+ 'sequence': 9999,
}
new_grid_id = grid_pool.create(cr, uid, record_data, context=context)
grid_id = [new_grid_id]
- #delete all existing grid lines
- grid_lines = [line.id for line in grid_pool.browse(cr, uid, grid_id[0]).line_ids if line.type == 'price']
- grid_line_pool.unlink(cr, uid, grid_lines, context=context)
+ lines = grid_line_pool.search(cr, uid, [('grid_id','in',grid_id)], context=context)
+ if lines:
+ grid_line_pool.unlink(cr, uid, lines, context=context)
#create the grid lines
if record.free_if_more_than:
data = {
'grid_id': grid_id and grid_id[0],
- 'name': _('Free if more than %d') % record.amount,
+ 'name': _('Free if more than %.2f') % record.amount,
'type': 'price',
'operator': '>=',
'max_value': record.amount,
@@ -217,7 +224,7 @@ class delivery_grid_line(osv.osv):
_description = "Delivery Grid Line"
_columns = {
'name': fields.char('Name', size=32, required=True),
- 'grid_id': fields.many2one('delivery.grid', 'Grid',required=True),
+ 'grid_id': fields.many2one('delivery.grid', 'Grid',required=True, ondelete='cascade'),
'type': fields.selection([('weight','Weight'),('volume','Volume'),\
('wv','Weight * Volume'), ('price','Price')],\
'Variable', required=True),
@@ -242,21 +249,19 @@ class define_delivery_steps(osv.osv_memory):
_name = 'delivery.define.delivery.steps.wizard'
_columns = {
- 'picking_policy' : fields.selection([('direct', 'Partial Delivery'), ('one', 'Complete Delivery'),],
- 'Picking Policy', required=True),
+ 'picking_policy' : fields.selection([('direct', 'Deliver each product when available'), ('one', 'Deliver all products at once')], 'Picking Policy'),
+ }
+ _defaults = {
+ 'picking_policy': lambda s,c,u,ctx: s.pool.get('sale.order').default_get(c,u,['picking_policy'],context=ctx)['picking_policy']
}
def apply_cb(self, cr, uid, ids, context=None):
ir_values_obj = self.pool.get('ir.values')
-
wizard = self.browse(cr, uid, ids, context=context)[0]
-
ir_values_obj.set(cr, uid, 'default', False, 'picking_policy', ['sale.order'], wizard.picking_policy)
-
return {'type' : 'ir.actions.act_window_close'}
define_delivery_steps()
-
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
diff --git a/addons/delivery/delivery_view.xml b/addons/delivery/delivery_view.xml
index 23147a2716f..deb13679355 100644
--- a/addons/delivery/delivery_view.xml
+++ b/addons/delivery/delivery_view.xml
@@ -9,6 +9,7 @@
tree
+
@@ -21,15 +22,16 @@
+
-
-
-
+
+
+
-
+
@@ -37,7 +39,6 @@
-
@@ -76,8 +77,8 @@
ir.actions.act_windowdelivery.carrierform
- form,tree
- Define the delivery methods you are using and their pricing in order to reinvoice the delivery costs when you are doing invoicing based on delivery orders
+ tree,form
+ Define your delivery methods and their pricing. The delivery costs can be added on the sale order form or in the invoice, based on the delivery orders.
@@ -325,7 +326,7 @@
-
+
@@ -341,9 +342,10 @@
delivery.define.delivery.steps.wizardform
-
-
+
+
+
@@ -353,7 +355,7 @@
- Setup Your Delivery Steps
+ Setup Your Picking Policydelivery.define.delivery.steps.wizardformform
@@ -362,6 +364,8 @@
+
+ once
diff --git a/addons/delivery/i18n/zh_TW.po b/addons/delivery/i18n/zh_TW.po
index 6a09d0860d7..91f4e8816a5 100644
--- a/addons/delivery/i18n/zh_TW.po
+++ b/addons/delivery/i18n/zh_TW.po
@@ -7,19 +7,19 @@ msgstr ""
"Project-Id-Version: OpenERP Server 5.0.4\n"
"Report-Msgid-Bugs-To: support@openerp.com\n"
"POT-Creation-Date: 2011-01-11 11:15+0000\n"
-"PO-Revision-Date: 2011-01-28 03:29+0000\n"
+"PO-Revision-Date: 2011-09-27 10:27+0000\n"
"Last-Translator: Walter Cheuk \n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
-"X-Launchpad-Export-Date: 2011-09-05 05:01+0000\n"
-"X-Generator: Launchpad (build 13830)\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:19+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
#. module: delivery
#: report:sale.shipping:0
msgid "Order Ref."
-msgstr "單號參照"
+msgstr "訂單參考"
#. module: delivery
#: model:product.template,name:delivery.delivery_product_product_template
@@ -67,7 +67,7 @@ msgstr "體積"
#. module: delivery
#: sql_constraint:sale.order:0
msgid "Order Reference must be unique !"
-msgstr "交貨參照不能重覆!"
+msgstr "訂單參考不能重覆!"
#. module: delivery
#: field:delivery.grid,line_ids:0
@@ -82,17 +82,17 @@ msgstr "交貨單"
#. module: delivery
#: view:res.partner:0
msgid "Deliveries Properties"
-msgstr ""
+msgstr "交貨性質"
#. module: delivery
#: model:ir.actions.act_window,name:delivery.action_picking_tree4
msgid "Picking to be invoiced"
-msgstr ""
+msgstr "要開立發票的提貨"
#. module: delivery
#: help:delivery.grid,sequence:0
msgid "Gives the sequence order when displaying a list of delivery grid."
-msgstr ""
+msgstr "提供顯示交貨格線清單的次序。"
#. module: delivery
#: view:delivery.grid:0
@@ -103,12 +103,12 @@ msgstr "國家"
#. module: delivery
#: report:sale.shipping:0
msgid "Delivery Order :"
-msgstr "交貨單:"
+msgstr "交貨單 :"
#. module: delivery
#: field:delivery.grid.line,variable_factor:0
msgid "Variable Factor"
-msgstr ""
+msgstr "可變因子"
#. module: delivery
#: model:ir.actions.act_window,help:delivery.action_delivery_grid_form
@@ -132,7 +132,7 @@ msgstr "固定"
#: field:res.partner,property_delivery_carrier:0
#: field:sale.order,carrier_id:0
msgid "Delivery Method"
-msgstr "交貨方式"
+msgstr "交貨方法"
#. module: delivery
#: model:ir.model,name:delivery.model_stock_move
@@ -143,12 +143,12 @@ msgstr "庫存調動"
#: code:addons/delivery/delivery.py:141
#, python-format
msgid "No line matched this order in the choosed delivery grids !"
-msgstr ""
+msgstr "選擇的交貨格無一行符合此訂單 !"
#. module: delivery
#: field:stock.picking,carrier_tracking_ref:0
msgid "Carrier Tracking Ref"
-msgstr "運輸公司追蹤編號"
+msgstr "運輸公司追蹤參考"
#. module: delivery
#: field:stock.picking,weight_net:0
@@ -172,7 +172,7 @@ msgstr "警告"
#. module: delivery
#: view:delivery.grid:0
msgid "Grid definition"
-msgstr ""
+msgstr "格線定義"
#. module: delivery
#: view:delivery.sale.order:0
@@ -197,12 +197,12 @@ msgstr "銷貨單"
#. module: delivery
#: model:ir.model,name:delivery.model_delivery_grid
msgid "Delivery Grid"
-msgstr ""
+msgstr "交貨格線"
#. module: delivery
#: report:sale.shipping:0
msgid "Invoiced to"
-msgstr "發票交至"
+msgstr "發票開立對象:"
#. module: delivery
#: model:ir.model,name:delivery.model_stock_picking
@@ -212,7 +212,7 @@ msgstr "提貨清單"
#. module: delivery
#: model:ir.model,name:delivery.model_delivery_sale_order
msgid "Make Delievery"
-msgstr ""
+msgstr "進行交貨"
#. module: delivery
#: model:ir.module.module,description:delivery.module_meta_information
@@ -228,12 +228,12 @@ msgstr ""
#. module: delivery
#: view:delivery.grid.line:0
msgid "Grid Lines"
-msgstr ""
+msgstr "格線"
#. module: delivery
#: field:delivery.grid.line,grid_id:0
msgid "Grid"
-msgstr ""
+msgstr "網格"
#. module: delivery
#: help:delivery.grid,active:0
@@ -245,17 +245,17 @@ msgstr ""
#. module: delivery
#: field:delivery.grid,zip_to:0
msgid "To Zip"
-msgstr ""
+msgstr "至郵遞區號"
#. module: delivery
#: report:sale.shipping:0
msgid "Order Date"
-msgstr "單子日期"
+msgstr "訂單日期"
#. module: delivery
#: field:delivery.grid,name:0
msgid "Grid Name"
-msgstr ""
+msgstr "網格名稱"
#. module: delivery
#: view:stock.move:0
@@ -287,7 +287,7 @@ msgstr ""
#: code:addons/delivery/wizard/delivery_sale_order.py:95
#, python-format
msgid "No grid available !"
-msgstr ""
+msgstr "無可用網格 !"
#. module: delivery
#: selection:delivery.grid.line,operator:0
@@ -299,7 +299,7 @@ msgstr ""
#: code:addons/delivery/wizard/delivery_sale_order.py:98
#, python-format
msgid "Order not in draft state !"
-msgstr ""
+msgstr "訂單不在草稿階段 !"
#. module: delivery
#: constraint:res.partner:0
@@ -314,7 +314,7 @@ msgstr "批次"
#. module: delivery
#: constraint:stock.move:0
msgid "You try to assign a lot which is not from the same product"
-msgstr ""
+msgstr "指定了不同產品的批次"
#. module: delivery
#: field:delivery.carrier,active:0
@@ -325,7 +325,7 @@ msgstr "活躍"
#. module: delivery
#: report:sale.shipping:0
msgid "Shipping Date"
-msgstr ""
+msgstr "貨運日期"
#. module: delivery
#: field:delivery.carrier,product_id:0
@@ -382,7 +382,7 @@ msgstr "運輸公司伙伴"
#. module: delivery
#: view:res.partner:0
msgid "Sales & Purchases"
-msgstr "銷售&採購"
+msgstr "銷售 及 購貨"
#. module: delivery
#: selection:delivery.grid.line,operator:0
@@ -392,12 +392,12 @@ msgstr ""
#. module: delivery
#: constraint:stock.move:0
msgid "You must assign a production lot for this product"
-msgstr "須為此產品分配生產批次"
+msgstr "須為此產品指定生產批次"
#. module: delivery
#: view:delivery.sale.order:0
msgid "Create Deliveries"
-msgstr ""
+msgstr "進行交貨"
#. module: delivery
#: model:ir.actions.act_window,name:delivery.action_delivery_cost
@@ -481,7 +481,7 @@ msgstr ""
#: code:addons/delivery/wizard/delivery_sale_order.py:98
#, python-format
msgid "The order state have to be draft to add delivery lines."
-msgstr ""
+msgstr "訂單狀態要是草稿才能添加交貨明細。"
#. module: delivery
#: model:ir.module.module,shortdesc:delivery.module_meta_information
@@ -491,12 +491,12 @@ msgstr "運輸公司與交貨"
#. module: delivery
#: field:delivery.carrier,grids_id:0
msgid "Delivery Grids"
-msgstr ""
+msgstr "交貨網格"
#. module: delivery
#: field:delivery.grid,sequence:0
msgid "Sequence"
-msgstr ""
+msgstr "次序"
#. module: delivery
#: field:delivery.grid.line,list_price:0
@@ -507,7 +507,7 @@ msgstr "銷售價"
#: view:delivery.grid:0
#: field:delivery.grid,state_ids:0
msgid "States"
-msgstr ""
+msgstr "狀態"
#. module: delivery
#: field:delivery.grid.line,price_type:0
diff --git a/addons/document/i18n/zh_HK.po b/addons/document/i18n/zh_HK.po
new file mode 100644
index 00000000000..d0e38ae37d2
--- /dev/null
+++ b/addons/document/i18n/zh_HK.po
@@ -0,0 +1,1030 @@
+# Chinese (Hong Kong) translation for openobject-addons
+# Copyright (c) 2011 Rosetta Contributors and Canonical Ltd 2011
+# This file is distributed under the same license as the openobject-addons package.
+# FIRST AUTHOR , 2011.
+#
+msgid ""
+msgstr ""
+"Project-Id-Version: openobject-addons\n"
+"Report-Msgid-Bugs-To: FULL NAME \n"
+"POT-Creation-Date: 2011-01-11 11:15+0000\n"
+"PO-Revision-Date: 2011-09-27 13:46+0000\n"
+"Last-Translator: FULL NAME \n"
+"Language-Team: Chinese (Hong Kong) \n"
+"MIME-Version: 1.0\n"
+"Content-Type: text/plain; charset=UTF-8\n"
+"Content-Transfer-Encoding: 8bit\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:20+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
+
+#. module: document
+#: field:document.directory,parent_id:0
+msgid "Parent Directory"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_document_configuration
+msgid "Auto Directory Configuration"
+msgstr ""
+
+#. module: document
+#: field:document.directory,resource_field:0
+msgid "Name field"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+msgid "Document board"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_process_node
+msgid "Process Node"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Search Document Directory"
+msgstr ""
+
+#. module: document
+#: help:document.directory,resource_field:0
+msgid ""
+"Field to be used as name on resource directories. If empty, the \"name\" "
+"will be used."
+msgstr ""
+
+#. module: document
+#: code:addons/document/document_directory.py:276
+#, python-format
+msgid "Directory name contains special characters!"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+#: view:document.storage:0
+msgid "Group By..."
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_document_directory_content_type
+msgid "Directory Content Type"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Resources"
+msgstr ""
+
+#. module: document
+#: field:document.directory,file_ids:0
+#: view:report.document.user:0
+msgid "Files"
+msgstr ""
+
+#. module: document
+#: view:report.files.partner:0
+msgid "Files per Month"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "March"
+msgstr ""
+
+#. module: document
+#: view:document.configuration:0
+msgid "title"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+#: field:document.directory,company_id:0
+msgid "Company"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_document_directory_content
+msgid "Directory Content"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Dynamic context"
+msgstr ""
+
+#. module: document
+#: model:ir.ui.menu,name:document.menu_document_management_configuration
+msgid "Document Management"
+msgstr ""
+
+#. module: document
+#: help:document.directory.dctx,expr:0
+msgid ""
+"A python expression used to evaluate the field.\n"
+"You can use 'dir_id' for current dir, 'res_id', 'res_model' as a reference "
+"to the current record, in dynamic folders"
+msgstr ""
+
+#. module: document
+#: view:report.document.user:0
+msgid "This Year"
+msgstr ""
+
+#. module: document
+#: field:document.storage,path:0
+msgid "Path"
+msgstr ""
+
+#. module: document
+#: code:addons/document/document_directory.py:266
+#: code:addons/document/document_directory.py:271
+#, python-format
+msgid "Directory name must be unique!"
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+#: field:ir.attachment,index_content:0
+msgid "Indexed Content"
+msgstr ""
+
+#. module: document
+#: help:document.directory,resource_find_all:0
+msgid ""
+"If true, all attachments that match this resource will be located. If "
+"false, only ones that have this as parent."
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+#: field:document.storage,dir_ids:0
+#: model:ir.actions.act_window,name:document.action_document_directory_form
+#: model:ir.ui.menu,name:document.menu_document_directories
+msgid "Directories"
+msgstr ""
+
+#. module: document
+#: field:document.configuration,sale_order:0
+msgid "Sale Order"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_report_document_user
+msgid "Files details by Users"
+msgstr ""
+
+#. module: document
+#: field:document.configuration,project:0
+msgid "Project"
+msgstr ""
+
+#. module: document
+#: code:addons/document/document_storage.py:573
+#: code:addons/document/document_storage.py:601
+#, python-format
+msgid "Error!"
+msgstr ""
+
+#. module: document
+#: help:document.configuration,product:0
+msgid "Auto directory configuration for Products."
+msgstr ""
+
+#. module: document
+#: field:document.directory,resource_find_all:0
+msgid "Find all resources"
+msgstr ""
+
+#. module: document
+#: selection:document.directory,type:0
+msgid "Folders per resource"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,suffix:0
+msgid "Suffix"
+msgstr ""
+
+#. module: document
+#: field:report.document.user,change_date:0
+msgid "Modified Date"
+msgstr ""
+
+#. module: document
+#: view:document.configuration:0
+msgid "Knowledge Application Configuration"
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+#: field:ir.attachment,partner_id:0
+#: field:report.files.partner,partner:0
+msgid "Partner"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+msgid "Files by Users"
+msgstr ""
+
+#. module: document
+#: field:process.node,directory_id:0
+msgid "Document directory"
+msgstr ""
+
+#. module: document
+#: code:addons/document/document.py:226
+#: code:addons/document/document.py:294
+#: code:addons/document/document_directory.py:266
+#: code:addons/document/document_directory.py:271
+#: code:addons/document/document_directory.py:276
+#, python-format
+msgid "ValidateError"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_ir_actions_report_xml
+msgid "ir.actions.report.xml"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.action_document_file_form
+#: view:ir.attachment:0
+#: model:ir.ui.menu,name:document.menu_document_doc
+#: model:ir.ui.menu,name:document.menu_document_files
+msgid "Documents"
+msgstr ""
+
+#. module: document
+#: constraint:document.directory:0
+msgid "Error! You can not create recursive Directories."
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+#: field:document.directory,storage_id:0
+msgid "Storage"
+msgstr ""
+
+#. module: document
+#: view:document.configuration:0
+msgid "Configure Resource Directory"
+msgstr ""
+
+#. module: document
+#: field:ir.attachment,file_size:0
+#: field:report.document.file,file_size:0
+#: field:report.document.user,file_size:0
+#: field:report.files.partner,file_size:0
+msgid "File Size"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content.type,name:0
+#: field:ir.attachment,file_type:0
+msgid "Content Type"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+#: field:document.directory,type:0
+#: view:document.storage:0
+#: field:document.storage,type:0
+msgid "Type"
+msgstr ""
+
+#. module: document
+#: help:document.directory,ressource_type_id:0
+msgid ""
+"Select an object here and there will be one folder per record of that "
+"resource."
+msgstr ""
+
+#. module: document
+#: help:document.directory,domain:0
+msgid ""
+"Use a domain if you want to apply an automatic filter on visible resources."
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.action_view_files_by_partner
+msgid "Files Per Partner"
+msgstr ""
+
+#. module: document
+#: field:document.directory,dctx_ids:0
+msgid "Context fields"
+msgstr ""
+
+#. module: document
+#: field:ir.attachment,store_fname:0
+msgid "Stored Filename"
+msgstr ""
+
+#. module: document
+#: field:document.directory,ressource_type_id:0
+msgid "Resource model"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+#: field:report.document.user,type:0
+msgid "Directory Type"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,report_id:0
+msgid "Report"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "July"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.open_board_document_manager
+#: model:ir.ui.menu,name:document.menu_reports_document_manager
+msgid "Document Dashboard"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content.type,code:0
+msgid "Extension"
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+msgid "Created"
+msgstr ""
+
+#. module: document
+#: field:document.directory,content_ids:0
+msgid "Virtual Files"
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+msgid "Modified"
+msgstr ""
+
+#. module: document
+#: code:addons/document/document_storage.py:639
+#, python-format
+msgid "Error at doc write!"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Generated Files"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,directory_id:0
+#: field:document.directory.dctx,dir_id:0
+#: model:ir.actions.act_window,name:document.action_document_file_directory_form
+#: view:ir.attachment:0
+#: field:ir.attachment,parent_id:0
+#: model:ir.model,name:document.model_document_directory
+#: field:report.document.user,directory:0
+msgid "Directory"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+msgid "Files by Partner"
+msgstr ""
+
+#. module: document
+#: field:document.directory,write_uid:0
+#: field:document.storage,write_uid:0
+#: field:ir.attachment,write_uid:0
+msgid "Last Modification User"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.act_res_partner_document
+#: model:ir.actions.act_window,name:document.zoom_directory
+msgid "Related Documents"
+msgstr ""
+
+#. module: document
+#: field:document.configuration,progress:0
+msgid "Configuration Progress"
+msgstr ""
+
+#. module: document
+#: field:document.directory,domain:0
+msgid "Domain"
+msgstr ""
+
+#. module: document
+#: field:document.directory,write_date:0
+#: field:document.storage,write_date:0
+#: field:ir.attachment,write_date:0
+msgid "Date Modified"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_report_document_file
+msgid "Files details by Directory"
+msgstr ""
+
+#. module: document
+#: view:report.document.user:0
+msgid "All users files"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+#: model:ir.actions.act_window,name:document.action_view_size_month
+#: view:report.document.file:0
+msgid "File Size by Month"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "December"
+msgstr ""
+
+#. module: document
+#: field:document.configuration,config_logo:0
+msgid "Image"
+msgstr ""
+
+#. module: document
+#: selection:document.directory,type:0
+msgid "Static Directory"
+msgstr ""
+
+#. module: document
+#: field:document.directory,child_ids:0
+msgid "Children"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Define words in the context, for all child directories and files"
+msgstr ""
+
+#. module: document
+#: model:ir.module.module,description:document.module_meta_information
+msgid ""
+"This is a complete document management system:\n"
+" * User Authentication\n"
+" * Document Indexation :- .pptx and .docx files are not support in "
+"windows platform.\n"
+" * Dashboard for Document that includes:\n"
+" * New Files (list)\n"
+" * Files by Resource Type (graph)\n"
+" * Files by Partner (graph)\n"
+" * Files by Month (graph)\n"
+" ATTENTION:\n"
+" - When you install this module in a running company that have already "
+"PDF files stored into the database,\n"
+" you will lose them all.\n"
+" - After installing this module PDF's are no longer stored into the "
+"database,\n"
+" but in the servers rootpad like /server/bin/filestore.\n"
+msgstr ""
+
+#. module: document
+#: help:document.storage,online:0
+msgid ""
+"If not checked, media is currently offline and its contents not available"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+#: field:document.directory,user_id:0
+#: field:document.storage,user_id:0
+#: view:ir.attachment:0
+#: field:ir.attachment,user_id:0
+#: field:report.document.user,user_id:0
+#: field:report.document.wall,user_id:0
+msgid "Owner"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "PDF Report"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Contents"
+msgstr ""
+
+#. module: document
+#: field:document.directory,create_date:0
+#: field:document.storage,create_date:0
+#: field:report.document.user,create_date:0
+msgid "Date Created"
+msgstr ""
+
+#. module: document
+#: help:document.directory.content,include_name:0
+msgid ""
+"Check this field if you want that the name of the file to contain the record "
+"name.\n"
+"If set, the directory will have to be a resource one."
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.action_config_auto_directory
+msgid "Auto Configure Directory"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,include_name:0
+msgid "Include Record Name"
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+msgid "Attachment"
+msgstr ""
+
+#. module: document
+#: field:ir.actions.report.xml,model_id:0
+msgid "Model Id"
+msgstr ""
+
+#. module: document
+#: field:document.storage,online:0
+msgid "Online"
+msgstr ""
+
+#. module: document
+#: help:document.directory,ressource_tree:0
+msgid ""
+"Check this if you want to use the same tree structure as the object selected "
+"in the system."
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Security"
+msgstr "保安"
+
+#. module: document
+#: help:document.directory,ressource_id:0
+msgid ""
+"Along with Parent Model, this ID attaches this folder to a specific record "
+"of Parent Model."
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "August"
+msgstr ""
+
+#. module: document
+#: sql_constraint:document.directory:0
+msgid "Directory cannot be parent of itself!"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "June"
+msgstr ""
+
+#. module: document
+#: field:report.document.user,user:0
+#: field:report.document.wall,user:0
+msgid "User"
+msgstr ""
+
+#. module: document
+#: field:document.directory,group_ids:0
+#: field:document.storage,group_ids:0
+msgid "Groups"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content.type,active:0
+msgid "Active"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "November"
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+#: field:ir.attachment,db_datas:0
+msgid "Data"
+msgstr ""
+
+#. module: document
+#: help:document.directory,ressource_parent_type_id:0
+msgid ""
+"If you put an object here, this directory template will appear bellow all of "
+"these objects. Such directories are \"attached\" to the specific model or "
+"record, just like attachments. Don't put a parent directory if you select a "
+"parent model."
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Definition"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "October"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Seq."
+msgstr ""
+
+#. module: document
+#: selection:document.storage,type:0
+msgid "Database"
+msgstr ""
+
+#. module: document
+#: help:document.configuration,project:0
+msgid "Auto directory configuration for Projects."
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+msgid "Related to"
+msgstr ""
+
+#. module: document
+#: model:ir.module.module,shortdesc:document.module_meta_information
+msgid "Integrated Document Management System"
+msgstr ""
+
+#. module: document
+#: view:document.configuration:0
+msgid "Choose the following Resouces to auto directory configuration."
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+msgid "Attached To"
+msgstr ""
+
+#. module: document
+#: model:ir.ui.menu,name:document.menu_reports_document
+msgid "Dashboard"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.action_view_user_graph
+msgid "Files By Users"
+msgstr ""
+
+#. module: document
+#: field:document.storage,readonly:0
+msgid "Read Only"
+msgstr ""
+
+#. module: document
+#: field:document.directory.dctx,expr:0
+msgid "Expression"
+msgstr ""
+
+#. module: document
+#: sql_constraint:document.directory:0
+msgid "The directory name must be unique !"
+msgstr ""
+
+#. module: document
+#: field:document.directory,create_uid:0
+#: field:document.storage,create_uid:0
+msgid "Creator"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+#: model:ir.actions.act_window,name:document.action_view_files_by_month_graph
+#: view:report.document.user:0
+msgid "Files by Month"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "September"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,prefix:0
+msgid "Prefix"
+msgstr ""
+
+#. module: document
+#: field:report.document.wall,last:0
+msgid "Last Posted Time"
+msgstr ""
+
+#. module: document
+#: field:report.document.user,datas_fname:0
+msgid "File Name"
+msgstr ""
+
+#. module: document
+#: view:document.configuration:0
+msgid "res_config_contents"
+msgstr ""
+
+#. module: document
+#: field:document.directory,ressource_id:0
+msgid "Resource ID"
+msgstr ""
+
+#. module: document
+#: selection:document.storage,type:0
+msgid "External file storage"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+#: model:ir.actions.act_window,name:document.action_view_wall
+#: view:report.document.wall:0
+msgid "Wall of Shame"
+msgstr ""
+
+#. module: document
+#: help:document.storage,path:0
+msgid "For file storage, the root path of the storage"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_report_files_partner
+msgid "Files details by Partners"
+msgstr ""
+
+#. module: document
+#: field:document.directory.dctx,field:0
+msgid "Field"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_document_directory_dctx
+msgid "Directory Dynamic Context"
+msgstr ""
+
+#. module: document
+#: field:document.directory,ressource_parent_type_id:0
+msgid "Parent Model"
+msgstr ""
+
+#. module: document
+#: view:report.document.user:0
+msgid "Files by users"
+msgstr ""
+
+#. module: document
+#: field:report.document.file,month:0
+#: field:report.document.user,month:0
+#: field:report.document.wall,month:0
+#: field:report.document.wall,name:0
+#: field:report.files.partner,month:0
+msgid "Month"
+msgstr ""
+
+#. module: document
+#: model:ir.ui.menu,name:document.menu_reporting
+msgid "Reporting"
+msgstr ""
+
+#. module: document
+#: field:document.configuration,product:0
+msgid "Product"
+msgstr ""
+
+#. module: document
+#: field:document.directory,ressource_tree:0
+msgid "Tree Structure"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "May"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.action_view_all_document_tree1
+msgid "All Users files"
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_report_document_wall
+msgid "Users that did not inserted documents since one month"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,help:document.action_document_file_form
+msgid ""
+"The Documents repository gives you access to all attachments, such as mails, "
+"project documents, invoices etc."
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "For each entry here, virtual files will appear in this folder."
+msgstr ""
+
+#. module: document
+#: model:ir.model,name:document.model_ir_attachment
+msgid "ir.attachment"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+msgid "New Files"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "January"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Static"
+msgstr ""
+
+#. module: document
+#: view:report.files.partner:0
+msgid "Files By Partner"
+msgstr ""
+
+#. module: document
+#: help:document.directory.dctx,field:0
+msgid ""
+"The name of the field. Note that the prefix \"dctx_\" will be prepended to "
+"what is typed here."
+msgstr ""
+
+#. module: document
+#: view:report.document.user:0
+msgid "This Month"
+msgstr ""
+
+#. module: document
+#: view:ir.attachment:0
+msgid "Notes"
+msgstr ""
+
+#. module: document
+#: help:document.configuration,sale_order:0
+msgid ""
+"Auto directory configuration for Sale Orders and Quotation with report."
+msgstr ""
+
+#. module: document
+#: help:document.directory,type:0
+msgid ""
+"Each directory can either have the type Static or be linked to another "
+"resource. A static directory, as with Operating Systems, is the classic "
+"directory that can contain a set of files. The directories linked to systems "
+"resources automatically possess sub-directories for each of resource types "
+"defined in the parent directory."
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "February"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.open_board_document_manager1
+#: model:ir.ui.menu,name:document.menu_reports_document_manager1
+msgid "Statistics by User"
+msgstr ""
+
+#. module: document
+#: field:document.directory,name:0
+#: field:document.storage,name:0
+msgid "Name"
+msgstr ""
+
+#. module: document
+#: sql_constraint:document.storage:0
+msgid "The storage path must be unique!"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid "Fields"
+msgstr ""
+
+#. module: document
+#: help:document.storage,readonly:0
+msgid "If set, media is for reading only"
+msgstr ""
+
+#. module: document
+#: selection:report.document.user,month:0
+#: selection:report.files.partner,month:0
+msgid "April"
+msgstr ""
+
+#. module: document
+#: field:report.document.file,nbr:0
+#: field:report.document.user,nbr:0
+#: field:report.files.partner,nbr:0
+msgid "# of Files"
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid ""
+"Only members of these groups will have access to this directory and its "
+"files."
+msgstr ""
+
+#. module: document
+#: view:document.directory:0
+msgid ""
+"These groups, however, do NOT apply to children directories, which must "
+"define their own groups."
+msgstr ""
+
+#. module: document
+#: field:document.directory.content.type,mimetype:0
+msgid "Mime Type"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,sequence:0
+msgid "Sequence"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,name:0
+msgid "Content Name"
+msgstr ""
+
+#. module: document
+#: code:addons/document/document.py:226
+#: code:addons/document/document.py:294
+#, python-format
+msgid "File name must be unique!"
+msgstr ""
+
+#. module: document
+#: selection:document.storage,type:0
+msgid "Internal File storage"
+msgstr ""
+
+#. module: document
+#: sql_constraint:document.directory:0
+msgid "Directory must have a parent or a storage"
+msgstr ""
+
+#. module: document
+#: model:ir.actions.act_window,name:document.action_document_directory_tree
+#: model:ir.ui.menu,name:document.menu_document_directories_tree
+msgid "Directories' Structure"
+msgstr ""
+
+#. module: document
+#: view:board.board:0
+#: model:ir.actions.act_window,name:document.action_view_document_by_resourcetype_graph
+#: view:report.document.user:0
+msgid "Files by Resource Type"
+msgstr ""
+
+#. module: document
+#: field:report.document.user,name:0
+#: field:report.files.partner,name:0
+msgid "Year"
+msgstr ""
+
+#. module: document
+#: view:document.storage:0
+#: model:ir.model,name:document.model_document_storage
+#: model:ir.ui.menu,name:document.menu_document_storage_media
+msgid "Storage Media"
+msgstr ""
+
+#. module: document
+#: view:document.storage:0
+msgid "Search Document storage"
+msgstr ""
+
+#. module: document
+#: field:document.directory.content,extension:0
+msgid "Document Type"
+msgstr ""
diff --git a/addons/document/wizard/document_configuration.py b/addons/document/wizard/document_configuration.py
index 3485e7412c7..97eda4e2d62 100644
--- a/addons/document/wizard/document_configuration.py
+++ b/addons/document/wizard/document_configuration.py
@@ -22,26 +22,16 @@
from osv import osv, fields
class document_configuration(osv.osv_memory):
-
_name='document.configuration'
- _description = 'Auto Directory Configuration'
+ _description = 'Directory Configuration'
_inherit = 'res.config'
- _columns = {
- 'sale_order' : fields.boolean('Sale Orders', help="Create virtual folders for Sale Orders and Quotations. One virtual folder will appear for each, in which the latest printed PDF document can be downloaded at any time, and where you can manage (view, add, delete) other attachments."),
- 'product' : fields.boolean('Products', help="Create virtual folders for Products. One virtual folder will appear for each product, where you can manage (view, add, delete) the files attached to the product"),
- 'project': fields.boolean('Projects', help="Create virtual folders for Projects. One virtual folder will appear for each project, where you can manage (view, add, delete) the files attached to the project"),
- }
-
-
def execute(self, cr, uid, ids, context=None):
- conf_id = ids and ids[0] or False
- conf = self.browse(cr, uid, conf_id, context=context)
dir_pool = self.pool.get('document.directory')
data_pool = self.pool.get('ir.model.data')
model_pool = self.pool.get('ir.model')
content_pool = self.pool.get('document.directory.content')
- if conf.sale_order and self.pool.get('sale.order'):
+ if self.pool.get('sale.order'):
# Sale order
dir_data_id = data_pool._get_id(cr, uid, 'document', 'dir_sale_order_all')
if dir_data_id:
@@ -90,7 +80,7 @@ class document_configuration(osv.osv_memory):
})
- if conf.product and self.pool.get('product.product'):
+ if self.pool.get('product.product'):
# Product
dir_data_id = data_pool._get_id(cr, uid, 'document', 'dir_product')
if dir_data_id:
@@ -104,7 +94,7 @@ class document_configuration(osv.osv_memory):
'ressource_type_id': mid[0],
})
- if conf.project and self.pool.get('account.analytic.account'):
+ if self.pool.get('account.analytic.account'):
# Project
dir_data_id = data_pool._get_id(cr, uid, 'document', 'dir_project')
if dir_data_id:
diff --git a/addons/document/wizard/document_configuration_view.xml b/addons/document/wizard/document_configuration_view.xml
index eaba3b7115e..a51a7877e60 100644
--- a/addons/document/wizard/document_configuration_view.xml
+++ b/addons/document/wizard/document_configuration_view.xml
@@ -1,31 +1,27 @@
- Auto Configure Directory
+ Auto Configure Directoriesdocument.configurationform
-
- Virtual Document Folders
-
-
- OpenERP's Document Management System supports mapping virtual folders with documents. The virtual folder of a document can be used to manage the files attached to the document, or to print and download any document report. A few common virtual folders can be created for you automatically from this screen.
-
-
- 12
-
-
+
+ Configure Direcories
+
+
+ OpenERP's Document Management System supports mapping virtual folders with documents. The virtual folder of a document can be used to manage the files attached to the document, or to print and download any report. This tool will create directories automatically according to modules installed.
+
+
+ 12
+
+
-
-
-
-
-
+
@@ -33,7 +29,7 @@
- Document Management System: Configure Virtual Folders
+ Configure Directoriesir.actions.act_windowdocument.configuration
@@ -50,7 +46,6 @@
- automatic
diff --git a/addons/document_ics/document_ics_config_wizard.xml b/addons/document_ics/document_ics_config_wizard.xml
index a751fb2ca6f..0b31eb85d73 100644
--- a/addons/document_ics/document_ics_config_wizard.xml
+++ b/addons/document_ics/document_ics_config_wizard.xml
@@ -21,9 +21,6 @@
15
-
- Configure
-
diff --git a/addons/email_template/wizard/mail_compose_message.py b/addons/email_template/wizard/mail_compose_message.py
index d40f9541b01..61006f96782 100644
--- a/addons/email_template/wizard/mail_compose_message.py
+++ b/addons/email_template/wizard/mail_compose_message.py
@@ -65,7 +65,9 @@ class mail_compose_message(osv.osv_memory):
_columns = {
'use_template': fields.boolean('Use Template'),
- 'template_id': fields.selection(_get_templates, 'Template'),
+ 'template_id': fields.selection(_get_templates, 'Template',
+ size=-1 # means we want an int db column
+ ),
}
def on_change_template(self, cr, uid, ids, use_template, template_id, email_from=None, email_to=None, context=None):
diff --git a/addons/event/i18n/zh_TW.po b/addons/event/i18n/zh_TW.po
index 7e94f517008..ba4b1d3655b 100644
--- a/addons/event/i18n/zh_TW.po
+++ b/addons/event/i18n/zh_TW.po
@@ -7,14 +7,14 @@ msgstr ""
"Project-Id-Version: OpenERP Server 5.0.4\n"
"Report-Msgid-Bugs-To: support@openerp.com\n"
"POT-Creation-Date: 2011-01-11 11:15+0000\n"
-"PO-Revision-Date: 2011-01-28 15:50+0000\n"
+"PO-Revision-Date: 2011-09-27 07:58+0000\n"
"Last-Translator: Walter Cheuk \n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
-"X-Launchpad-Export-Date: 2011-09-05 05:04+0000\n"
-"X-Generator: Launchpad (build 13830)\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:19+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
#. module: event
#: view:event.event:0
@@ -717,7 +717,7 @@ msgstr "八月"
#: field:res.partner,event_ids:0
#: field:res.partner,event_registration_ids:0
msgid "unknown"
-msgstr "不明"
+msgstr "不詳"
#. module: event
#: selection:report.event.registration,month:0
diff --git a/addons/fetchmail/fetchmail.py b/addons/fetchmail/fetchmail.py
index f45b5e955a0..e7f7250458b 100644
--- a/addons/fetchmail/fetchmail.py
+++ b/addons/fetchmail/fetchmail.py
@@ -60,10 +60,9 @@ class fetchmail_server(osv.osv):
'date': fields.datetime('Last Fetch Date', readonly=True),
'user' : fields.char('Username', size=256, required=True, readonly=True, states={'draft':[('readonly', False)]}),
'password' : fields.char('Password', size=1024, required=True, readonly=True, states={'draft':[('readonly', False)]}),
- 'note': fields.text('Description'),
'action_id':fields.many2one('ir.actions.server', 'Server Action', help="Optional custom server action to trigger for each incoming mail, "
"on the record that was created or updated by this mail"),
- 'object_id': fields.many2one('ir.model', "Target document type", required=True, help="Process each incoming mail as part of a conversation "
+ 'object_id': fields.many2one('ir.model', "Create a New Record", required=True, help="Process each incoming mail as part of a conversation "
"corresponding to this document type. This will create "
"new documents for new conversations, or attach follow-up "
"emails to the existing conversations (documents)."),
@@ -73,6 +72,7 @@ class fetchmail_server(osv.osv):
}
_defaults = {
'state': "draft",
+ 'type': "pop",
'active': True,
'priority': 5,
'attach': True,
diff --git a/addons/fetchmail/fetchmail_installer_view.xml b/addons/fetchmail/fetchmail_installer_view.xml
index 911ad8101da..b5bd7df80ca 100644
--- a/addons/fetchmail/fetchmail_installer_view.xml
+++ b/addons/fetchmail/fetchmail_installer_view.xml
@@ -1,18 +1,19 @@
-
- Setup Incoming Mail Server (fetchmail)
- ir.actions.act_window
- fetchmail.server
- form
- tree,form
-
-
+
+ Setup Incoming Mail Servers
+ ir.actions.act_window
+ fetchmail.server
+ form
+ tree,form
+
+ You can connect OpenERP to your incoming mail server so that documents (leads, tasks, issues, etc) are synchronized automatically with your incoming emails.
+
-
-
-
- 4
+
+
+
+ 4
diff --git a/addons/fetchmail/fetchmail_view.xml b/addons/fetchmail/fetchmail_view.xml
index 05f62f4b9fb..61992629b2a 100644
--- a/addons/fetchmail/fetchmail_view.xml
+++ b/addons/fetchmail/fetchmail_view.xml
@@ -26,7 +26,7 @@
+
+
+
+
+ Employees Structurehr.employee
@@ -149,13 +212,27 @@
Employeeshr.employeeform
- tree,form
+ tree,form,kanban[]{"search_default_department_id": department_id,"search_default_active":eval('True')}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.
+
+
+
+ tree
+
+
+
+
+
+
+ form
+
+
+
diff --git a/addons/hr_attendance/report/attendance_by_month.py b/addons/hr_attendance/report/attendance_by_month.py
index 2b708434317..80646be85f4 100644
--- a/addons/hr_attendance/report/attendance_by_month.py
+++ b/addons/hr_attendance/report/attendance_by_month.py
@@ -30,9 +30,10 @@ from report.interface import toxml
from report import report_sxw
from tools import ustr
+from tools.translate import _
one_day = relativedelta(days=1)
-month2name = [0, 'January', 'February', 'March', 'April', 'May', 'Jun', 'July', 'August', 'September', 'October', 'November', 'December']
+month2name = [0, 'January', 'February', 'March', 'April', 'May', 'June', 'July', 'August', 'September', 'October', 'November', 'December']
def hour2str(h):
hours = int(h)
@@ -52,7 +53,7 @@ class report_custom(report_rml):
context = {}
month = datetime(datas['form']['year'], datas['form']['month'], 1)
emp_ids = context.get('active_ids', [])
- user_xml = ['%s' % month2name[month.month], '%s' % month.year]
+ user_xml = ['%s' % _(month2name[month.month]), '%s' % month.year]
if emp_ids:
for emp in obj_emp.read(cr, uid, emp_ids, ['name']):
stop, days_xml = False, []
@@ -95,7 +96,7 @@ class report_custom(report_rml):
days_xml.append(today_xml)
today, tomor = tomor, tomor + one_day
user_xml.append(user_repr % '\n'.join(days_xml))
-
+
rpt_obj = pooler.get_pool(cr.dbname).get('hr.employee')
rml_obj=report_sxw.rml_parse(cr, uid, rpt_obj._name,context)
header_xml = '''
@@ -104,7 +105,7 @@ class report_custom(report_rml):
%s
''' % (str(rml_obj.formatLang(time.strftime("%Y-%m-%d"),date=True))+' ' + str(time.strftime("%H:%M")),pooler.get_pool(cr.dbname).get('res.users').browse(cr,uid,uid).company_id.name)
-
+
first_date = str(month)
som = datetime.strptime(first_date, '%Y-%m-%d %H:%M:%S')
eom = som + timedelta(int(dy)-1)
@@ -113,12 +114,12 @@ class report_custom(report_rml):
cell=1
date_xml.append('')
if day_diff.days>=30:
- date_xml += ['' % (x, som.replace(day=x).strftime('%a'),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
+ date_xml += ['' % (x, _(som.replace(day=x).strftime('%a')),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
else:
if day_diff.days>=(lengthmonth(som.year, som.month)-som.day):
- date_xml += ['' % (x, som.replace(day=x).strftime('%a'),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
+ date_xml += ['' % (x, _(som.replace(day=x).strftime('%a')),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
else:
- date_xml += ['' % (x, som.replace(day=x).strftime('%a'),x-som.day+1) for x in range(som.day, eom.day+1)]
+ date_xml += ['' % (x, _(som.replace(day=x).strftime('%a')),x-som.day+1) for x in range(som.day, eom.day+1)]
cell=x-som.day+1
day_diff1=day_diff.days-cell+1
width_dict={}
@@ -129,12 +130,12 @@ class report_custom(report_rml):
month=som.month
month_dict[j]=som.strftime('%B')
width_dict[j]=cell
-
+
while day_diff1>0:
if month+i<=12:
if day_diff1 > lengthmonth(year,i+month): # Not on 30 else you have problems when entering 01-01-2009 for example
som1=datetime.date(year,month+i,1)
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, lengthmonth(year,i+month)+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, lengthmonth(year,i+month)+1)]
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
@@ -142,7 +143,7 @@ class report_custom(report_rml):
width_dict[j]=x
else:
som1=datetime.date(year,month+i,1)
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, eom.day+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, eom.day+1)]
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
@@ -156,7 +157,7 @@ class report_custom(report_rml):
i=1
if day_diff1>=30:
som1=datetime.date(years,i,1)
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, lengthmonth(years,i)+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, lengthmonth(years,i)+1)]
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
@@ -167,7 +168,7 @@ class report_custom(report_rml):
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, eom.day+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, eom.day+1)]
cell=cell+x
width_dict[j]=x
day_diff1=day_diff1-x
@@ -176,10 +177,11 @@ class report_custom(report_rml):
xml = '''
%s
+ %s
%s
%s
- ''' % (header_xml,'\n'.join(user_xml),date_xml)
+ ''' % (header_xml,_('Attendances By Month'),'\n'.join(user_xml),date_xml)
return xml
report_custom('report.hr.attendance.bymonth', 'hr.employee', '', 'addons/hr_attendance/report/bymonth.xsl')
diff --git a/addons/hr_attendance/report/bymonth.xsl b/addons/hr_attendance/report/bymonth.xsl
index 23e7fb14b3d..0ec0a23cc8d 100644
--- a/addons/hr_attendance/report/bymonth.xsl
+++ b/addons/hr_attendance/report/bymonth.xsl
@@ -12,6 +12,7 @@
+
@@ -29,7 +30,7 @@
- Attendances By Month
+ week
@@ -53,7 +54,14 @@
-
+
+
+
+
+
+
+
+
diff --git a/addons/hr_attendance/wizard/hr_attendance_sign_in_out.py b/addons/hr_attendance/wizard/hr_attendance_sign_in_out.py
index 7a51c2b9e1e..2631139b38d 100644
--- a/addons/hr_attendance/wizard/hr_attendance_sign_in_out.py
+++ b/addons/hr_attendance/wizard/hr_attendance_sign_in_out.py
@@ -29,7 +29,7 @@ class hr_si_so_ask(osv.osv_memory):
_columns = {
'name': fields.char('Employees name', size=32, required=True, readonly=True),
'last_time': fields.datetime('Your last sign out', required=True),
- 'emp_id': fields.char('Empoyee ID', size=32, required=True, readonly=True),
+ 'emp_id': fields.many2one('hr.employee', 'Empoyee ID', readonly=True),
}
def _get_empname(self, cr, uid, context=None):
@@ -52,10 +52,12 @@ class hr_si_so_ask(osv.osv_memory):
def sign_in(self, cr, uid, ids, context=None):
data = self.read(cr, uid, ids, [], context=context)[0]
+ data['emp_id'] = data['emp_id'] and data['emp_id'][0]
return self.pool.get('hr.sign.in.out').sign_in(cr, uid, data, context)
def sign_out(self, cr, uid, ids, context=None):
data = self.read(cr, uid, ids, [], context=context)[0]
+ data['emp_id'] = data['emp_id'] and data['emp_id'][0]
return self.pool.get('hr.sign.in.out').sign_out(cr, uid, data, context)
hr_si_so_ask()
@@ -68,7 +70,7 @@ class hr_sign_in_out(osv.osv_memory):
_columns = {
'name': fields.char('Employees name', size=32, required=True, readonly=True),
'state': fields.char('Current state', size=32, required=True, readonly=True),
- 'emp_id': fields.char('Employee ID', size=32, required=True, readonly=True),
+ 'emp_id': fields.many2one('hr.employee', 'Empoyee ID', readonly=True),
}
def _get_empid(self, cr, uid, context=None):
@@ -88,6 +90,7 @@ class hr_sign_in_out(osv.osv_memory):
obj_model = self.pool.get('ir.model.data')
att_obj = self.pool.get('hr.attendance')
data = self.read(cr, uid, ids, [], context=context)[0]
+ data['emp_id'] = data['emp_id'] and data['emp_id'][0]
emp_id = data['emp_id']
att_id = att_obj.search(cr, uid, [('employee_id', '=', emp_id)], limit=1, order='name desc')
last_att = att_obj.browse(cr, uid, att_id, context=context)
@@ -113,6 +116,7 @@ class hr_sign_in_out(osv.osv_memory):
obj_model = self.pool.get('ir.model.data')
att_obj = self.pool.get('hr.attendance')
data = self.read(cr, uid, ids, [], context=context)[0]
+ data['emp_id'] = data['emp_id'] and data['emp_id'][0]
emp_id = data['emp_id']
att_id = att_obj.search(cr, uid, [('employee_id', '=', emp_id),('action', '!=', 'action')], limit=1, order='name desc')
last_att = att_obj.browse(cr, uid, att_id, context=context)
diff --git a/addons/hr_evaluation/__openerp__.py b/addons/hr_evaluation/__openerp__.py
index 95ef4512d5c..6deba41c05f 100644
--- a/addons/hr_evaluation/__openerp__.py
+++ b/addons/hr_evaluation/__openerp__.py
@@ -39,7 +39,7 @@ level of employee hierarchy fills what and final review and evaluation
is done by the manager.Every evaluation filled by the employees can be viewed
in the form of pdf file. Implements a dashboard for My Current Evaluations
""",
- "demo": ["hr_evaluation_demo.xml", ],
+ "demo": [],
"data": [
"security/ir.model.access.csv",
"security/hr_evaluation_security.xml",
diff --git a/addons/hr_evaluation/hr_evaluation.py b/addons/hr_evaluation/hr_evaluation.py
index d79cf90b915..03ff1692009 100644
--- a/addons/hr_evaluation/hr_evaluation.py
+++ b/addons/hr_evaluation/hr_evaluation.py
@@ -39,6 +39,8 @@ class hr_evaluation_plan(osv.osv):
}
_defaults = {
'active': True,
+ 'month_first': 6,
+ 'month_next': 12,
'company_id': lambda s,cr,uid,c: s.pool.get('res.company')._company_default_get(cr, uid, 'account.account', context=c),
}
hr_evaluation_plan()
diff --git a/addons/hr_evaluation/hr_evaluation_data.xml b/addons/hr_evaluation/hr_evaluation_data.xml
index a83caa71173..b69671f2343 100644
--- a/addons/hr_evaluation/hr_evaluation_data.xml
+++ b/addons/hr_evaluation/hr_evaluation_data.xml
@@ -593,5 +593,636 @@ Once the form had been filled, the employee send it to his supervisor.
+
+
+ Employee Opinion
+ 20
+
+
+
+ 5
+
+
+ Process
+
+
+
+
+ Survey
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Employee Details
+
+ multiple_textboxes_diff_type
+ The comment you entered is in an invalid format.
+
+
+
+ Other
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Engagement
+
+ matrix_of_choices_only_one_ans
+ The comment you entered is in an invalid format.
+
+
+
+ Other
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Leadership
+
+ matrix_of_choices_only_one_ans
+
+
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Effectiveness
+
+ matrix_of_choices_only_one_ans
+ The comment you entered is in an invalid format.
+
+
+
+ Other
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Continuous Improvement
+
+ matrix_of_choices_only_one_ans
+ The comment you entered is in an invalid format.
+
+
+
+ Other
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Openness
+
+ matrix_of_choices_only_one_ans
+ The comment you entered is in an invalid format.
+
+
+
+ Other
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Miscellaneous
+
+ matrix_of_choices_only_one_ans
+ The comment you entered is in an invalid format.
+
+
+
+ Other
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ Additional comments :
+
+ comment
+ The comment you entered is in an invalid format.
+
+
+
+ Other
+
+
+
+
+ 1
+ do_not_validate
+ do_not_validate
+ Please enter a comment.
+ The choices need to add up to [enter sum here].
+
+ The comment you entered is in an invalid format.
+
+ This question requires an answer.
+
+ At the supervisor's appraisal date
+
+ descriptive_text
+ The comment you entered is in an invalid format.
+ * His direct reports will be invited through OpenERP to express a feedback on their supervisor's leadership and to give their opinion about their own engagement and effectiveness, the continuous improvement and openness in action in the company, ...
+
+* The employees will send back their anonymous answers to OpenERP. The data will be handled by the HR manager and a brief summary of the data will be sent to the concerned supervisor, to his team and to the supervisor's supervisor.
+* The appraiser should rate the employee’s major work accomplishments and performance according to the metric provided below :
+
+ 1 - Significantly exceeds standards and expectations required of the position
+ 2 - Exceeds standards and expectations
+ 3 - Meet standards and expectations
+ 4 - Did not meet standards and expectations
+ 5 - Significantly below standards and expectations
+
+
+
+ Other
+
+
+
+
+ 1
+ 1
+ 1
+
+
+
+ 1
+ 1
+ 2
+
+
+
+ 1
+ 1
+ 3
+
+
+
+ 1
+ 1
+ 4
+
+
+
+ 1
+ 1
+ 5
+
+
+
+ 1
+ 1
+ 1
+
+
+
+ 1
+ 1
+ 2
+
+
+
+ 1
+ 1
+ 3
+
+
+
+ 1
+ 1
+ 4
+
+
+
+ 1
+ 1
+ 5
+
+
+
+ 1
+ 1
+ 1
+
+
+
+ 1
+ 1
+ 2
+
+
+
+ 1
+ 1
+ 3
+
+
+
+ 1
+ 1
+ 4
+
+
+
+ 1
+ 1
+ 5
+
+
+
+ 1
+ 1
+ 1
+
+
+
+ 1
+ 1
+ 2
+
+
+
+ 1
+ 1
+ 3
+
+
+
+ 1
+ 1
+ 4
+
+
+
+ 1
+ 1
+ 5
+
+
+
+ 1
+ 1
+ 1
+
+
+
+ 1
+ 1
+ 2
+
+
+
+ 1
+ 1
+ 3
+
+
+
+ 1
+ 1
+ 4
+
+
+
+ 1
+ 1
+ 5
+
+
+
+ 1
+ 1
+ 1
+
+
+
+ 1
+ 1
+ 2
+
+
+
+ 1
+ 1
+ 3
+
+
+
+ 1
+ 1
+ 4
+
+
+
+ 1
+ 1
+ 5
+
+
+
+ 1
+ Demonstrates genuine concern for me as a person.
+
+
+
+
+ 1
+ I'm efficient at work and my achievements are successful.
+
+
+
+
+ 1
+ I am proud to tell others I work here.
+
+
+
+
+ 0
+ Name of your direct supervisor
+
+ char
+
+
+
+ 1
+ Actions by Executive management show genuine interest in the well-being of employees.
+
+
+
+
+ 1
+ I know the company's values and live them.
+
+
+
+
+ 1
+ My work contributes towards the continuous improvement of the company, our services or products.
+
+
+
+
+ 1
+ I have enough work.
+
+
+
+
+ 0
+ Date
+
+ datetime
+
+
+
+ 1
+ I consistently acquire new knowledge, skills or understanding through contact with my supervisor. He helps me growing my compete
+
+
+
+
+ 1
+ My job provides me with a sense of personal accomplishment.
+
+
+
+
+ 1
+ What I did several months ago is still of use to the company, the services or the products today.
+
+
+
+
+ 1
+ My best achievements have been communicated to the community, internally or to customers.
+
+
+
+
+ 1
+ I have the same opportunity to succeed as others with similar experiences, performance and educational background.
+
+
+
+
+ 1
+ Compared to similar jobs in other companies where I could work, my total compensation is:
+(Scale: Well below others, Below othe
+
+
+
+
+ 1
+ Overall, I believe the quality of products and/or services my workgroup delivers is improving.
+
+
+
+
+ 1
+ I would prefer to remain with this company even if a comparable job were available in another company.
+
+
+
+
+ 1
+ Listens and takes into account all ideas and do his best to put in place the best of these.
+
+
+
+
+ 1
+ I mostly work on value-added tasks for the company, the products or the services. (Value-added task : significant improvement pe
+
+
+
+
+ 1
+ Our workgroup identifies and reduces waste of time in our activities and processes.
+
+
+
+
+ 1
+ Taking everything into account, how satisfied are you with your current job?
+
+
+
+
+ 1
+ I understand the company strategy and how my workgroup supports it.
+
+
+
+
+ 1
+ I am willing to put in a great deal of effort beyond what is expected to help my workgroup succeed.
+
+
+
+
+ 1
+ I believe the information that I get from the person I report to.
+
+
+
+
+
+
+
+
+ Manager's Evaluation Plan
+
+
+
+
+
+
+
+
+ Send to Subordinates
+
+
+
+ bottom-up
+
+
+
+
+
+
+
+
+ Send to Managers
+
+
+
+ top-down
+
+
+
+
+
+
+
+
+ Send to Employee
+
+
+
+ self
+
+
+
+
+
+
+
+
+ Final Interview With Manager
+
+
+
+ final
+
+
+
+
+
+
+
+
+
+
+ Run Employee Evaluation
+
+
+ 1
+ days
+ -1
+
+
+
+
+
+
diff --git a/addons/hr_evaluation/hr_evaluation_demo.xml b/addons/hr_evaluation/hr_evaluation_demo.xml
deleted file mode 100644
index a7be585272f..00000000000
--- a/addons/hr_evaluation/hr_evaluation_demo.xml
+++ /dev/null
@@ -1,857 +0,0 @@
-
-
-
-
-
- Employee Opinion
- 20
-
-
-
- 5
-
-
-
-
-
- Process
-
-
-
-
-
-
-
- Survey
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Employee Details
-
- multiple_textboxes_diff_type
- The comment you entered is in an invalid format.
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Engagement
-
- matrix_of_choices_only_one_ans
- The comment you entered is in an invalid format.
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Leadership
-
- matrix_of_choices_only_one_ans
-
-
-
-
-
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Effectiveness
-
- matrix_of_choices_only_one_ans
- The comment you entered is in an invalid format.
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Continuous Improvement
-
- matrix_of_choices_only_one_ans
- The comment you entered is in an invalid format.
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Openness
-
- matrix_of_choices_only_one_ans
- The comment you entered is in an invalid format.
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Miscellaneous
-
- matrix_of_choices_only_one_ans
- The comment you entered is in an invalid format.
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- Additional comments :
-
- comment
- The comment you entered is in an invalid format.
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- do_not_validate
- do_not_validate
- Please enter a comment.
- The choices need to add up to [enter sum here].
-
- The comment you entered is in an invalid format.
-
- This question requires an answer.
-
- At the supervisor's appraisal date
-
- descriptive_text
- The comment you entered is in an invalid format.
- * His direct reports will be invited through OpenERP to express a feedback on their supervisor's leadership and to give their opinion about their own engagement and effectiveness, the continuous improvement and openness in action in the company, ...
-
-* The employees will send back their anonymous answers to OpenERP. The data will be handled by the HR manager and a brief summary of the data will be sent to the concerned supervisor, to his team and to the supervisor's supervisor.
-* The appraiser should rate the employee’s major work accomplishments and performance according to the metric provided below :
-
- 1 - Significantly exceeds standards and expectations required of the position
- 2 - Exceeds standards and expectations
- 3 - Meet standards and expectations
- 4 - Did not meet standards and expectations
- 5 - Significantly below standards and expectations
-
-
-
- Other
-
-
-
-
-
-
-
- 1
- 1
- 1
-
-
-
-
-
-
- 1
- 1
- 2
-
-
-
-
-
-
- 1
- 1
- 3
-
-
-
-
-
-
- 1
- 1
- 4
-
-
-
-
-
-
- 1
- 1
- 5
-
-
-
-
-
-
- 1
- 1
- 1
-
-
-
-
-
-
- 1
- 1
- 2
-
-
-
-
-
-
- 1
- 1
- 3
-
-
-
-
-
-
- 1
- 1
- 4
-
-
-
-
-
-
- 1
- 1
- 5
-
-
-
-
-
-
- 1
- 1
- 1
-
-
-
-
-
-
- 1
- 1
- 2
-
-
-
-
-
-
- 1
- 1
- 3
-
-
-
-
-
-
- 1
- 1
- 4
-
-
-
-
-
-
- 1
- 1
- 5
-
-
-
-
-
-
- 1
- 1
- 1
-
-
-
-
-
-
- 1
- 1
- 2
-
-
-
-
-
-
- 1
- 1
- 3
-
-
-
-
-
-
- 1
- 1
- 4
-
-
-
-
-
-
- 1
- 1
- 5
-
-
-
-
-
-
- 1
- 1
- 1
-
-
-
-
-
-
- 1
- 1
- 2
-
-
-
-
-
-
- 1
- 1
- 3
-
-
-
-
-
-
- 1
- 1
- 4
-
-
-
-
-
-
- 1
- 1
- 5
-
-
-
-
-
-
- 1
- 1
- 1
-
-
-
-
-
-
- 1
- 1
- 2
-
-
-
-
-
-
- 1
- 1
- 3
-
-
-
-
-
-
- 1
- 1
- 4
-
-
-
-
-
-
- 1
- 1
- 5
-
-
-
-
-
-
- 1
- Demonstrates genuine concern for me as a person.
-
-
-
-
-
-
-
- 1
- I'm efficient at work and my achievements are successful.
-
-
-
-
-
-
-
- 1
- I am proud to tell others I work here.
-
-
-
-
-
-
-
- 0
- Name of your direct supervisor
-
- char
-
-
-
-
-
-
- 1
- Actions by Executive management show genuine interest in the well-being of employees.
-
-
-
-
-
-
-
- 1
- I know the company's values and live them.
-
-
-
-
-
-
-
- 1
- My work contributes towards the continuous improvement of the company, our services or products.
-
-
-
-
-
-
-
- 1
- I have enough work.
-
-
-
-
-
-
-
- 0
- Date
-
- datetime
-
-
-
-
-
-
- 1
- I consistently acquire new knowledge, skills or understanding through contact with my supervisor. He helps me growing my compete
-
-
-
-
-
-
-
- 1
- My job provides me with a sense of personal accomplishment.
-
-
-
-
-
-
-
- 1
- What I did several months ago is still of use to the company, the services or the products today.
-
-
-
-
-
-
-
- 1
- My best achievements have been communicated to the community, internally or to customers.
-
-
-
-
-
-
-
- 1
- I have the same opportunity to succeed as others with similar experiences, performance and educational background.
-
-
-
-
-
-
-
- 1
- Compared to similar jobs in other companies where I could work, my total compensation is:
-(Scale: Well below others, Below othe
-
-
-
-
-
-
-
- 1
- Overall, I believe the quality of products and/or services my workgroup delivers is improving.
-
-
-
-
-
-
-
- 1
- I would prefer to remain with this company even if a comparable job were available in another company.
-
-
-
-
-
-
-
- 1
- Listens and takes into account all ideas and do his best to put in place the best of these.
-
-
-
-
-
-
-
- 1
- I mostly work on value-added tasks for the company, the products or the services. (Value-added task : significant improvement pe
-
-
-
-
-
-
-
- 1
- Our workgroup identifies and reduces waste of time in our activities and processes.
-
-
-
-
-
-
-
- 1
- Taking everything into account, how satisfied are you with your current job?
-
-
-
-
-
-
-
- 1
- I understand the company strategy and how my workgroup supports it.
-
-
-
-
-
-
-
-
- 1
- I am willing to put in a great deal of effort beyond what is expected to help my workgroup succeed.
-
-
-
-
-
-
-
- 1
- I believe the information that I get from the person I report to.
-
-
-
-
-
-
-
-
-
- Manager's Evaluation Plan
-
-
-
-
-
-
-
-
- Send to Subordinates
-
-
-
- bottom-up
-
-
-
-
-
-
-
-
-
-
-
- Send to Managers
-
-
-
- top-down
-
-
-
-
-
-
-
-
-
-
-
- Send to Employee
-
-
-
- self
-
-
-
-
-
-
-
-
-
-
-
- Final Interview With Manager
-
-
-
- final
-
-
-
-
-
-
-
-
-
-
- Run Employee Evaluation
-
-
- 1
- minutes
- -1
-
-
-
-
-
-
- Employee Evaluation
-
- [('employee_id.user_id','=',user.id)]
-
-
-
- Manager Evaluation
-
- ['|',('employee_id.user_id','=',user.id),('employee_id.parent_id.user_id','=',user.id )]
-
-
-
-
-
diff --git a/addons/hr_evaluation/hr_evaluation_installer.xml b/addons/hr_evaluation/hr_evaluation_installer.xml
index 4ef0013a4c2..842363559a9 100644
--- a/addons/hr_evaluation/hr_evaluation_installer.xml
+++ b/addons/hr_evaluation/hr_evaluation_installer.xml
@@ -6,7 +6,7 @@
ir.actions.act_windowhr_evaluation.planform
- form,tree
+ tree,form
diff --git a/addons/hr_expense/hr_expense_installer_view.xml b/addons/hr_expense/hr_expense_installer_view.xml
index a5c378238a6..bdb5fdedcb4 100644
--- a/addons/hr_expense/hr_expense_installer_view.xml
+++ b/addons/hr_expense/hr_expense_installer_view.xml
@@ -24,6 +24,7 @@
[('hr_expense_ok','=',True)]
+ Define one product for each expense type allowed for an employee (travel by car, hostel, restaurant, etc). If you reimburse the employees at a fixed rate, set a cost and a unit of measure on the product. If you reimburse based on real costs, set the cost at 0.00. The user will set the real price when recording his expense sheet.
diff --git a/addons/hr_holidays/hr_holidays.py b/addons/hr_holidays/hr_holidays.py
index 2dcb448d3cf..77cd53551b8 100644
--- a/addons/hr_holidays/hr_holidays.py
+++ b/addons/hr_holidays/hr_holidays.py
@@ -358,12 +358,24 @@ class hr_employee(osv.osv):
leave_id = holiday_obj.create(cr, uid, {'name': _('Leave Request for %s') % employee.name, 'employee_id': employee.id, 'holiday_status_id': status_id, 'type': 'remove', 'holiday_type': 'employee', 'number_of_days_temp': abs(diff)}, context=context)
else:
return False
- holiday_obj.holidays_confirm(cr, uid, [leave_id])
- holiday_obj.holidays_validate2(cr, uid, [leave_id])
+ wf_service = netsvc.LocalService("workflow")
+ wf_service.trg_validate(uid, 'hr.holidays', leave_id, 'confirm', cr)
+ wf_service.trg_validate(uid, 'hr.holidays', leave_id, 'validate', cr)
+ wf_service.trg_validate(uid, 'hr.holidays', leave_id, 'second_validate', cr)
return True
def _get_remaining_days(self, cr, uid, ids, name, args, context=None):
- cr.execute("SELECT sum(h.number_of_days_temp) as days, h.employee_id from hr_holidays h join hr_holidays_status s on (s.id=h.holiday_status_id) where h.type='add' and h.state='validate' and s.limit=False group by h.employee_id")
+ cr.execute("""SELECT
+ sum(h.number_of_days) as days,
+ h.employee_id
+ from
+ hr_holidays h
+ join hr_holidays_status s on (s.id=h.holiday_status_id)
+ where
+ h.state='validate' and
+ s.limit=False and
+ h.employee_id in (%s)
+ group by h.employee_id"""% (','.join(map(str,ids)),) )
res = cr.dictfetchall()
remaining = {}
for r in res:
@@ -373,11 +385,10 @@ class hr_employee(osv.osv):
remaining[employee_id] = 0.0
return remaining
-
_columns = {
- 'remaining_leaves': fields.function(_get_remaining_days, string='Remaining Legal Leaves', fnct_inv=_set_remaining_days, type="float", help='Total number of legal leaves allocated to this employee, change this value to create allocation/leave requests.', store=True),
+ 'remaining_leaves': fields.function(_get_remaining_days, string='Remaining Legal Leaves', fnct_inv=_set_remaining_days, type="float", help='Total number of legal leaves allocated to this employee, change this value to create allocation/leave requests.'),
}
hr_employee()
-# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
\ No newline at end of file
+# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
diff --git a/addons/hr_holidays/hr_holidays_view.xml b/addons/hr_holidays/hr_holidays_view.xml
index 80a33b0b72c..b6d6a64ed26 100644
--- a/addons/hr_holidays/hr_holidays_view.xml
+++ b/addons/hr_holidays/hr_holidays_view.xml
@@ -10,7 +10,7 @@
-
+
@@ -21,8 +21,6 @@
-
-
@@ -145,7 +143,7 @@
hr.holidaystree
-
+
@@ -225,7 +223,7 @@
hr.holidaystree
-
+
@@ -314,7 +312,7 @@
formtree,form
- {'search_default_my_leaves': 1, 'search_default_group_type': 1}
+ {'search_default_my_leaves': 1, 'search_default_group_type': 1, 'search_default_validated': 1}[('holiday_type','=','employee')]
@@ -437,7 +435,7 @@
hr.employeetree
-
+
@@ -451,13 +449,14 @@
formtree,form
+ You can assign remaining Legal Leaves for each employee, OpenERP will automatically create and validate allocation requests.
-
-
+
+
@@ -467,7 +466,7 @@
-
+
diff --git a/addons/hr_holidays/report/holidays_summary_report.py b/addons/hr_holidays/report/holidays_summary_report.py
index dd0bd91a0d0..d756dfe6dfd 100644
--- a/addons/hr_holidays/report/holidays_summary_report.py
+++ b/addons/hr_holidays/report/holidays_summary_report.py
@@ -30,6 +30,7 @@ import pooler
import time
from report import report_sxw
from tools import ustr
+from tools.translate import _
def lengthmonth(year, month):
if month == 2 and ((year % 4 == 0) and ((year % 100 != 0) or (year % 400 == 0))):
@@ -69,9 +70,9 @@ def emp_create_xml(self, cr, uid, dept, holiday_type, row_id, empid, name, som,
for index in range(1,61):
display[index]=' '
count=''
-
+
data_xml=['' % (row_id,x,display[x]) for x in range(1,len(display)+1) ]
-
+
# Computing the xml
xml = '''
%s
@@ -120,18 +121,17 @@ class report_custom(report_rml):
# date_xml=[]
for l in range(0,len(legend)):
- date_xml += ['' % (l+1,legend[l][0],legend[l][1],legend[l][2])]
-
+ date_xml += ['' % (l+1,legend[l][0],_(legend[l][1]),legend[l][2])]
date_xml += ['' % (som.strftime('%B'), som.year),'']
cell=1
if day_diff.days>=30:
- date_xml += ['' % (x, som.replace(day=x).strftime('%a'),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
+ date_xml += ['' % (x, _(som.replace(day=x).strftime('%a')),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
else:
if day_diff.days>=(lengthmonth(som.year, som.month)-som.day):
- date_xml += ['' % (x, som.replace(day=x).strftime('%a'),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
+ date_xml += ['' % (x, _(som.replace(day=x).strftime('%a')),x-som.day+1) for x in range(som.day, lengthmonth(som.year, som.month)+1)]
else:
- date_xml += ['' % (x, som.replace(day=x).strftime('%a'),x-som.day+1) for x in range(som.day, eom.day+1)]
+ date_xml += ['' % (x, _(som.replace(day=x).strftime('%a')),x-som.day+1) for x in range(som.day, eom.day+1)]
cell=x-som.day+1
day_diff1=day_diff.days-cell+1
@@ -150,7 +150,7 @@ class report_custom(report_rml):
if month+i<=12:
if day_diff1 > lengthmonth(year,i+month): # Not on 30 else you have problems when entering 01-01-2009 for example
som1=datetime.date(year,month+i,1)
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, lengthmonth(year,i+month)+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, lengthmonth(year,i+month)+1)]
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
@@ -159,7 +159,7 @@ class report_custom(report_rml):
else:
som1=datetime.date(year,month+i,1)
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, eom.day+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, eom.day+1)]
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
@@ -174,7 +174,7 @@ class report_custom(report_rml):
i=1
if day_diff1>=30:
som1=datetime.date(years,i,1)
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, lengthmonth(years,i)+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, lengthmonth(years,i)+1)]
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
@@ -186,7 +186,7 @@ class report_custom(report_rml):
i=i+1
j=j+1
month_dict[j]=som1.strftime('%B')
- date_xml += ['' % (x, som1.replace(day=x).strftime('%a'),cell+x) for x in range(1, eom.day+1)]
+ date_xml += ['' % (x, _(som1.replace(day=x).strftime('%a')),cell+x) for x in range(1, eom.day+1)]
cell=cell+x
width_dict[j]=x
@@ -200,16 +200,16 @@ class report_custom(report_rml):
st+=',' + str(0.4 *width_dict[m])+'cm'
st+=',0.4cm\n'
- months_xml =['' % (x,month_dict[x]) for x in range(1,len(month_dict)+1) ]
+ months_xml =['' % (x, _(month_dict[x])) for x in range(1,len(month_dict)+1) ]
months_xml.append(st)
-
+
emp_xml=''
row_id=1
-
+
if data['model']=='hr.employee':
for id in data['form']['emp']:
items = obj_emp.read(cr, uid, id, ['id','name'])
-
+
emp_xml += emp_create_xml(self, cr, uid, 0, holiday_type, row_id, items['id'], items['name'], som, eom)
row_id = row_id +1
@@ -229,7 +229,7 @@ class report_custom(report_rml):
dept_done=1
emp_xml += emp_create_xml(self, cr, uid, 0, holiday_type, row_id, item['id'], item['name'], som, eom)
row_id = row_id +1
-
+
header_xml = '''
%s
diff --git a/addons/hr_recruitment/hr_recruitment.py b/addons/hr_recruitment/hr_recruitment.py
index 77a1bcb7b8f..e2ecf522cae 100644
--- a/addons/hr_recruitment/hr_recruitment.py
+++ b/addons/hr_recruitment/hr_recruitment.py
@@ -180,6 +180,7 @@ class hr_applicant(crm.crm_case, osv.osv):
multi='day_open', type="float", store=True),
'day_close': fields.function(_compute_day, string='Days to Close', \
multi='day_close', type="float", store=True),
+ 'color': fields.integer('Color Index'),
}
def _get_stage(self, cr, uid, context=None):
@@ -194,6 +195,7 @@ class hr_applicant(crm.crm_case, osv.osv):
'priority': lambda *a: '',
'company_id': lambda s, cr, uid, c: s.pool.get('res.company')._company_default_get(cr, uid, 'crm.helpdesk', context=c),
'priority': lambda *a: crm.AVAILABLE_PRIORITIES[2][0],
+ 'color': 0,
}
def onchange_job(self,cr, uid, ids, job, context=None):
@@ -442,6 +444,21 @@ class hr_applicant(crm.crm_case, osv.osv):
res = super(hr_applicant, self).case_reset(cr, uid, ids, *args)
self.write(cr, uid, ids, {'date_open': False, 'date_closed': False})
return res
+
+ def set_priority(self, cr, uid, ids, priority):
+ """Set lead priority
+ """
+ return self.write(cr, uid, ids, {'priority' : priority})
+
+ def set_high_priority(self, cr, uid, ids, *args):
+ """Set lead priority to high
+ """
+ return self.set_priority(cr, uid, ids, '1')
+
+ def set_normal_priority(self, cr, uid, ids, *args):
+ """Set lead priority to normal
+ """
+ return self.set_priority(cr, uid, ids, '3')
def write(self, cr, uid, ids, vals, context=None):
if 'stage_id' in vals and vals['stage_id']:
diff --git a/addons/hr_recruitment/hr_recruitment_menu.xml b/addons/hr_recruitment/hr_recruitment_menu.xml
index 9883e311fba..0bac3f8615a 100644
--- a/addons/hr_recruitment/hr_recruitment_menu.xml
+++ b/addons/hr_recruitment/hr_recruitment_menu.xml
@@ -6,7 +6,7 @@
Applicantshr.applicant
- tree,form,graph,calendar
+ tree,form,graph,calendar,kanban{"search_default_user_id":uid, 'search_default_current': 1,"search_default_department_id": department_id}
diff --git a/addons/hr_recruitment/hr_recruitment_view.xml b/addons/hr_recruitment/hr_recruitment_view.xml
index 8dd5e171206..e5905b16a77 100644
--- a/addons/hr_recruitment/hr_recruitment_view.xml
+++ b/addons/hr_recruitment/hr_recruitment_view.xml
@@ -277,7 +277,81 @@
+
+
+ Hr Applicants kanban
+ hr.applicant
+ kanban
+
+
+
+
+
+
-
+
@@ -300,7 +300,7 @@
-
+
diff --git a/addons/mail/mail_installer.xml b/addons/mail/mail_installer.xml
index 3faf5fad630..022bff6e53b 100644
--- a/addons/mail/mail_installer.xml
+++ b/addons/mail/mail_installer.xml
@@ -2,11 +2,11 @@
- Configure Email Server
+ Configure Email Serversir.actions.act_windowir.mail_serverform
- form
+ tree,form
diff --git a/addons/mail/wizard/mail_compose_message.py b/addons/mail/wizard/mail_compose_message.py
index 0bfaf06890a..93bf0b004d8 100644
--- a/addons/mail/wizard/mail_compose_message.py
+++ b/addons/mail/wizard/mail_compose_message.py
@@ -82,9 +82,9 @@ class mail_compose_message(osv.osv_memory):
else:
# default mode
result['model'] = context.get('active_model', False)
- if vals:
- for field in fields:
- result.update({field : vals.get(field, False)})
+ for field in vals:
+ if field in fields:
+ result.update({field : vals[field]})
# link to model and record if not done yet
if not result.get('model') or not result.get('res_id'):
diff --git a/addons/mrp/mrp_installer.xml b/addons/mrp/mrp_installer.xml
index af2a35b3ce7..33ef333d8ca 100644
--- a/addons/mrp/mrp_installer.xml
+++ b/addons/mrp/mrp_installer.xml
@@ -40,16 +40,8 @@
-
- Create Bill of Materials
- ir.actions.act_window
- mrp.bom
- form,tree
- form
-
-
-
+
diff --git a/addons/mrp/report/price.py b/addons/mrp/report/price.py
index 733312ba799..5027bd372ea 100644
--- a/addons/mrp/report/price.py
+++ b/addons/mrp/report/price.py
@@ -19,6 +19,7 @@
#
##############################################################################
+import time
import pooler
from report.interface import report_rml
#from report.interface import toxml
@@ -39,6 +40,7 @@ class report_custom(report_rml):
workcenter_pool = pool.get('mrp.workcenter')
user_pool = pool.get('res.users')
bom_pool = pool.get('mrp.bom')
+ pricelist_pool = pool.get('product.pricelist')
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
@@ -56,8 +58,12 @@ class report_custom(report_rml):
if prod.seller_id:
main_sp_name = "%s\r\n" %(prod.seller_id.name)
- price = supplier_info_pool.price_get(cr, uid, prod.seller_id.id, prod.id, number*prod_qtty)[prod.seller_id.id]
- price = product_uom_pool._compute_price(cr, uid, prod.uom_id.id, price, to_uom_id=product_uom.id)
+ pricelist = prod.seller_id.property_product_pricelist_purchase
+ price = pricelist_pool.price_get(cr,uid,[pricelist.id],
+ prod.id, number*prod_qtty or 1.0, prod.seller_id.id, {
+ 'uom': prod.uom_po_id.id,
+ 'date': time.strftime('%Y-%m-%d'),
+ })[pricelist.id]
main_sp_price = """"""+rml_obj.formatLang(price)+' '+ company_currency.symbol+"""\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)
@@ -65,8 +71,12 @@ class report_custom(report_rml):
sum_strd = prod_qtty*std_price
for seller_id in prod.seller_ids:
sellers += '- '+ seller_id.name.name +'\r\n'
- price = supplier_info_pool.price_get(cr, uid, seller_id.name.id, prod.id, number*prod_qtty)[seller_id.name.id]
- price = product_uom_pool._compute_price(cr, uid, prod.uom_id.id, price, to_uom_id=product_uom.id)
+ pricelist = seller_id.name.property_product_pricelist_purchase
+ price = pricelist_pool.price_get(cr,uid,[pricelist.id],
+ prod.id, number*prod_qtty or 1.0, seller_id.name.id, {
+ 'uom': prod.uom_po_id.id,
+ 'date': time.strftime('%Y-%m-%d'),
+ })[pricelist.id]
sellers_price += """"""+rml_obj.formatLang(price) +' '+ company_currency.symbol +"""\r\n"""
xml += """
"""+ prod_name +"""
"""+ main_sp_name + sellers + """
diff --git a/addons/mrp/test/mrp_phantom_bom.yml b/addons/mrp/test/mrp_phantom_bom.yml
index 6bb297fbcfb..1f499a5fb7f 100644
--- a/addons/mrp/test/mrp_phantom_bom.yml
+++ b/addons/mrp/test/mrp_phantom_bom.yml
@@ -205,9 +205,8 @@
I am checking Procurement orders. There are 3 orders generated for Oranges, Sugar and Water.
-
!python {model: procurement.order}: |
- from tools.translate import _
proc_ids = self.search(cr, uid, [('product_id','in',[ref('product_product_orange0'),ref('product_product_sugar0'),ref('product_product_water0')])])
- assert proc_ids, _('No Procurements!')
+ assert proc_ids, 'No Procurements!'
-
The scheduler runs.
-
@@ -219,9 +218,8 @@
stock moves for Oranges, Sugar and Water made correctly.
-
!python {model: stock.picking}: |
- from tools.translate import _
pick_ids = self.search(cr, uid, [('type','=','internal')])
- assert pick_ids, _('No Internal Pickings!')
+ assert pick_ids, 'No Internal Pickings!'
-
According to minimum stock rules. I have 2 purchase orders for
Sugar with 6 Kg from Axelor and Orange 60 Kg from ASUStek.
@@ -229,50 +227,24 @@
I confirm the purchase order of Sugar and Orange.
-
!python {model: purchase.order}: |
- from tools.translate import _
import netsvc
purch_ids = self.search(cr, uid, [('state','=','draft')])
- assert purch_ids, _('No Purchase Orders were made!')
+ assert purch_ids, 'No Purchase Orders were made!'
wf_service = netsvc.LocalService("workflow")
for p_id in purch_ids:
wf_service.trg_validate(uid, 'purchase.order', p_id, 'purchase_confirm', cr)
-
- I see two incoming pickings for Orange and Sugar.
+ I see two incoming pickings for Orange and Sugar, and receive them.
-
!python {model: stock.picking}: |
- from tools.translate import _
pick_ids = self.search(cr, uid, [('type','=','in')])
- assert pick_ids, _('No Incoming Shipments found!')
--
- I receive both the products. My incoming pickings are done.
--
- I create record for the incoming picking wizard.
--
- !record {model: stock.partial.picking, id: stock_partial_picking0}:
- date: !eval datetime.today().strftime("%Y-%m-%d %H:%M:%S")
--
- I make my pickings done.
--
- !python {model: stock.partial.picking}: |
- pick_obj = self.pool.get('stock.picking')
- picking_ids = pick_obj.search(cr, uid, [('type','=','in'),('state','=','assigned')])
- partial = self.browse(cr, uid, 1, context)
- partial_datas = {
- 'delivery_date': partial.date
- }
- for pick in pick_obj.browse(cr, uid, picking_ids):
- for m in pick.move_lines:
- partial_datas['move%s'%(m.id)] = {
- 'product_id': m.product_id.id,
- 'product_qty': m.product_qty,
- 'product_uom': m.product_uom.id
- }
- if (pick.type == 'in') and (m.product_id.cost_method == 'average'):
- partial_datas['move%s'%(m.id)].update({
- 'product_price': m.product_price,
- 'product_currency': m.product_currency
- })
- pick_obj.do_partial(cr, uid, picking_ids, partial_datas, context=context)
+ assert pick_ids, 'No Incoming Shipments found!'
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ for pick_id in pick_ids:
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick_id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
Again the scheduler runs.
-
@@ -283,19 +255,15 @@
I check my internal picking of "Orange Juice" is done.
-
!python {model: stock.picking}: |
- from tools.translate import _
pick_ids = self.search(cr, uid, [('type','=','internal'),('state','=','done')])
- assert pick_ids, _('Internal Picking is not done yet!')
+ assert pick_ids, 'Internal Picking is not done yet!'
-
I check my manufacturing order for "Orange Juice" is ready or not.
-
!python {model: mrp.production}: |
- from tools.translate import _
- pick_ids = self.search(cr, uid, [('state','=','ready'),('id','=',ref('mrp_production_mo0'))])
- assert pick_ids, _('Manufacturing order is not ready!')
+ prod_ids = self.search(cr, uid, [('state','=','ready'),('id','=',ref('mrp_production_mo0'))])
+ assert prod_ids, 'Manufacturing order is not ready!'
-
I start the production order.
-
!workflow {model: mrp.production, action: button_produce, ref: mrp_production_mo0}
-
-
diff --git a/addons/mrp/test/mrp_procurement.yml b/addons/mrp/test/mrp_procurement.yml
index 568a5f0b0e8..4aaf1560432 100644
--- a/addons/mrp/test/mrp_procurement.yml
+++ b/addons/mrp/test/mrp_procurement.yml
@@ -195,74 +195,26 @@
I Check incoming shipments for cloth. And receive products.
-
!python {model: stock.picking}: |
- from tools.translate import _
pick_ids = self.search(cr, uid, [('address_id.name','=','Wong'),('state','=','assigned')])
- assert pick_ids, _('No Incoming Shipments found!')
--
- I create record for partial picking.
--
- !record {model: stock.partial.picking, id: stock_partial_picking0}:
- date: !eval datetime.today().strftime("%Y-%m-%d %H:%M:%S")
-
--
- I make my picking done.
--
- !python {model: stock.partial.picking}: |
- pick_obj = self.pool.get('stock.picking')
- picking_ids = pick_obj.search(cr, uid, [('address_id.name','=','Wong'),('state','=','assigned')])
- partial = self.browse(cr, uid, 1, context)
- partial_datas = {
- 'delivery_date' : partial.date
- }
- for pick in pick_obj.browse(cr, uid, picking_ids):
- for m in pick.move_lines:
- partial_datas['move%s'%(m.id)] = {
- 'product_id' : m.product_id.id,
- 'product_qty' : m.product_qty,
- 'product_uom' : m.product_uom.id
- }
- if (pick.type == 'in') and (m.product_id.cost_method == 'average'):
- partial_datas['move%s'%(m.id)].update({
- 'product_price' : m.product_price,
- 'product_currency': m.product_currency
- })
- pick_obj.do_partial(cr, uid, picking_ids, partial_datas, context=context)
+ assert pick_ids, 'No Incoming Shipments found!'
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ for pick_id in pick_ids:
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick_id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I Check incoming shipments for buttons and receive products.
-
!python {model: stock.picking}: |
- from tools.translate import _
pick_ids = self.search(cr, uid, [('address_id.name','=','Tang'),('state','=','assigned')])
- assert pick_ids, _('No Incoming Shipments found!')
--
- I create record for partial picking.
--
- !record {model: stock.partial.picking, id: stock_partial_picking0}:
- date: !eval datetime.today().strftime("%Y-%m-%d %H:%M:%S")
-
--
- I make my picking done.
--
- !python {model: stock.partial.picking}: |
- pick_obj = self.pool.get('stock.picking')
- picking_ids = pick_obj.search(cr, uid, [('address_id.name','=','Tang'),('state','=','assigned')])
- partial = self.browse(cr, uid, 1, context)
- partial_datas = {
- 'delivery_date': partial.date
- }
- for pick in pick_obj.browse(cr, uid, picking_ids):
- for m in pick.move_lines:
- partial_datas['move%s'%(m.id)] = {
- 'product_id': m.product_id.id,
- 'product_qty': m.product_qty,
- 'product_uom': m.product_uom.id
- }
- if (pick.type == 'in') and (m.product_id.cost_method == 'average'):
- partial_datas['move%s'%(m.id)].update({
- 'product_price': m.product_price,
- 'product_currency': m.product_currency
- })
- pick_obj.do_partial(cr, uid, picking_ids, partial_datas, context=context)
+ assert pick_ids, 'No Incoming Shipments found!'
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ for pick_id in pick_ids:
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick_id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
Run scheduler again.
-
@@ -297,7 +249,6 @@
I produce 2 products with 5.00 quantities each.
-
!python {model: mrp.product.produce}: |
- from tools.translate import _
prod_obj = self.pool.get('mrp.production')
prod_ids = prod_obj.search(cr, uid, [('product_id.name','=','Shirt')])
self.do_produce(cr, uid, [ref('mrp_product_produce0')], context={'active_ids': prod_ids})
@@ -321,8 +272,7 @@
And finally production order is done.
-
!python {model: mrp.product.produce}: |
- from tools.translate import _
prod_obj = self.pool.get('mrp.production')
prod_ids = prod_obj.search(cr, uid, [('product_id.name','=','Shirt')])
- self.do_produce(cr, uid, [1], context={'active_ids': prod_ids})
+ self.do_produce(cr, uid, [ref('mrp_product_produce0')], context={'active_ids': prod_ids})
diff --git a/addons/mrp_operations/mrp_operations.py b/addons/mrp_operations/mrp_operations.py
index 4e665b3f9dc..7dc93731b03 100644
--- a/addons/mrp_operations/mrp_operations.py
+++ b/addons/mrp_operations/mrp_operations.py
@@ -235,6 +235,8 @@ class mrp_production(osv.osv):
obj = self.browse(cr, uid, ids)[0]
wf_service = netsvc.LocalService("workflow")
for workcenter_line in obj.workcenter_lines:
+ if workcenter_line.state == 'draft':
+ wf_service.trg_validate(uid, 'mrp.production.workcenter.line', workcenter_line.id, 'button_start_working', cr)
wf_service.trg_validate(uid, 'mrp.production.workcenter.line', workcenter_line.id, 'button_done', cr)
return super(mrp_production,self).action_production_end(cr, uid, ids)
@@ -243,9 +245,11 @@ class mrp_production(osv.osv):
@return: True
"""
obj = self.browse(cr, uid, ids)[0]
+ workcenter_pool = self.pool.get('mrp.production.workcenter.line')
wf_service = netsvc.LocalService("workflow")
- for workcenter_line in obj.workcenter_lines:
- wf_service.trg_validate(uid, 'mrp.production.workcenter.line', workcenter_line.id, 'button_start_working', cr)
+ for prod in self.browse(cr, uid, ids):
+ if prod.workcenter_lines:
+ wf_service.trg_validate(uid, 'mrp.production.workcenter.line', prod.workcenter_lines[0].id, 'button_start_working', cr)
return super(mrp_production,self).action_in_production(cr, uid, ids)
def action_cancel(self, cr, uid, ids, context=None):
diff --git a/addons/outlook/installer.py b/addons/outlook/installer.py
index 4d0ac1e1971..2be0c243037 100644
--- a/addons/outlook/installer.py
+++ b/addons/outlook/installer.py
@@ -41,7 +41,7 @@ class outlook_installer(osv.osv_memory):
'doc_name':fields.char('File name', size=64),
'outlook':fields.boolean('Outlook Plug-in ', help="Allows you to select an object that you would like to add to your email and its attachments."),
'plugin_file':fields.binary('Outlook Plug-in', readonly=True, help="outlook plug-in file. Save as this file and install this plug-in in outlook."),
- 'doc_file':fields.char('Installation Manual',size="264",help="The documentation file :- how to install Outlook Plug-in.", readonly=True),
+ 'doc_file':fields.char('Installation Manual',size=264,help="The documentation file :- how to install Outlook Plug-in.", readonly=True),
'description':fields.text('Description', readonly=True)
}
diff --git a/addons/outlook/outlook_installer.xml b/addons/outlook/outlook_installer.xml
index a85a16c245b..bb2aeb31fd2 100644
--- a/addons/outlook/outlook_installer.xml
+++ b/addons/outlook/outlook_installer.xml
@@ -8,20 +8,18 @@
- Load Outlook Plug-In
+ Install Outlook Plug-In
- Load Outlook Plug-In
+ Install Outlook Plug-InThis plug-in allows you to link your e-mail to OpenERP's documents. You can attach it to any existing one in OpenERP or create a new one.
-
-
+
-
@@ -46,7 +44,7 @@
- Load Outlook Plug-In
+ Install Outlook Plug-Inir.actions.act_windowoutlook.installer
@@ -59,10 +57,11 @@
4
+ automatic
- Load Outlook Plug-In
+ Install Outlook Plug-Inir.actions.act_windowoutlook.installer
@@ -73,10 +72,7 @@
+
-
-
-
-
diff --git a/addons/point_of_sale/point_of_sale.py b/addons/point_of_sale/point_of_sale.py
index 19f18d92dd6..ee2173dcd49 100644
--- a/addons/point_of_sale/point_of_sale.py
+++ b/addons/point_of_sale/point_of_sale.py
@@ -264,7 +264,7 @@ class pos_order(osv.osv):
args['partner_id'] = order.partner_id and order.partner_id.id or None
statement_id = statement_obj.search(cr,uid, [
- ('journal_id', '=', data['journal']),
+ ('journal_id', '=', int(data['journal'])),
('company_id', '=', curr_company),
('user_id', '=', uid),
('state', '=', 'open')], context=context)
@@ -274,7 +274,7 @@ class pos_order(osv.osv):
statement_id = statement_id[0]
args['statement_id'] = statement_id
args['pos_statement_id'] = order_id
- args['journal_id'] = data['journal']
+ args['journal_id'] = int(data['journal'])
args['type'] = 'customer'
args['ref'] = order.name
statement_line_obj.create(cr, uid, args, context=context)
diff --git a/addons/point_of_sale/test/point_of_sale_report.yml b/addons/point_of_sale/test/point_of_sale_report.yml
index f31f9ec0f49..f3ea5995b9e 100644
--- a/addons/point_of_sale/test/point_of_sale_report.yml
+++ b/addons/point_of_sale/test/point_of_sale_report.yml
@@ -34,6 +34,11 @@
if tools.config['test_report_directory']:
file(os.path.join(tools.config['test_report_directory'], 'point_of_sale-receipt report'+format), 'wb+').write(data)
+-
+ Create a record for the root user in pos.payment.report.user (used by the next python block).
+-
+ !record {model: pos.payment.report.user, id: pos_payment_report_user_1}:
+ user_id: []
-
Print the POS Payment Report through the wizard
-
diff --git a/addons/point_of_sale/wizard/pos_open_statement.py b/addons/point_of_sale/wizard/pos_open_statement.py
index 038ca3b6990..47c5348943b 100644
--- a/addons/point_of_sale/wizard/pos_open_statement.py
+++ b/addons/point_of_sale/wizard/pos_open_statement.py
@@ -53,9 +53,9 @@ class pos_open_statement(osv.osv_memory):
continue
if journal.sequence_id:
- number = sequence_obj.get_id(cr, uid, journal.sequence_id.id)
+ number = sequence_obj.next_by_id(cr, uid, journal.sequence_id.id)
else:
- number = sequence_obj.get(cr, uid, 'account.cash.statement')
+ number = sequence_obj.next_by_code(cr, uid, 'account.cash.statement')
data.update({
'journal_id': journal.id,
diff --git a/addons/product/pricelist_view.xml b/addons/product/pricelist_view.xml
index f284dcbc47b..79e6773980c 100644
--- a/addons/product/pricelist_view.xml
+++ b/addons/product/pricelist_view.xml
@@ -56,6 +56,7 @@
+
diff --git a/addons/product/product.py b/addons/product/product.py
index 78fc05fe7e7..b055e704785 100644
--- a/addons/product/product.py
+++ b/addons/product/product.py
@@ -460,6 +460,7 @@ class product_product(osv.osv):
'active': lambda *a: 1,
'price_extra': lambda *a: 0.0,
'price_margin': lambda *a: 1.0,
+ 'color': 0,
}
_name = "product.product"
@@ -486,8 +487,10 @@ class product_product(osv.osv):
'price_margin': fields.float('Variant Price Margin', digits_compute=dp.get_precision('Sale Price')),
'pricelist_id': fields.dummy(string='Pricelist', relation='product.pricelist', type='many2one'),
'name_template': fields.related('product_tmpl_id', 'name', string="Name", type='char', size=128, store=True),
+ 'color': fields.integer('Color Index'),
+ 'product_image': fields.binary('Image'),
}
-
+
def unlink(self, cr, uid, ids, context=None):
unlink_ids = []
unlink_product_tmpl_ids = []
diff --git a/addons/product/product_view.xml b/addons/product/product_view.xml
index a50a7b404e2..35798ce939d 100644
--- a/addons/product/product_view.xml
+++ b/addons/product/product_view.xml
@@ -69,7 +69,7 @@
-
+
project.task.tree
@@ -502,6 +511,21 @@
A task represents a work that has to be done. Each user works in his own list of tasks where he can record his task work in hours. He can work and close the task itself or delegate it to another user. If you delegate a task to another user, you get a new task in pending state, which will be reopened when you have to review the work achieved. If you install the project_timesheet module, task work can be invoiced based on the project configuration. With the project_mrp module, sales orders can create tasks automatically when they are confirmed.
+
+
+
+ tree
+
+
+
+
+
+
+ form
+
+
+
+
@@ -533,6 +557,21 @@
+
+ project.task.type.search
+ project.task.type
+ search
+
+
+
+
+
+
+
+
+
+
+
project.task.type.formproject.task.type
@@ -540,7 +579,7 @@
+
+
+
+
+
+
+
+
+
+
+
# ------------------------------------------------------
# Feature Requests
# ------------------------------------------------------
diff --git a/addons/purchase/purchase.py b/addons/purchase/purchase.py
index dcf29bfaceb..db494add04b 100644
--- a/addons/purchase/purchase.py
+++ b/addons/purchase/purchase.py
@@ -188,11 +188,11 @@ class purchase_order(osv.osv):
'shipped_rate': fields.function(_shipped_rate, string='Received', type='float'),
'invoiced': fields.function(_invoiced, string='Invoiced & Paid', type='boolean', help="It indicates that an invoice has been paid"),
'invoiced_rate': fields.function(_invoiced_rate, string='Invoiced', type='float'),
- 'invoice_method': fields.selection([('manual','From PO/PO lines'),('order','Draft invoices pre-generated'),('picking','From receptions')], 'Invoicing Control', required=True,
- help="From Order: a draft invoice will be generated based on the purchase order. The accountant " \
+ 'invoice_method': fields.selection([('manual','Based on purchase order lines'),('order','Draft invoices pre-generated'),('picking','Based on receptions')], 'Invoicing Control', required=True,
+ help="Based on orders: a draft invoice will be generated based on the purchase order. The accountant " \
"will just have to validate this invoice for control.\n" \
- "From Reception: a draft invoice will be generated based on validated receptions.\n" \
- "Manual: allows you to generate suppliers invoices by chosing in the uninvoiced lines of all manual purchase orders."
+ "Based on receptions: a draft invoice will be generated based on validated receptions.\n" \
+ "Pre-generate Invoice: allows you to generate draft suppliers invoices on validation of the PO."
),
'minimum_planned_date':fields.function(_minimum_planned_date, fnct_inv=_set_minimum_planned_date, string='Expected Date', type='date', select=True, help="This is computed as the minimum scheduled date of all purchase order lines' products.",
store = {
diff --git a/addons/purchase/purchase_view.xml b/addons/purchase/purchase_view.xml
index cb7224faaf0..60c6c39bf05 100644
--- a/addons/purchase/purchase_view.xml
+++ b/addons/purchase/purchase_view.xml
@@ -497,14 +497,14 @@
- On Purchase Order Line
+ On Purchase Order Linesir.actions.act_windowpurchase.order.line[('order_id.invoice_method','<>','picking'), ('state','in',('confirmed','done')), ('invoiced', '=', False)]formtree,form
- If you set the invoicing control on a purchase order as "Manual", you can track here all the purchase order lines for which you have not received the supplier invoice yet. Once you are ready to receive a supplier invoice, you can generate a draft supplier invoice based on the lines from this menu.
+ If you set the invoicing control on a purchase order as "Based on Purchase Order Lines", you can track here all the purchase order lines for which you have not received the supplier invoice yet. Once you are ready to receive a supplier invoice, you can generate a draft supplier invoice based on the lines from this menu.
diff --git a/addons/purchase/stock.py b/addons/purchase/stock.py
index 696c4d708fe..29b4aa29318 100644
--- a/addons/purchase/stock.py
+++ b/addons/purchase/stock.py
@@ -124,68 +124,15 @@ class stock_picking(osv.osv):
purchase_obj.write(cursor, user, [picking.purchase_id.id], {'invoice_id': invoice_id,})
return super(stock_picking, self)._invoice_hook(cursor, user, picking, invoice_id)
-stock_picking()
-
class stock_partial_picking(osv.osv_memory):
_inherit = 'stock.partial.picking'
- def default_get(self, cr, uid, fields, context=None):
- """ To get default values for the object.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param fields: List of fields for which we want default values
- @param context: A standard dictionary
- @return: A dictionary which of fields with values.
- """
- if context is None:
- context = {}
- pick_obj = self.pool.get('stock.picking')
- res = super(stock_partial_picking, self).default_get(cr, uid, fields, context=context)
- for pick in pick_obj.browse(cr, uid, context.get('active_ids', []), context=context):
- has_product_cost = (pick.type == 'in' and pick.purchase_id)
- for m in pick.move_lines:
- if m.state in ('done','cancel') :
- continue
- if has_product_cost and m.product_id.cost_method == 'average' and m.purchase_line_id:
- # We use the original PO unit purchase price as the basis for the cost, expressed
- # in the currency of the PO (i.e the PO's pricelist currency)
- list_index = 0
- for item in res['product_moves_in']:
- if item['move_id'] == m.id:
- res['product_moves_in'][list_index]['cost'] = m.purchase_line_id.price_unit
- res['product_moves_in'][list_index]['currency'] = m.picking_id.purchase_id.pricelist_id.currency_id.id
- list_index += 1
- return res
-stock_partial_picking()
+ # Overridden to inject the purchase price as true 'cost price' when processing
+ # incoming pickings.
+ def _product_cost_for_average_update(self, cr, uid, move):
+ if move.picking_id.purchase_id:
+ return {'cost': move.purchase_line_id.price_unit,
+ 'currency': move.picking_id.purchase_id.pricelist_id.currency_id.id}
+ return super(stock_partial_picking, self)._product_cost_for_average_update(cr, uid, move)
-class stock_partial_move(osv.osv_memory):
- _inherit = "stock.partial.move"
- def default_get(self, cr, uid, fields, context=None):
- """ To get default values for the object.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param fields: List of fields for which we want default values
- @param context: A standard dictionary
- @return: A dictionary which of fields with values.
- """
- if context is None:
- context = {}
- res = super(stock_partial_move, self).default_get(cr, uid, fields, context=context)
- move_obj = self.pool.get('stock.move')
- for m in move_obj.browse(cr, uid, context.get('active_ids', []), context=context):
- if m.picking_id.type == 'in' and m.product_id.cost_method == 'average' \
- and m.purchase_line_id and m.picking_id.purchase_id:
- # We use the original PO unit purchase price as the basis for the cost, expressed
- # in the currency of the PO (i.e the PO's pricelist currency)
- list_index = 0
- for item in res['product_moves_in']:
- if item['move_id'] == m.id:
- res['product_moves_in'][list_index]['cost'] = m.purchase_line_id.price_unit
- res['product_moves_in'][list_index]['currency'] = m.picking_id.purchase_id.pricelist_id.currency_id.id
- list_index += 1
- return res
-stock_partial_move()
# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
-
diff --git a/addons/purchase/test/purchase_from_picking.yml b/addons/purchase/test/purchase_from_picking.yml
index 9425ad94812..8d63aa3e02c 100644
--- a/addons/purchase/test/purchase_from_picking.yml
+++ b/addons/purchase/test/purchase_from_picking.yml
@@ -137,7 +137,7 @@
pur_id1=pur_obj.browse(cr, uid, ref("purchase_order_po2"))
pick_ids = [x.id for x in pur_id1.picking_ids]
id = self.create(cr, uid, {'invoice_date': time.strftime('%Y-%m-%d'), 'journal_id': ref('account.expenses_journal')},
- {'active_ids': pick_ids})
+ {'active_ids': pick_ids, 'active_model': 'stock.picking'})
self.create_invoice(cr, uid, [id], {"active_ids": pick_ids, "active_id": pick_ids[0]})
-
I check that an invoice_ids field of Delivery&Invoices gets bind with the value.
diff --git a/addons/purchase/wizard/purchase_installer.py b/addons/purchase/wizard/purchase_installer.py
index c6d70947893..03327002953 100644
--- a/addons/purchase/wizard/purchase_installer.py
+++ b/addons/purchase/wizard/purchase_installer.py
@@ -31,24 +31,24 @@ purchase_installer()
class purchase_config_wizard(osv.osv_memory):
_name = 'purchase.config.wizard'
+ _inherit = 'res.config'
_columns = {
'default_method' : fields.selection(
- [('manual', 'Based on Purchase Orders'),
+ [('manual', 'Based on Purchase Order Lines'),
('picking', 'Based on Receptions'),
- ('order', 'Pre-Generate Draft Invoices on Purchase Orders'),
- ],
- 'Default Invoicing Control Method',
- required=True,
- ),
+ ('order', 'Pre-Generate Draft Invoices on Based Purchase Orders'),
+ ], 'Default Invoicing Control Method', required=True,
+ )
+ }
+ _defaults = {
+ 'default_method': lambda s,c,u,ctx: s.pool.get('purchase.order').default_get(c,u,['invoice_method'],context=ctx)['invoice_method']
}
- def validate_cb(self, cr, uid, ids, context=None):
+ def execute(self, cr, uid, ids, context=None):
wizard = self.browse(cr, uid, ids, context=context)[0]
-
proxy = self.pool.get('ir.values')
proxy.set(cr, uid, 'default', False, 'invoice_method', ['purchase.order'], wizard.default_method),
-
return {'type' : 'ir.actions.act_window_close'}
purchase_config_wizard()
diff --git a/addons/purchase/wizard/purchase_installer.xml b/addons/purchase/wizard/purchase_installer.xml
index cf9b6a985db..0519ac3dd01 100644
--- a/addons/purchase/wizard/purchase_installer.xml
+++ b/addons/purchase/wizard/purchase_installer.xml
@@ -40,32 +40,49 @@
- purchase.view_purchase_config
- form
+ Invoicing Control on Purchasespurchase.config.wizard
+ form
+
-
-
-
-
-
-
-
-
+
+
+ Invoicing Control on Purchases
+
+
+ Invoicing Control on Purchases
+
+
+ This tool will help you to select the method you want to use to control supplier invoices.
+
+
+
+ 12
+
+
+
+
+
+
+
+
Set the Default Invoicing Control Methodpurchase.config.wizardformformnew
+
+
+ once
diff --git a/addons/purchase_double_validation/purchase_double_validation_installer.xml b/addons/purchase_double_validation/purchase_double_validation_installer.xml
index 9a06f66164a..490581e472b 100644
--- a/addons/purchase_double_validation/purchase_double_validation_installer.xml
+++ b/addons/purchase_double_validation/purchase_double_validation_installer.xml
@@ -44,6 +44,7 @@
+ once
diff --git a/addons/sale/sale.py b/addons/sale/sale.py
index f2f953398a2..d9b8cfb88f9 100644
--- a/addons/sale/sale.py
+++ b/addons/sale/sale.py
@@ -216,7 +216,7 @@ class sale_order(osv.osv):
'partner_shipping_id': fields.many2one('res.partner.address', 'Shipping Address', readonly=True, required=True, states={'draft': [('readonly', False)]}, help="Shipping address for current sales order."),
'incoterm': fields.many2one('stock.incoterms', 'Incoterm', help="Incoterm which stands for 'International Commercial terms' implies its a series of sales terms which are used in the commercial transaction."),
- 'picking_policy': fields.selection([('direct', 'Partial Delivery'), ('one', 'Complete Delivery')],
+ 'picking_policy': fields.selection([('direct', 'Deliver each products when available'), ('one', 'Deliver all products at once')],
'Picking Policy', required=True, readonly=True, states={'draft': [('readonly', False)]}, help="""If you don't have enough stock available to deliver all at once, do you accept partial shipments or not?"""),
'order_policy': fields.selection([
('prepaid', 'Pay before delivery'),
@@ -728,6 +728,7 @@ class sale_order(osv.osv):
#'state': 'waiting',
'note': line.notes,
'company_id': order.company_id.id,
+ 'price_unit': line.product_id.standard_price or 0.0
})
if line.product_id:
@@ -1215,7 +1216,7 @@ class sale_config_picking_policy(osv.osv_memory):
('manual', 'Invoice Based on Sales Orders'),
('picking', 'Invoice Based on Deliveries'),
], 'Main Method Based On', required=True, help="You can generate invoices based on sales orders or based on shippings."),
- 'charge_delivery': fields.boolean('Do you charge the delivery'),
+ 'charge_delivery': fields.boolean('Do you charge the delivery?'),
'time_unit': fields.many2one('product.uom','Main Working Time Unit')
}
_defaults = {
@@ -1224,12 +1225,10 @@ class sale_config_picking_policy(osv.osv_memory):
def onchange_order(self, cr, uid, ids, sale, deli, context=None):
res = {}
- if sale or deli:
+ if sale:
res.update({'order_policy': 'manual'})
- elif not sale and not deli:
- res.update({'order_policy': 'manual'})
- else:
- return {}
+ elif deli:
+ res.update({'order_policy': 'picking'})
return {'value':res}
def execute(self, cr, uid, ids, context=None):
@@ -1239,26 +1238,18 @@ class sale_config_picking_policy(osv.osv_memory):
module_obj = self.pool.get('ir.module.module')
module_upgrade_obj = self.pool.get('base.module.upgrade')
module_name = []
- group_ids=[]
- group_name = ['group_sale_salesman','group_sale_manager']
- for name in group_name:
- data_id = data_obj.name_search(cr, uid, name)
- group_ids.append(data_obj.browse(cr,uid,data_id[0][0]).res_id)
+ group_id = data_obj.get_object(cr, uid, 'base', 'group_sale_salesman').id
wizard = self.browse(cr, uid, ids)[0]
if wizard.sale_orders:
- menu_name = 'menu_invoicing_sales_order_lines'
- data_id = data_obj.name_search(cr, uid, menu_name)
- menu_id = data_obj.browse(cr,uid,data_id[0][0]).res_id
- menu_obj.write(cr, uid, menu_id, {'groups_id':[(4,group_ids[0]),(4,group_ids[1])]})
+ menu_id = data_obj.get_object(cr, uid, 'sale', 'menu_invoicing_sales_order_lines').id
+ menu_obj.write(cr, uid, menu_id, {'groups_id':[(4,group_id)]})
if wizard.deli_orders:
- menu_name = 'menu_action_picking_list_to_invoice'
- data_id = data_obj.name_search(cr, uid, menu_name)
- menu_id = data_obj.browse(cr,uid,data_id[0][0]).res_id
- menu_obj.write(cr, uid, menu_id, {'groups_id':[(4,group_ids[0]),(4,group_ids[1])]})
+ menu_id = data_obj.get_object(cr, uid, 'sale', 'menu_action_picking_list_to_invoice').id
+ menu_obj.write(cr, uid, menu_id, {'groups_id':[(4,group_id)]})
if wizard.task_work:
module_name.append('project_timesheet')
@@ -1268,12 +1259,7 @@ class sale_config_picking_policy(osv.osv_memory):
module_name.append('account_analytic_analysis')
if wizard.charge_delivery:
- module_name.append('delivery')
-
- if wizard.time_unit:
- product_obj = self.pool.get('product.product')
- product_id = product_obj.name_search(cr, uid, 'Employee')
- product_obj.write(cr, uid, product_id[0][0], {'uom_id':wizard.time_unit.id})
+ module_name.append('delivery')
if len(module_name):
module_ids = []
@@ -1291,7 +1277,17 @@ class sale_config_picking_policy(osv.osv_memory):
if need_install:
pooler.restart_pool(cr.dbname, update_module=True)[1]
+ if wizard.time_unit:
+ prod_id = data_obj.get_object(cr, uid, 'hr_timesheet', 'product_consultant').id
+ product_obj = self.pool.get('product.product')
+ product_obj.write(cr, uid, prod_id, {'uom_id':wizard.time_unit.id, 'uom_po_id': wizard.time_unit.id})
+
ir_values_obj.set(cr, uid, 'default', False, 'order_policy', ['sale.order'], wizard.order_policy)
+ if wizard.task_work and wizard.time_unit:
+ company_id = self.pool.get('res.users').browse(cr, uid, uid).company_id.id
+ self.pool.get('res.company').write(cr, uid, [company_id], {
+ 'project_time_mode_id': wizard.time_unit.id
+ }, context=context)
sale_config_picking_policy()
diff --git a/addons/sale/sale_data.xml b/addons/sale/sale_data.xml
index 41f7534c8e2..4622577ac3d 100644
--- a/addons/sale/sale_data.xml
+++ b/addons/sale/sale_data.xml
@@ -13,11 +13,15 @@
Resource: sale.shop
-->
-
-
-
-
+
+
+
+
+
+
diff --git a/addons/sale/sale_view.xml b/addons/sale/sale_view.xml
index b7f5d11e15f..4669a9d7d9c 100644
--- a/addons/sale/sale_view.xml
+++ b/addons/sale/sale_view.xml
@@ -481,54 +481,50 @@
- Set Up Your Invoicing Method
+ Setup Your Invoicing Methodsale.config.picking_policyform
- Sales Application Configuration
+ Setup your Invoicing Method
-
-
-
+
+
+ Setup your Invoicing Method
+
+
+ This tool will help you to install the right module and configure the system according to the method you use to invoice your customers.
+
+
+
+ 12
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
+
- Set up your Invoicing Method
+ Setup your Invoicing Methodir.actions.act_windowsale.config.picking_policy
@@ -541,6 +537,7 @@
+ once
diff --git a/addons/sale/test/data_test.yml b/addons/sale/test/data_test.yml
index 7064a549335..0be8474754c 100644
--- a/addons/sale/test/data_test.yml
+++ b/addons/sale/test/data_test.yml
@@ -122,7 +122,6 @@
default_credit_account_id: account_account_purchases0
default_debit_account_id: account_account_purchases0
name: Purchase Journal - (test)
- sequence_id: account.sequence_purchase_journal
type: purchase
view_id: account.account_journal_view
-
@@ -134,7 +133,6 @@
default_credit_account_id: account_account_sales0
default_debit_account_id: account_account_sales0
name: Sale Journal
- sequence_id: account.sequence_sale_journal
type: sale
view_id: account.account_journal_view
-
@@ -146,7 +144,6 @@
default_credit_account_id: account_account_cash0
default_debit_account_id: account_account_cash0
name: Bank Journal
- sequence_id: account.sequence_journal
type: cash
view_id: account.account_journal_bank_view
-
diff --git a/addons/sale/test/invoice_on_ordered_qty.yml b/addons/sale/test/invoice_on_ordered_qty.yml
index 785b2d8835e..313aa3a0d63 100644
--- a/addons/sale/test/invoice_on_ordered_qty.yml
+++ b/addons/sale/test/invoice_on_ordered_qty.yml
@@ -31,39 +31,17 @@
-
!workflow {model: sale.order, action: order_confirm, ref: sale_order_so9}
-
- I verify that the picking has been generated for the sale order
+ I verify that the picking has been generated for the sale order and I process it
-
!python {model: sale.order}: |
so = self.browse(cr, uid, ref("sale_order_so9"))
assert so.picking_ids,"Picking has not been generated for sale_order_so9"
--
- Then I confirm the picking
--
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
--
- Then I done the picking
--
- !python {model: stock.picking }: |
- import time
- sale_order_obj = self.pool.get('sale.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so9"))
- picking_id = self.search(cr, uid, [('origin','=',so.name),('type','=','out')])
- if picking_id:
- pick=self.browse(cr,uid,picking_id[0])
- pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': '100',
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ picking, = so.picking_ids
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [picking.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I click on Create Invoice button to create the invoice.
-
diff --git a/addons/sale/test/invoice_on_shipped_qty.yml b/addons/sale/test/invoice_on_shipped_qty.yml
index bf2795e0f5b..c6ac86471be 100644
--- a/addons/sale/test/invoice_on_shipped_qty.yml
+++ b/addons/sale/test/invoice_on_shipped_qty.yml
@@ -30,41 +30,21 @@
-
!workflow {model: sale.order, action: order_confirm, ref: sale_order_so6}
-
- I verify that the picking has been generated for the sale order
+ I verify that the picking has been generated for the sale order and I process it
-
!python {model: sale.order}: |
so = self.browse(cr, uid, ref("sale_order_so6"))
assert so.picking_ids,"Picking has not been generated for sale_order_so6"
--
- Then I click on the "Product Sent" button of Outgoing Shipments
--
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
--
- I change the quantity on the picking to 199, and confirm partially 100 PCE.
--
- !python {model: stock.picking }: |
- import time
- sale_order_obj = self.pool.get('sale.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so6"))
- picking_id = self.search(cr, uid, [('origin','=',so.name),('type','=','out')])
- if picking_id:
- pick=self.browse(cr,uid,picking_id[0])
- self.pool.get('stock.move').write(cr, uid, [pick.move_lines[0].id], {'product_qty': 199, 'product_uos_qty': 199})
- pick=self.browse(cr,uid,picking_id[0])
- pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': '100',
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ picking, = so.picking_ids
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [picking.id]})
+ # I change the qty to 100 for a partial delivery
+ partial = stock_partial_picking.browse(cr,uid,partial_id)
+ line_id = partial.move_ids[0].id
+ partial.write({'move_ids': [(1,line_id,{'quantity':100})]})
+ partial.do_partial()
-
Then I click on 'Create Invoices' button
-
@@ -72,9 +52,9 @@
import time
sale_obj = self.pool.get('sale.order')
sale_id = sale_obj.browse(cr, uid, ref("sale_order_so6"))
- ids = [x.id for x in sale_id.picking_ids]
+ ids = [x.id for x in sale_id.picking_ids if x.state == 'done']
wiz_id = self.create(cr, uid, {'invoice_date': time.strftime('%Y-%m-%d'), 'journal_id': ref('account.sales_journal')},
- {'active_ids': ids})
+ {'active_ids': ids, 'active_model': 'stock.picking'})
self.create_invoice(cr, uid, [wiz_id], {"active_ids": ids, "active_id": ids[0]})
-
I verify whether the invoice has been generated for SO
@@ -98,7 +78,7 @@
inv_brw = self.browse(cr,uid,inv_id)[0]
for inv_lines in inv_brw.invoice_line:
qty1=inv_lines.quantity
- assert (qty1 == qty), "Quantities are not the same"
+ assert (qty1 == qty), "Quantities are not the same: invoiced: %s, shipped: %s" % (qty1,qty)
-
I open the Invoice for the SO.
-
diff --git a/addons/sale/test/manual_order_policy.yml b/addons/sale/test/manual_order_policy.yml
index c1535402f9b..af515b2d4e4 100644
--- a/addons/sale/test/manual_order_policy.yml
+++ b/addons/sale/test/manual_order_policy.yml
@@ -136,15 +136,11 @@
I verify that a procurement state is "running"
-
!python {model: procurement.order}: |
- from tools.translate import _
- modules = self.pool.get('ir.module.module')
- mod_pur = modules.search(cr, uid, [('name','=','purchase')])
- mod_brw = modules.browse(cr,uid,mod_pur)[0]
- if (mod_brw.state == 'installed'):
- sale_order_obj = self.pool.get('sale.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so0"))
- proc_ids = self.search(cr, uid, [('origin','=',so.name),('state','=','running')])
- assert(proc_ids),"Procurement is not in the running state!"
+ sale_order_obj = self.pool.get('sale.order')
+ so = sale_order_obj.browse(cr, uid, ref("sale_order_so0"))
+ proc_ids = self.search(cr, uid, [('origin','=',so.name),('state','in',['running','ready'])])
+ # should be running is 'purchase' is installed, else 'ready'
+ assert(proc_ids),"Procurement is not in running/ready state!"
-
I verify that a purchase order has been generated
-
@@ -192,7 +188,7 @@
for pur in pur_ids:
wf_service.trg_validate(uid, 'purchase.order',pur,'purchase_approve', cr)
-
- I verify that a picking related to purchase order has been generated.
+ I verify that a picking related to purchase order has been generated and I process it
-
!python {model: sale.order}: |
modules = self.pool.get('ir.module.module')
@@ -204,29 +200,12 @@
pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
po = pur_obj.browse(cr, uid, pur_id)[0]
assert(po.picking_ids),"Picking for purchase order has not been generated"
--
- Then I click on the "Products Received" button of Incoming Shipments
--
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
--
- I click on the "Validate" button
--
- !python {model: stock.picking}: |
- modules = self.pool.get('ir.module.module')
- sale_order_obj = self.pool.get('sale.order')
- pur_obj = self.pool.get('purchase.order')
- mod_pur = modules.search(cr, uid, [('name','=','purchase')])
- mod_brw = modules.browse(cr,uid,mod_pur)[0]
- if (mod_brw.state == 'installed'):
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so0"))
- pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
- po = pur_obj.browse(cr, uid, pur_id)[0]
- pick_ser_id = self.search(cr, uid, [('purchase_id', '=', po.id )])
- import netsvc
- wf_service = netsvc.LocalService("workflow")
- for pick in pick_ser_id:
- wf_service.trg_validate(uid, 'stock.picking',pick,'button_done', cr)
+ picking, = po.picking_ids
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [picking.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I verify that picking for purchase order has been done.
-
@@ -244,7 +223,7 @@
ids = picking_obj.search(cr, uid, [('purchase_id', '=', po.id ),('state', '=', 'done')])
assert(ids),"Picking is not in the done state!"
-
- Then I done the picking
+ Then I process the picking
-
!python {model: stock.picking }: |
import time
@@ -254,18 +233,11 @@
if picking_id:
pick=self.browse(cr,uid,picking_id[0])
pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': move.product_qty,
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I verify that picking for sale order is in done state.
-
@@ -275,38 +247,6 @@
picking_id = self.search(cr, uid, [('origin','=',so.name),('type','=','out')])
pick = self.browse(cr,uid,picking_id[0])
assert (pick.state) =='done', "Picking for SO is not in done state."
--
- Then I done the delivery order
--
- !python {model: stock.picking }: |
- import time
- sale_order_obj = self.pool.get('sale.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so0"))
- picking_id = self.search(cr, uid, [('origin','=',so.name)])
- if picking_id:
- pick=self.browse(cr,uid,picking_id[0])
- pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': move.product_qty,
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
--
- I verify that delivery state is done
--
- !python {model: stock.picking }: |
- sale_order_obj = self.pool.get('sale.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so0"))
- picking_id = self.search(cr, uid, [('origin','=',so.name)])
- pick = self.browse(cr,uid,picking_id[0])
- assert (pick.state) =='done', "Picking for SO is not in done state."
-
I verify that a "Picked" has been set to true
-
diff --git a/addons/sale/test/picking_order_policy.yml b/addons/sale/test/picking_order_policy.yml
index 4381c78f010..1dcbf980da4 100644
--- a/addons/sale/test/picking_order_policy.yml
+++ b/addons/sale/test/picking_order_policy.yml
@@ -46,18 +46,11 @@
if picking_id:
pick=self.browse(cr,uid,picking_id[0])
pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': move.product_qty,
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
Then I click on 'Create Invoices' button
-
@@ -67,7 +60,7 @@
sale_id=sale_obj.browse(cr, uid, ref("sale_order_so7"))
ids = [x.id for x in sale_id.picking_ids]
wiz_id = self.create(cr, uid, {'invoice_date': time.strftime('%Y-%m-%d'), 'journal_id': ref('account.sales_journal')},
- {'active_ids': ids})
+ {'active_ids': ids, 'active_model': 'stock.picking'})
self.create_invoice(cr, uid, [wiz_id], {"active_ids": ids, "active_id": ids[0]})
-
I check that an invoice has been created.
@@ -197,7 +190,7 @@
for pur in pur_ids:
wf_service.trg_validate(uid, 'purchase.order',pur,'purchase_approve', cr)
-
- I verify that a picking related to purchase order has been generated.
+ I verify that a picking related to purchase order has been generated and I process it
-
!python {model: sale.order}: |
modules = self.pool.get('ir.module.module')
@@ -209,29 +202,12 @@
pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
po = pur_obj.browse(cr, uid, pur_id)[0]
assert(po.picking_ids),"Picking for purchase order has not been generated"
--
- Then I click on the "Products Received" button of Incoming Shipments
--
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
--
- I click on the "Validate" button
--
- !python {model: stock.picking}: |
- modules = self.pool.get('ir.module.module')
- mod_pur = modules.search(cr, uid, [('name','=','purchase')])
- mod_brw = modules.browse(cr,uid,mod_pur)[0]
- if (mod_brw.state == 'installed'):
- sale_order_obj = self.pool.get('sale.order')
- pur_obj = self.pool.get('purchase.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so7"))
- pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
- po = pur_obj.browse(cr, uid, pur_id)[0]
- pick_ser_id = self.search(cr, uid, [('purchase_id', '=', po.id )])
- import netsvc
- wf_service = netsvc.LocalService("workflow")
- for pick in pick_ser_id:
- wf_service.trg_validate(uid, 'stock.picking',pick,'button_done', cr)
+ picking, = po.picking_ids
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [picking.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I verify that picking for purchase order has been done.
-
@@ -249,36 +225,20 @@
ids = picking_obj.search(cr, uid, [('purchase_id', '=', po.id ),('state', '=', 'done')])
assert ids, _('Picking is not in the done state!')
-
- I verify that delivery order has been generated for sale order
+ I verify that delivery order has been generated for sale order, and process it
-
!python {model: stock.picking }: |
sale_order_obj = self.pool.get('sale.order')
so = sale_order_obj.browse(cr, uid, ref("sale_order_so7"))
picking_id = self.search(cr, uid, [('origin','=',so.name)])
assert (picking_id),"Delivery order has not been generated"
--
- I verify that delivery has been done
--
- !python {model: stock.picking }: |
- import time
- sale_order_obj = self.pool.get('sale.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so7"))
- picking_id = self.search(cr, uid, [('origin','=',so.name)])
- if picking_id:
- pick=self.browse(cr,uid,picking_id[0])
- pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': move.product_qty,
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ pick=self.browse(cr,uid,picking_id[0])
+ pick.force_assign(cr, uid)
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I verify that delivery state is done
-
@@ -290,7 +250,7 @@
pick = self.browse(cr,uid,picking_id[0])
assert (pick.state) =='done', "Picking for SO is not in done state."
-
- I verify that a "Picked" has been set to true
+ I verify that the sale order is marked as delivered
-
!python {model: sale.order}: |
so = self.browse(cr, uid, ref("sale_order_so7"))
diff --git a/addons/sale/test/postpaid_order_policy.yml b/addons/sale/test/postpaid_order_policy.yml
index 330c6d17308..a0d5a8e1928 100644
--- a/addons/sale/test/postpaid_order_policy.yml
+++ b/addons/sale/test/postpaid_order_policy.yml
@@ -45,18 +45,11 @@
if picking_id:
pick=self.browse(cr,uid,picking_id[0])
pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': move.product_qty,
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I verify that picking order is in done state.
-
@@ -76,7 +69,7 @@
picking_id = self.search(cr, uid, [('origin','=',so.name)])
assert (picking_id),"Delivery order has not been generated"
-
- I click on the Products Sent button and then on the Validate button
+ I process the delivery order
-
!python {model: stock.picking }: |
import time
@@ -86,20 +79,13 @@
if picking_id:
pick=self.browse(cr,uid,picking_id[0])
pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': move.product_qty,
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
- I verify that delivery state is done
+ I verify that delivery order is marked done
-
!python {model: stock.picking }: |
sale_order_obj = self.pool.get('sale.order')
@@ -187,7 +173,7 @@
for pur in pur_ids:
wf_service.trg_validate(uid, 'purchase.order',pur,'purchase_approve', cr)
-
- I verify that a picking related to purchase order has been generated.
+ I verify that a picking related to purchase order has been generated and I process it
-
!python {model: sale.order}: |
modules = self.pool.get('ir.module.module')
@@ -199,31 +185,14 @@
pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
po = pur_obj.browse(cr, uid, pur_id)[0]
assert(po.picking_ids),"Picking for purchase order has not been generated"
+ picking, = po.picking_ids
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [picking.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
- Then I click on the "Products Received" button of Incoming Shipments
--
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
--
- I click on the "Validate" button
--
- !python {model: stock.picking}: |
- modules = self.pool.get('ir.module.module')
- mod_pur = modules.search(cr, uid, [('name','=','purchase')])
- mod_brw = modules.browse(cr,uid,mod_pur)[0]
- if (mod_brw.state == 'installed'):
- sale_order_obj = self.pool.get('sale.order')
- pur_obj = self.pool.get('purchase.order')
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so8"))
- pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
- po = pur_obj.browse(cr, uid, pur_id)[0]
- pick_ser_id = self.search(cr, uid, [('purchase_id', '=', po.id )])
- import netsvc
- wf_service = netsvc.LocalService("workflow")
- for pick in pick_ser_id:
- wf_service.trg_validate(uid, 'stock.picking',pick,'button_done', cr)
--
- I verify that picking for purchase order has been done.
+ I verify that picking for purchase order has been marked done.
-
!python {model: sale.order}: |
from tools.translate import _
@@ -239,7 +208,7 @@
ids = picking_obj.search(cr, uid, [('purchase_id', '=', po.id ),('state', '=', 'done')])
assert ids, _('Picking is not in the done state!')
-
- I verify that a "Picked" has been set to true
+ I verify that the sale order is marked as delivered
-
!python {model: sale.order}: |
so = self.browse(cr, uid, ref("sale_order_so8"))
diff --git a/addons/sale/test/prepaid_order_policy.yml b/addons/sale/test/prepaid_order_policy.yml
index 4bf132e5bee..d6f3da64a2c 100644
--- a/addons/sale/test/prepaid_order_policy.yml
+++ b/addons/sale/test/prepaid_order_policy.yml
@@ -101,18 +101,11 @@
if picking_id:
pick=self.browse(cr,uid,picking_id[0])
pick.force_assign(cr, uid)
- partial_datas = {
- 'partner_id':pick.address_id.partner_id.id,
- 'address_id': pick.address_id.id,
- 'delivery_date' : time.strftime('%Y-%m-%d'),
- }
- move = pick.move_lines[0]
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id.id,
- 'product_qty': move.product_qty,
- 'product_uom': move.product_uom.id,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [pick.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I verify that picking order is in done state.
-
@@ -201,7 +194,7 @@
for pur in pur_ids:
wf_service.trg_validate(uid, 'purchase.order',pur,'purchase_approve', cr)
-
- I verify that a picking related to purchase order has been generated.
+ I verify that a picking related to purchase order has been generated and I process it
-
!python {model: sale.order}: |
modules = self.pool.get('ir.module.module')
@@ -213,51 +206,21 @@
pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
po = pur_obj.browse(cr, uid, pur_id)[0]
assert(po.picking_ids),"Picking for purchase order has not been generated"
--
- Then I click on the "Products Received" button of Incoming Shipments
--
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
--
- I click on the "Validate" button
--
- !python {model: stock.picking}: |
- modules = self.pool.get('ir.module.module')
- sale_order_obj = self.pool.get('sale.order')
- pur_obj = self.pool.get('purchase.order')
- mod_pur = modules.search(cr, uid, [('name','=','purchase')])
- mod_brw = modules.browse(cr,uid,mod_pur)[0]
- if (mod_brw.state == 'installed'):
- so = sale_order_obj.browse(cr, uid, ref("sale_order_so1"))
- pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
- po = pur_obj.browse(cr, uid, pur_id)[0]
- pick_ser_id = self.search(cr, uid, [('purchase_id', '=', po.id )])
- import netsvc
- wf_service = netsvc.LocalService("workflow")
- for pick in pick_ser_id:
- wf_service.trg_validate(uid, 'stock.picking',pick,'button_done', cr)
--
- I verify that picking for purchase order has been done.
--
- !python {model: sale.order}: |
- from tools.translate import _
- modules = self.pool.get('ir.module.module')
- mod_pur = modules.search(cr, uid, [('name','=','purchase')])
- mod_brw = modules.browse(cr,uid,mod_pur)[0]
- if(mod_brw.state == 'installed'):
- pur_obj = self.pool.get('purchase.order')
- so = self.browse(cr, uid, ref("sale_order_so1"))
- pur_id = pur_obj.search(cr, uid, [('origin','=',so.name)])
- po = pur_obj.browse(cr, uid, pur_id)[0]
+ picking, = po.picking_ids
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [picking.id]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
picking_obj = self.pool.get('stock.picking')
- ids = picking_obj.search(cr, uid, [('purchase_id', '=', po.id ),('state', '=', 'done')])
- assert ids, _('Picking is not in the done state!')
+ ids = picking_obj.search(cr, uid, [('purchase_id', '=', po.id),('state', '=', 'done')])
+ assert ids, 'Picking should be marked done!'
-
- I verify that a "Picked" has been set to true
+ I verify that the sale order is marked as delivered
-
!python {model: sale.order}: |
so = self.browse(cr, uid, ref("sale_order_so1"))
- assert (so.shipped == True), "Picking is not done."
+ assert (so.shipped == True), "Sale order is not marked as delivered"
-
I verify that a sale order is in done state
-
diff --git a/addons/sale/wizard/sale_make_invoice_advance.py b/addons/sale/wizard/sale_make_invoice_advance.py
index 4b1e4511021..4d9e0058e94 100644
--- a/addons/sale/wizard/sale_make_invoice_advance.py
+++ b/addons/sale/wizard/sale_make_invoice_advance.py
@@ -27,8 +27,8 @@ class sale_advance_payment_inv(osv.osv_memory):
_columns = {
'product_id': fields.many2one('product.product', 'Advance Product', required=True,
help="Select a product of type service which is called 'Advance Product'. You may have to create it and set it as a default value on this field."),
- 'amount': fields.float('Advance Amount', size=(16, 2), required=True, help="The amount to be invoiced in advance."),
- 'qtty': fields.float('Quantity', size=(16, 2), required=True),
+ 'amount': fields.float('Advance Amount', digits=(16, 2), required=True, help="The amount to be invoiced in advance."),
+ 'qtty': fields.float('Quantity', digits=(16, 2), required=True),
}
_defaults = {
'qtty': 1.0
@@ -173,4 +173,4 @@ class sale_open_invoice(osv.osv_memory):
sale_open_invoice()
-# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
\ No newline at end of file
+# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
diff --git a/addons/share/res_users.py b/addons/share/res_users.py
index 81683066220..07031ab3845 100644
--- a/addons/share/res_users.py
+++ b/addons/share/res_users.py
@@ -24,7 +24,7 @@ class res_groups(osv.osv):
_name = "res.groups"
_inherit = 'res.groups'
_columns = {
- 'share': fields.boolean('Share Group', groups='share.group_share', readonly=True,
+ 'share': fields.boolean('Share Group', readonly=True,
help="Group created to set access rights for sharing data with some users.")
}
res_groups()
@@ -33,7 +33,7 @@ class res_users(osv.osv):
_name = 'res.users'
_inherit = 'res.users'
_columns = {
- 'share': fields.boolean('Share User', groups='share.group_share', readonly=True,
+ 'share': fields.boolean('Share User', readonly=True,
help="External user with limited access, created only for the purpose of sharing data.")
}
res_users()
diff --git a/addons/stock/i18n/zh_TW.po b/addons/stock/i18n/zh_TW.po
index b59cc94b1b2..93cab1256ae 100644
--- a/addons/stock/i18n/zh_TW.po
+++ b/addons/stock/i18n/zh_TW.po
@@ -7,14 +7,14 @@ msgstr ""
"Project-Id-Version: OpenERP Server 5.0.4\n"
"Report-Msgid-Bugs-To: support@openerp.com\n"
"POT-Creation-Date: 2011-01-11 11:16+0000\n"
-"PO-Revision-Date: 2011-01-28 03:06+0000\n"
+"PO-Revision-Date: 2011-09-27 10:25+0000\n"
"Last-Translator: Walter Cheuk \n"
"Language-Team: \n"
"MIME-Version: 1.0\n"
"Content-Type: text/plain; charset=UTF-8\n"
"Content-Transfer-Encoding: 8bit\n"
-"X-Launchpad-Export-Date: 2011-09-05 04:57+0000\n"
-"X-Generator: Launchpad (build 13830)\n"
+"X-Launchpad-Export-Date: 2011-09-28 05:19+0000\n"
+"X-Generator: Launchpad (build 14049)\n"
#. module: stock
#: field:product.product,track_outgoing:0
@@ -163,7 +163,7 @@ msgstr ""
#: view:report.stock.move:0
#: field:stock.change.standard.price,stock_journal:0
msgid "Stock journal"
-msgstr ""
+msgstr "庫存日誌"
#. module: stock
#: view:report.stock.move:0
@@ -475,7 +475,7 @@ msgstr "調動統計"
#. module: stock
#: view:stock.production.lot:0
msgid "Product Lots Filter"
-msgstr ""
+msgstr "生產批次篩選"
#. module: stock
#: report:lot.stock.overview:0
@@ -636,7 +636,7 @@ msgstr ""
#. module: stock
#: constraint:stock.move:0
msgid "You try to assign a lot which is not from the same product"
-msgstr ""
+msgstr "指定了不同產品的批次"
#. module: stock
#: view:res.partner:0
@@ -1152,7 +1152,7 @@ msgstr ""
#: code:addons/stock/stock.py:1319
#, python-format
msgid "is in draft state."
-msgstr "尚在草案階段"
+msgstr "尚在草案階段。"
#. module: stock
#: model:ir.actions.act_window,help:stock.action_tracking_form
@@ -1402,6 +1402,12 @@ msgid ""
"* Done: has been processed, can't be modified or cancelled anymore\n"
"* Cancelled: has been cancelled, can't be confirmed anymore"
msgstr ""
+"* 草案(Draft): 未確認,不會安排處理直至確認\n"
+"* 確認(Confirmed): 仍等候產品有貨供應\n"
+"* 供貨(Available): 已預留產品,只等候確認\n"
+"* 等待(Waiting): 自動供貨前要再等候下一步 (如於「接單生產(Make-To-Order)」流程)\n"
+"* 完成(Done): 已處理,無法再修改或取消\n"
+"* 取消(Cancelled): 已取消,無法再確認"
#. module: stock
#: help:stock.location,company_id:0
@@ -1440,6 +1446,11 @@ msgid ""
" When the picking is done the state is 'Done'. \n"
"The state is 'Waiting' if the move is waiting for another one."
msgstr ""
+"建立調動時先處於「草案(Draft)」狀態。\n"
+" 然後,如安排者找不到貨,設為「無貨(Not Available)」狀態。\n"
+" 當已預留貨物,變成「供貨(Available)」。\n"
+" 完成提貨後狀態為「完成(Done)」。 \n"
+"如調動正等候其他工作完成,狀態為「等待(Waiting)」。"
#. module: stock
#: selection:report.stock.inventory,location_type:0
@@ -1486,7 +1497,7 @@ msgstr "貨幣"
#. module: stock
#: field:product.product,track_production:0
msgid "Track Manufacturing Lots"
-msgstr ""
+msgstr "追蹤生產批次"
#. module: stock
#: code:addons/stock/wizard/stock_inventory_merge.py:44
@@ -1537,7 +1548,7 @@ msgstr "貨架 2"
#. module: stock
#: field:stock.report.tracklots,tracking_id:0
msgid "Tracking lot"
-msgstr ""
+msgstr "追蹤批次"
#. module: stock
#: view:stock.picking:0
@@ -1558,7 +1569,7 @@ msgstr "本地化"
#. module: stock
#: model:ir.model,name:stock.model_stock_report_tracklots
msgid "Stock report by tracking lots"
-msgstr ""
+msgstr "按追蹤批次庫存報告"
#. module: stock
#: code:addons/stock/product.py:370
@@ -2119,7 +2130,7 @@ msgstr ""
#: code:addons/stock/stock.py:2210
#, python-format
msgid "You can only delete draft moves."
-msgstr "不能刪除調動草案"
+msgstr "只能刪除調動草案。"
#. module: stock
#: code:addons/stock/wizard/stock_partial_picking.py:97
@@ -2542,7 +2553,7 @@ msgstr "數量(量度單位)"
#, python-format
msgid ""
"You are moving %.2f %s products but only %.2f %s available in this lot."
-msgstr ""
+msgstr "您正移動%.2f件 %s 產品,但此批次只有%.2f件 %s。"
#. module: stock
#: view:stock.move:0
@@ -3032,7 +3043,7 @@ msgstr ""
#. module: stock
#: view:stock.inventory:0
msgid "Lot Inventory"
-msgstr ""
+msgstr "批次存貨"
#. module: stock
#: view:stock.move:0
@@ -3501,6 +3512,11 @@ msgid ""
" When the picking it done the state is 'Done'. \n"
"The state is 'Waiting' if the move is waiting for another one."
msgstr ""
+"建立調動時先處於「草案(Draft)」狀態。\n"
+" 然後設為「確認(Confirmed)」狀態。\n"
+" 如庫存有貨,變成「供貨(Available)」。\n"
+" 完成提貨後狀態為「完成(Done)」。 \n"
+"如調動正等候其他工作完成,狀態為「等待(Waiting)」。"
#. module: stock
#: view:board.board:0
@@ -3720,7 +3736,7 @@ msgstr ""
#. module: stock
#: constraint:stock.move:0
msgid "You must assign a production lot for this product"
-msgstr "須為此產品分配生產批次"
+msgstr "須為此產品指定生產批次"
#. module: stock
#: view:stock.move:0
@@ -3817,7 +3833,7 @@ msgstr ""
#. module: stock
#: model:ir.model,name:stock.model_stock_report_prodlots
msgid "Stock report by production lots"
-msgstr "生產批次回報之庫存"
+msgstr "按生產批次庫存報告"
#. module: stock
#: view:stock.location:0
@@ -3878,7 +3894,7 @@ msgstr "輸出"
#. module: stock
#: selection:stock.move.split.lines,action:0
msgid "Keep in one lot"
-msgstr ""
+msgstr "保持為同一批次"
#. module: stock
#: view:product.product:0
diff --git a/addons/stock/product_view.xml b/addons/stock/product_view.xml
index 80d7ed6efa0..a0059ce60d3 100644
--- a/addons/stock/product_view.xml
+++ b/addons/stock/product_view.xml
@@ -120,6 +120,67 @@
+
+
+ Product Kanban
+ product.product
+ kanban
+
+
+
+
+
+
+
+
+
+
+ []
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ No Stock
+
+
On Hand , Available
+
Public Price : , Cost :
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+ product.normal.stock.property.form.inherit
diff --git a/addons/stock/stock.py b/addons/stock/stock.py
index 2dbfc5105c1..d9debe6641b 100644
--- a/addons/stock/stock.py
+++ b/addons/stock/stock.py
@@ -664,8 +664,8 @@ class stock_picking(osv.osv):
def action_process(self, cr, uid, ids, context=None):
if context is None: context = {}
- partial_id = self.pool.get("stock.partial.picking").create(
- cr, uid, {}, context=dict(context, active_ids=ids))
+ context = dict(context, active_ids=ids, active_model=self._name)
+ partial_id = self.pool.get("stock.partial.picking").create(cr, uid, {}, context=context)
return {
'name':_("Products to Process"),
'view_mode': 'form',
@@ -677,7 +677,7 @@ class stock_picking(osv.osv):
'nodestroy': True,
'target': 'new',
'domain': '[]',
- 'context': dict(context, active_ids=ids)
+ 'context': context,
}
def copy(self, cr, uid, id, default=None, context=None):
@@ -1474,6 +1474,8 @@ class stock_move(osv.osv):
def action_partial_move(self, cr, uid, ids, context=None):
if context is None: context = {}
+ if context.get('active_model') != self._name:
+ context.update(active_ids=ids, active_model=self._name)
partial_id = self.pool.get("stock.partial.move").create(
cr, uid, {}, context=context)
return {
@@ -2127,14 +2129,9 @@ class stock_move(osv.osv):
""" Makes the move done and if all moves are done, it will finish the picking.
@return:
"""
- partial_datas=''
picking_ids = []
move_ids = []
- partial_obj=self.pool.get('stock.partial.picking')
wf_service = netsvc.LocalService("workflow")
- partial_id=partial_obj.search(cr,uid,[])
- if partial_id:
- partial_datas = partial_obj.read(cr, uid, partial_id, context=context)[0]
if context is None:
context = {}
@@ -2164,9 +2161,6 @@ class stock_move(osv.osv):
self.action_done(cr, uid, [move.move_dest_id.id], context=context)
self._create_product_valuation_moves(cr, uid, move, context=context)
- prodlot_id = partial_datas and partial_datas.get('move%s_prodlot_id' % (move.id), False)
- if prodlot_id:
- self.write(cr, uid, [move.id], {'prodlot_id': prodlot_id}, context=context)
if move.state not in ('confirmed','done','assigned'):
todo.append(move.id)
diff --git a/addons/stock/stock_data.xml b/addons/stock/stock_data.xml
index bcde818c78a..c0c872e99f2 100644
--- a/addons/stock/stock_data.xml
+++ b/addons/stock/stock_data.xml
@@ -2,12 +2,17 @@
+
+ Stock Journal Sequence
+
+ STJ/%(year)s/
+ Stock JournalSTJgeneral
-
+
diff --git a/addons/stock/test/stock_test.yml b/addons/stock/test/stock_test.yml
index ebd3c6670b4..63650ffeb38 100644
--- a/addons/stock/test/stock_test.yml
+++ b/addons/stock/test/stock_test.yml
@@ -184,37 +184,32 @@
self.fill_inventory(cr, uid, [ref("stock_fill_inventory_0")], context)
-
- I create stock.inventory.line.split record.
+ I split the PC3 inventory line to create 5 PC3 with production lot 00002-stock-test
-
!record {model: stock.inventory.line.split, id: stock_inventory_line_0}:
line_ids:
- name: '00002-stock-test'
quantity: 5
- line_exist_ids:
- - name: '00003-stock-test'
- quantity: 5
product_id: product.product_product_pc1
product_uom: product.product_uom_unit
use_exist: False
qty: 10
-
-
- I Split stock.inventory.line into production line.
+ I confirm the split operation
-
- !python {model: stock.inventory.line.split}: |
- context = {"lang": 'en_US', "active_model": "stock.inventory.line",
- "active_ids": [ref("stock_inventory_line_0")], "tz": False, "active_id": ref("stock_inventory_line_0")}
- self.default_get(cr, uid, ["product_id", "product_uom", "line_exist_ids", "qty",
- "line_ids", "use_exist"], context)
- self.split_lot(cr, uid, [ref("stock_inventory_line_0")], context)
-
+ !python {model: stock.inventory.line}: |
+ line_ids = self.search(cr, uid, [('inventory_id','=',ref('stock_inventory_physicalinventoy0')),
+ ('product_id','=',ref('product.product_product_pc1'))])
+ assert line_ids, 'Inventory lines are missing'
+ self.pool.get('stock.inventory.line.split').split_lot(cr, uid, [ref("stock_inventory_line_0")],
+ {'active_model': 'stock.inventory.line',
+ 'active_ids': [line_ids[0]]})
-
I confirm the Inventory for PC3.
-
!python {model: stock.inventory}: |
self.action_confirm(cr,uid,[ref('stock_inventory_physicalinventoy0')])
self.action_done(cr,uid,[ref('stock_inventory_physicalinventoy0')])
-
-
I cancel the Inventory for PC3.
-
@@ -251,7 +246,7 @@
type: out
-
- I Performing an osv_memory action split on module stock.split.into
+ I split the picking with a first batch of 20 PCs
-
!python {model: stock.picking }: |
pick=self.browse(cr,uid,ref('stock_picking_0'))
@@ -285,31 +280,15 @@
ref("stock.menu_action_picking_tree6"), })
-
- I create a record for stock.partial.move.
+ I process the partial picking with 20 PCE
-
- !record {model: stock.partial.move, id: stock_partial_move_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
-
--
- I done stock.partial.move record.
--
- !python {model: stock.partial.move }: |
- pick_obj = self.pool.get('stock.picking')
- move_obj = self.pool.get('stock.move')
- pick=pick_obj.browse(cr,uid,ref('stock_picking_0'))
- search_id = move_obj.search(cr, uid, [('picking_id', '=', pick.id)])
- partial_datas={}
- for move in pick.move_lines:
- partial_datas['move%s'%(move.id)]= {
- 'quantity': 20,
- 'product_uom': move.product_uom.id,
- 'prodlot_id': move.prodlot_id and move.prodlot_id.id or False,
- 'wizard_id': ref('stock_partial_move_0'),
- }
- context = {"lang": 'en_US', "active_model": "stock.move", "active_ids": search_id, "tz": False, "active_id":search_id[0]}
- self.fields_view_get(cr, uid, False,"form", context)
- self.do_partial(cr, uid, [ref('stock_partial_move_0')], context)
-
+ !python {model: stock.picking }: |
+ pick = self.browse(cr,uid,ref('stock_picking_0'))
+ stock_partial_move = self.pool.get('stock.partial.move')
+ partial_id = stock_partial_move.create(cr, uid, {},
+ context={'active_model': 'stock.move',
+ 'active_ids': [x.id for x in pick.move_lines]})
+ stock_partial_move.do_partial(cr, uid, [partial_id])
-
I Performing an osv_memory action split_lot on module stock.move.split
-
@@ -384,34 +363,14 @@
consume_obj.do_move_consume(cr, uid, [consume_id], context)
-
- I create a record for stock partial picking.
+ I process the picking with the 80 remaining PCs
-
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
-
--
- I make stock partial picking order Done.
--
- !python {model: stock.partial.picking}: |
- pick_obj = self.pool.get('stock.picking')
- partial = self.browse(cr, uid, ref('stock_partial_picking_0'), context)
- partial_datas = {
- 'delivery_date' : partial.date
- }
- for pick in pick_obj.browse(cr, uid, [ref('stock_picking_0')]):
- for m in pick.move_lines:
- partial_datas['move%s'%(m.id)] = {
- 'product_id' : m.product_id.id,
- 'product_qty' : 80,
- 'product_uom' : m.product_uom.id
- }
- context = {"lang": "en_US", "search_default_available":
- 1, "tz": False, "active_model": "ir.ui.menu",
- "active_ids": [ref('stock_picking_0')], "active_id": ref("stock_picking_0"),
- }
- self.fields_view_get(cr, uid, False,"form", context)
- self.do_partial(cr, uid, [ref('stock_partial_picking_0')], context)
-
+ !python {model: stock.picking}: |
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ partial_id = stock_partial_picking.create(cr, uid, {},
+ context={'active_model': 'stock.picking',
+ 'active_ids': [ref('stock_picking_0')]})
+ stock_partial_picking.do_partial(cr, uid, [partial_id])
-
I Performing an osv_memory action create_invoice on module stock.invoice.onshipping
-
@@ -447,35 +406,20 @@
1, "tz": False, "active_model": "ir.ui.menu", "contact_display": "partner_address",
"active_ids": [ref("stock.menu_action_picking_tree4")], "active_id": ref("stock.menu_action_picking_tree4"),
})
- pick=self.browse(cr,uid,copy_id)
self.allow_cancel(cr, uid, [copy_id], context= None)
-
- I create a record of stock.picking and I reaturn the picking
+ I process a copy of the picking and I return it
-
!python {model: stock.picking}: |
copy_id = self.copy(cr, uid, (ref("stock_picking_0")))
- ctx = {"lang": "en_US", "active_model":
- "ir.ui.menu", "tz": False, "search_default_confirmed": 1, "contact_display":
- "partner", "active_ids": [ref("stock.menu_action_picking_tree6")], "active_id":
- ref("stock.menu_action_picking_tree6")}
- self.draft_force_assign(cr, uid, [copy_id], ctx)
- self.force_assign(cr, uid, [copy_id], ctx)
- pick=self.browse(cr,uid,copy_id)
- partial_datas={}
- for move in pick.move_lines:
- partial_datas['move%s'%(move.id)]= {
- 'product_id': move.product_id,
- 'product_qty': move.product_qty,
- }
- self.do_partial(cr, uid, [pick.id],partial_datas)
- reurn_datas={}
- context = {"lang": 'en_US', "active_model":
- "stock.picking", "active_ids": [pick.id], "tz": False, "active_id":pick.id}
+ self.draft_force_assign(cr, uid, [copy_id])
+ self.force_assign(cr, uid, [copy_id])
+ stock_partial_picking = self.pool.get('stock.partial.picking')
+ context = {'active_model': 'stock.picking',
+ 'active_ids': [copy_id],
+ 'active_id': copy_id}
+ partial_id = stock_partial_picking.create(cr, uid, {}, context=context)
+ stock_partial_picking.do_partial(cr, uid, [partial_id], context)
return_pick_id = self.pool.get('stock.return.picking').create(cr, uid,{}, context)
- for move in pick.move_lines:
- reurn_datas= {
- 'product_id': move.product_id.id,
- 'quantity': move.product_qty,
- }
self.pool.get('stock.return.picking').create_returns(cr, uid, [return_pick_id], context)
diff --git a/addons/stock/wizard/stock_inventory_line_split.py b/addons/stock/wizard/stock_inventory_line_split.py
index 2e8b93ad52b..ae4ce54ab9b 100644
--- a/addons/stock/wizard/stock_inventory_line_split.py
+++ b/addons/stock/wizard/stock_inventory_line_split.py
@@ -21,24 +21,17 @@
from osv import fields, osv
-from tools.translate import _
-import time
-
class stock_inventory_line_split(osv.osv_memory):
_inherit = "stock.move.split"
_name = "stock.inventory.line.split"
_description = "Split inventory lines"
+ _columns = {
+ 'line_ids': fields.one2many('stock.inventory.line.split.lines', 'wizard_id', 'Production Lots'),
+ 'line_exist_ids': fields.one2many('stock.inventory.line.split.lines', 'wizard_exist_id', 'Production Lots'),
+ }
def default_get(self, cr, uid, fields, context=None):
- """ To check the availability of production lot.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param fields: List of fields for which we want default values
- @param context: A standard dictionary
- @return: A dictionary which of fields with values.
- """
if context is None:
context = {}
record_id = context and context.get('active_id',False)
@@ -54,14 +47,13 @@ class stock_inventory_line_split(osv.osv_memory):
def split(self, cr, uid, ids, line_ids, context=None):
""" To split stock inventory lines according to production lot.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param ids: the ID or list of IDs if we want more than one
- @param line_ids: the ID or list of IDs of inventory lines we want to split
- @param context: A standard dictionary
- @return:
+
+ :param line_ids: the ID or list of IDs of inventory lines we want to split
"""
+ if context is None:
+ context = {}
+ assert context.get('active_model') == 'stock.inventory.line',\
+ 'Incorrect use of the inventory line split wizard'
prodlot_obj = self.pool.get('stock.production.lot')
ir_sequence_obj = self.pool.get('ir.sequence')
line_obj = self.pool.get('stock.inventory.line')
@@ -108,7 +100,14 @@ class stock_inventory_line_split(osv.osv_memory):
line_obj.write(cr, uid, [inv_line.id], update_val)
return new_line
-stock_inventory_line_split()
-# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
+class stock_inventory_split_lines(osv.osv_memory):
+ _inherit = "stock.move.split.lines"
+ _name = "stock.inventory.line.split.lines"
+ _description = "Inventory Split lines"
+ _columns = {
+ 'wizard_id': fields.many2one('stock.inventory.line.split', 'Parent Wizard'),
+ 'wizard_exist_id': fields.many2one('stock.inventory.line.split', 'Parent Wizard'),
+ }
+# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
\ No newline at end of file
diff --git a/addons/stock/wizard/stock_invoice_onshipping.py b/addons/stock/wizard/stock_invoice_onshipping.py
index 66256509c7b..f4618249e37 100644
--- a/addons/stock/wizard/stock_invoice_onshipping.py
+++ b/addons/stock/wizard/stock_invoice_onshipping.py
@@ -28,7 +28,7 @@ class stock_invoice_onshipping(osv.osv_memory):
def _get_journal(self, cr, uid, context=None):
res = self._get_journal_id(cr, uid, context=context)
if res:
- return res[0]
+ return res[0][0]
return False
def _get_journal_id(self, cr, uid, context=None):
diff --git a/addons/stock/wizard/stock_move.py b/addons/stock/wizard/stock_move.py
index 0e84997db85..1a655878d8a 100644
--- a/addons/stock/wizard/stock_move.py
+++ b/addons/stock/wizard/stock_move.py
@@ -20,7 +20,7 @@
##############################################################################
from osv import fields, osv
-
+from tools.translate import _
import decimal_precision as dp
class stock_move_consume(osv.osv_memory):
@@ -146,14 +146,6 @@ class split_in_production_lot(osv.osv_memory):
_description = "Split in Production lots"
def default_get(self, cr, uid, fields, context=None):
- """ Get default values
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param fields: List of fields for default value
- @param context: A standard dictionary
- @return: Default values of fields
- """
if context is None:
context = {}
res = super(split_in_production_lot, self).default_get(cr, uid, fields, context=context)
@@ -175,38 +167,28 @@ class split_in_production_lot(osv.osv_memory):
'qty': fields.float('Quantity', digits_compute=dp.get_precision('Product UoM')),
'product_id': fields.many2one('product.product', 'Product', required=True, select=True),
'product_uom': fields.many2one('product.uom', 'UoM'),
- 'line_ids': fields.one2many('stock.move.split.lines', 'lot_id', 'Production Lots'),
- 'line_exist_ids': fields.one2many('stock.move.split.lines.exist', 'lot_id', 'Production Lots'),
+ 'line_ids': fields.one2many('stock.move.split.lines', 'wizard_id', 'Production Lots'),
+ 'line_exist_ids': fields.one2many('stock.move.split.lines', 'wizard_exist_id', 'Production Lots'),
'use_exist' : fields.boolean('Existing Lots', help="Check this option to select existing lots in the list below, otherwise you should enter new ones line by line."),
'location_id': fields.many2one('stock.location', 'Source Location')
}
def split_lot(self, cr, uid, ids, context=None):
- """ To split a lot
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param ids: An ID or list of IDs if we want more than one
- @param context: A standard dictionary
- @return:
- """
+ """ To split a lot"""
if context is None:
context = {}
- self.split(cr, uid, ids, context.get('active_ids'), context=context)
+ res = self.split(cr, uid, ids, context.get('active_ids'), context=context)
return {'type': 'ir.actions.act_window_close'}
def split(self, cr, uid, ids, move_ids, context=None):
""" To split stock moves into production lot
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param ids: the ID or list of IDs if we want more than one
- @param move_ids: the ID or list of IDs of stock move we want to split
- @param context: A standard dictionary
- @return:
+
+ :param move_ids: the ID or list of IDs of stock move we want to split
"""
if context is None:
context = {}
+ assert context.get('active_model') == 'stock.move',\
+ 'Incorrect use of the stock move split wizard'
inventory_id = context.get('inventory_id', False)
prodlot_obj = self.pool.get('stock.production.lot')
inventory_obj = self.pool.get('stock.inventory')
@@ -231,7 +213,8 @@ class split_in_production_lot(osv.osv_memory):
uos_qty_rest = quantity_rest / move_qty * move.product_uos_qty
if quantity_rest < 0:
quantity_rest = quantity
- break
+ self.pool.get('stock.move').log(cr, uid, move.id, _('Unable to assign all lots to this move!'))
+ return False
default_val = {
'product_qty': quantity,
'product_uos_qty': uos_qty,
@@ -268,12 +251,13 @@ class split_in_production_lot(osv.osv_memory):
split_in_production_lot()
class stock_move_split_lines_exist(osv.osv_memory):
- _name = "stock.move.split.lines.exist"
- _description = "Exist Split lines"
+ _name = "stock.move.split.lines"
+ _description = "Stock move Split lines"
_columns = {
'name': fields.char('Tracking serial', size=64),
'quantity': fields.float('Quantity', digits_compute=dp.get_precision('Product UoM')),
- 'lot_id': fields.many2one('stock.move.split', 'Lot'),
+ 'wizard_id': fields.many2one('stock.move.split', 'Parent Wizard'),
+ 'wizard_exist_id': fields.many2one('stock.move.split', 'Parent Wizard (for existing lines)'),
'prodlot_id': fields.many2one('stock.production.lot', 'Production Lot'),
}
_defaults = {
@@ -284,21 +268,3 @@ class stock_move_split_lines_exist(osv.osv_memory):
loc_id=False, product_id=False, uom_id=False):
return self.pool.get('stock.move').onchange_lot_id(cr, uid, [], prodlot_id, product_qty,
loc_id, product_id, uom_id)
-
-stock_move_split_lines_exist()
-
-class stock_move_split_lines(osv.osv_memory):
- _name = "stock.move.split.lines"
- _description = "Split lines"
- _columns = {
- 'name': fields.char('Tracking serial', size=64),
- 'quantity': fields.float('Quantity', digits_compute=dp.get_precision('Product UoM')),
- 'use_exist' : fields.boolean('Existing Lot'),
- 'lot_id': fields.many2one('stock.move.split', 'Lot'),
- 'action': fields.selection([('split','Split'),('keepinone','Keep in one lot')],'Action'),
- }
- _defaults = {
- 'quantity': 1.00,
- 'action' : 'split',
- }
-stock_move_split_lines()
diff --git a/addons/stock/wizard/stock_partial_move.py b/addons/stock/wizard/stock_partial_move.py
index 2c593e811c5..ec348656ce0 100644
--- a/addons/stock/wizard/stock_partial_move.py
+++ b/addons/stock/wizard/stock_partial_move.py
@@ -2,7 +2,7 @@
##############################################################################
#
# OpenERP, Open Source Management Solution
-# Copyright (C) 2004-2010 Tiny SPRL ().
+# Copyright (C) 2004-TODAY OpenERP SA ().
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
@@ -20,210 +20,65 @@
##############################################################################
from osv import fields, osv
-from tools.translate import _
+from tools.misc import DEFAULT_SERVER_DATETIME_FORMAT
import time
-import decimal_precision as dp
-
-class stock_partial_move_memory_out(osv.osv_memory):
- _name = "stock.move.memory.out"
- _rec_name = 'product_id'
+class stock_partial_move_line(osv.osv_memory):
+ _inherit = "stock.partial.picking.line"
+ _name = "stock.partial.move.line"
_columns = {
- 'product_id' : fields.many2one('product.product', string="Product", required=True),
- 'quantity' : fields.float("Quantity", required=True),
- 'product_uom': fields.many2one('product.uom', 'Unit of Measure', required=True),
- 'prodlot_id' : fields.many2one('stock.production.lot', 'Production Lot'),
- 'location_id': fields.many2one('stock.location', 'Location', required=True),
- 'location_dest_id': fields.many2one('stock.location', 'Dest. Location', required=True),
- 'move_id' : fields.many2one('stock.move', "Move"),
- 'wizard_id' : fields.many2one('stock.partial.move', string="Wizard"),
- 'cost' : fields.float('Cost', digits_compute = dp.get_precision('Purchase Price'),help="Unit Cost for this product line"),
- 'currency' : fields.many2one('res.currency', string="Currency", help="Currency in which Unit cost is expressed"),
+ 'wizard_id' : fields.many2one('stock.partial.move', string="Wizard", ondelete='CASCADE'),
}
-
-class stock_partial_move_memory_in(osv.osv_memory):
- _inherit = "stock.move.memory.out"
- _name = "stock.move.memory.in"
-
+
class stock_partial_move(osv.osv_memory):
_name = "stock.partial.move"
- _description = "Partial Move"
+ _inherit = 'stock.partial.picking'
+ _description = "Partial Move Processing Wizard"
_columns = {
'date': fields.datetime('Date', required=True),
- 'type': fields.char("Type", size=3),
- 'product_moves_out' : fields.one2many('stock.move.memory.out', 'wizard_id', 'Moves'),
- 'product_moves_in' : fields.one2many('stock.move.memory.in', 'wizard_id', 'Moves'),
- }
-
-
- def __is_in(self,cr, uid, move_ids):
- """
- @return: True if one of the moves has as picking type 'in'
- """
- if not move_ids:
- return False
-
- move_obj = self.pool.get('stock.move')
- move_ids = move_obj.search(cr, uid, [('id','in',move_ids)])
-
- for move in move_obj.browse(cr, uid, move_ids):
- if move.picking_id.type == 'in' and move.product_id.cost_method == 'average':
- return True
- return False
-
- def __get_picking_type(self, cr, uid, move_ids):
- if self.__is_in(cr, uid, move_ids):
- return "product_moves_in"
- else:
- return "product_moves_out"
-
- def view_init(self, cr, uid, fields_list, context=None):
- res = super(stock_partial_move, self).view_init(cr, uid, fields_list, context=context)
- move_obj = self.pool.get('stock.move')
-
- if context is None:
- context = {}
- for move in move_obj.browse(cr, uid, context.get('active_ids', []), context=context):
- if move.state in ('done', 'cancel'):
- raise osv.except_osv(_('Invalid action !'), _('Cannot deliver products which are already delivered !'))
-
- return res
-
-
- def __create_partial_move_memory(self, move):
- move_memory = {
- 'product_id' : move.product_id.id,
- 'quantity' : move.product_qty,
- 'product_uom' : move.product_uom.id,
- 'prodlot_id' : move.prodlot_id.id,
- 'move_id' : move.id,
- }
-
- if move.picking_id.type == 'in':
- move_memory.update({
- 'cost' : move.product_id.standard_price,
- 'currency' : move.product_id.company_id and move.product_id.company_id.currency_id and move.product_id.company_id.currency_id.id or False,
- })
- return move_memory
+ 'move_ids' : fields.one2many('stock.partial.move.line', 'wizard_id', 'Moves'),
- def __get_active_stock_moves(self, cr, uid, context=None):
- move_obj = self.pool.get('stock.move')
- if context is None:
- context = {}
-
- res = []
- for move in move_obj.browse(cr, uid, context.get('active_ids', []), context=context):
- if move.state in ('done', 'cancel'):
- continue
- res.append(self.__create_partial_move_memory(move))
-
+ # picking_id is not used for move processing, so we remove the required attribute
+ # from the inherited column, and ignore it
+ 'picking_id': fields.many2one('stock.picking', 'Picking'),
+ }
+
+ def default_get(self, cr, uid, fields, context=None):
+ if context is None: context = {}
+ # no call to super!
+ res = {}
+ move_ids = context.get('active_ids', [])
+ if not move_ids or not context.get('active_model') == 'stock.move':
+ return res
+ if 'move_ids' in fields:
+ move_ids = self.pool.get('stock.move').browse(cr, uid, move_ids, context=context)
+ moves = [self._partial_move_for(cr, uid, m) for m in move_ids if m.state not in ('done','cancel')]
+ res.update(move_ids=moves)
+ if 'date' in fields:
+ res.update(date=time.strftime(DEFAULT_SERVER_DATETIME_FORMAT))
return res
-
- _defaults = {
- 'product_moves_in' : __get_active_stock_moves,
- 'product_moves_out' : __get_active_stock_moves,
- 'date' : lambda *a : time.strftime('%Y-%m-%d %H:%M:%S'),
- }
-
-
- def fields_view_get(self, cr, uid, view_id=None, view_type='form', context=None, toolbar=False, submenu=False):
- if not context:
- context = {}
-
- message = {
- 'title' : _('Deliver Products'),
- 'info' : _('Delivery Information'),
- 'button' : _('Deliver'),
- }
- if context:
- if context.get('product_receive', False):
- message = {
- 'title' : _('Receive Products'),
- 'info' : _('Receive Information'),
- 'button' : _('Receive'),
- }
-
- move_ids = context.get('active_ids', False)
- message['picking_type'] = self.__get_picking_type(cr, uid, move_ids)
- result = super(stock_partial_move, self).fields_view_get(cr, uid, view_id, view_type, context, toolbar, submenu)
- _moves_fields = result['fields']
- _moves_fields.update({
- 'product_moves_in' : {'relation': 'stock.move.memory.in', 'type' : 'one2many', 'string' : 'Product Moves'},
- 'product_moves_out' : {'relation': 'stock.move.memory.out', 'type' : 'one2many', 'string' : 'Product Moves'}
- })
-
- _moves_arch_lst = """
-
-
-
-
-
-
-
-
-
-
-
-
""" % message
-
- result['arch'] = _moves_arch_lst
- result['fields'] = _moves_fields
- return result
-
+
def do_partial(self, cr, uid, ids, context=None):
- """ Makes partial moves and pickings done.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param fields: List of fields for which we want default values
- @param context: A standard dictionary
- @return: A dictionary which of fields with values.
- """
-
- if context is None:
- context = {}
- move_obj = self.pool.get('stock.move')
-
- move_ids = context.get('active_ids', False)
+ # no call to super!
+ assert len(ids) == 1, 'Partial move processing may only be done one form at a time'
partial = self.browse(cr, uid, ids[0], context=context)
- partial_datas = {
+ partial_data = {
'delivery_date' : partial.date
}
-
- p_moves = {}
- picking_type = self.__get_picking_type(cr, uid, move_ids)
-
- moves_list = picking_type == 'product_moves_in' and partial.product_moves_in or partial.product_moves_out
- for product_move in moves_list:
- p_moves[product_move.move_id.id] = product_move
-
- moves_ids_final = []
- for move in move_obj.browse(cr, uid, move_ids, context=context):
- if move.state in ('done', 'cancel'):
- continue
- if not p_moves.get(move.id):
- continue
- partial_datas['move%s' % (move.id)] = {
- 'product_id' : p_moves[move.id].product_id.id,
- 'product_qty' : p_moves[move.id].quantity,
- 'product_uom' :p_moves[move.id].product_uom.id,
- 'prodlot_id' : p_moves[move.id].prodlot_id.id,
+ moves_ids = []
+ for move in partial.move_ids:
+ move_id = move.move_id.id
+ partial_data['move%s' % (move_id)] = {
+ 'product_id': move.product_id.id,
+ 'product_qty': move.quantity,
+ 'product_uom': move.product_uom.id,
+ 'prodlot_id': move.prodlot_id.id,
}
-
- moves_ids_final.append(move.id)
- if (move.picking_id.type == 'in') and (move.product_id.cost_method == 'average'):
- partial_datas['move%s' % (move.id)].update({
- 'product_price' : p_moves[move.id].cost,
- 'product_currency': p_moves[move.id].currency.id,
- })
-
-
- move_obj.do_partial(cr, uid, moves_ids_final, partial_datas, context=context)
+ moves_ids.append(move_id)
+ if (move.move_id.picking_id.type == 'in') and (move.product_id.cost_method == 'average'):
+ partial_data['move%s' % (move_id)].update(product_price=move.cost,
+ product_currency=move.currency.id)
+ self.pool.get('stock.move').do_partial(cr, uid, moves_ids, partial_data, context=context)
return {'type': 'ir.actions.act_window_close'}
-stock_partial_move()
-stock_partial_move_memory_out()
-stock_partial_move_memory_in()
-# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
-
+# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
\ No newline at end of file
diff --git a/addons/stock/wizard/stock_partial_move_view.xml b/addons/stock/wizard/stock_partial_move_view.xml
index 8d4be66b243..2df6adcc9e7 100644
--- a/addons/stock/wizard/stock_partial_move_view.xml
+++ b/addons/stock/wizard/stock_partial_move_view.xml
@@ -1,16 +1,13 @@
-
-
-
Deliver/Receive Productscodeaction = obj.action_partial_move(context=context)
-
+
@@ -19,75 +16,60 @@
-
-
-
- stock.move.memory.tree
- stock.move.memory.in
- tree
-
-
-
-
-
-
-
-
-
-
-
-
-
-
-
- stock.move.memory.form
- stock.move.memory.in
+
+ stock.partial.move.form
+ stock.partial.moveform
+
+
diff --git a/addons/stock/wizard/stock_partial_picking.py b/addons/stock/wizard/stock_partial_picking.py
index 9ac3fab9f72..3580b21035d 100644
--- a/addons/stock/wizard/stock_partial_picking.py
+++ b/addons/stock/wizard/stock_partial_picking.py
@@ -1,9 +1,8 @@
-
# -*- coding: utf-8 -*-
##############################################################################
#
# OpenERP, Open Source Management Solution
-# Copyright (C) 2004-2010 Tiny SPRL ().
+# Copyright (C) 2004-TODAY OpenERP SA ().
#
# This program is free software: you can redistribute it and/or modify
# it under the terms of the GNU Affero General Public License as
@@ -20,169 +19,119 @@
#
##############################################################################
-from osv import fields, osv
-from tools.translate import _
import time
+from osv import fields, osv
+from tools.misc import DEFAULT_SERVER_DATETIME_FORMAT
+
+class stock_partial_picking_line(osv.TransientModel):
+ _name = "stock.partial.picking.line"
+ _rec_name = 'product_id'
+ _columns = {
+ 'product_id' : fields.many2one('product.product', string="Product", required=True, ondelete='CASCADE'),
+ 'quantity' : fields.float("Quantity", required=True),
+ 'product_uom': fields.many2one('product.uom', 'Unit of Measure', required=True, ondelete='CASCADE'),
+ 'prodlot_id' : fields.many2one('stock.production.lot', 'Production Lot', ondelete='CASCADE'),
+ 'location_id': fields.many2one('stock.location', 'Location', required=True, ondelete='CASCADE'),
+ 'location_dest_id': fields.many2one('stock.location', 'Dest. Location', required=True, ondelete='CASCADE'),
+ 'move_id' : fields.many2one('stock.move', "Move", ondelete='CASCADE'),
+ 'wizard_id' : fields.many2one('stock.partial.picking', string="Wizard", ondelete='CASCADE'),
+ 'update_cost': fields.boolean('Need cost update'),
+ 'cost' : fields.float("Cost", help="Unit Cost for this product line"),
+ 'currency' : fields.many2one('res.currency', string="Currency", help="Currency in which Unit cost is expressed", ondelete='CASCADE'),
+ }
class stock_partial_picking(osv.osv_memory):
_name = "stock.partial.picking"
- _description = "Partial Picking"
+ _description = "Partial Picking Processing Wizard"
_columns = {
'date': fields.datetime('Date', required=True),
- 'product_moves_out' : fields.one2many('stock.move.memory.out', 'wizard_id', 'Moves'),
- 'product_moves_in' : fields.one2many('stock.move.memory.in', 'wizard_id', 'Moves'),
+ 'move_ids' : fields.one2many('stock.partial.picking.line', 'wizard_id', 'Product Moves'),
+ 'picking_id': fields.many2one('stock.picking', 'Picking', required=True, ondelete='CASCADE'),
}
-
- def get_picking_type(self, cr, uid, picking, context=None):
- picking_type = picking.type
- for move in picking.move_lines:
- if picking.type == 'in' and move.product_id.cost_method == 'average':
- picking_type = 'in'
- break
- else:
- picking_type = 'out'
- return picking_type
-
+
def default_get(self, cr, uid, fields, context=None):
- """ To get default values for the object.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param fields: List of fields for which we want default values
- @param context: A standard dictionary
- @return: A dictionary which of fields with values.
- """
- if context is None:
- context = {}
-
- pick_obj = self.pool.get('stock.picking')
+ if context is None: context = {}
res = super(stock_partial_picking, self).default_get(cr, uid, fields, context=context)
picking_ids = context.get('active_ids', [])
- if not picking_ids:
+ if not picking_ids or (not context.get('active_model') == 'stock.picking') \
+ or len(picking_ids) != 1:
+ # Partial Picking Processing may only be done for one picking at a time
return res
-
- result = []
- for pick in pick_obj.browse(cr, uid, picking_ids, context=context):
- pick_type = self.get_picking_type(cr, uid, pick, context=context)
- for m in pick.move_lines:
- if m.state in ('done', 'cancel'):
- continue
- result.append(self.__create_partial_picking_memory(m, pick_type))
-
- if 'product_moves_in' in fields:
- res.update({'product_moves_in': result})
- if 'product_moves_out' in fields:
- res.update({'product_moves_out': result})
+ picking_id, = picking_ids
+ if 'picking_id' in fields:
+ res.update(picking_id=picking_id)
+ if 'move_ids' in fields:
+ picking = self.pool.get('stock.picking').browse(cr, uid, picking_id, context=context)
+ moves = [self._partial_move_for(cr, uid, m) for m in picking.move_lines if m.state not in ('done','cancel')]
+ res.update(move_ids=moves)
if 'date' in fields:
- res.update({'date': time.strftime('%Y-%m-%d %H:%M:%S')})
+ res.update(date=time.strftime(DEFAULT_SERVER_DATETIME_FORMAT))
return res
-
- def fields_view_get(self, cr, uid, view_id=None, view_type='form', context=None, toolbar=False, submenu=False):
- result = super(stock_partial_picking, self).fields_view_get(cr, uid, view_id, view_type, context, toolbar, submenu)
-
- pick_obj = self.pool.get('stock.picking')
- picking_ids = context.get('active_ids', False)
- if not picking_ids:
- # not called through an action (e.g. buildbot), return the default.
- return result
-
- for pick in pick_obj.browse(cr, uid, picking_ids, context=context):
- picking_type = self.get_picking_type(cr, uid, pick, context=context)
+ def _product_cost_for_average_update(self, cr, uid, move):
+ """Returns product cost and currency ID for the given move, suited for re-computing
+ the average product cost.
- _moves_arch_lst = """
-
-
-
- """ % (_('Process Document'), _('Products'), "product_moves_" + picking_type)
- _moves_fields = result['fields']
+ :return: map of the form::
- # add field related to picking type only
- _moves_fields.update({
- 'product_moves_' + picking_type: {'relation': 'stock.move.memory.'+picking_type, 'type' : 'one2many', 'string' : 'Product Moves'},
- })
+ {'cost': 123.34,
+ 'currency': 42}
+ """
+ # Currently, the cost on the product form is supposed to be expressed in the currency
+ # of the company owning the product. If not set, we fall back to the picking's company,
+ # which should work in simple cases.
+ return {'cost': move.product_id.standard_price,
+ 'currency': move.product_id.company_id.currency_id.id \
+ or move.picking_id.company_id.currency_id.id \
+ or False}
- _moves_arch_lst += """
-
-
-
-
-
-
-
"""
- result['arch'] = _moves_arch_lst
- result['fields'] = _moves_fields
- return result
-
- def __create_partial_picking_memory(self, picking, pick_type):
- move_memory = {
- 'product_id' : picking.product_id.id,
- 'quantity' : picking.product_qty,
- 'product_uom' : picking.product_uom.id,
- 'prodlot_id' : picking.prodlot_id.id,
- 'move_id' : picking.id,
- 'location_id' : picking.location_id.id,
- 'location_dest_id' : picking.location_dest_id.id,
+ def _partial_move_for(self, cr, uid, move):
+ partial_move = {
+ 'product_id' : move.product_id.id,
+ 'quantity' : move.product_qty,
+ 'product_uom' : move.product_uom.id,
+ 'prodlot_id' : move.prodlot_id.id,
+ 'move_id' : move.id,
+ 'location_id' : move.location_id.id,
+ 'location_dest_id' : move.location_dest_id.id,
}
-
- if pick_type == 'in':
- move_memory.update({
- 'cost' : picking.product_id.standard_price,
- 'currency' : picking.product_id.company_id and picking.product_id.company_id.currency_id and picking.product_id.company_id.currency_id.id or False,
- })
- return move_memory
+ if move.picking_id.type == 'in' and move.product_id.cost_method == 'average':
+ partial_move.update(update_cost=True, **self._product_cost_for_average_update(cr, uid, move))
+ return partial_move
def do_partial(self, cr, uid, ids, context=None):
- """ Makes partial moves and pickings done.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param fields: List of fields for which we want default values
- @param context: A standard dictionary
- @return: A dictionary which of fields with values.
- """
- pick_obj = self.pool.get('stock.picking')
- stock_move_obj = self.pool.get('stock.move')
- picking_ids = context.get('active_ids', False)
+ assert len(ids) == 1, 'Partial picking processing may only be done one at a time'
+ stock_picking = self.pool.get('stock.picking')
+ stock_move = self.pool.get('stock.move')
partial = self.browse(cr, uid, ids[0], context=context)
- partial_datas = {
+ partial_data = {
'delivery_date' : partial.date
}
- for pick in pick_obj.browse(cr, uid, picking_ids, context=context):
- picking_type = self.get_picking_type(cr, uid, pick, context=context)
- moves_list = picking_type == 'in' and partial.product_moves_in or partial.product_moves_out
- for move in moves_list:
- if not move.move_id.id:
- seq_obj_name = 'stock.picking.' + picking_type
- move_id = stock_move_obj.create(cr,uid,{'name' : self.pool.get('ir.sequence').get(cr, uid, seq_obj_name),
- 'product_id': move.product_id.id,
- 'product_qty': move.quantity,
- 'product_uom': move.product_uom.id,
- 'prodlot_id': move.prodlot_id.id,
- 'location_id' : move.location_id.id,
- 'location_dest_id' : move.location_dest_id.id,
- 'picking_id': pick.id
- },context=context)
- stock_move_obj.action_done(cr, uid, [move_id], context)
- else:
- move_id = move.move_id.id
-
- partial_datas['move%s' % (move_id)] = {
- 'product_id': move.product_id.id,
- 'product_qty': move.quantity,
- 'product_uom': move.product_uom.id,
- 'prodlot_id': move.prodlot_id.id,
- }
- if (picking_type == 'in') and (move.product_id.cost_method == 'average'):
- partial_datas['move%s' % (move.move_id.id)].update({
- 'product_price' : move.cost,
- 'product_currency': move.currency.id,
- })
- pick_obj.do_partial(cr, uid, picking_ids, partial_datas, context=context)
+ picking_type = partial.picking_id.type
+ for move in partial.move_ids:
+ move_id = move.move_id.id
+ if not move_id:
+ seq_obj_name = 'stock.picking.' + picking_type
+ move_id = stock_move.create(cr,uid,{'name' : self.pool.get('ir.sequence').get(cr, uid, seq_obj_name),
+ 'product_id': move.product_id.id,
+ 'product_qty': move.quantity,
+ 'product_uom': move.product_uom.id,
+ 'prodlot_id': move.prodlot_id.id,
+ 'location_id' : move.location_id.id,
+ 'location_dest_id' : move.location_dest_id.id,
+ 'picking_id': partial.picking_id.id
+ },context=context)
+ stock_move.action_done(cr, uid, [move_id], context)
+ partial_data['move%s' % (move_id)] = {
+ 'product_id': move.product_id.id,
+ 'product_qty': move.quantity,
+ 'product_uom': move.product_uom.id,
+ 'prodlot_id': move.prodlot_id.id,
+ }
+ if (picking_type == 'in') and (move.product_id.cost_method == 'average'):
+ partial_data['move%s' % (move.move_id.id)].update(product_price=move.cost,
+ product_currency=move.currency.id)
+ stock_picking.do_partial(cr, uid, [partial.picking_id.id], partial_data, context=context)
return {'type': 'ir.actions.act_window_close'}
-stock_partial_picking()
-
-# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
+# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
\ No newline at end of file
diff --git a/addons/stock/wizard/stock_partial_picking_view.xml b/addons/stock/wizard/stock_partial_picking_view.xml
index 4887c1e16d8..be85d266673 100644
--- a/addons/stock/wizard/stock_partial_picking_view.xml
+++ b/addons/stock/wizard/stock_partial_picking_view.xml
@@ -9,5 +9,59 @@
new
+
+ stock.partial.picking.form
+ stock.partial.picking
+ form
+
+
+
+
diff --git a/addons/stock_invoice_directly/test/stock_invoice_directly.yml b/addons/stock_invoice_directly/test/stock_invoice_directly.yml
index 806792868d4..795da509d04 100644
--- a/addons/stock_invoice_directly/test/stock_invoice_directly.yml
+++ b/addons/stock_invoice_directly/test/stock_invoice_directly.yml
@@ -38,36 +38,19 @@
"active_ids": [ref("stock.menu_action_picking_tree")], "active_id": ref("stock.menu_action_picking_tree"),
})
-
- I create a record for partial picking.
--
- !record {model: stock.partial.picking, id: stock_partial_picking_0}:
- date: !eval time.strftime('%Y-%m-%d %H:%M:%S')
--
- I make picking order Done.
+ I process the delivery
-
!python {model: stock.partial.picking}: |
- pick_obj = self.pool.get('stock.picking')
- partial = self.browse(cr, uid, ref('stock_partial_picking_0'), context)
- partial_datas = {
- 'delivery_date' : partial.date
- }
- for pick in pick_obj.browse(cr, uid, [ref('stock_picking_out0')]):
- for m in pick.move_lines:
- partial_datas['move%s'%(m.id)] = {
- 'product_id' : m.product_id.id,
- 'product_qty' : m.product_qty,
- 'product_uom' : m.product_uom.id
- }
- self.do_partial(cr, uid, [ref('stock_partial_picking_0')], {"lang": "en_US", "search_default_available":
- 1, "tz": False, "active_model": "ir.ui.menu", "contact_display": "partner",
- "active_ids": [ref('stock_picking_out0')], "active_id": ref("stock_picking_out0"),
- })
+ partial_id = self.create(cr, uid, {}, context={'active_model':'stock.picking',
+ 'active_ids':[ref('stock_picking_out0')]})
+ self.do_partial(cr, uid, [partial_id])
+
-
As the Invoice state of the picking order is To be invoiced. I create invoice for my outgoing picking order.
-
!python {model: stock.invoice.onshipping}: |
- wiz_id = self.create(cr, uid, {'invoice_date': '2010-08-04', 'journal_id': ref('account.bank_journal')},
- {'active_ids': [ref("stock_picking_out0")]})
+ wiz_id = self.create(cr, uid, {'invoice_date': '2010-08-04', 'journal_id': ref('account.sales_journal')},
+ {'active_ids': [ref("stock_picking_out0")], "active_model": "stock.picking"})
self.create_invoice(cr, uid, [wiz_id], {"lang": "en_US",
"search_default_available": 1, "tz": False, "active_model": "stock.picking",
"contact_display": "partner", "active_ids": [ref("stock_picking_out0")], "active_id": ref("stock_picking_out0")})
diff --git a/addons/stock_invoice_directly/wizard/stock_invoice.py b/addons/stock_invoice_directly/wizard/stock_invoice.py
index 11b31725a88..3725d9b6d7f 100644
--- a/addons/stock_invoice_directly/wizard/stock_invoice.py
+++ b/addons/stock_invoice_directly/wizard/stock_invoice.py
@@ -25,24 +25,15 @@ class invoice_directly(osv.osv_memory):
_inherit = 'stock.partial.picking'
def do_partial(self, cr, uid, ids, context=None):
- """ Makes partial moves and pickings done and
- launches Create invoice wizard if invoice state is To be Invoiced.
- @param self: The object pointer.
- @param cr: A database cursor
- @param uid: ID of the user currently logged in
- @param context: A standard dictionary
- @return:
+ """Launch Create invoice wizard if invoice state is To be Invoiced,
+ after processing the partial picking.
"""
- if context is None:
- context = {}
+ if context is None: context = {}
result = super(invoice_directly, self).do_partial(cr, uid, ids, context)
- pick_obj = self.pool.get('stock.picking')
- context.update({'active_model':'stock.picking'})
- picking_ids = context.get('active_ids', False)
- if picking_ids:
- context.update({'active_id':picking_ids[0]})
- pick = pick_obj.browse(cr, uid, picking_ids, context=context)[0]
- if pick.invoice_state == '2binvoiced':
+ partial = self.browse(cr, uid, ids[0], context)
+ context.update(active_model='stock.picking',
+ active_ids=[partial.picking_id.id])
+ if partial.picking_id.invoice_state == '2binvoiced':
return {
'name': 'Create Invoice',
'view_type': 'form',
@@ -55,5 +46,5 @@ class invoice_directly(osv.osv_memory):
return {'type': 'ir.actions.act_window_close'}
invoice_directly()
-# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
+# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
\ No newline at end of file
diff --git a/addons/stock_planning/stock_planning.py b/addons/stock_planning/stock_planning.py
index fe0b2f8f3ce..3ec992ecd0c 100644
--- a/addons/stock_planning/stock_planning.py
+++ b/addons/stock_planning/stock_planning.py
@@ -46,7 +46,7 @@ class stock_period(osv.osv):
'name': fields.char('Period Name', size=64, required=True),
'date_start': fields.datetime('Start Date', required=True),
'date_stop': fields.datetime('End Date', required=True),
- 'state': fields.selection([('draft','Draft'), ('open','Open'),('close','Close')], 'State')
+ 'state': fields.selection([('draft','Draft'), ('open','Open'),('close','Close')], 'State'),
}
_defaults = {
'state': 'draft'
diff --git a/addons/stock_planning/wizard/stock_planning_create_periods.py b/addons/stock_planning/wizard/stock_planning_create_periods.py
index 05f8aa925a9..963ff416822 100644
--- a/addons/stock_planning/wizard/stock_planning_create_periods.py
+++ b/addons/stock_planning/wizard/stock_planning_create_periods.py
@@ -46,6 +46,7 @@ class stock_period_createlines(osv.osv_memory):
'date_start': fields.date('Start Date', required=True, help="Starting date for planning period."),
'date_stop': fields.date('End Date', required=True, help="Ending date for planning period."),
'period_ids': fields.one2many('stock.period', 'planning_id', 'Periods'),
+ 'period_ids': fields.many2many('stock.period', 'stock_period_createlines_stock_period_rel', 'wizard_id', 'period_id', 'Periods'),
}
_defaults={
'date_start': _get_new_period_start,
diff --git a/addons/subscription/subscription.py b/addons/subscription/subscription.py
index 0f2630ffbb5..466defd1fa2 100644
--- a/addons/subscription/subscription.py
+++ b/addons/subscription/subscription.py
@@ -38,12 +38,6 @@ class subscription_document(osv.osv):
_defaults = {
'active' : lambda *a: True,
}
-
- def write(self, cr, uid, ids, vals, context=None):
- if 'model' in vals:
- raise osv.except_osv(_('Error !'),_('You cannot modify the Object linked to the Document Type!\nCreate another Document instead !'))
- return super(subscription_document, self).write(cr, uid, ids, vals, context=context)
-
subscription_document()
class subscription_document_fields(osv.osv):
diff --git a/addons/survey/survey_demo.xml b/addons/survey/survey_demo.xml
index a351a3da9b4..89571bd647a 100644
--- a/addons/survey/survey_demo.xml
+++ b/addons/survey/survey_demo.xml
@@ -1281,6 +1281,7 @@
20
+ open5
diff --git a/addons/survey/test/survey00.yml b/addons/survey/test/survey00.yml
index 7bfe8a5320d..fa56e9fac39 100644
--- a/addons/survey/test/survey00.yml
+++ b/addons/survey/test/survey00.yml
@@ -144,8 +144,8 @@
Give answer of the survey, Run "Answer a Survey" wizard and select the survey and press on start button then run the selected survey.
-
!python {model: survey.name.wiz}: |
- ids = self.create(cr, uid, {'survey_id': ref("survey_partner_0")})
- self.action_next(cr, uid, [ids], context)
+ id = self.create(cr, uid, {'survey_id': ref("survey_partner_0")})
+ self.action_next(cr, uid, [id], context)
-
Give answer of the first and second page in "Partner Feedback" suvey.
-
diff --git a/addons/survey/wizard/survey_answer.py b/addons/survey/wizard/survey_answer.py
index 471290af2cb..be43a409774 100644
--- a/addons/survey/wizard/survey_answer.py
+++ b/addons/survey/wizard/survey_answer.py
@@ -40,14 +40,6 @@ class survey_question_wiz(osv.osv_memory):
def fields_view_get(self, cr, uid, view_id=None, view_type='form', context=None, toolbar=False, submenu=False):
"""
Fields View Get method :- generate the new view and display the survey pages of selected survey.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param view_id : view id of the current object.
- @param view_type : which type of view is create. like :- form, tree ,search etc...
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for created view of particular survey pages.
"""
result = super(survey_question_wiz, self).fields_view_get(cr, uid, view_id, \
@@ -88,7 +80,7 @@ class survey_question_wiz(osv.osv_memory):
if not survey_id:
# Try one more time to find it
if sur_name_rec and sur_name_rec.survey_id:
- survey_id = sur_name_rec.survey_id[0]
+ survey_id = sur_name_rec.survey_id.id
else:
# raise osv.except_osv(_('Error!'), _("Cannot locate survey for the question wizard!"))
# If this function is called without a survey_id in
@@ -398,10 +390,10 @@ class survey_question_wiz(osv.osv_memory):
sur_response_obj.write(cr, uid, [sur_name_read.response], {'state' : 'done'})
if sur_rec.send_response:
- survey_data = survey_obj.browse(cr, uid, int(survey_id))
+ survey_data = survey_obj.browse(cr, uid, survey_id)
response_id = surv_name_wiz.read(cr, uid, context.get('sur_name_id',False))['response']
context.update({'response_id':response_id})
- report = self.create_report(cr, uid, [int(survey_id)], 'report.survey.browse.response', survey_data.title,context)
+ report = self.create_report(cr, uid, [survey_id], 'report.survey.browse.response', survey_data.title,context)
attachments = {}
file = open(addons.get_module_resource('survey', 'report') + survey_data.title + ".pdf")
file_data = ""
@@ -445,15 +437,6 @@ class survey_question_wiz(osv.osv_memory):
def create_report(self, cr, uid, res_ids, report_name=False, file_name=False, context=None):
"""
If any user give answer of survey then last create report of this answer and if 'E-mail Notification on Answer' set True in survey then send mail on responsible person of this survey and attach survey answer report in pdf format.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param res_ids: List of survey answer IDs,
- @param report_name: name of the report,
- @param file_name: To give file name of the report,
- @param context: A standard dictionary for contextual values,
- @return : Dictionary value for created report with file nameself.
"""
if not report_name or not res_ids:
return (False, Exception('Report name and Resources ids are required !!!'))
@@ -474,13 +457,6 @@ class survey_question_wiz(osv.osv_memory):
def default_get(self, cr, uid, fields_list, context=None):
"""
Assign Default value in particular field. If Browse Answers wizard run then read the value into database and Assigne to a particular fields.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param fields_list: List of fields of current view,
- @param context: A standard dictionary for contextual values,
- @return : Dictionary value for fields list with value.
"""
value = {}
if context is None:
@@ -556,13 +532,6 @@ class survey_question_wiz(osv.osv_memory):
def create(self, cr, uid, vals, context=None):
"""
Create the Answer of survey and store in survey.response object, and if set validation of question then check the value of question if value is wrong then raise the exception.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param vals: Values,
- @param context: A standard dictionary for contextual values
- @return : True.
"""
if context is None: context = {}
if context.has_key('active') and context.get('active',False):
@@ -600,9 +569,10 @@ class survey_question_wiz(osv.osv_memory):
#click first time on next button then increemnet on total start suvey
if not sur_name_read['store_ans']:
his_id = self.pool.get('survey.history').create(cr, uid, {'user_id': uid, \
- 'date': strftime('%Y-%m-%d %H:%M:%S'), 'survey_id': sur_name_read['survey_id']})
- sur_rec = survey_obj.read(cr, uid, sur_name_read['survey_id'])
- survey_obj.write(cr, uid, sur_name_read['survey_id'], {'tot_start_survey' : sur_rec['tot_start_survey'] + 1})
+ 'date': strftime('%Y-%m-%d %H:%M:%S'), 'survey_id': sur_name_read['survey_id'][0]})
+ survey_id = sur_name_read['survey_id'][0]
+ sur_rec = survey_obj.read(cr, uid, survey_id)
+ survey_obj.write(cr, uid, survey_id, {'tot_start_survey' : sur_rec['tot_start_survey'] + 1})
if context.has_key('cur_id'):
if context.has_key('request') and context.get('request',False):
self.pool.get(context.get('object',False)).write(cr, uid, [int(context.get('cur_id',False))], {'response' : response_id})
@@ -1016,13 +986,6 @@ class survey_question_wiz(osv.osv_memory):
def action_new_question(self,cr, uid, ids, context=None):
"""
New survey.Question form.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open new survey.Qestion form.
"""
if context is None:
context = {}
@@ -1044,13 +1007,6 @@ class survey_question_wiz(osv.osv_memory):
def action_new_page(self, cr, uid, ids, context=None):
"""
New survey.Page form.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open new survey.page form.
"""
if context is None:
context = {}
@@ -1072,13 +1028,6 @@ class survey_question_wiz(osv.osv_memory):
def action_edit_page(self,cr, uid, ids, context=None):
"""
Edit survey.page.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open Edit survey.page form.
"""
if context is None:
context = {}
@@ -1101,13 +1050,6 @@ class survey_question_wiz(osv.osv_memory):
def action_delete_page(self,cr, uid, ids, context=None):
"""
Delete survey.page.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open next survey.page form, but delete the selected page.
"""
if context is None:
context = {}
@@ -1134,13 +1076,6 @@ class survey_question_wiz(osv.osv_memory):
def action_edit_question(self,cr, uid, ids, context=None):
"""
Edit survey.question.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open Edit survey.question form.
"""
if context is None:
context = {}
@@ -1163,13 +1098,6 @@ class survey_question_wiz(osv.osv_memory):
def action_delete_question(self,cr, uid, ids, context=None):
"""
Delete survey.question.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open same survey.page form, but delete the selected survey.question in current survey.page.
"""
if context is None:
context = {}
@@ -1197,13 +1125,6 @@ class survey_question_wiz(osv.osv_memory):
def action_forward_previous(self, cr, uid, ids, context=None):
"""
Goes to previous Survey Answer.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open Previous Answer form.
"""
if context is None:
context = {}
@@ -1229,13 +1150,6 @@ class survey_question_wiz(osv.osv_memory):
def action_forward_next(self, cr, uid, ids, context=None):
"""
Goes to Next Survey Answer.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open Next Answer form.
"""
if context is None:
context = {}
@@ -1261,13 +1175,6 @@ class survey_question_wiz(osv.osv_memory):
def action_next(self, cr, uid, ids, context=None):
"""
Goes to Next page.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open Next survey.page form.
"""
if context is None:
context = {}
@@ -1288,13 +1195,6 @@ class survey_question_wiz(osv.osv_memory):
def action_previous(self, cr, uid, ids, context=None):
"""
Goes to previous page.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.question.wiz IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for Open Previous survey.page form.
"""
if context is None:
context = {}
diff --git a/addons/survey/wizard/survey_browse_answer.py b/addons/survey/wizard/survey_browse_answer.py
index 1798a7c418c..5af913993b2 100644
--- a/addons/survey/wizard/survey_browse_answer.py
+++ b/addons/survey/wizard/survey_browse_answer.py
@@ -24,26 +24,9 @@ from osv import fields
class survey_browse_answer(osv.osv_memory):
_name = 'survey.browse.answer'
-
- def _get_survey(self, cr, uid, context=None):
- """
- Set the value in survey_id field,
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param context: A standard dictionary for contextual values,
- @return : Tuple in list with values.
- """
- surv_obj = self.pool.get("survey")
- surv_resp_obj = self.pool.get("survey.response")
- result = []
- for sur in surv_obj.browse(cr, uid, surv_obj.search(cr, uid, [])):
- if surv_resp_obj.search(cr, uid, [('survey_id', '=', sur.id)]):
- result.append((sur.id, sur.title))
- return result
_columns = {
- 'survey_id': fields.selection(_get_survey, "Survey", required="1"),
+ 'survey_id': fields.many2one('survey', "Survey", required="1"),
'response_id': fields.many2one("survey.response", "Survey Answers", help="If this field is empty, all answers of the selected survey will be print."),
}
@@ -51,13 +34,6 @@ class survey_browse_answer(osv.osv_memory):
"""
Open Browse Response wizard. if you select only survey_id then this wizard open with all response_ids and
if you select survey_id and response_id then open the particular response of the survey.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of survey.browse.answer IDs,
- @param context: A standard dictionary for contextual values,
- @return : Dictionary value for Open the browse answer wizard.
"""
if context is None: context = {}
record = self.read(cr, uid, ids, [])
@@ -66,8 +42,8 @@ class survey_browse_answer(osv.osv_memory):
res_id = [(record.get('response_id') and record['response_id'][0])]
else:
sur_response_obj = self.pool.get('survey.response')
- res_id = sur_response_obj.search(cr, uid, [('survey_id', '=',int(record['survey_id']))])
- context.update({'active' : True,'survey_id' : record['survey_id'], 'response_id' : res_id, 'response_no' : 0})
+ res_id = sur_response_obj.search(cr, uid, [('survey_id', '=', record['survey_id'][0])])
+ context.update({'active' : True,'survey_id' : record['survey_id'][0], 'response_id' : res_id, 'response_no' : 0})
search_obj = self.pool.get('ir.ui.view')
search_id = search_obj.search(cr,uid,[('model','=','survey.question.wiz'),('name','=','Survey Search')])
return {
diff --git a/addons/survey/wizard/survey_print.py b/addons/survey/wizard/survey_print.py
index 87767f34a68..6ae84ed37cc 100644
--- a/addons/survey/wizard/survey_print.py
+++ b/addons/survey/wizard/survey_print.py
@@ -27,8 +27,7 @@ from tools.translate import _
class survey_print(osv.osv_memory):
_name = 'survey.print'
_columns = {
- 'survey_ids': fields.many2many('survey','survey_print',\
- 'survey_id','print_id', "Survey", required="1"),
+ 'survey_ids': fields.many2many('survey', string="Survey", required="1"),
'orientation' : fields.selection([('vertical','Portrait(Vertical)'),\
('horizontal','Landscape(Horizontal)')], 'Orientation'),
'paper_size' : fields.selection([('letter','Letter (8.5" x 11")'),\
diff --git a/addons/survey/wizard/survey_print_statistics.py b/addons/survey/wizard/survey_print_statistics.py
index 10b321fcf45..bd8b9f2ad14 100644
--- a/addons/survey/wizard/survey_print_statistics.py
+++ b/addons/survey/wizard/survey_print_statistics.py
@@ -26,20 +26,12 @@ from tools.translate import _
class survey_print_statistics(osv.osv_memory):
_name = 'survey.print.statistics'
_columns = {
- 'survey_ids': fields.many2many('survey','survey_print_statistics','survey_id',\
- 'print_id', "Survey", required="1"),
+ 'survey_ids': fields.many2many('survey', string="Survey", required="1"),
}
def action_next(self, cr, uid, ids, context=None):
"""
Print Survey Statistics in pdf format.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of Survey statistics IDs
- @param context: A standard dictionary for contextual values
- @return: Dictionary value for created survey statistics report
"""
if context is None:
context = {}
diff --git a/addons/survey/wizard/survey_selection.py b/addons/survey/wizard/survey_selection.py
index c6eebd62a67..a803459899c 100644
--- a/addons/survey/wizard/survey_selection.py
+++ b/addons/survey/wizard/survey_selection.py
@@ -26,71 +26,8 @@ from tools.translate import _
class survey_name_wiz(osv.osv_memory):
_name = 'survey.name.wiz'
- def default_get(self, cr, uid, fields, context=None):
- """
- Set the default value in survey_id field. if open this wizard in survey form then set the default value in survey_id = active survey id.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param fields: List of Survey statistics IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for created survey statistics report
- """
- if context is None:
- context = {}
- data = super(survey_name_wiz, self).default_get(cr, uid, fields, context)
- if context.has_key('survey_id'):
- data['survey_id'] = context.get('survey_id',False)
- return data
-
- def _get_survey(self, cr, uid, context=None):
- """
- Set the value In survey_id field.
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of Survey statistics IDs
- @param context: A standard dictionary for contextual values
- @return: Dictionary value for created survey statistics report
- """
- surv_obj = self.pool.get("survey")
- result = []
- if context.has_key('survey_id'):
- for sur in surv_obj.browse(cr, uid, [context.get('survey_id',False)]):
- result.append((sur.id, sur.title))
- return result
- survey_user_group_id = self.pool.get('res.groups').search(cr, uid, [('name', '=', 'Survey / User')])
- group_id = self.pool.get('res.groups').search(cr, uid, [('name', 'in', ('Tools / Manager','Tools / User','Survey / User'))])
- user_obj = self.pool.get('res.users')
- user_rec = user_obj.read(cr, uid, uid, [])
- if survey_user_group_id:
- if survey_user_group_id == user_rec['groups_id']:
- for sur in surv_obj.browse(cr, uid, surv_obj.search(cr, uid, [])):
- if sur.state == 'open':
- u_list = []
- for use in sur.invited_user_ids:
- u_list.append(use.id)
- if uid in u_list:
- result.append((sur.id, sur.title))
- return result
- for sur in surv_obj.browse(cr, uid, surv_obj.search(cr, uid, [])):
- if sur.state == 'open':
- res = False
- for i in group_id:
- if i in user_rec['groups_id']:
- res = True
- break
- elif sur.id in user_rec['survey_id']:
- res = True
- break
- if res:
- result.append((sur.id, sur.title))
- return result
-
_columns = {
- 'survey_id': fields.selection(_get_survey, "Survey", required="1"),
+ 'survey_id': fields.many2one('survey', 'Survey', required=True, ondelete='cascade'),
'page_no': fields.integer('Page Number'),
'note': fields.text("Description"),
'page': fields.char('Page Position',size = 12),
@@ -99,10 +36,11 @@ class survey_name_wiz(osv.osv_memory):
'response': fields.char('Answer',size=16)
}
_defaults = {
- 'page_no': lambda * a: - 1,
- 'page': lambda * a: 'next',
- 'transfer': lambda * a: 1,
- 'response': lambda * a: 0,
+ 'page_no': -1,
+ 'page': 'next',
+ 'transfer': 1,
+ 'response': 0,
+ 'survey_id': lambda self,cr,uid,context:context.get('survey_id',False),
}
def action_next(self, cr, uid, ids, context=None):
@@ -110,30 +48,22 @@ class survey_name_wiz(osv.osv_memory):
Start the survey, Increment in started survey field but if set the max_response_limit of
survey then check the current user how many times start this survey. if current user max_response_limit
is reach then this user can not start this survey(Raise Exception).
-
- @param self: The object pointer
- @param cr: the current row, from the database cursor,
- @param uid: the current user’s ID for security checks,
- @param ids: List of Survey IDs
- @param context: A standard dictionary for contextual values
- @return : Dictionary value for open survey question wizard.
"""
survey_obj = self.pool.get('survey')
search_obj = self.pool.get('ir.ui.view')
if context is None: context = {}
this = self.browse(cr, uid, ids, context=context)[0]
- survey_id = this.survey_id
+ survey_id = this.survey_id.id
context.update({'survey_id': survey_id, 'sur_name_id': this.id})
cr.execute('select count(id) from survey_history where user_id=%s\
and survey_id=%s' % (uid,survey_id))
res = cr.fetchone()[0]
- user_limit = survey_obj.read(cr, uid, survey_id, ['response_user'])['response_user']
- if user_limit and res >= user_limit:
+ sur_rec = survey_obj.browse(cr,uid,survey_id,context=context)
+ if sur_rec.response_user and res >= sur_rec.response_user:
raise osv.except_osv(_('Warning !'),_("You can not give response for this survey more than %s times") % (user_limit))
- sur_rec = survey_obj.browse(cr,uid,ids,context=context)[0]
if sur_rec.max_response_limit and sur_rec.max_response_limit <= sur_rec.tot_start_survey:
raise osv.except_osv(_('Warning !'),_("You can not give more response. Please contact the author of this survey for further assistance."))
@@ -152,16 +82,10 @@ class survey_name_wiz(osv.osv_memory):
def on_change_survey(self, cr, uid, ids, survey_id, context=None):
"""
on change event of survey_id field, if note is available in selected survey then display this note in note fields.
- @param ids: List of Survey IDs
- @param survey_id: Id of Survey
- @param context: A standard dictionary for contextual values
- @return : Dictionary values of notes fields.
"""
if not survey_id:
return {}
notes = self.pool.get('survey').read(cr, uid, survey_id, ['note'])['note']
return {'value': {'note': notes}}
-survey_name_wiz()
-
-# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
+# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4:
\ No newline at end of file
diff --git a/addons/survey/wizard/survey_selection.xml b/addons/survey/wizard/survey_selection.xml
index a72566f7888..144525979dd 100644
--- a/addons/survey/wizard/survey_selection.xml
+++ b/addons/survey/wizard/survey_selection.xml
@@ -15,7 +15,8 @@
+ on_change="on_change_survey(survey_id)" width="250"
+ domain="[('state','=','open')]"/>
diff --git a/addons/thunderbird/installer.py b/addons/thunderbird/installer.py
index 5bf11218842..35d31b9d636 100644
--- a/addons/thunderbird/installer.py
+++ b/addons/thunderbird/installer.py
@@ -41,7 +41,7 @@ class thunderbird_installer(osv.osv_memory):
'pdf_name':fields.char('File name', size=64),
'thunderbird':fields.boolean('Thunderbird Plug-in', help="Allows you to select an object that you would like to add to your email and its attachments."),
'plugin_file':fields.binary('Thunderbird Plug-in', readonly=True, help="Thunderbird plug-in file. Save as this file and install this plug-in in thunderbird."),
- 'pdf_file':fields.char('Installation Manual', size="264", help="The documentation file :- how to install Thunderbird Plug-in.", readonly=True),
+ 'pdf_file':fields.char('Installation Manual', size=264, help="The documentation file :- how to install Thunderbird Plug-in.", readonly=True),
'description':fields.text('Description', readonly=True)
}
diff --git a/addons/thunderbird/thunderbird_installer.xml b/addons/thunderbird/thunderbird_installer.xml
index cf23cdf45c1..2fb5d3177c3 100644
--- a/addons/thunderbird/thunderbird_installer.xml
+++ b/addons/thunderbird/thunderbird_installer.xml
@@ -9,26 +9,24 @@