Merge lp:~julie-w/unifield-server/US-6076-BIS into lp:unifield-server
- US-6076-BIS
- Merge into trunk
Proposed by
jftempo
Status: | Merged |
---|---|
Merged at revision: | 5440 |
Proposed branch: | lp:~julie-w/unifield-server/US-6076-BIS |
Merge into: | lp:unifield-server |
Diff against target: |
3653 lines (+1487/-495) (has conflicts) 50 files modified
bin/addons/account/__openerp__.py (+0/-1) bin/addons/account/account_invoice_view.xml (+88/-25) bin/addons/account/account_invoice_workflow.xml (+9/-7) bin/addons/account/account_move_line.py (+17/-0) bin/addons/account/account_report.xml (+1/-1) bin/addons/account/invoice.py (+109/-35) bin/addons/account/report/account_invoice_report.py (+5/-4) bin/addons/account/report/account_invoice_report_view.xml (+1/-1) bin/addons/account/report/account_report.py (+11/-10) bin/addons/account/report/account_report_view.xml (+1/-1) bin/addons/account/report/account_tax_report.py (+21/-21) bin/addons/account/wizard/__init__.py (+0/-2) bin/addons/account/wizard/account_invoice_refund.py (+50/-14) bin/addons/account/wizard/account_invoice_refund_view.xml (+4/-1) bin/addons/account/wizard/account_invoice_state.py (+2/-25) bin/addons/account/wizard/account_invoice_state_view.xml (+0/-24) bin/addons/account/wizard/account_state_open.py (+0/-44) bin/addons/account/wizard/account_state_open_view.xml (+0/-35) bin/addons/account_override/__init__.py (+1/-0) bin/addons/account_override/account.py (+17/-9) bin/addons/account_override/account_invoice_sync.py (+346/-0) bin/addons/account_override/account_invoice_view.xml (+155/-42) bin/addons/account_override/invoice.py (+114/-13) bin/addons/account_override/report/report_open_invoices.py (+2/-2) bin/addons/account_voucher/report/account_voucher_sales_receipt_view.xml (+2/-2) bin/addons/analytic_distribution/account_invoice_refund.py (+26/-5) bin/addons/analytic_distribution/account_invoice_view.xml (+8/-2) bin/addons/analytic_distribution/wizard/analytic_distribution_wizard.py (+4/-4) bin/addons/finance/__openerp__.py (+0/-1) bin/addons/finance/account_invoice_workflow.xml (+0/-13) bin/addons/msf_audittrail/audittrail_invoice_data.yml (+2/-1) bin/addons/msf_outgoing/msf_outgoing.py (+39/-28) bin/addons/msf_profile/data/patches.xml (+12/-0) bin/addons/msf_profile/i18n/fr_MF.po (+323/-57) bin/addons/msf_profile/msf_profile.py (+40/-0) bin/addons/msf_sync_data_server/data/sync_server.message_rule.csv (+2/-0) bin/addons/product_attributes/product_attributes.py (+1/-1) bin/addons/purchase/purchase_workflow.py (+3/-3) bin/addons/register_accounting/account_invoice_view.xml (+30/-43) bin/addons/register_accounting/wizard/down_payment.py (+1/-1) bin/addons/res_currency_tables/res_currency.py (+1/-1) bin/addons/sale/report/sale_report.py (+2/-2) bin/addons/sale/sale_order.py (+3/-3) bin/addons/sale/sale_view.xml (+0/-1) bin/addons/sale/sale_workflow.py (+3/-3) bin/addons/stock/stock.py (+8/-0) bin/addons/stock_override/stock.py (+5/-0) bin/addons/sync_so/picking.py (+3/-3) bin/addons/sync_so/specific_xml_id.py (+14/-2) bin/addons/vertical_integration/report/report_open_invoices.py (+1/-2) Text conflict in bin/addons/msf_profile/data/patches.xml Text conflict in bin/addons/msf_profile/i18n/fr_MF.po |
To merge this branch: | bzr merge lp:~julie-w/unifield-server/US-6076-BIS |
Related bugs: |
Reviewer | Review Type | Date Requested | Status |
---|---|---|---|
UniField Reviewer Team | Pending | ||
Review via email: mp+370751@code.launchpad.net |
Commit message
Description of the change
To post a comment you must log in.
Preview Diff
[H/L] Next/Prev Comment, [J/K] Next/Prev File, [N/P] Next/Prev Hunk
1 | === modified file 'bin/addons/account/__openerp__.py' |
2 | --- bin/addons/account/__openerp__.py 2017-09-28 14:05:02 +0000 |
3 | +++ bin/addons/account/__openerp__.py 2019-07-30 10:04:49 +0000 |
4 | @@ -73,7 +73,6 @@ |
5 | 'wizard/account_report_central_journal_view.xml', |
6 | 'wizard/account_subscription_generate_view.xml', |
7 | 'wizard/account_fiscalyear_close_view.xml', |
8 | - 'wizard/account_state_open_view.xml', |
9 | 'wizard/account_journal_select_view.xml', |
10 | 'wizard/account_change_currency_view.xml', |
11 | 'wizard/account_validate_move_view.xml', |
12 | |
13 | === modified file 'bin/addons/account/account_invoice_view.xml' |
14 | --- bin/addons/account/account_invoice_view.xml 2018-02-13 15:48:51 +0000 |
15 | +++ bin/addons/account/account_invoice_view.xml 2019-07-30 10:04:49 +0000 |
16 | @@ -53,11 +53,29 @@ |
17 | <form string="Invoice Line"> |
18 | <notebook> |
19 | <page string="Line"> |
20 | - <field name="product_id" on_change="product_id_change(product_id, uos_id, quantity, name, parent.type, parent.partner_id, parent.fiscal_position, price_unit, parent.address_invoice_id, parent.currency_id, {'company_id': parent.company_id})" default_focus="1"/> |
21 | - <field name="uos_id" on_change="uos_id_change(product_id, uos_id, quantity, name, parent.type, parent.partner_id, parent.fiscal_position, price_unit, parent.address_invoice_id, parent.currency_id, {'company_id': parent.company_id})"/> |
22 | - <field name="quantity"/> |
23 | - <field name="price_unit"/> |
24 | - <field name="discount" groups="base.group_extended"/> |
25 | + <field name="invoice_type" invisible="1"/> |
26 | + <field name="from_supply" invisible="1"/> |
27 | + <field name="partner_type" invisible="1"/> |
28 | + <field name="product_id" |
29 | + on_change="product_id_change(product_id, uos_id, quantity, name, parent.type, parent.partner_id, parent.fiscal_position, price_unit, parent.address_invoice_id, parent.currency_id, {'company_id': parent.company_id})" |
30 | + default_focus="1" |
31 | + attrs="{'readonly': ['|', |
32 | + '&', ('invoice_type', '=', 'in_invoice'), ('synced', '=', True), |
33 | + '&', '&', ('invoice_type', '=', 'out_invoice'), ('from_supply', '=', True), ('partner_type', 'in', ('intermission', 'section'))]}" |
34 | + /> |
35 | + <field name="uos_id" |
36 | + on_change="uos_id_change(product_id, uos_id, quantity, name, parent.type, parent.partner_id, parent.fiscal_position, price_unit, parent.address_invoice_id, parent.currency_id, {'company_id': parent.company_id})" |
37 | + attrs="{'readonly': ['|', |
38 | + '&', ('invoice_type', '=', 'in_invoice'), ('synced', '=', True), |
39 | + '&', '&', ('invoice_type', '=', 'out_invoice'), ('from_supply', '=', True), ('partner_type', 'in', ('intermission', 'section'))]}" |
40 | + /> |
41 | + <field name="quantity" attrs="{'readonly': ['|', |
42 | + '&', ('invoice_type', '=', 'in_invoice'), ('synced', '=', True), |
43 | + '&', '&', ('invoice_type', '=', 'out_invoice'), ('from_supply', '=', True), ('partner_type', 'in', ('intermission', 'section'))]}" |
44 | + /> |
45 | + <field name="price_unit" attrs="{'readonly': [('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
46 | + <field name="discount" groups="base.group_extended" |
47 | + attrs="{'readonly': [('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
48 | <field colspan="4" name="name"/> |
49 | <field domain="[('company_id', '=', parent.company_id), ('journal_id', '=', parent.journal_id), ('type', '<>', 'view')]" name="account_id"/> |
50 | <field domain="[('type','<>','view'), ('company_id', '=', parent.company_id), ('parent_id', '!=', False)]" name="account_analytic_id" groups="analytic.group_analytic_accounting"/> |
51 | @@ -152,10 +170,18 @@ |
52 | <field name="journal_id" widget="selection"/> |
53 | <field name="number" readonly="1"/> |
54 | <field name="type" invisible="1"/> |
55 | - <field name="currency_id" width="50"/> |
56 | - <button name="%(action_account_change_currency)d" type="action" icon="terp-stock_effects-object-colorize" string="Change" attrs="{'invisible':[('state','!=','draft')]}" groups="account.group_account_user"/> |
57 | + <field name="currency_id" width="50" attrs="{'readonly': ['|', ('state', '!=', 'draft'), |
58 | + '&', ('type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
59 | + <button name="%(action_account_change_currency)d" type="action" icon="terp-stock_effects-object-colorize" |
60 | + string="Change" groups="account.group_account_user" |
61 | + attrs="{'invisible':[('state', '!=', 'draft')], |
62 | + 'readonly': [('type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
63 | <newline/> |
64 | - <field string="Supplier" name="partner_id" domain="[('supplier', '=', True)]" on_change="onchange_partner_id(type,partner_id,date_invoice,payment_term, partner_bank_id,company_id)" context="{'default_customer': 0, 'search_default_supplier': 1, 'default_supplier': 1}"/> |
65 | + <field string="Supplier" name="partner_id" domain="[('supplier', '=', True)]" |
66 | + on_change="onchange_partner_id(type, partner_id, date_invoice, payment_term, partner_bank_id, company_id)" |
67 | + context="{'default_customer': 0, 'search_default_supplier': 1, 'default_supplier': 1}" |
68 | + attrs="{'readonly': ['|', ('state', '!=', 'draft'), '&', ('type', '=', 'in_invoice'), ('synced', '=', True)]}" |
69 | + /> |
70 | <field domain="[('partner_id','=',partner_id)]" name="address_invoice_id"/> |
71 | <field name="fiscal_position" groups="base.group_extended" widget="selection"/> |
72 | <newline/> |
73 | @@ -187,7 +213,7 @@ |
74 | </tree> |
75 | </field> |
76 | <group col="1" colspan="2"> |
77 | - <field name="tax_line" nolabel="1"> |
78 | + <field name="tax_line" nolabel="1" attrs="{'invisible': [('vat_ok', '=', False)], 'readonly': ['|', ('state','!=', 'draft'), '&', ('type', '=', 'in_invoice'), ('synced', '=', True)]}"> |
79 | <tree editable="bottom" string="Taxes"> |
80 | <field name="invoice_id" invisible="True"/> |
81 | <field name="account_tax_id" on_change="tax_code_change(account_tax_id,parent.amount_untaxed,context)"/> |
82 | @@ -196,7 +222,7 @@ |
83 | <field name="account_id" groups="account.group_account_invoice" |
84 | domain="[('type', 'not in', ['view', 'consolidation']), |
85 | ('user_type_code', '=', 'tax')]"/> |
86 | - |
87 | + |
88 | <field name="base" on_change="base_change(base,parent.currency_id,parent.company_id,parent.date_invoice)" readonly="1"/> |
89 | <field name="amount" on_change="amount_change(amount,parent.currency_id,parent.company_id,parent.date_invoice)"/> |
90 | |
91 | @@ -217,10 +243,8 @@ |
92 | <field name="state"/> |
93 | <field name="residual"/> |
94 | <group col="6" colspan="4"> |
95 | - <button name="invoice_cancel" states="draft,proforma2,sale,open" string="Cancel" icon="gtk-cancel"/> |
96 | <button name="action_cancel_draft" states="cancel" string="Set to Draft" type="object" icon="terp-stock_effects-object-colorize"/> |
97 | - <button name="%(action_account_invoice_refund)d" type='action' string='Refund' states='open,paid' icon="gtk-execute"/> |
98 | - <button name="%(action_account_state_open)d" type='action' string='Re-Open' states='paid' icon="gtk-convert" groups="base.group_no_one"/> |
99 | + <button name="%(action_account_invoice_refund)d" type='action' string='Refund' states='open,paid,inv_close' icon="gtk-execute"/> |
100 | <button name="invoice_open" states="draft,proforma2" string="Approve" icon="terp-camera_test"/> |
101 | </group> |
102 | </group> |
103 | @@ -230,11 +254,18 @@ |
104 | <field name="company_id" on_change="onchange_company_id(company_id,partner_id,type,invoice_line,currency_id)" widget="selection" groups="base.group_multi_company"/> |
105 | <newline/> |
106 | <field name="payment_term" widget="selection"/> |
107 | - <field name="name"/> |
108 | + <field name="name" |
109 | + attrs="{'readonly': ['|', |
110 | + ('state', '!=', 'draft'), |
111 | + '&', '&', ('type', '=', 'in_invoice'), ('synced', '=', True), ('from_supply', '=', True)]}"/> |
112 | <newline/> |
113 | - <field name="origin" groups="base.group_extended"/> |
114 | + <field name="origin" groups="base.group_extended" |
115 | + attrs="{'readonly': ['|', |
116 | + ('state', '!=', 'draft'), |
117 | + '&', '&', ('type', '=', 'in_invoice'), ('synced', '=', True), ('from_supply', '=', True)]}"/> |
118 | <field domain="[('partner_id','=',partner_id)]" name="address_contact_id" groups="base.group_extended"/> |
119 | - <field name="user_id"/> |
120 | + <field name="user_id" |
121 | + attrs="{'readonly': ['|', ('state', '!=', 'draft'), '&', ('type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
122 | <field name="move_id" groups="account.group_account_user"/> |
123 | <separator colspan="4" string="Additional Information"/> |
124 | <field colspan="4" name="comment" nolabel="1"/> |
125 | @@ -273,7 +304,16 @@ |
126 | <field name="currency_id" width="50"/> |
127 | <button name="%(action_account_change_currency)d" type="action" icon="terp-stock_effects-object-colorize" string="Change" attrs="{'invisible':[('state','!=','draft')]}" groups="account.group_account_user"/> |
128 | <newline/> |
129 | - <field string="Customer" name="partner_id" domain="[('customer', '=', True)]" on_change="onchange_partner_id(type,partner_id,date_invoice,payment_term, partner_bank_id,company_id)" groups="base.group_user" context="{'search_default_customer': 1}"/> |
130 | + <field string="Customer" name="partner_id" |
131 | + domain="[('customer', '=', True)]" |
132 | + on_change="onchange_partner_id(type,partner_id,date_invoice,payment_term, partner_bank_id,company_id)" |
133 | + groups="base.group_user" context="{'search_default_customer': 1}" |
134 | + attrs="{'readonly': ['|', |
135 | + ('state', '!=', 'draft'), |
136 | + '&', '&', |
137 | + ('type', '=', 'out_invoice'), |
138 | + ('from_supply', '=', True), |
139 | + ('partner_type', 'in', ('intermission', 'section'))]}"/> |
140 | <field domain="[('partner_id','=',partner_id)]" name="address_invoice_id"/> |
141 | <field name="fiscal_position" groups="base.group_extended" widget="selection"/> |
142 | <newline/> |
143 | @@ -286,9 +326,14 @@ |
144 | <notebook colspan="4"> |
145 | <page string="Invoice"> |
146 | <field domain="[('company_id', '=', company_id),('type','=', 'receivable')]" name="account_id" groups="account.group_account_user"/> |
147 | - <field name="name"/> |
148 | + <field name="name" attrs="{'readonly': ['|', |
149 | + ('state', '!=', 'draft'), |
150 | + '&', '&', |
151 | + ('type', '=', 'out_invoice'), |
152 | + ('from_supply', '=', True), |
153 | + ('partner_type', 'in', ('intermission', 'section'))]}"/> |
154 | <field name="payment_term" widget="selection"/> |
155 | - <field colspan="4" name="invoice_line" nolabel="1" widget="one2many_list" context="{'fake':1}"/> |
156 | + <field colspan="4" name="invoice_line" nolabel="1" widget="one2many_list" context="{'fake': 1, 'from_inv_form': True}"/> |
157 | <group col="1" colspan="2"> |
158 | <field name="tax_line" nolabel="1"> |
159 | <tree editable="bottom" string="Taxes"> |
160 | @@ -313,14 +358,12 @@ |
161 | <field name="state"/> |
162 | <field name="residual"/> |
163 | <group col="8" colspan="4" groups="base.group_user"> |
164 | - <button name="invoice_cancel" states="draft,proforma2,sale,open" string="Cancel" icon="gtk-cancel"/> |
165 | <button name="action_cancel_draft" states="cancel" string="Reset to Draft" type="object" icon="terp-stock_effects-object-colorize"/> |
166 | |
167 | - <button name="%(action_account_invoice_refund)d" type='action' string='Refund' states='open,paid' icon="gtk-execute"/> |
168 | - <button name='%(action_account_state_open)d' type='action' string='Re-Open' states='paid' icon="gtk-convert" groups="base.group_no_one"/> |
169 | + <button name="%(action_account_invoice_refund)d" type='action' string='Refund' states='open,paid,inv_close' icon="gtk-execute"/> |
170 | <button name="invoice_proforma2" states="draft" string="PRO-FORMA" icon="terp-gtk-media-pause" groups="account.group_account_user"/> |
171 | <button name="invoice_open" states="draft,proforma2" string="Validate" icon="gtk-go-forward"/> |
172 | - <button name="%(account_invoices)d" string="Print Invoice" type="action" icon="gtk-print" states="open,paid,proforma,sale,proforma2"/> |
173 | + <button name="%(account_invoices)d" string="Print Invoice" type="action" icon="gtk-print" states="open,paid,inv_close,proforma,sale,proforma2"/> |
174 | </group> |
175 | </group> |
176 | </page> |
177 | @@ -328,11 +371,21 @@ |
178 | <field name="company_id" on_change="onchange_company_id(company_id,partner_id,type,invoice_line,currency_id)" widget="selection" groups="base.group_multi_company"/> |
179 | <newline/> |
180 | <field name="date_due"/> |
181 | - <field name="user_id"/> |
182 | + <field name="user_id" attrs="{'readonly': ['|', |
183 | + ('state', '!=', 'draft'), |
184 | + '&', '&', |
185 | + ('type', '=', 'out_invoice'), |
186 | + ('from_supply', '=', True), |
187 | + ('partner_type', 'in', ('intermission', 'section'))]}"/> |
188 | <newline/> |
189 | <field domain="[('partner_id.ref_companies', 'in', [company_id])]" name="partner_bank_id" |
190 | groups="base.group_extended"/> |
191 | - <field name="origin"/> |
192 | + <field name="origin" attrs="{'readonly': ['|', |
193 | + ('state', '!=', 'draft'), |
194 | + '&', '&', |
195 | + ('type', '=', 'out_invoice'), |
196 | + ('from_supply', '=', True), |
197 | + ('partner_type', 'in', ('intermission', 'section'))]}"/> |
198 | <field colspan="4" domain="[('partner_id','=',partner_id)]" name="address_contact_id" |
199 | groups="base.group_extended"/> |
200 | <field name="move_id" groups="account.group_account_user"/> |
201 | @@ -353,6 +406,16 @@ |
202 | </tree> |
203 | </field> |
204 | </page> |
205 | + <!-- display the Counterpart Invoice tab in STV, hide it in Customer Refunds --> |
206 | + <page string="Counterpart Invoice" attrs="{'invisible': [('type', '!=', 'out_invoice')]}"> |
207 | + <field name="from_supply" invisible="1"/> |
208 | + <field name="synced" |
209 | + attrs="{'readonly': ['|', ('from_supply', '=', True), ('state', '!=', 'draft')]}" |
210 | + on_change="onchange_synced(synced, partner_id)"/> |
211 | + <newline/> |
212 | + <field name="counterpart_inv_number"/> |
213 | + <field name="counterpart_inv_status"/> |
214 | + </page> |
215 | </notebook> |
216 | </form> |
217 | </field> |
218 | |
219 | === modified file 'bin/addons/account/account_invoice_workflow.xml' |
220 | --- bin/addons/account/account_invoice_workflow.xml 2018-09-28 15:47:23 +0000 |
221 | +++ bin/addons/account/account_invoice_workflow.xml 2019-07-30 10:04:49 +0000 |
222 | @@ -24,23 +24,24 @@ |
223 | <record id="act_open" model="workflow.activity"> |
224 | <field name="wkf_id" ref="wkf"/> |
225 | <field name="name">open</field> |
226 | - <field name="action">action_date_assign() |
227 | -action_move_create() |
228 | -action_number() |
229 | -write({'state':'open'})</field> |
230 | + <field name="action">action_open_invoice() |
231 | +write({'state':'open'}) |
232 | +action_gen_sync_msg()</field> |
233 | <field name="kind">function</field> |
234 | </record> |
235 | <record model="workflow.activity" id="act_open_test"> |
236 | <field name="wkf_id" ref="wkf"/> |
237 | <field name="name">re-open</field> |
238 | - <field name="action">write({'state':'open'})</field> |
239 | + <field name="action">write({'state':'open'}) |
240 | +action_gen_sync_msg()</field> |
241 | <field name="kind">function</field> |
242 | </record> |
243 | <record id="act_paid" model="workflow.activity"> |
244 | <field name="wkf_id" ref="wkf"/> |
245 | <field name="name">paid</field> |
246 | <!--<field name="flow_stop">True</field>--> |
247 | - <field name="action">confirm_paid()</field> |
248 | + <field name="action">confirm_paid() |
249 | +action_gen_sync_msg()</field> |
250 | <field name="kind">function</field> |
251 | <field name="signal_send">subflow.paid</field> |
252 | </record> |
253 | @@ -49,7 +50,8 @@ |
254 | <field name="name">cancel</field> |
255 | <field name="flow_stop">True</field> |
256 | <field name="action">action_cancel() |
257 | -write({'state':'cancel'})</field> |
258 | +write({'state':'cancel'}) |
259 | +action_gen_sync_msg()</field> |
260 | <field name="kind">function</field> |
261 | </record> |
262 | |
263 | |
264 | === modified file 'bin/addons/account/account_move_line.py' |
265 | --- bin/addons/account/account_move_line.py 2019-03-14 11:20:01 +0000 |
266 | +++ bin/addons/account/account_move_line.py 2019-07-30 10:04:49 +0000 |
267 | @@ -27,6 +27,7 @@ |
268 | from tools.translate import _ |
269 | import decimal_precision as dp |
270 | import tools |
271 | +import netsvc |
272 | |
273 | class account_move_line(osv.osv): |
274 | _name = "account.move.line" |
275 | @@ -993,8 +994,24 @@ |
276 | 'unreconcile_date': time.strftime('%Y-%m-%d'), |
277 | 'unreconcile_txt': obj_move_line.browse(cr, uid, aml, context=context, fields_to_fetch=['reconcile_txt']).reconcile_txt, |
278 | }, context=context) |
279 | + |
280 | + # if full reconcile linked to an invoice, set it as (re-)open |
281 | + cr.execute(''' |
282 | + select distinct(inv.id) |
283 | + from account_invoice inv |
284 | + left join account_move_line move_line on move_line.move_id = inv.move_id |
285 | + where |
286 | + move_line.reconcile_id in %s and |
287 | + move_line.is_counterpart |
288 | + ''', (tuple(unlink_ids), ) |
289 | + ) |
290 | + inv_ids = [x[0] for x in cr.fetchall()] |
291 | + |
292 | # then delete the account.move.reconciles |
293 | obj_move_rec.unlink(cr, uid, unlink_ids) |
294 | + |
295 | + if inv_ids: |
296 | + netsvc.LocalService("workflow").trg_validate(uid, 'account.invoice', inv_ids, 'open_test', cr) |
297 | return True |
298 | |
299 | def check_unlink(self, cr, uid, ids, context=None): |
300 | |
301 | === modified file 'bin/addons/account/account_report.xml' |
302 | --- bin/addons/account/account_report.xml 2018-08-03 12:27:21 +0000 |
303 | +++ bin/addons/account/account_report.xml 2019-07-30 10:04:49 +0000 |
304 | @@ -33,7 +33,7 @@ |
305 | name="account.invoice" |
306 | rml="account/report/account_print_invoice.rml" |
307 | string="Invoices" |
308 | - attachment="(object.state in ('open','paid')) and ('INV'+(object.number or '').replace('/',''))" |
309 | + attachment="(object.state in ('open','paid', 'inv_close')) and ('INV'+(object.number or '').replace('/',''))" |
310 | attachment_use="1" |
311 | multi="True"/> |
312 | <report id="account_transfers" model="account.transfer" name="account.transfer" string="Transfers" xml="account/report/transfer.xml" xsl="account/report/transfer.xsl"/> |
313 | |
314 | === modified file 'bin/addons/account/invoice.py' |
315 | --- bin/addons/account/invoice.py 2019-06-05 09:09:37 +0000 |
316 | +++ bin/addons/account/invoice.py 2019-07-30 10:04:49 +0000 |
317 | @@ -26,6 +26,7 @@ |
318 | import netsvc |
319 | from osv import fields, osv, orm |
320 | from tools.translate import _ |
321 | +from msf_partner import PARTNER_TYPE |
322 | |
323 | |
324 | class account_invoice(osv.osv): |
325 | @@ -93,7 +94,7 @@ |
326 | for invoice in self.browse(cr, uid, ids, context=context): |
327 | # UNIFIELD REFACTORING: UF-1536 have change this method |
328 | # Not needed to do process if invoice is draft or paid |
329 | - if invoice.state in ['draft', 'paid']: |
330 | + if invoice.state in ['draft', 'paid', 'inv_close']: |
331 | result[invoice.id] = 0.0 |
332 | continue |
333 | result[invoice.id] = invoice.amount_total |
334 | @@ -167,8 +168,7 @@ |
335 | if invoice.move_id: |
336 | # US-1882 The payments should only concern the "header line" of the SI on the counterpart account. |
337 | # For example the import of a tax line shouldn't be considered as a payment (out or in). |
338 | - invoice_amls = [ml for ml in invoice.move_id.line_id if ml.account_id == invoice.account_id |
339 | - and abs(abs(invoice.amount_total) - abs(ml.amount_currency)) <= 10**-3] |
340 | + invoice_amls = [ml for ml in invoice.move_id.line_id if ml.account_id == invoice.account_id and ml.is_counterpart] |
341 | for m in invoice_amls: |
342 | temp_lines = set() |
343 | if m.reconcile_id: |
344 | @@ -257,7 +257,7 @@ |
345 | _order = "id desc" |
346 | |
347 | _columns = { |
348 | - 'name': fields.char('Description', size=64, select=True, readonly=True, states={'draft':[('readonly',False)]}), |
349 | + 'name': fields.char('Description', size=256, select=True, readonly=True, states={'draft': [('readonly', False)]}), |
350 | 'origin': fields.char('Source Document', size=512, help="Reference of the document that produced this invoice.", readonly=True, states={'draft':[('readonly',False)]}), |
351 | 'type': fields.selection([ |
352 | ('out_invoice','Customer Invoice'), |
353 | @@ -279,6 +279,7 @@ |
354 | ('proforma2','Pro-forma'), |
355 | ('open','Open'), |
356 | ('paid','Paid'), |
357 | + ('inv_close','Closed'), |
358 | ('cancel','Cancelled') |
359 | ],'State', select=True, readonly=True, |
360 | help=' * The \'Draft\' state is used when a user is encoding a new and unconfirmed Invoice. \ |
361 | @@ -286,8 +287,8 @@ |
362 | \n* The \'Open\' state is used when user create invoice,a invoice number is generated.Its in open state till user does not pay invoice. \ |
363 | \n* The \'Paid\' state is set automatically when invoice is paid.\ |
364 | \n* The \'Cancelled\' state is used when user cancel invoice.'), |
365 | - 'date_invoice': fields.date('Invoice Date', states={'paid':[('readonly',True)], 'open':[('readonly',True)], 'close':[('readonly',True)]}, select=True, help="Keep empty to use the current date"), |
366 | - 'date_due': fields.date('Due Date', states={'paid':[('readonly',True)], 'open':[('readonly',True)], 'close':[('readonly',True)]}, select=True, |
367 | + 'date_invoice': fields.date('Invoice Date', states={'paid':[('readonly',True)], 'open':[('readonly',True)], 'inv_close':[('readonly',True)]}, select=True, help="Keep empty to use the current date"), |
368 | + 'date_due': fields.date('Due Date', states={'paid':[('readonly',True)], 'open':[('readonly',True)], 'inv_close':[('readonly',True)]}, select=True, |
369 | help="If you use payment terms, the due date will be computed automatically at the generation "\ |
370 | "of accounting entries. If you keep the payment term and the due date empty, it means direct payment. The payment term may compute several due dates, for example 50% now, 50% in one month."), |
371 | 'partner_id': fields.many2one('res.partner', 'Partner', change_default=True, readonly=True, required=True, states={'draft':[('readonly',False)]}), |
372 | @@ -301,8 +302,7 @@ |
373 | |
374 | 'account_id': fields.many2one('account.account', 'Account', required=True, readonly=True, states={'draft':[('readonly',False)]}, help="The partner account used for this invoice."), |
375 | 'invoice_line': fields.one2many('account.invoice.line', 'invoice_id', 'Invoice Lines', readonly=True, states={'draft':[('readonly',False)]}), |
376 | - 'tax_line': fields.one2many('account.invoice.tax', 'invoice_id', 'Tax Lines', readonly=True, states={'draft':[('readonly',False)]}), |
377 | - |
378 | + 'tax_line': fields.one2many('account.invoice.tax', 'invoice_id', 'Tax Lines'), |
379 | 'move_id': fields.many2one('account.move', 'Journal Entry', readonly=True, select=1, ondelete='restrict', help="Link to the automatically generated Journal Items."), |
380 | 'amount_untaxed': fields.function(_amount_all, method=True, digits_compute=dp.get_precision('Account'), string='Untaxed', |
381 | store={ |
382 | @@ -328,7 +328,7 @@ |
383 | 'currency_id': fields.many2one('res.currency', 'Currency', required=True, readonly=True, states={'draft':[('readonly',False)]}), |
384 | 'journal_id': fields.many2one('account.journal', 'Journal', required=True, hide_default_menu=True, readonly=True, states={'draft':[('readonly',False)]}), |
385 | 'company_id': fields.many2one('res.company', 'Company', required=True, change_default=True, readonly=True, states={'draft':[('readonly',False)]}), |
386 | - 'check_total': fields.float('Total', digits_compute=dp.get_precision('Account'), states={'open':[('readonly',True)],'close':[('readonly',True)],'paid':[('readonly',True)]}), |
387 | + 'check_total': fields.float('Total', digits_compute=dp.get_precision('Account'), states={'open':[('readonly',True)],'inv_close':[('readonly',True)],'paid':[('readonly',True)]}), |
388 | 'reconciled': fields.function(_reconciled, method=True, string='Paid/Reconciled', type='boolean', |
389 | store={ |
390 | 'account.invoice': (lambda self, cr, uid, ids, c={}: ids, None, 50), # Check if we can remove ? |
391 | @@ -454,22 +454,47 @@ |
392 | def confirm_paid(self, cr, uid, ids, context=None): |
393 | if context is None: |
394 | context = {} |
395 | - self.write(cr, uid, ids, {'state':'paid'}, context=context) |
396 | - for inv_id, name in self.name_get(cr, uid, ids, context=context): |
397 | - message = _("Invoice '%s' is paid.") % name |
398 | - self.log(cr, uid, inv_id, message) |
399 | + # if reconciled with at least 1 liquidity journal then paid else cancel aka Closed |
400 | + cr.execute(""" |
401 | + SELECT i.id, min(j.id), i.number |
402 | + FROM account_invoice i |
403 | + LEFT JOIN account_move_line l ON i.move_id=l.move_id |
404 | + LEFT JOIN account_move_line rec_line ON rec_line.reconcile_id = l.reconcile_id |
405 | + LEFT JOIN account_journal j ON j.id = rec_line.journal_id AND j.type in ('cash', 'bank', 'cheque') |
406 | + WHERE i.id IN %s |
407 | + AND l.reconcile_id is not null |
408 | + AND l.account_id=i.account_id |
409 | + AND l.is_counterpart |
410 | + GROUP BY i.id, i.number""", (tuple(ids), ) |
411 | + ) |
412 | + |
413 | + for x in cr.fetchall(): |
414 | + if x[1]: |
415 | + state = 'paid' |
416 | + display_state = _('paid') |
417 | + else: |
418 | + state = 'inv_close' |
419 | + display_state = _('closed') |
420 | + |
421 | + self.write(cr, uid, x[0], {'state': state}, context=context) |
422 | + self.log(cr, uid, x[0], _("Invoice '%s' is %s.") % (x[2], display_state)) |
423 | + |
424 | return True |
425 | |
426 | def unlink(self, cr, uid, ids, context=None): |
427 | if context is None: |
428 | context = {} |
429 | - invoices = self.read(cr, uid, ids, ['state'], context=context) |
430 | + invoices = self.read(cr, uid, ids, ['state', 'synced', 'from_supply'], context=context) |
431 | unlink_ids = [] |
432 | for t in invoices: |
433 | - if t['state'] in ('draft', 'cancel'): |
434 | + if t['state'] not in ('draft', 'cancel'): |
435 | + raise osv.except_osv(_('Invalid action !'), _('Cannot delete invoice(s) that are already opened or paid !')) |
436 | + elif t['from_supply']: |
437 | + raise osv.except_osv(_('Invalid action !'), _('Cannot delete invoice(s) generated by a Supply workflow!')) |
438 | + elif t['synced']: |
439 | + raise osv.except_osv(_('Invalid action !'), _('Cannot delete invoice(s) set as "Synchronized"!')) |
440 | + else: |
441 | unlink_ids.append(t['id']) |
442 | - else: |
443 | - raise osv.except_osv(_('Invalid action !'), _('Cannot delete invoice(s) that are already opened or paid !')) |
444 | osv.osv.unlink(self, cr, uid, unlink_ids, context=context) |
445 | return True |
446 | |
447 | @@ -481,6 +506,7 @@ |
448 | acc_id = False |
449 | bank_id = False |
450 | fiscal_position = False |
451 | + partner_type = False |
452 | |
453 | opt = [('uid', str(uid))] |
454 | if partner_id: |
455 | @@ -490,6 +516,8 @@ |
456 | contact_addr_id = res['contact'] |
457 | invoice_addr_id = res['invoice'] |
458 | p = self.pool.get('res.partner').browse(cr, uid, partner_id) |
459 | + partner_type = p.partner_type # update the partner type immediately as it is used in a domain in attrs |
460 | + |
461 | if company_id: |
462 | if p.property_account_receivable.company_id.id != company_id and p.property_account_payable.company_id.id != company_id: |
463 | property_obj = self.pool.get('ir.property') |
464 | @@ -526,7 +554,8 @@ |
465 | 'address_invoice_id': invoice_addr_id, |
466 | 'account_id': acc_id, |
467 | 'payment_term': partner_payment_term, |
468 | - 'fiscal_position': fiscal_position |
469 | + 'fiscal_position': fiscal_position, |
470 | + 'partner_type': partner_type, |
471 | } |
472 | } |
473 | |
474 | @@ -662,6 +691,22 @@ |
475 | val['currency_id'] = currency.id |
476 | return {'value': val, 'domain': dom} |
477 | |
478 | + def onchange_synced(self, cr, uid, ids, synced, partner_id): |
479 | + """ |
480 | + Resets "synced" field and informs the user in case the box is ticked whereas the partner is neither Intermission nor Intersection |
481 | + """ |
482 | + res = {} |
483 | + partner_obj = self.pool.get('res.partner') |
484 | + if synced and partner_id: |
485 | + if partner_obj.browse(cr, uid, partner_id, fields_to_fetch=['partner_type']).partner_type not in ('intermission', 'section'): |
486 | + warning = { |
487 | + 'title': _('Warning!'), |
488 | + 'message': _('Synchronization is allowed only with Intermission and Intersection partners.') |
489 | + } |
490 | + res['warning'] = warning |
491 | + res['value'] = {'synced': False, } |
492 | + return res |
493 | + |
494 | # go from canceled state to draft state |
495 | def action_cancel_draft(self, cr, uid, ids, *args): |
496 | self.write(cr, uid, ids, {'state':'draft'}) |
497 | @@ -674,25 +719,31 @@ |
498 | # Workflow stuff |
499 | ################# |
500 | |
501 | - # return the ids of the move lines which has the same account than the invoice |
502 | - # whose id is in ids |
503 | def move_line_id_payment_get(self, cr, uid, ids, *args): |
504 | - if not ids: return [] |
505 | + ''' |
506 | + return the ids of the SI header move line |
507 | + ''' |
508 | + if not ids: |
509 | + return [] |
510 | result = self.move_line_id_payment_gets(cr, uid, ids, *args) |
511 | return result.get(ids[0], []) |
512 | |
513 | def move_line_id_payment_gets(self, cr, uid, ids, *args): |
514 | + if not ids: |
515 | + return {} |
516 | + |
517 | res = {} |
518 | - if not ids: return res |
519 | - cr.execute('SELECT i.id, l.id '\ |
520 | - 'FROM account_move_line l '\ |
521 | - 'LEFT JOIN account_invoice i ON (i.move_id=l.move_id) '\ |
522 | - 'WHERE i.id IN %s '\ |
523 | - 'AND l.account_id=i.account_id', |
524 | - (tuple(ids),)) |
525 | + cr.execute(""" |
526 | + SELECT i.id, l.id |
527 | + FROM account_move_line l |
528 | + LEFT JOIN account_invoice i ON (i.move_id=l.move_id) |
529 | + WHERE i.id IN %s |
530 | + AND l.account_id=i.account_id |
531 | + AND l.is_counterpart""", (tuple(ids), ) |
532 | + ) |
533 | for r in cr.fetchall(): |
534 | res.setdefault(r[0], []) |
535 | - res[r[0]].append( r[1] ) |
536 | + res[r[0]].append(r[1]) |
537 | return res |
538 | |
539 | def copy(self, cr, uid, id, default={}, context=None): |
540 | @@ -705,6 +756,10 @@ |
541 | 'move_name':False, |
542 | 'internal_number': False, |
543 | 'main_purchase_id': False, |
544 | + 'from_supply': False, |
545 | + 'synced': False, |
546 | + 'counterpart_inv_number': False, |
547 | + 'counterpart_inv_status': False, |
548 | }) |
549 | if 'date_invoice' not in default: |
550 | default.update({ |
551 | @@ -1324,12 +1379,18 @@ |
552 | for invoice in invoices: |
553 | del invoice['id'] |
554 | |
555 | - type_dict = { |
556 | - 'out_invoice': 'out_refund', # Customer Invoice |
557 | - 'in_invoice': 'in_refund', # Supplier Invoice |
558 | - 'out_refund': 'out_invoice', # Customer Refund |
559 | - 'in_refund': 'in_invoice', # Supplier Refund |
560 | - } |
561 | + if context.get('is_intermission', False): |
562 | + type_dict = { |
563 | + 'out_invoice': 'in_invoice', # IVO |
564 | + 'in_invoice': 'out_invoice', # IVI |
565 | + } |
566 | + else: |
567 | + type_dict = { |
568 | + 'out_invoice': 'out_refund', # Customer Invoice |
569 | + 'in_invoice': 'in_refund', # Supplier Invoice |
570 | + 'out_refund': 'out_invoice', # Customer Refund |
571 | + 'in_refund': 'in_invoice', # Supplier Refund |
572 | + } |
573 | |
574 | invoice_lines = obj_invoice_line.read(cr, uid, invoice['invoice_line']) |
575 | invoice_lines = self._refund_cleanup_lines(cr, uid, invoice_lines, is_account_inv_line=True, context=context) |
576 | @@ -1355,6 +1416,10 @@ |
577 | 'journal_id': refund_journal_ids, |
578 | 'origin': invoice['number'] |
579 | }) |
580 | + if context.get('is_intermission', False): |
581 | + invoice.update({ |
582 | + 'is_intermission': True, |
583 | + }) |
584 | if period_id: |
585 | invoice.update({ |
586 | 'period_id': period_id, |
587 | @@ -1475,6 +1540,13 @@ |
588 | self.pool.get('account.invoice').write(cr, uid, ids, {}, context=context) |
589 | return True |
590 | |
591 | + |
592 | + def action_gen_sync_msg(self, cr, uid, ids, context=None): |
593 | + for inv_id in ids: |
594 | + self.pool.get('sync.client.message_rule')._manual_create_sync_message(cr, uid, 'account.invoice', inv_id, {}, |
595 | + 'account.invoice.update_counterpart_inv', self._logger, check_identifier=False, context=context) |
596 | + return True |
597 | + |
598 | account_invoice() |
599 | |
600 | class account_invoice_line(osv.osv): |
601 | @@ -1515,6 +1587,8 @@ |
602 | 'name': fields.char('Description', size=256, required=True), |
603 | 'origin': fields.char('Origin', size=512, help="Reference of the document that produced this invoice."), |
604 | 'invoice_id': fields.many2one('account.invoice', 'Invoice Reference', ondelete='cascade', select=True), |
605 | + 'partner_type': fields.related('invoice_id', 'partner_type', string='Partner Type', type='selection', |
606 | + selection=PARTNER_TYPE, readonly=True, store=False), |
607 | 'uos_id': fields.many2one('product.uom', 'Unit of Measure', ondelete='set null'), |
608 | 'product_id': fields.many2one('product.product', 'Product', ondelete='set null'), |
609 | 'account_id': fields.many2one('account.account', 'Account', required=True, domain=[('type','<>','view'), ('type', '<>', 'closed')], help="The income or expense account related to the selected product."), |
610 | |
611 | === modified file 'bin/addons/account/report/account_invoice_report.py' |
612 | --- bin/addons/account/report/account_invoice_report.py 2011-04-07 12:29:55 +0000 |
613 | +++ bin/addons/account/report/account_invoice_report.py 2019-07-30 10:04:49 +0000 |
614 | @@ -32,8 +32,8 @@ |
615 | 'year': fields.char('Year', size=4, readonly=True), |
616 | 'day': fields.char('Day', size=128, readonly=True), |
617 | 'month': fields.selection([('01','January'), ('02','February'), ('03','March'), ('04','April'), |
618 | - ('05','May'), ('06','June'), ('07','July'), ('08','August'), ('09','September'), |
619 | - ('10','October'), ('11','November'), ('12','December')], 'Month', readonly=True), |
620 | + ('05','May'), ('06','June'), ('07','July'), ('08','August'), ('09','September'), |
621 | + ('10','October'), ('11','November'), ('12','December')], 'Month', readonly=True), |
622 | 'product_id': fields.many2one('product.product', 'Product', readonly=True), |
623 | 'product_qty':fields.float('Qty', readonly=True), |
624 | 'uom_name': fields.char('Reference UoM', size=128, readonly=True), |
625 | @@ -56,15 +56,16 @@ |
626 | ('in_invoice','Supplier Invoice'), |
627 | ('out_refund','Customer Refund'), |
628 | ('in_refund','Supplier Refund'), |
629 | - ],'Type', readonly=True), |
630 | + ],'Type', readonly=True), |
631 | 'state': fields.selection([ |
632 | ('draft','Draft'), |
633 | ('proforma','Pro-forma'), |
634 | ('proforma2','Pro-forma'), |
635 | ('open','Open'), |
636 | ('paid','Done'), |
637 | + ('inv_close','Closed'), |
638 | ('cancel','Cancelled') |
639 | - ], 'Invoice State', readonly=True), |
640 | + ], 'Invoice State', readonly=True), |
641 | 'date_due': fields.date('Due Date', readonly=True), |
642 | 'address_contact_id': fields.many2one('res.partner.address', 'Contact Address Name', readonly=True), |
643 | 'address_invoice_id': fields.many2one('res.partner.address', 'Invoice Address Name', readonly=True), |
644 | |
645 | === modified file 'bin/addons/account/report/account_invoice_report_view.xml' |
646 | --- bin/addons/account/report/account_invoice_report_view.xml 2017-10-04 05:23:42 +0000 |
647 | +++ bin/addons/account/report/account_invoice_report_view.xml 2019-07-30 10:04:49 +0000 |
648 | @@ -6,7 +6,7 @@ |
649 | <field name="model">account.invoice.report</field> |
650 | <field name="type">tree</field> |
651 | <field name="arch" type="xml"> |
652 | - <tree colors="blue:state in ('draft');gray:state in ('cancel','paid');black:state in ('proforma','proforma2')" string="Invoices Analysis"> |
653 | + <tree colors="blue:state in ('draft');gray:state in ('cancel','paid','inv_close');black:state in ('proforma','proforma2')" string="Invoices Analysis"> |
654 | <field name="date" invisible="1"/> |
655 | <field name="user_id" invisible="1"/> |
656 | <field name="year" invisible="1"/> |
657 | |
658 | === modified file 'bin/addons/account/report/account_report.py' |
659 | --- bin/addons/account/report/account_report.py 2015-02-05 16:24:18 +0000 |
660 | +++ bin/addons/account/report/account_report.py 2019-07-30 10:04:49 +0000 |
661 | @@ -68,7 +68,7 @@ |
662 | )""") |
663 | report_account_receivable() |
664 | |
665 | - #a.type in ('receivable','payable') |
666 | +#a.type in ('receivable','payable') |
667 | class temp_range(osv.osv): |
668 | _name = 'temp.range' |
669 | _description = 'A Temporary table used for Dashboard view' |
670 | @@ -101,14 +101,14 @@ |
671 | def _calc_bal(self, cr, uid, ids, name, args, context=None): |
672 | res = {} |
673 | for period in self.read(cr, uid, ids, ['name'], context=context): |
674 | - date1,date2 = period['name'].split(' to ') |
675 | - cr.execute("SELECT SUM(credit-debit) FROM account_move_line AS line, account_account as ac \ |
676 | + date1,date2 = period['name'].split(' to ') |
677 | + cr.execute("SELECT SUM(credit-debit) FROM account_move_line AS line, account_account as ac \ |
678 | WHERE (line.account_id=ac.id) AND ac.type='receivable' \ |
679 | AND (COALESCE(line.date,date) BETWEEN %s AND %s) \ |
680 | AND (reconcile_id IS NULL) AND ac.active",(str(date2),str(date1),)) |
681 | - amount = cr.fetchone() |
682 | - amount = amount[0] or 0.00 |
683 | - res[period['id']] = amount |
684 | + amount = cr.fetchone() |
685 | + amount = amount[0] or 0.00 |
686 | + res[period['id']] = amount |
687 | |
688 | return res |
689 | |
690 | @@ -159,7 +159,7 @@ |
691 | ('in_invoice','Supplier Invoice'), |
692 | ('out_refund','Customer Refund'), |
693 | ('in_refund','Supplier Refund'), |
694 | - ],'Type', readonly=True), |
695 | + ],'Type', readonly=True), |
696 | 'number': fields.char('Invoice Number', size=32, readonly=True), |
697 | 'partner_id': fields.many2one('res.partner', 'Partner', readonly=True), |
698 | 'amount_untaxed': fields.float('Untaxed', readonly=True), |
699 | @@ -174,6 +174,7 @@ |
700 | ('proforma2','Pro-forma'), |
701 | ('open','Open'), |
702 | ('paid','Done'), |
703 | + ('inv_close','Closed'), |
704 | ('cancel','Cancelled') |
705 | ],'State', readonly=True), |
706 | 'origin': fields.char('Source Document', size=512, readonly=True, help="Reference of the document that generated this invoice report."), |
707 | @@ -235,7 +236,7 @@ |
708 | inner join account_invoice inv on inv.id = inv_line.invoice_id |
709 | inner join account_account account on account.id = inv_line.account_id |
710 | where |
711 | - inv.state in ('open','paid') |
712 | + inv.state in ('open','paid', 'inv_close') |
713 | group by |
714 | to_char(inv.date_invoice, 'YYYY'),to_char(inv.date_invoice,'MM'),inv.currency_id, inv.period_id, inv_line.product_id, account.user_type |
715 | )""") |
716 | @@ -277,10 +278,10 @@ |
717 | inner join account_invoice inv on inv.id = inv_line.invoice_id |
718 | inner join account_account account on account.id = inv_line.account_id |
719 | where |
720 | - inv.state in ('open','paid') |
721 | + inv.state in ('open','paid', 'inv_close') |
722 | group by |
723 | to_char(inv.date_invoice, 'YYYY'),to_char(inv.date_invoice,'MM'),inv.currency_id, inv.period_id, inv_line.product_id, account.id |
724 | )""") |
725 | report_account_sales() |
726 | |
727 | -# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
728 | \ No newline at end of file |
729 | +# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
730 | |
731 | === modified file 'bin/addons/account/report/account_report_view.xml' |
732 | --- bin/addons/account/report/account_report_view.xml 2011-01-14 00:11:01 +0000 |
733 | +++ bin/addons/account/report/account_report_view.xml 2019-07-30 10:04:49 +0000 |
734 | @@ -88,7 +88,7 @@ |
735 | <field name="model">report.invoice.created</field> |
736 | <field name="type">tree</field> |
737 | <field name="arch" type="xml"> |
738 | - <tree colors="blue:state in ('draft');black:state in ('proforma','proforma2','open');gray:state in('paid','cancel') " string="Invoices"> |
739 | + <tree colors="blue:state in ('draft');black:state in ('proforma','proforma2','open');gray:state in('paid', 'inv_close', 'cancel') " string="Invoices"> |
740 | <field name="create_date" select="1"/> |
741 | <field name="name" select="1"/> |
742 | <field name="type"/> |
743 | |
744 | === modified file 'bin/addons/account/report/account_tax_report.py' |
745 | --- bin/addons/account/report/account_tax_report.py 2014-09-24 09:16:10 +0000 |
746 | +++ bin/addons/account/report/account_tax_report.py 2019-07-30 10:04:49 +0000 |
747 | @@ -84,14 +84,14 @@ |
748 | while i < len(res): |
749 | |
750 | res_dict = { 'code': res[i][1].code, |
751 | - 'name': res[i][1].name, |
752 | - 'debit': 0, |
753 | - 'credit': 0, |
754 | - 'tax_amount': res[i][1].sum_period, |
755 | - 'type': 1, |
756 | - 'level': res[i][0], |
757 | - 'pos': 0 |
758 | - } |
759 | + 'name': res[i][1].name, |
760 | + 'debit': 0, |
761 | + 'credit': 0, |
762 | + 'tax_amount': res[i][1].sum_period, |
763 | + 'type': 1, |
764 | + 'level': res[i][0], |
765 | + 'pos': 0 |
766 | + } |
767 | |
768 | top_result.append(res_dict) |
769 | res_general = self._get_general(res[i][1].id, period_list, company_id, based_on, context=context) |
770 | @@ -128,10 +128,10 @@ |
771 | AND account.company_id = %s \ |
772 | AND move.id = line.move_id \ |
773 | AND line.period_id IN %s \ |
774 | - AND ((invoice.state = %s) \ |
775 | + AND ((invoice.state in (\'paid\', \'inv_close\')) \ |
776 | OR (invoice.id IS NULL)) \ |
777 | GROUP BY account.id,account.name,account.code', ('draft', tax_code_id, |
778 | - company_id, periods_ids, 'paid',)) |
779 | + company_id, periods_ids)) |
780 | |
781 | else: |
782 | self.cr.execute('SELECT SUM(line.tax_amount) AS tax_amount, \ |
783 | @@ -150,7 +150,7 @@ |
784 | AND line.period_id IN %s\ |
785 | AND account.active \ |
786 | GROUP BY account.id,account.name,account.code', ('draft', tax_code_id, |
787 | - company_id, periods_ids,)) |
788 | + company_id, periods_ids,)) |
789 | res = self.cr.dictfetchall() |
790 | |
791 | i = 0 |
792 | @@ -206,14 +206,14 @@ |
793 | |
794 | while (bcl_current_level >= int(accounts[bcl_rup_ind]['level']) and bcl_rup_ind >= 0 ): |
795 | res_tot = { 'code': accounts[bcl_rup_ind]['code'], |
796 | - 'name': '', |
797 | - 'debit': 0, |
798 | - 'credit': 0, |
799 | - 'tax_amount': accounts[bcl_rup_ind]['tax_amount'], |
800 | - 'type': accounts[bcl_rup_ind]['type'], |
801 | - 'level': 0, |
802 | - 'pos': 0 |
803 | - } |
804 | + 'name': '', |
805 | + 'debit': 0, |
806 | + 'credit': 0, |
807 | + 'tax_amount': accounts[bcl_rup_ind]['tax_amount'], |
808 | + 'type': accounts[bcl_rup_ind]['type'], |
809 | + 'level': 0, |
810 | + 'pos': 0 |
811 | + } |
812 | |
813 | if res_tot['type'] == 1: |
814 | # on change le type pour afficher le total |
815 | @@ -229,6 +229,6 @@ |
816 | return result_accounts |
817 | |
818 | report_sxw.report_sxw('report.account.vat.declaration', 'account.tax.code', |
819 | - 'addons/account/report/account_tax_report.rml', parser=tax_report, header="internal") |
820 | + 'addons/account/report/account_tax_report.rml', parser=tax_report, header="internal") |
821 | |
822 | -# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
823 | \ No newline at end of file |
824 | +# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
825 | |
826 | === modified file 'bin/addons/account/wizard/__init__.py' |
827 | --- bin/addons/account/wizard/__init__.py 2018-08-02 15:01:48 +0000 |
828 | +++ bin/addons/account/wizard/__init__.py 2019-07-30 10:04:49 +0000 |
829 | @@ -53,8 +53,6 @@ |
830 | import account_validate_account_move |
831 | import account_use_model |
832 | |
833 | -import account_state_open |
834 | - |
835 | import account_report_print_journal |
836 | import account_report_central_journal |
837 | import account_report_general_journal |
838 | |
839 | === modified file 'bin/addons/account/wizard/account_invoice_refund.py' |
840 | --- bin/addons/account/wizard/account_invoice_refund.py 2018-05-14 12:41:04 +0000 |
841 | +++ bin/addons/account/wizard/account_invoice_refund.py 2019-07-30 10:04:49 +0000 |
842 | @@ -29,13 +29,24 @@ |
843 | |
844 | _name = "account.invoice.refund" |
845 | _description = "Invoice Refund" |
846 | + |
847 | + def _get_filter_refund(self, cr, uid, context=None): |
848 | + """ |
849 | + Returns the selectable Refund Types (no simple "Refund" in case of an IVO/IVI) |
850 | + """ |
851 | + if context is None: |
852 | + context = {} |
853 | + if context.get('is_intermission', False): |
854 | + return [('modify', 'Modify'), ('cancel', 'Cancel')] |
855 | + return [('modify', 'Modify'), ('refund', 'Refund'), ('cancel', 'Cancel')] |
856 | + |
857 | _columns = { |
858 | 'date': fields.date('Operation date', help='This date will be used as the invoice date for Refund Invoice and Period will be chosen accordingly!'), |
859 | 'period': fields.many2one('account.period', 'Force period'), |
860 | 'journal_id': fields.many2one('account.journal', 'Refund Journal', hide_default_menu=True, |
861 | help='You can select here the journal to use for the refund invoice that will be created. If you leave that field empty, it will use the same journal as the current invoice.'), |
862 | 'description': fields.char('Description', size=128, required=True), |
863 | - 'filter_refund': fields.selection([('modify', 'Modify'), ('refund', 'Refund'), ('cancel', 'Cancel')], "Refund Type", required=True, help='Refund invoice base on this type. You can not Modify and Cancel if the invoice is already reconciled'), |
864 | + 'filter_refund': fields.selection(_get_filter_refund, "Refund Type", required=True, help='Refund invoice based on this type. You can not Modify and Cancel if the invoice is already reconciled'), |
865 | } |
866 | |
867 | def _get_journal(self, cr, uid, context=None): |
868 | @@ -109,9 +120,8 @@ |
869 | """ |
870 | for ml in aml_list: |
871 | if ml.account_id.reconcile: |
872 | - if ml.account_id.id not in to_reconcile_dict: |
873 | - to_reconcile_dict[ml.account_id.id] = [] |
874 | - to_reconcile_dict[ml.account_id.id].append(ml.id) |
875 | + key = (ml.account_id.id, ml.is_counterpart) |
876 | + to_reconcile_dict.setdefault(key, []).append(ml.id) |
877 | |
878 | def compute_refund(self, cr, uid, ids, mode='refund', context=None): |
879 | """ |
880 | @@ -144,8 +154,20 @@ |
881 | for inv in inv_obj.browse(cr, uid, invoice_ids, context=context): |
882 | if inv.state in ['draft', 'proforma2', 'cancel']: |
883 | raise osv.except_osv(_('Error !'), _('Can not %s draft/proforma/cancel invoice.') % (mode)) |
884 | + if mode in ('cancel', 'modify') and not inv.account_id.reconcile: |
885 | + raise osv.except_osv(_('Error !'), _("Cannot Cancel / Modify if the account can't be reconciled.")) |
886 | if mode in ('cancel', 'modify') and inv_obj.has_one_line_reconciled(cr, uid, [inv.id], context=context): |
887 | - raise osv.except_osv(_('Error !'), _('Can not %s invoice which is already reconciled, invoice should be unreconciled first. You can only Refund this invoice') % (mode)) |
888 | + if inv.is_intermission: |
889 | + # error specific to IVO/IVI for which there is no simple refund option |
890 | + raise osv.except_osv(_('Error !'), _('Cannot %s an Intermission Voucher which is already reconciled, it should be unreconciled first.') % _(mode)) |
891 | + if inv.state == 'inv_close': |
892 | + raise osv.except_osv(_('Error !'), _('Can not %s invoice which is already reconciled, invoice should be unreconciled first.') % (mode)) |
893 | + else: |
894 | + raise osv.except_osv(_('Error !'), _('Can not %s invoice which is already reconciled, invoice should be unreconciled first. You can only Refund this invoice') % (mode)) |
895 | + |
896 | + if mode == 'refund' and inv.state == 'inv_close': |
897 | + raise osv.except_osv(_('Error !'), _('It is not possible to refund a Closed invoice')) |
898 | + |
899 | if form['period']: |
900 | period = form['period'] |
901 | else: |
902 | @@ -188,8 +210,14 @@ |
903 | refund_id = self._hook_create_refund(cr, uid, [inv.id], date, period, description, journal_id, form, context=context) |
904 | del context['refund_mode'] # ignore it for the remaining process (in particular for the SI created in a refund modify...) |
905 | refund = inv_obj.browse(cr, uid, refund_id[0], context=context) |
906 | + # for Intermission Vouchers OUT: at standard creation time there is no "check_total" entered manually, |
907 | + # its value is always 0.0 => use the "amount_total" value for the IVI generated so it won't block at validation step |
908 | + if inv.is_intermission and inv.type == 'out_invoice': |
909 | + check_total = inv.amount_total or 0.0 |
910 | + else: |
911 | + check_total = inv.check_total |
912 | inv_obj.write(cr, uid, [refund.id], {'date_due': date, |
913 | - 'check_total': inv.check_total}) |
914 | + 'check_total': check_total}) |
915 | |
916 | created_inv.append(refund_id[0]) |
917 | if mode in ('cancel', 'modify'): |
918 | @@ -206,8 +234,8 @@ |
919 | self._get_reconcilable_amls(movelines, to_reconcile) |
920 | self._get_reconcilable_amls(refund.move_id.line_id, to_reconcile) |
921 | # reconcile the lines grouped by account |
922 | - for account_id in to_reconcile: |
923 | - account_m_line_obj.reconcile(cr, uid, to_reconcile[account_id], |
924 | + for account_id, is_counterpart in to_reconcile: |
925 | + account_m_line_obj.reconcile(cr, uid, to_reconcile[(account_id, is_counterpart)], |
926 | writeoff_period_id=period, |
927 | writeoff_journal_id = inv.journal_id.id, |
928 | writeoff_acc_id=account_id |
929 | @@ -230,6 +258,7 @@ |
930 | 'period_id': False, |
931 | 'name': description, |
932 | 'origin': source_doc, |
933 | + 'is_intermission': inv.is_intermission, |
934 | }) |
935 | for field in self._hook_fields_m2o_for_modify_refund(cr, uid): |
936 | invoice[field] = invoice[field] and invoice[field][0] |
937 | @@ -243,8 +272,7 @@ |
938 | # Refund cancel/modify: set the invoice JI/AJIs as Corrected by the system so that they can't be |
939 | # corrected manually. This must be done at the end of the refund process to handle the right AJI ids |
940 | # get the list of move lines excluding invoice header |
941 | - ml_list = [ml.id for ml in movelines if not (ml.account_id.id == inv.account_id.id and |
942 | - abs(abs(inv.amount_total) - abs(ml.amount_currency)) <= 10**-3)] |
943 | + ml_list = [ml.id for ml in movelines if not ml.is_counterpart] |
944 | account_m_line_obj.set_as_corrected(cr, uid, ml_list, manual=False, context=None) |
945 | # all JI lines of the SI and SR (including header) should be not corrigible, no matter if they |
946 | # are marked as corrected, reversed... |
947 | @@ -254,11 +282,19 @@ |
948 | # write on JIs without recreating AJIs |
949 | account_m_line_obj.write(cr, uid, ji_ids, {'is_si_refund': True}, context=context, check=False, update_check=False) |
950 | |
951 | - if inv.type in ('out_invoice', 'out_refund'): |
952 | - xml_id = 'action_invoice_tree3' |
953 | + if context.get('is_intermission', False): |
954 | + module = 'account_override' |
955 | + if inv.type == 'in_invoice': |
956 | + xml_id = 'action_intermission_out' |
957 | + else: |
958 | + xml_id = 'action_intermission_in' |
959 | else: |
960 | - xml_id = 'action_invoice_tree4' |
961 | - result = mod_obj.get_object_reference(cr, uid, 'account', xml_id) |
962 | + module = 'account' |
963 | + if inv.type in ('out_invoice', 'out_refund'): |
964 | + xml_id = 'action_invoice_tree3' |
965 | + else: |
966 | + xml_id = 'action_invoice_tree4' |
967 | + result = mod_obj.get_object_reference(cr, uid, module, xml_id) |
968 | id = result and result[1] or False |
969 | result = act_obj.read(cr, uid, id, context=context) |
970 | invoice_domain = eval(result['domain']) |
971 | |
972 | === modified file 'bin/addons/account/wizard/account_invoice_refund_view.xml' |
973 | --- bin/addons/account/wizard/account_invoice_refund_view.xml 2018-05-15 08:55:26 +0000 |
974 | +++ bin/addons/account/wizard/account_invoice_refund_view.xml 2019-07-30 10:04:49 +0000 |
975 | @@ -15,11 +15,14 @@ |
976 | <field name="date" required="1"/> |
977 | <field name="period"/> |
978 | <field name="filter_refund"/> |
979 | + <field name="is_intermission" invisible="1"/> |
980 | </group> |
981 | <separator colspan="4"/> |
982 | <group col="4" colspan="4" fill="1"> |
983 | <label align="0.0" width="550" colspan="4" string="Modify Invoice: Cancels the current invoice and creates a new copy of it ready for editing."/> |
984 | - <label align="0.0" width="300" string="Refund Invoice: Creates the refund invoice, ready for editing."/> |
985 | + <group attrs="{'invisible': [('is_intermission', '=', True)] }"> |
986 | + <label align="0.0" width="300" string="Refund Invoice: Creates the refund invoice, ready for editing."/> |
987 | + </group> |
988 | <label align="0.0" width="500" colspan="4" string="Cancel Invoice: Creates the refund invoice, validate and reconcile it to cancel the current invoice."/> |
989 | </group> |
990 | <separator colspan="4"/> |
991 | |
992 | === modified file 'bin/addons/account/wizard/account_invoice_state.py' |
993 | --- bin/addons/account/wizard/account_invoice_state.py 2011-01-14 00:11:01 +0000 |
994 | +++ bin/addons/account/wizard/account_invoice_state.py 2019-07-30 10:04:49 +0000 |
995 | @@ -47,28 +47,5 @@ |
996 | |
997 | account_invoice_confirm() |
998 | |
999 | -class account_invoice_cancel(osv.osv_memory): |
1000 | - """ |
1001 | - This wizard will cancel the all the selected invoices. |
1002 | - If in the journal, the option allow cancelling entry is not selected then it will give warning message. |
1003 | - """ |
1004 | - |
1005 | - _name = "account.invoice.cancel" |
1006 | - _description = "Cancel the Selected Invoices" |
1007 | - |
1008 | - def invoice_cancel(self, cr, uid, ids, context=None): |
1009 | - if context is None: |
1010 | - context = {} |
1011 | - wf_service = netsvc.LocalService('workflow') |
1012 | - pool_obj = pooler.get_pool(cr.dbname) |
1013 | - data_inv = pool_obj.get('account.invoice').read(cr, uid, context['active_ids'], ['state'], context=context) |
1014 | - |
1015 | - for record in data_inv: |
1016 | - if record['state'] in ('cancel','paid'): |
1017 | - raise osv.except_osv(_('Warning'), _("Selected Invoice(s) cannot be cancelled as they are already in 'Cancelled' or 'Done' state!")) |
1018 | - wf_service.trg_validate(uid, 'account.invoice', record['id'], 'invoice_cancel', cr) |
1019 | - return {'type': 'ir.actions.act_window_close'} |
1020 | - |
1021 | -account_invoice_cancel() |
1022 | - |
1023 | -# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
1024 | \ No newline at end of file |
1025 | + |
1026 | +# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
1027 | |
1028 | === modified file 'bin/addons/account/wizard/account_invoice_state_view.xml' |
1029 | --- bin/addons/account/wizard/account_invoice_state_view.xml 2017-10-04 05:23:42 +0000 |
1030 | +++ bin/addons/account/wizard/account_invoice_state_view.xml 2019-07-30 10:04:49 +0000 |
1031 | @@ -16,29 +16,5 @@ |
1032 | </field> |
1033 | </record> |
1034 | |
1035 | - <record id="account_invoice_cancel_view" model="ir.ui.view"> |
1036 | - <field name="name">account.invoice.cancel.form</field> |
1037 | - <field name="model">account.invoice.cancel</field> |
1038 | - <field name="type">form</field> |
1039 | - <field name="arch" type="xml"> |
1040 | - <form string="Cancel Selected Invoices"> |
1041 | - <separator string="Cancel Selected Invoices" colspan="4"/> |
1042 | - <group colspan="4" col="6"> |
1043 | - <button icon="gtk-cancel" string="Cancel Invoices" name="invoice_cancel" type="object" default_focus="1"/> |
1044 | - <button icon="terp-dialog-close" special="cancel" string="Close"/> |
1045 | - </group> |
1046 | - </form> |
1047 | - </field> |
1048 | - </record> |
1049 | - |
1050 | - <record id="action_account_invoice_cancel" model="ir.actions.act_window"> |
1051 | - <field name="name">Cancel Selected Invoices</field> |
1052 | - <field name="res_model">account.invoice.cancel</field> |
1053 | - <field name="view_type">form</field> |
1054 | - <field name="view_mode">form</field> |
1055 | - <field name="view_id" ref="account_invoice_cancel_view"/> |
1056 | - <field name="target">new</field> |
1057 | - </record> |
1058 | - |
1059 | </data> |
1060 | </openerp> |
1061 | |
1062 | === removed file 'bin/addons/account/wizard/account_state_open.py' |
1063 | --- bin/addons/account/wizard/account_state_open.py 2011-01-14 00:11:01 +0000 |
1064 | +++ bin/addons/account/wizard/account_state_open.py 1970-01-01 00:00:00 +0000 |
1065 | @@ -1,44 +0,0 @@ |
1066 | -# -*- coding: utf-8 -*- |
1067 | -############################################################################## |
1068 | -# |
1069 | -# OpenERP, Open Source Management Solution |
1070 | -# Copyright (C) 2004-2010 Tiny SPRL (<http://tiny.be>). |
1071 | -# |
1072 | -# This program is free software: you can redistribute it and/or modify |
1073 | -# it under the terms of the GNU Affero General Public License as |
1074 | -# published by the Free Software Foundation, either version 3 of the |
1075 | -# License, or (at your option) any later version. |
1076 | -# |
1077 | -# This program is distributed in the hope that it will be useful, |
1078 | -# but WITHOUT ANY WARRANTY; without even the implied warranty of |
1079 | -# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
1080 | -# GNU Affero General Public License for more details. |
1081 | -# |
1082 | -# You should have received a copy of the GNU Affero General Public License |
1083 | -# along with this program. If not, see <http://www.gnu.org/licenses/>. |
1084 | -# |
1085 | -############################################################################## |
1086 | -from osv import osv |
1087 | - |
1088 | -import netsvc |
1089 | -from tools.translate import _ |
1090 | - |
1091 | -class account_state_open(osv.osv_memory): |
1092 | - _name = 'account.state.open' |
1093 | - _description = 'Account State Open' |
1094 | - |
1095 | - def change_inv_state(self, cr, uid, ids, context=None): |
1096 | - obj_invoice = self.pool.get('account.invoice') |
1097 | - if context is None: |
1098 | - context = {} |
1099 | - if 'active_ids' in context: |
1100 | - data_inv = obj_invoice.browse(cr, uid, context['active_ids'][0], context=context) |
1101 | - if data_inv.reconciled: |
1102 | - raise osv.except_osv(_('Warning'), _('Invoice is already reconciled')) |
1103 | - wf_service = netsvc.LocalService("workflow") |
1104 | - res = wf_service.trg_validate(uid, 'account.invoice', context['active_ids'][0], 'open_test', cr) |
1105 | - return {'type': 'ir.actions.act_window_close'} |
1106 | - |
1107 | -account_state_open() |
1108 | - |
1109 | -# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
1110 | \ No newline at end of file |
1111 | |
1112 | === removed file 'bin/addons/account/wizard/account_state_open_view.xml' |
1113 | --- bin/addons/account/wizard/account_state_open_view.xml 2011-01-14 00:11:01 +0000 |
1114 | +++ bin/addons/account/wizard/account_state_open_view.xml 1970-01-01 00:00:00 +0000 |
1115 | @@ -1,35 +0,0 @@ |
1116 | -<?xml version="1.0" encoding="utf-8"?> |
1117 | -<openerp> |
1118 | - <data> |
1119 | - |
1120 | - <record id="view_account_state_open" model="ir.ui.view"> |
1121 | - <field name="name">Account State Open</field> |
1122 | - <field name="model">account.state.open</field> |
1123 | - <field name="type">form</field> |
1124 | - <field name="arch" type="xml"> |
1125 | - <form string="Open Invoice"> |
1126 | - <label string="Are you sure you want to open this invoice ?"/> |
1127 | - <newline/> |
1128 | - <label string="(Invoice should be unreconciled if you want to open it)"/> |
1129 | - <separator colspan="4"/> |
1130 | - <group colspan="2" col="4"> |
1131 | - <button special="cancel" string="No" icon="terp-gtk-stop"/> |
1132 | - <button name="change_inv_state" string="Yes" type="object" icon="terp-camera_test"/> |
1133 | - </group> |
1134 | - </form> |
1135 | - </field> |
1136 | - </record> |
1137 | - |
1138 | - <record id="action_account_state_open" model="ir.actions.act_window"> |
1139 | - <field name="name">Account State Open</field> |
1140 | - <field name="type">ir.actions.act_window</field> |
1141 | - <field name="res_model">account.state.open</field> |
1142 | - <field name="view_type">form</field> |
1143 | - <field name="view_mode">form</field> |
1144 | - <field name="view_id" ref="view_account_state_open"/> |
1145 | - <field name="context">{'record_id' : active_id}</field> |
1146 | - <field name="target">new</field> |
1147 | - </record> |
1148 | - |
1149 | - </data> |
1150 | -</openerp> |
1151 | |
1152 | === modified file 'bin/addons/account_override/__init__.py' |
1153 | --- bin/addons/account_override/__init__.py 2019-01-08 11:20:04 +0000 |
1154 | +++ bin/addons/account_override/__init__.py 2019-07-30 10:04:49 +0000 |
1155 | @@ -230,4 +230,5 @@ |
1156 | import report |
1157 | import wizard |
1158 | import finance_export |
1159 | +import account_invoice_sync |
1160 | # vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
1161 | |
1162 | === modified file 'bin/addons/account_override/account.py' |
1163 | --- bin/addons/account_override/account.py 2019-05-24 15:09:28 +0000 |
1164 | +++ bin/addons/account_override/account.py 2019-07-30 10:04:49 +0000 |
1165 | @@ -246,20 +246,28 @@ |
1166 | elif args == [('restricted_area', '=', 'intermission_header')]: |
1167 | if context_ivo or context.get('check_header_ivo'): |
1168 | # HEADER of Intermission Voucher OUT: |
1169 | - # restrict to 'is_intermission_counterpart', or Regular/Cash or Income, or Receivable/Receivables or Cash |
1170 | + # restrict to 'is_intermission_counterpart', or Regular/Cash or Income, or Receivable/Receivables or Cash, |
1171 | + # or Payable/Payables (for refund UC) |
1172 | # + prevent from using donation accounts |
1173 | - arg = [('type_for_register', 'not in', ['donation', 'advance', 'transfer', 'transfer_same']), |
1174 | - '|', '|', ('is_intermission_counterpart', '=', True), |
1175 | - '&', ('type', '=', 'other'), ('user_type_code', 'in', ['cash', 'income']), |
1176 | - '&', ('type', '=', 'receivable'), ('user_type_code', 'in', ['receivables', 'cash'])] |
1177 | + arg = [ |
1178 | + ('type_for_register', 'not in', ['donation', 'advance', 'transfer', 'transfer_same']), |
1179 | + '|', '|', '|', ('is_intermission_counterpart', '=', True), |
1180 | + '&', ('type', '=', 'other'), ('user_type_code', 'in', ['cash', 'income']), |
1181 | + '&', ('type', '=', 'receivable'), ('user_type_code', 'in', ['receivables', 'cash']), |
1182 | + '&', ('user_type_code', '=', 'payables'), ('type', '=', 'payable') |
1183 | + ] |
1184 | elif context_ivi or context.get('check_header_ivi'): |
1185 | # HEADER of Intermission Voucher IN: |
1186 | # restrict to 'is_intermission_counterpart' or Regular/Cash or Regular/Income or Payable/Payables |
1187 | + # or Receivable/Receivables or Cash (for refund UC) |
1188 | # + prevent from using donation accounts |
1189 | - arg = [('type_for_register', 'not in', ['donation', 'advance', 'transfer', 'transfer_same']), |
1190 | - '|', '|', ('is_intermission_counterpart', '=', True), |
1191 | - '&', ('type', '=', 'other'), ('user_type_code', 'in', ['cash', 'income']), |
1192 | - '&', ('user_type_code', '=', 'payables'), ('type', '=', 'payable')] |
1193 | + arg = [ |
1194 | + ('type_for_register', 'not in', ['donation', 'advance', 'transfer', 'transfer_same']), |
1195 | + '|', '|', '|', ('is_intermission_counterpart', '=', True), |
1196 | + '&', ('type', '=', 'other'), ('user_type_code', 'in', ['cash', 'income']), |
1197 | + '&', ('user_type_code', '=', 'payables'), ('type', '=', 'payable'), |
1198 | + '&', ('type', '=', 'receivable'), ('user_type_code', 'in', ['receivables', 'cash']), |
1199 | + ] |
1200 | return arg |
1201 | |
1202 | def _get_fake_cash_domain(self, cr, uid, ids, field_name, arg, context=None): |
1203 | |
1204 | === added file 'bin/addons/account_override/account_invoice_sync.py' |
1205 | --- bin/addons/account_override/account_invoice_sync.py 1970-01-01 00:00:00 +0000 |
1206 | +++ bin/addons/account_override/account_invoice_sync.py 2019-07-30 10:04:49 +0000 |
1207 | @@ -0,0 +1,346 @@ |
1208 | +#!/usr/bin/env python |
1209 | +#-*- encoding:utf-8 -*- |
1210 | +############################################################################## |
1211 | +# |
1212 | +# OpenERP, Open Source Management Solution |
1213 | +# Copyright (C) 2019 TeMPO Consulting, MSF. All Rights Reserved |
1214 | +# |
1215 | +# This program is free software: you can redistribute it and/or modify |
1216 | +# it under the terms of the GNU Affero General Public License as |
1217 | +# published by the Free Software Foundation, either version 3 of the |
1218 | +# License, or (at your option) any later version. |
1219 | +# |
1220 | +# This program is distributed in the hope that it will be useful, |
1221 | +# but WITHOUT ANY WARRANTY; without even the implied warranty of |
1222 | +# MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the |
1223 | +# GNU Affero General Public License for more details. |
1224 | +# |
1225 | +# You should have received a copy of the GNU Affero General Public License |
1226 | +# along with this program. If not, see <http://www.gnu.org/licenses/>. |
1227 | +# |
1228 | +############################################################################## |
1229 | + |
1230 | + |
1231 | +from osv import osv |
1232 | +from osv import fields |
1233 | +from tools.translate import _ |
1234 | +import logging |
1235 | +import time |
1236 | + |
1237 | + |
1238 | +class account_invoice_sync(osv.osv): |
1239 | + _inherit = 'account.invoice' |
1240 | + _logger = logging.getLogger('------sync.account.invoice') |
1241 | + |
1242 | + _columns = { |
1243 | + 'synced': fields.boolean("Synchronized"), |
1244 | + 'from_supply': fields.boolean('From Supply', help="Internal field indicating whether the document is related to a Supply workflow"), |
1245 | + 'counterpart_inv_number': fields.char('Counterpart Invoice Number', size=64, readonly=True), |
1246 | + 'counterpart_inv_status': fields.selection([ |
1247 | + ('draft', 'Draft'), |
1248 | + ('open', 'Open'), |
1249 | + ('paid', 'Paid'), |
1250 | + ('inv_close', 'Closed'), |
1251 | + ('cancel', 'Cancelled'), |
1252 | + ], string='Counterpart Invoice Status', readonly=True), |
1253 | + } |
1254 | + |
1255 | + _defaults = { |
1256 | + 'synced': lambda *a: False, |
1257 | + 'from_supply': lambda *a: False, |
1258 | + } |
1259 | + |
1260 | + def _create_analytic_distrib(self, cr, uid, vals, distrib, context=None): |
1261 | + """ |
1262 | + Updates vals with the new analytic_distribution_id created based on the distrib in parameter if it exists |
1263 | + """ |
1264 | + if context is None: |
1265 | + context = {} |
1266 | + analytic_distrib_obj = self.pool.get('analytic.distribution') |
1267 | + cc_distrib_line_obj = self.pool.get('cost.center.distribution.line') |
1268 | + fp_distrib_line_obj = self.pool.get('funding.pool.distribution.line') |
1269 | + data_obj = self.pool.get('ir.model.data') |
1270 | + # get the Funding Pool "PF" |
1271 | + try: |
1272 | + fp_id = data_obj.get_object_reference(cr, uid, 'analytic_distribution', 'analytic_account_msf_private_funds')[1] |
1273 | + except ValueError: |
1274 | + fp_id = 0 |
1275 | + if distrib: # original distrib from PO or PO line |
1276 | + # create the Analytic Distribution |
1277 | + distrib_id = analytic_distrib_obj.create(cr, uid, {}, context=context) |
1278 | + for cc_line in distrib.cost_center_lines: |
1279 | + distrib_vals = { |
1280 | + 'analytic_id': cc_line.analytic_id and cc_line.analytic_id.id, # analytic_id = Cost Center for the CC distrib line |
1281 | + 'percentage': cc_line.percentage or 0.0, |
1282 | + 'distribution_id': distrib_id, |
1283 | + 'currency_id': cc_line.currency_id.id, |
1284 | + 'destination_id': cc_line.destination_id.id, |
1285 | + } |
1286 | + cc_distrib_line_obj.create(cr, uid, distrib_vals, context=context) |
1287 | + distrib_vals.update({ |
1288 | + 'analytic_id': fp_id, # analytic_id = Funding Pool for the FP distrib line |
1289 | + 'cost_center_id': cc_line.analytic_id and cc_line.analytic_id.id, |
1290 | + }) |
1291 | + fp_distrib_line_obj.create(cr, uid, distrib_vals, context=context) |
1292 | + vals.update({'analytic_distribution_id': distrib_id,}) |
1293 | + |
1294 | + def _create_invoice_lines(self, cr, uid, inv_lines_data, inv_id, inv_posting_date, inv_linked_po, from_supply, context=None): |
1295 | + """ |
1296 | + Creates the lines of the automatic counterpart invoice (inv_id) generated at synchro time. |
1297 | + """ |
1298 | + if context is None: |
1299 | + context = {} |
1300 | + so_po_common_obj = self.pool.get('so.po.common') |
1301 | + product_obj = self.pool.get('product.product') |
1302 | + account_obj = self.pool.get('account.account') |
1303 | + product_uom_obj = self.pool.get('product.uom') |
1304 | + inv_line_obj = self.pool.get('account.invoice.line') |
1305 | + for inv_line in inv_lines_data: |
1306 | + line_name = inv_line.get('name', '') |
1307 | + if not line_name: # required field |
1308 | + raise osv.except_osv(_('Error'), _("Impossible to retrieve the line description.")) |
1309 | + product_id = False |
1310 | + product_data = inv_line.get('product_id', {}) |
1311 | + line_account_id = False |
1312 | + # for the lines related to a product: use the account of the product / else use the one of the source invoice line |
1313 | + if product_data: |
1314 | + default_code = product_data.get('default_code', '') |
1315 | + product_id = so_po_common_obj.get_product_id(cr, uid, product_data, default_code=default_code, context=context) or False |
1316 | + if not product_id: |
1317 | + raise osv.except_osv(_('Error'), _("Product %s not found.") % default_code) |
1318 | + product = product_obj.browse(cr, uid, product_id, fields_to_fetch=['active', 'default_code', 'product_tmpl_id', 'categ_id'], |
1319 | + context=context) |
1320 | + if not product.active: |
1321 | + raise osv.except_osv(_('Error'), _("The product %s is inactive.") % product.default_code or '') |
1322 | + line_account_id = product.product_tmpl_id.property_account_expense and product.product_tmpl_id.property_account_expense.id |
1323 | + if not line_account_id: |
1324 | + line_account_id = product.categ_id and product.categ_id.property_account_expense_categ and product.categ_id.property_account_expense_categ.id |
1325 | + else: |
1326 | + account_code = inv_line.get('account_id', {}).get('code', '') |
1327 | + if not account_code: |
1328 | + raise osv.except_osv(_('Error'), _("Impossible to retrieve the account code at line level.")) |
1329 | + account_ids = account_obj.search(cr, uid, [('code', '=', account_code)], limit=1, context=context) |
1330 | + if not account_ids: |
1331 | + raise osv.except_osv(_('Error'), _("Account code %s not found.") % account_code) |
1332 | + line_account_id = account_ids[0] |
1333 | + if not line_account_id: |
1334 | + raise osv.except_osv(_('Error'), _("Error when retrieving the account at line level.")) |
1335 | + line_account = account_obj.browse(cr, uid, line_account_id, |
1336 | + fields_to_fetch=['activation_date', 'inactivation_date'], context=context) |
1337 | + if inv_posting_date < line_account.activation_date or \ |
1338 | + (line_account.inactivation_date and inv_posting_date >= line_account.inactivation_date): |
1339 | + raise osv.except_osv(_('Error'), _('The account "%s - %s" is inactive.') % (line_account.code, line_account.name)) |
1340 | + uom_id = False |
1341 | + uom_data = inv_line.get('uos_id', {}) |
1342 | + if uom_data: |
1343 | + uom_name = uom_data.get('name', '') |
1344 | + uom_ids = product_uom_obj.search(cr, uid, [('name', '=', uom_name)], limit=1, context=context) |
1345 | + if not uom_ids: |
1346 | + raise osv.except_osv(_('Error'), _("Unit of Measure %s not found.") % uom_name) |
1347 | + uom_id = uom_ids[0] |
1348 | + quantity = inv_line.get('quantity', 0.0) |
1349 | + inv_line_vals = { |
1350 | + 'invoice_id': inv_id, |
1351 | + 'account_id': line_account_id, |
1352 | + 'name': line_name, |
1353 | + 'quantity': quantity, |
1354 | + 'price_unit': inv_line.get('price_unit', 0.0), |
1355 | + 'discount': inv_line.get('discount', 0.0), |
1356 | + 'product_id': product_id, |
1357 | + 'uos_id': uom_id, |
1358 | + } |
1359 | + if from_supply and inv_linked_po: |
1360 | + # fill in the AD at line level if applicable |
1361 | + # search the matching between PO line and invoice line based on description/product/quantity |
1362 | + matching_po_line = False |
1363 | + for po_line in inv_linked_po.order_line: |
1364 | + if po_line.name == line_name and po_line.product_id and po_line.product_id.id == product_id and \ |
1365 | + po_line.product_qty == quantity and po_line.state not in ('draft', 'cancel', 'cancel_r'): |
1366 | + matching_po_line = po_line |
1367 | + break |
1368 | + if matching_po_line: |
1369 | + po_line_distrib = matching_po_line.analytic_distribution_id |
1370 | + self._create_analytic_distrib(cr, uid, inv_line_vals, po_line_distrib, context=context) # update inv_line_vals |
1371 | + inv_line_obj.create(cr, uid, inv_line_vals, context=context) |
1372 | + |
1373 | + def create_invoice_from_sync(self, cr, uid, source, invoice_data, context=None): |
1374 | + """ |
1375 | + Creates automatic counterpart invoice at synchro time. |
1376 | + Intermission workflow: an IVO sent generates an IVI |
1377 | + Intersection workflow: an STV sent generates an SI |
1378 | + """ |
1379 | + self._logger.info("+++ Create an account.invoice in %s matching the one sent by %s" % (cr.dbname, source)) |
1380 | + if context is None: |
1381 | + context = {} |
1382 | + journal_obj = self.pool.get('account.journal') |
1383 | + currency_obj = self.pool.get('res.currency') |
1384 | + partner_obj = self.pool.get('res.partner') |
1385 | + user_obj = self.pool.get('res.users') |
1386 | + po_obj = self.pool.get('purchase.order') |
1387 | + stock_picking_obj = self.pool.get('stock.picking') |
1388 | + invoice_dict = invoice_data.to_dict() |
1389 | + # the counterpart instance must exist and be active |
1390 | + partner_ids = partner_obj.search(cr, uid, [('name', '=', source), ('active', '=', True)], limit=1, context=context) |
1391 | + if not partner_ids: |
1392 | + raise osv.except_osv(_('Error'), _("The partner %s doesn't exist or is inactive.") % source) |
1393 | + partner_id = partner_ids[0] |
1394 | + partner = partner_obj.browse(cr, uid, partner_id, fields_to_fetch=['property_account_payable', 'name'], context=context) |
1395 | + journal_type = invoice_dict.get('journal_id', {}).get('type', '') |
1396 | + if not journal_type or journal_type not in ('sale', 'intermission'): |
1397 | + raise osv.except_osv(_('Error'), _("Impossible to retrieve the journal type, or the journal type is incorrect.")) |
1398 | + currency_name = invoice_dict.get('currency_id', {}).get('name', '') |
1399 | + if not currency_name: |
1400 | + raise osv.except_osv(_('Error'), _("Impossible to retrieve the currency.")) |
1401 | + currency_ids = currency_obj.search(cr, uid, [('name', '=', currency_name), ('currency_table_id', '=', False), |
1402 | + ('active', '=', True)], limit=1, context=context) |
1403 | + if not currency_ids: |
1404 | + raise osv.except_osv(_('Error'), _("Currency %s not found or inactive.") % currency_name) |
1405 | + currency_id = currency_ids[0] |
1406 | + number = invoice_dict.get('number', '') |
1407 | + state = invoice_dict.get('state', '') # note that we get the real state as the doc can be beyond the "open" state at sync. time |
1408 | + doc_date = invoice_dict.get('document_date', time.strftime('%Y-%m-%d')) |
1409 | + posting_date = invoice_dict.get('date_invoice', time.strftime('%Y-%m-%d')) |
1410 | + description = invoice_dict.get('name', '') |
1411 | + source_doc = invoice_dict.get('origin', '') |
1412 | + from_supply = invoice_dict.get('from_supply', False) |
1413 | + inv_lines = invoice_dict.get('invoice_line', []) |
1414 | + po = False |
1415 | + vals = {} |
1416 | + # STV in sending instance: generates an SI in the receiving instance |
1417 | + if journal_type == 'sale': |
1418 | + pur_journal_ids = journal_obj.search(cr, uid, [('type', '=', 'purchase'), ('is_current_instance', '=', True)], limit=1, context=context) |
1419 | + if not pur_journal_ids: |
1420 | + raise osv.except_osv(_('Error'), _("No Purchase journal found for the current instance.")) |
1421 | + # for the SI use the Account Payable of the partner |
1422 | + si_account = partner.property_account_payable |
1423 | + if not si_account or posting_date < si_account.activation_date or \ |
1424 | + (si_account.inactivation_date and posting_date >= si_account.inactivation_date): |
1425 | + raise osv.except_osv(_('Error'), _("Account Payable not found or inactive for the partner %s.") % partner.name) |
1426 | + vals.update( |
1427 | + { |
1428 | + 'journal_id': pur_journal_ids[0], |
1429 | + 'account_id': si_account.id, |
1430 | + 'type': 'in_invoice', |
1431 | + 'is_direct_invoice': False, |
1432 | + 'is_inkind_donation': False, |
1433 | + 'is_debit_note': False, |
1434 | + 'is_intermission': False, |
1435 | + } |
1436 | + ) |
1437 | + # IVO in sending instance: generates an IVI in the receiving instance |
1438 | + elif journal_type == 'intermission': |
1439 | + int_journal_ids = journal_obj.search(cr, uid, [('type', '=', 'intermission'), ('is_current_instance', '=', True)], limit=1, context=context) |
1440 | + if not int_journal_ids: |
1441 | + raise osv.except_osv(_('Error'), _("No Intermission journal found for the current instance.")) |
1442 | + # for the IVI use the Intermission counterpart account from the Company form |
1443 | + ivi_account = user_obj.browse(cr, uid, uid, fields_to_fetch=['company_id'], context=context).company_id.intermission_default_counterpart |
1444 | + if not ivi_account or posting_date < ivi_account.activation_date or \ |
1445 | + (ivi_account.inactivation_date and posting_date >= ivi_account.inactivation_date): |
1446 | + raise osv.except_osv(_('Error'), _("The Intermission counterpart account is missing in the Company form or is inactive.")) |
1447 | + vals.update( |
1448 | + { |
1449 | + 'journal_id': int_journal_ids[0], |
1450 | + 'account_id': ivi_account.id, |
1451 | + 'type': 'in_invoice', |
1452 | + 'is_inkind_donation': False, |
1453 | + 'is_debit_note': False, |
1454 | + 'is_intermission': True, |
1455 | + } |
1456 | + ) |
1457 | + # common fields whatever the invoice type |
1458 | + if from_supply: |
1459 | + po_id = False |
1460 | + po_number = '' |
1461 | + fo_number = '' |
1462 | + ship_or_out_ref = '' |
1463 | + main_in = False |
1464 | + # extract PO number, and Shipment or Simple Out ref, from refs looking like: |
1465 | + # "se_HQ2C1.19/se_HQ2/HT101/PO00001 : SHIP/00002-01" or "se_HQ1C2.19/se_HQ1/HT201/PO00003 : OUT/00001" |
1466 | + inv_name_split = description.split() |
1467 | + if inv_name_split: |
1468 | + po_number = inv_name_split[0].split('.')[-1] |
1469 | + po_ids = po_obj.search(cr, uid, [('name', '=', po_number)], limit=1, context=context) |
1470 | + if po_ids: |
1471 | + po_id = po_ids[0] |
1472 | + ship_or_out_ref = inv_name_split[-1] |
1473 | + # extract FO number from source docs looking like: |
1474 | + # "SHIP/00001-04:19/se_HQ1/HT101/FO00007" or "OUT/00003:19/se_HQ1/HT101/FO00008" |
1475 | + inv_source_doc_split = source_doc.split(':') |
1476 | + if inv_source_doc_split: |
1477 | + fo_number = inv_source_doc_split[-1] |
1478 | + if po_id: |
1479 | + po = po_obj.browse(cr, uid, po_id, fields_to_fetch=['picking_ids', 'analytic_distribution_id', 'order_line'], context=context) |
1480 | + shipment_ref = "%s.%s" % (source or '', ship_or_out_ref or '') |
1481 | + # get the "main" IN |
1482 | + main_in_ids = stock_picking_obj.search(cr, uid, |
1483 | + [('id', 'in', [picking.id for picking in po.picking_ids]), |
1484 | + ('shipment_ref', '=', shipment_ref)], |
1485 | + limit=1, context=context) |
1486 | + if main_in_ids: |
1487 | + main_in = stock_picking_obj.browse(cr, uid, main_in_ids[0], fields_to_fetch=['name'], context=context) |
1488 | + # fill in the Analytic Distribution |
1489 | + # at header level if applicable |
1490 | + po_distrib = po.analytic_distribution_id |
1491 | + self._create_analytic_distrib(cr, uid, vals, po_distrib, context=context) # update vals |
1492 | + # note: in case a FO would have been manually created the PO and IN would be missing in the ref/source doc, |
1493 | + # but the same codification is used so it's visible that sthg is missing |
1494 | + description = "%s.%s : %s" % (source, fo_number, main_in and main_in.name or '') # e.g. se_HQ1C1.19/se_HQ1/HT101/FO00008 : IN/00009 |
1495 | + source_doc = "%s:%s" % (main_in and main_in.name or '', po_id and po_number or '') # e.g. IN/00009:19/se_HQ1/HT201/PO00009 |
1496 | + vals.update( |
1497 | + { |
1498 | + 'partner_id': partner_id, |
1499 | + 'currency_id': currency_id, |
1500 | + 'document_date': doc_date, |
1501 | + 'date_invoice': posting_date, |
1502 | + 'name': description, |
1503 | + 'origin': source_doc, |
1504 | + 'counterpart_inv_number': number, |
1505 | + 'counterpart_inv_status': state, |
1506 | + 'from_supply': from_supply, |
1507 | + 'synced': True, |
1508 | + } |
1509 | + ) |
1510 | + inv_id = self.create(cr, uid, vals, context=context) |
1511 | + if inv_id: |
1512 | + self._create_invoice_lines(cr, uid, inv_lines, inv_id, posting_date, po, from_supply, context=context) |
1513 | + if journal_type == 'sale': |
1514 | + self._logger.info("SI No. %s created successfully." % inv_id) |
1515 | + elif journal_type == 'intermission': |
1516 | + self._logger.info("IVI No. %s created successfully." % inv_id) |
1517 | + |
1518 | + def update_counterpart_inv(self, cr, uid, source, invoice_data, context=None): |
1519 | + """ |
1520 | + Updates the Counterpart Invoice Number and Status (to be triggered at synchro time) |
1521 | + """ |
1522 | + self._logger.info("+++ Update Counterpart Invoice data from %s" % source) |
1523 | + if context is None: |
1524 | + context = {} |
1525 | + invoice_dict = invoice_data.to_dict() |
1526 | + number = invoice_dict.get('number', '') |
1527 | + state = invoice_dict.get('state') |
1528 | + counterpart_inv_number = invoice_dict.get('counterpart_inv_number', '') |
1529 | + if state: |
1530 | + vals = { |
1531 | + 'counterpart_inv_status': state, |
1532 | + } |
1533 | + if number: |
1534 | + vals.update( |
1535 | + { |
1536 | + 'counterpart_inv_number': number, |
1537 | + } |
1538 | + ) |
1539 | + inv_ids = [] |
1540 | + if counterpart_inv_number: |
1541 | + inv_ids = self.search(cr, uid, [('number', '=', counterpart_inv_number)], limit=1, context=context) |
1542 | + elif not counterpart_inv_number and number: |
1543 | + # use case where the state of the IVO/STV is updated before the related IVI/SI has been opened |
1544 | + inv_ids = self.search(cr, uid, [('counterpart_inv_number', '=', number)], limit=1, context=context) |
1545 | + if inv_ids: |
1546 | + self.write(cr, uid, inv_ids[0], vals, context=context) |
1547 | + # note that the "Counterpart Inv. Number" received is the "Number" of the invoice updated! |
1548 | + self._logger.info("account.invoice %s: Counterpart Invoice %s set to %s" % (counterpart_inv_number, number, state)) |
1549 | + |
1550 | +account_invoice_sync() |
1551 | + |
1552 | + |
1553 | +# vim:expandtab:smartindent:tabstop=4:softtabstop=4:shiftwidth=4: |
1554 | |
1555 | === modified file 'bin/addons/account_override/account_invoice_view.xml' |
1556 | --- bin/addons/account_override/account_invoice_view.xml 2018-02-01 13:22:25 +0000 |
1557 | +++ bin/addons/account_override/account_invoice_view.xml 2019-07-30 10:04:49 +0000 |
1558 | @@ -43,17 +43,12 @@ |
1559 | <field name="line_number"/> |
1560 | </xpath> |
1561 | <xpath expr="//field[@name='date_invoice']" position="before"> |
1562 | - <field name="document_date"/> |
1563 | + <field name="document_date" /> |
1564 | </xpath> |
1565 | <xpath expr="//field[@name='period_id']" position="replace"> |
1566 | </xpath> |
1567 | <xpath expr="//label[@string='(keep empty to use the current period)']" position="replace"> |
1568 | </xpath> |
1569 | - <button name='invoice_cancel' position="replace"> |
1570 | - <!-- The widget boolean permit to the attrs to work efficiently --> |
1571 | - <field name="purchase_ids" invisible="1" widget="boolean" readonly="1" /> |
1572 | - <button name="invoice_cancel" string="Cancel" icon="gtk-cancel" attrs="{'invisible': ['|', ('state', 'in', ['open', 'paid']), ('purchase_ids', '!=', False)]}" confirm="You are about to cancel this invoice. Do you want to proceed?"/> |
1573 | - </button> |
1574 | <xpath expr="//button[@name='invoice_open']" position="after" > |
1575 | <button name="button_split_invoice" states="draft,proforma2" type="object" string="Split Invoice" icon="gtk-cut"/> |
1576 | <newline/> |
1577 | @@ -155,6 +150,12 @@ |
1578 | </xpath> |
1579 | <xpath expr="/search/group[1]/filter[@name='unpaid']" position="after"> |
1580 | <filter name="paid" icon="terp-dolar" string="Paid" domain="[('state', '=', 'paid')]"/> |
1581 | + <filter name="closed" icon="terp-dialog-close" string="Closed" domain="[('state', '=', 'inv_close')]" /> |
1582 | + <separator orientation="vertical"/> |
1583 | + <filter name="not_imported" icon="gtk-cancel" string="Not imported" domain="[('imported_state', '=', 'not')]"/> |
1584 | + <filter name="partial" icon="terp-dolar_ok!" string="Partially imported" domain="[('imported_state', '=', 'partial')]"/> |
1585 | + <filter name="imported" icon="gtk-apply" string="Imported" domain="[('imported_state', '=', 'imported')]"/> |
1586 | + <separator orientation="vertical"/> |
1587 | </xpath> |
1588 | </data> |
1589 | </field> |
1590 | @@ -278,11 +279,9 @@ |
1591 | <field name="residual"/> |
1592 | </group> |
1593 | <group col="8" colspan="4"> |
1594 | - <button name="invoice_cancel" states="draft,proforma2,sale,open" string="Cancel" icon="gtk-cancel"/> |
1595 | - <button name="%(account.action_account_invoice_refund)d" type='action' string='Refund' states='open,paid' icon="gtk-execute"/> |
1596 | - <button name='%(account.action_account_state_open)d' type='action' string='Re-Open' states='paid' icon="gtk-convert" groups="base.group_no_one"/> |
1597 | + <button name="%(account.action_account_invoice_refund)d" type='action' string='Refund' states='open,paid,inv_close' icon="gtk-execute"/> |
1598 | <button name="invoice_open" type="object" states="draft,proforma2" string="Validate" icon="gtk-go-forward"/> |
1599 | - <button name="%(account.account_invoices)d" string="Print Invoice" type="action" icon="gtk-print" states="open,paid,proforma,sale,proforma2"/> |
1600 | + <button name="%(account.account_invoices)d" string="Print Invoice" type="action" icon="gtk-print" states="open,paid,inv_close,proforma,sale,proforma2"/> |
1601 | </group> |
1602 | </page> |
1603 | <page string="Other Info"> |
1604 | @@ -429,13 +428,10 @@ |
1605 | <field name="state"/> |
1606 | <field name="amount_total"/> |
1607 | </group> |
1608 | - <group col="2" colspan="4" states="draft"> |
1609 | + <group col="4" colspan="4"> |
1610 | <label string=""/> |
1611 | <button name="invoice_open" type="object" states="draft" string="Validate" icon="gtk-go-forward"/> |
1612 | - </group> |
1613 | - <group col="2" colspan="4" states="open,paid"> |
1614 | - <button name="invoice_cancel" states="open" string="Cancel" icon="gtk-cancel" confirm="Do you confirm Donation received cancellation?"/> |
1615 | - <button name="%(account.account_invoices)d" string="Print Donation" type="action" icon="gtk-print" states="open,paid"/> |
1616 | + <button name="%(account.account_invoices)d" string="Print Donation" type="action" icon="gtk-print" states="open,paid,inv_close"/> |
1617 | </group> |
1618 | </page> |
1619 | </notebook> |
1620 | @@ -482,13 +478,30 @@ |
1621 | <field name="type" invisible="1"/> |
1622 | <field name="is_intermission" invisible="1"/> |
1623 | <!-- US-370: use the change currency button --> |
1624 | - <field name="currency_id" width="50"/> |
1625 | - <button name="%(account.action_account_change_currency)d" type="action" icon="terp-stock_effects-object-colorize" string="Change" attrs="{'invisible':[('state','!=','draft')]}" /> |
1626 | + <field name="currency_id" width="50" |
1627 | + attrs="{'readonly': ['|', '|', |
1628 | + ('state', '!=', 'draft'), |
1629 | + '&', ('type', '=', 'in_invoice'), ('synced', '=', True), |
1630 | + '&', ('type', '=', 'out_invoice'), ('from_supply', '=', True)]}"/> |
1631 | + <button name="%(account.action_account_change_currency)d" type="action" |
1632 | + icon="terp-stock_effects-object-colorize" string="Change" |
1633 | + attrs="{'invisible': [('state', '!=', 'draft')], |
1634 | + 'readonly': ['|', '|', |
1635 | + ('state', '!=', 'draft'), |
1636 | + '&', ('type', '=', 'in_invoice'), ('synced', '=', True), |
1637 | + '&', ('type', '=', 'out_invoice'), ('from_supply', '=', True)]}" /> |
1638 | <newline/> |
1639 | - <field string="Partner" name="partner_id" on_change="onchange_partner_id(type,partner_id,date_invoice,payment_term, partner_bank_id,company_id, False, is_intermission, False, False, account_id)" domain="[('by_invoice_type', '=', True), ('partner_type', '=', 'intermission')]" context="{'type': context.get('type')}"/> |
1640 | + <field string="Partner" name="partner_id" |
1641 | + on_change="onchange_partner_id(type,partner_id, date_invoice,payment_term, partner_bank_id, company_id, False, is_intermission, False, False, account_id)" |
1642 | + domain="[('by_invoice_type', '=', True), ('partner_type', '=', 'intermission')]" |
1643 | + context="{'type': context.get('type')}" |
1644 | + attrs="{'readonly': ['|', '|', |
1645 | + ('state', '!=', 'draft'), |
1646 | + '&', ('type', '=', 'in_invoice'), ('synced', '=', True), |
1647 | + '&', ('type', '=', 'out_invoice'), ('from_supply', '=', True)]}"/> |
1648 | <field domain="[('partner_id','=',partner_id)]" name="address_invoice_id" string="Partner address"/> |
1649 | <newline/> |
1650 | - <field name="document_date" string="I/MI voucher date"/> |
1651 | + <field name="document_date" string="I/MI voucher date" /> |
1652 | <field name="date_invoice"/> |
1653 | <newline/> |
1654 | <group colspan="8" col="8" attrs="{'invisible': [('analytic_distribution_id', '=', False)]}"> |
1655 | @@ -505,13 +518,20 @@ |
1656 | <notebook colspan="4"> |
1657 | <page string="Invoice"> |
1658 | <field name="account_id" domain="[('company_id', '=', company_id), ('restricted_area', '=', 'intermission_header')]"/> |
1659 | - <field name="name" string="Reference"/> |
1660 | + <field name="name" string="Reference" |
1661 | + attrs="{'readonly': ['|', ('state', '!=', 'draft'), ('from_supply', '=', True)]}"/> |
1662 | <newline/> |
1663 | <group name="import" string=" Import Lines " colspan="4" col="4" attrs="{'invisible':[('state', '!=', 'draft')]}"> |
1664 | - <button name="wizard_import_si_line" string="Import lines" icon="gtk-dnd" type="object" attrs="{'invisible':[('state', '!=', 'draft')]}"/> |
1665 | + <button name="wizard_import_si_line" string="Import lines" icon="gtk-dnd" type="object" |
1666 | + attrs="{'invisible': [('state', '!=', 'draft')], |
1667 | + 'readonly': ['|', |
1668 | + ('from_supply', '=', True), |
1669 | + '&', ('type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
1670 | </group> |
1671 | - <field colspan="4" name="invoice_line" nolabel="1" widget="one2many_list" context="{'is_intermission': True}"> |
1672 | - <tree string="Intermission Voucher Lines"> |
1673 | + <field colspan="4" name="invoice_line" nolabel="1" widget="one2many_list" context="{'is_intermission': True, 'from_inv_form': True}"> |
1674 | + <tree string="Intermission Voucher Lines" |
1675 | + colors="red:analytic_distribution_state == 'invalid' or inactive_product == True;black:inactive_product == False and analytic_distribution_state in ('none', 'valid')"> |
1676 | + <field name="line_number"/> |
1677 | <field name="is_corrected" invisible="1"/> |
1678 | <button name="button_open_analytic_lines" string="Have been corrected" type="object" icon="terp-mail-" attrs="{'invisible': [('is_corrected', '=', False)]}"/> |
1679 | <field name="name"/> |
1680 | @@ -523,7 +543,7 @@ |
1681 | <field name="analytic_distribution_state" invisible="1"/> |
1682 | <field name="have_analytic_distribution_from_header" invisible="1"/> |
1683 | <field name="quantity"/> |
1684 | - <field name="uos_id" string="UOM" invisible="1" /> |
1685 | + <field name="uos_id" string="UOM"/> |
1686 | <field name="price_unit"/> |
1687 | <field name="price_subtotal"/> |
1688 | <field name="inactive_product" invisible="1" /> |
1689 | @@ -532,12 +552,42 @@ |
1690 | <form string="Intermission Voucher Lines"> |
1691 | <notebook> |
1692 | <page string="Line"> |
1693 | - <field name="name" default_focus="1"/> |
1694 | + <field name="from_supply" invisible="1"/> |
1695 | + <field name="synced" invisible="1"/> |
1696 | + <field name="invoice_type" invisible="1"/> |
1697 | + <field name="product_id" |
1698 | + on_change="product_id_change(product_id, uos_id, quantity, name, parent.type, parent.partner_id, parent.fiscal_position, price_unit, parent.address_invoice_id, parent.currency_id, {'company_id': parent.company_id})" |
1699 | + default_focus="1" |
1700 | + attrs="{'readonly': ['|', |
1701 | + ('from_supply', '=', True), |
1702 | + '&', ('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}" /> |
1703 | + <field name="uos_id" |
1704 | + on_change="uos_id_change(product_id, uos_id, quantity, name, parent.type, parent.partner_id, parent.fiscal_position, price_unit, parent.address_invoice_id, parent.currency_id, {'company_id': parent.company_id})" |
1705 | + attrs="{'readonly': ['|', |
1706 | + ('from_supply', '=', True), |
1707 | + '&', ('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}" |
1708 | + /> |
1709 | + <field name="quantity" attrs="{'readonly': ['|', |
1710 | + ('from_supply', '=', True), |
1711 | + '&', ('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
1712 | + <field name="price_unit" attrs="{'readonly': [('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
1713 | + <field name="discount" groups="base.group_extended" attrs="{'readonly': [('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
1714 | + <field name="name" colspan="4"/> |
1715 | <field name="account_id" domain="[('restricted_area', '=', 'intermission_lines')]"/> |
1716 | - <field name="quantity"/> |
1717 | - <field name="uos_id" string="UOM" invisible="1"/> |
1718 | - <field name="price_unit"/> |
1719 | - <field name="price_subtotal"/> |
1720 | + <group colspan="6"> |
1721 | + <field name="analytic_distribution_state" invisible="1"/> |
1722 | + <field name="newline" invisible="1" /> |
1723 | + <field name="is_allocatable" invisible="1"/> |
1724 | + <group colspan="2" col="4"> |
1725 | + <button name="button_analytic_distribution" string="Change analytic distribution" |
1726 | + type="object" icon="terp-check" context="context" colspan="1" |
1727 | + attrs="{'invisible': ['|','|', ('newline', '=', True), ('analytic_distribution_state', '!=', 'valid'), ('is_allocatable', '=', False)]}" /> |
1728 | + <button name="button_analytic_distribution" string="Change analytic distribution" |
1729 | + type="object" icon="terp-emblem-important" context="context" colspan="1" |
1730 | + attrs="{'invisible': ['|','|', ('newline', '=', True), ('analytic_distribution_state', '=', 'valid'), ('is_allocatable', '=', False)]}" /> |
1731 | + <field name="analytic_distribution_state_recap" attrs="{'invisible': [('is_allocatable', '=', False)]}"/> |
1732 | + </group> |
1733 | + </group> |
1734 | </page> |
1735 | <page string="Notes"> |
1736 | <field name="note" nolabel="1" colspan="4"/> |
1737 | @@ -550,28 +600,64 @@ |
1738 | <field name="state"/> |
1739 | <field name="amount_total"/> |
1740 | </group> |
1741 | - <group col="2" colspan="4" states="draft"> |
1742 | + <group col="6" colspan="4" states="draft"> |
1743 | <label string=""/> |
1744 | - <button name="invoice_open" type="object" states="draft" string="Validate" icon="gtk-go-forward"/> |
1745 | + <!-- add a confirmation step only for IVOs when "synced" isn't selected --> |
1746 | + <button name="invoice_open" type="object" string="Validate" |
1747 | + icon="gtk-go-forward" |
1748 | + attrs="{'invisible': ['|', |
1749 | + ('state', '!=', 'draft'), |
1750 | + ('type', '=', 'out_invoice')]}"/> |
1751 | + <button name="invoice_open_with_confirmation" type="object" string="Validate" |
1752 | + icon="gtk-go-forward" |
1753 | + confirm="Are you sure you want to validate this invoice without synchronization?" |
1754 | + attrs="{'invisible': ['|', '|', |
1755 | + ('state', '!=', 'draft'), |
1756 | + ('type', '!=', 'out_invoice'), |
1757 | + ('synced', '=', True)]}"/> |
1758 | + <button name="invoice_open_with_sync_confirmation" type="object" string="Validate" |
1759 | + icon="gtk-go-forward" |
1760 | + confirm="This invoice will sync to its counterpart instance." |
1761 | + attrs="{'invisible': ['|', '|', |
1762 | + ('state', '!=', 'draft'), |
1763 | + ('type', '!=', 'out_invoice'), |
1764 | + ('synced', '=', False)]}"/> |
1765 | </group> |
1766 | - <group col="2" colspan="4" states="open,paid"> |
1767 | + <group col="6" colspan="4" states="open,paid,inv_close"> |
1768 | <label string=""/> |
1769 | - <button name="%(account.account_invoices)d" string="Print Intermission Voucher" type="action" icon="gtk-print" states="open,paid"/> |
1770 | + <button name="%(account.action_account_invoice_refund)d" type="action" string="Refund" icon="gtk-execute" |
1771 | + attrs="{'invisible': [('state', '!=', 'open')]}"/> |
1772 | + <button name="%(account.account_invoices)d" string="Print Intermission Voucher" type="action" icon="gtk-print" states="open,paid,inv_close"/> |
1773 | </group> |
1774 | </page> |
1775 | <page string="Other Info"> |
1776 | <field name="company_id" on_change="onchange_company_id(company_id,partner_id,type,invoice_line,currency_id)" widget="selection" groups="base.group_multi_company"/> |
1777 | <newline/> |
1778 | <field name="date_due"/> |
1779 | - <field name="user_id"/> |
1780 | + <field name="user_id" |
1781 | + attrs="{'readonly': ['|', '|', |
1782 | + ('state', '!=', 'draft'), |
1783 | + '&', ('type', '=', 'in_invoice'), ('synced', '=', True), |
1784 | + '&', ('type', '=', 'out_invoice'), ('from_supply', '=', True)]}"/> |
1785 | <newline/> |
1786 | <field domain="[('partner_id.ref_companies', 'in', [company_id])]" name="partner_bank_id" /> |
1787 | - <field name="origin"/> |
1788 | + <field name="origin" attrs="{'readonly': ['|', ('state', '!=', 'draft'), ('from_supply', '=', True)]}"/> |
1789 | <field colspan="4" domain="[('partner_id','=',partner_id)]" name="address_contact_id" /> |
1790 | <field name="move_id" /> |
1791 | <separator colspan="4" string="Additional Information"/> |
1792 | <field colspan="4" name="comment" nolabel="1"/> |
1793 | </page> |
1794 | + <page string="Counterpart Invoice"> |
1795 | + <field name="from_supply" invisible="1"/> |
1796 | + <field name="synced" |
1797 | + attrs="{'readonly': ['|', '|', |
1798 | + ('from_supply', '=', True), |
1799 | + ('state', '!=', 'draft'), |
1800 | + ('type', '=', 'in_invoice')]}"/> <!-- IVI can never be ticked as "Synced" manually --> |
1801 | + <newline/> |
1802 | + <field name="counterpart_inv_number"/> |
1803 | + <field name="counterpart_inv_status"/> |
1804 | + </page> |
1805 | </notebook> |
1806 | </form> |
1807 | </field> |
1808 | @@ -610,7 +696,11 @@ |
1809 | <button name="invoice_proforma2" position="replace"/> |
1810 | <xpath expr="/form/notebook/page[@string='Invoice']/field[@name='invoice_line']" position="before" > |
1811 | <group name="import" string=" Import Lines " colspan="4" col="4" attrs="{'invisible':[('state', '!=', 'draft')]}"> |
1812 | - <button name="wizard_import_si_line" string="Import lines" icon="gtk-dnd" type="object" attrs="{'invisible':[('state', '!=', 'draft')]}"/> |
1813 | + <button name="wizard_import_si_line" string="Import lines" icon="gtk-dnd" type="object" |
1814 | + attrs="{'invisible': [('state', '!=', 'draft')], |
1815 | + 'readonly': [('type', '=', 'out_invoice'), |
1816 | + ('from_supply', '=', True), |
1817 | + ('partner_type', 'in', ('intermission', 'section'))]}"/> |
1818 | </group> |
1819 | </xpath> |
1820 | <xpath expr="/form/notebook/page[@string='Invoice']/group[3]" position="replace"> |
1821 | @@ -623,12 +713,35 @@ |
1822 | <field name="residual"/> |
1823 | <field name="is_debit_note" invisible="1"/> |
1824 | </group> |
1825 | + <field name="partner_type" invisible="1"/> |
1826 | <group col="8" colspan="4"> |
1827 | - <button name="invoice_cancel" states="proforma2,open" string="Cancel" icon="gtk-cancel"/> |
1828 | <button name="%(account.action_account_invoice_refund)d" type='action' string='Refund' icon="gtk-execute" attrs="{'invisible': ['|', ('state', 'in', ['draft']), ('type', 'in', ['in_refund', 'out_refund'])]}"/> |
1829 | - <button name='%(account.action_account_state_open)d' type='action' string='Re-Open' states='paid' icon="gtk-convert" groups="base.group_no_one"/> |
1830 | - <button name="invoice_open" states="draft,proforma2" string="Validate" icon="gtk-go-forward" type="object"/> |
1831 | - <button name="%(account.account_invoices)d" string="Print Invoice" type="action" icon="gtk-print" states="open,paid,proforma,sale,proforma2"/> |
1832 | + <!-- add a confirmation step only for STV (not for Customer Refunds) |
1833 | + when the partner type is compatible with a synchro but "synced" isn't ticked --> |
1834 | + <button name="invoice_open" type="object" string="Validate" |
1835 | + icon="gtk-go-forward" |
1836 | + attrs="{'invisible': ['|', |
1837 | + ('state', '!=', 'draft'), |
1838 | + '&', |
1839 | + ('type', '=', 'out_invoice'), ('partner_type', 'in', ('intermission', 'section')) ]}"/> |
1840 | + <button name="invoice_open_with_confirmation" type="object" string="Validate" |
1841 | + icon="gtk-go-forward" |
1842 | + confirm="Are you sure you want to validate this invoice without synchronization?" |
1843 | + attrs="{'invisible': ['|', '|', '|', |
1844 | + ('state', '!=', 'draft'), |
1845 | + ('type', '!=', 'out_invoice'), |
1846 | + ('synced', '=', True), |
1847 | + ('partner_type', 'not in', ('intermission', 'section'))]}"/> |
1848 | + |
1849 | + <button name="invoice_open_with_sync_confirmation" type="object" string="Validate" |
1850 | + icon="gtk-go-forward" |
1851 | + confirm="This invoice will sync to its counterpart instance." |
1852 | + attrs="{'invisible': ['|', '|', '|', |
1853 | + ('state', '!=', 'draft'), |
1854 | + ('type', '!=', 'out_invoice'), |
1855 | + ('synced', '=', False), |
1856 | + ('partner_type', 'not in', ('intermission', 'section'))]}"/> |
1857 | + <button name="%(account.account_invoices)d" string="Print Invoice" type="action" icon="gtk-print" states="open,paid,inv_close,proforma,sale,proforma2"/> |
1858 | </group> |
1859 | </xpath> |
1860 | <xpath expr="//page[@string='Payments']" position="replace"> |
1861 | @@ -813,7 +926,7 @@ |
1862 | <field eval="False" name="view_id"/> |
1863 | <!-- US-2704 if the domain change, do not forget to update the domain of account_board_supplier_invoice_draft in finance/board_account_view.xml --> |
1864 | <field name="domain">[('type','=','in_invoice'), ('is_direct_invoice', '=', False), ('is_inkind_donation', '=', False), ('is_debit_note', "=", False), ('is_intermission', '=', False)]</field> |
1865 | - <field name="context">{'type':'in_invoice', 'journal_type': 'purchase'}</field> |
1866 | + <field name="context">{'type': 'in_invoice', 'journal_type': 'purchase', 'from_inv_form': True}</field> |
1867 | <field name="search_view_id" ref="account.view_account_invoice_filter"/> |
1868 | <field name="help">With Supplier Invoices you can enter and manage invoices issued by your suppliers. |
1869 | OpenERP can also generate draft invoices automatically from purchase orders or receipts. This way, you can control the invoice |
1870 | @@ -848,7 +961,7 @@ |
1871 | rml="account_override/report/account_print_invoice.rml" |
1872 | string="Print report" |
1873 | target_filename="${eval(_get_invoice_report_name)}" |
1874 | - attachment="(object.state in ('open','paid')) and ('INV'+(object.number or '').replace('/',''))" |
1875 | + attachment="(object.state in ('open','paid', 'inv_close')) and ('INV'+(object.number or '').replace('/',''))" |
1876 | attachment_use="1" |
1877 | multi="True"/> |
1878 | |
1879 | |
1880 | === modified file 'bin/addons/account_override/invoice.py' |
1881 | --- bin/addons/account_override/invoice.py 2019-05-21 08:19:49 +0000 |
1882 | +++ bin/addons/account_override/invoice.py 2019-07-30 10:04:49 +0000 |
1883 | @@ -28,12 +28,14 @@ |
1884 | from tools.translate import _ |
1885 | from lxml import etree |
1886 | from datetime import datetime |
1887 | +from msf_partner import PARTNER_TYPE |
1888 | import re |
1889 | import netsvc |
1890 | |
1891 | |
1892 | import decimal_precision as dp |
1893 | |
1894 | + |
1895 | class account_invoice(osv.osv): |
1896 | _name = 'account.invoice' |
1897 | _inherit = 'account.invoice' |
1898 | @@ -223,9 +225,9 @@ |
1899 | 'sequence_id': fields.many2one('ir.sequence', string='Lines Sequence', ondelete='cascade', |
1900 | help="This field contains the information related to the numbering of the lines of this order."), |
1901 | 'date_invoice': fields.date('Posting Date', states={'paid':[('readonly',True)], 'open':[('readonly',True)], |
1902 | - 'close':[('readonly',True)]}, select=True), |
1903 | + 'inv_close':[('readonly',True)]}, select=True), |
1904 | 'document_date': fields.date('Document Date', states={'paid':[('readonly',True)], 'open':[('readonly',True)], |
1905 | - 'close':[('readonly',True)]}, select=True), |
1906 | + 'inv_close':[('readonly',True)]}, select=True), |
1907 | 'is_debit_note': fields.boolean(string="Is a Debit Note?"), |
1908 | 'is_inkind_donation': fields.boolean(string="Is an In-kind Donation?"), |
1909 | 'is_intermission': fields.boolean(string="Is an Intermission Voucher?"), |
1910 | @@ -251,6 +253,8 @@ |
1911 | 'st_lines': fields.one2many('account.bank.statement.line', 'invoice_id', string="Register lines", readonly=True, help="Register lines that have a link to this invoice."), |
1912 | 'can_merge_lines': fields.function(_get_can_merge_lines, method=True, type='boolean', string='Can merge lines ?'), |
1913 | 'is_merged_by_account': fields.boolean("Is merged by account"), |
1914 | + 'partner_type': fields.related('partner_id', 'partner_type', string='Partner Type', type='selection', |
1915 | + selection=PARTNER_TYPE, readonly=True, store=False), |
1916 | } |
1917 | |
1918 | _defaults = { |
1919 | @@ -814,6 +818,35 @@ |
1920 | 'view_id': supplier_view_id} |
1921 | return super(account_invoice, self).log(cr, uid, inv_id, message, secondary, action_xmlid, local_ctx) |
1922 | |
1923 | + def _check_tax_allowed(self, cr, uid, ids, context=None): |
1924 | + """ |
1925 | + Raises an error if a tax is used with an Intermission or Intersection partner |
1926 | + """ |
1927 | + if context is None: |
1928 | + context = {} |
1929 | + if isinstance(ids, (int, long)): |
1930 | + ids = [ids] |
1931 | + warning_msg = _('Taxes are forbidden with Intermission and Intersection partners.') |
1932 | + for inv in self.browse(cr, uid, ids, fields_to_fetch=['partner_id', 'tax_line', 'invoice_line'], context=context): |
1933 | + if inv.partner_id.partner_type in ('intermission', 'section'): |
1934 | + if inv.tax_line: |
1935 | + raise osv.except_osv(_('Warning'), warning_msg) |
1936 | + for inv_line in inv.invoice_line: |
1937 | + if inv_line.invoice_line_tax_id: |
1938 | + raise osv.except_osv(_('Warning'), warning_msg) |
1939 | + |
1940 | + def _check_sync_allowed(self, cr, uid, ids, context=None): |
1941 | + """ |
1942 | + Raises an error if the doc is marked as Synced whereas the Partner is neither Intermission nor Intersection |
1943 | + """ |
1944 | + if context is None: |
1945 | + context = {} |
1946 | + if isinstance(ids, (int, long)): |
1947 | + ids = [ids] |
1948 | + for inv in self.browse(cr, uid, ids, fields_to_fetch=['partner_id', 'synced'], context=context): |
1949 | + if inv.partner_id.partner_type not in ('intermission', 'section') and inv.synced: |
1950 | + raise osv.except_osv(_('Warning'), _('Synchronized invoices are allowed only with Intermission and Intersection partners.')) |
1951 | + |
1952 | def invoice_open(self, cr, uid, ids, context=None): |
1953 | """ |
1954 | No longer fills the date automatically, but requires it to be set |
1955 | @@ -823,6 +856,8 @@ |
1956 | context = {} |
1957 | self._check_invoice_merged_lines(cr, uid, ids, context=context) |
1958 | self.check_accounts_for_partner(cr, uid, ids, context=context) |
1959 | + self._check_tax_allowed(cr, uid, ids, context=context) |
1960 | + self._check_sync_allowed(cr, uid, ids, context=context) |
1961 | |
1962 | # Prepare workflow object |
1963 | wf_service = netsvc.LocalService("workflow") |
1964 | @@ -871,6 +906,18 @@ |
1965 | |
1966 | return True |
1967 | |
1968 | + def invoice_open_with_confirmation(self, cr, uid, ids, context=None): |
1969 | + """ |
1970 | + Simply calls "invoice_open" (asking for confirmation is done at form level) |
1971 | + """ |
1972 | + return self.invoice_open(cr, uid, ids, context=context) |
1973 | + |
1974 | + def invoice_open_with_sync_confirmation(self, cr, uid, ids, context=None): |
1975 | + """ |
1976 | + Simply calls "invoice_open" (asking for confirmation is done at form level) |
1977 | + """ |
1978 | + return self.invoice_open(cr, uid, ids, context=context) |
1979 | + |
1980 | def action_reconcile_imported_invoice(self, cr, uid, ids, context=None): |
1981 | """ |
1982 | Reconcile each imported invoice with its attached invoice line |
1983 | @@ -1107,6 +1154,21 @@ |
1984 | self._check_header_account(cr, uid, inv_id, inv_type=inv_type, context=context) |
1985 | self._check_line_accounts(cr, uid, inv_id, inv_type=inv_type, context=context) |
1986 | |
1987 | + def update_counterpart_inv_status(self, cr, uid, ids, context=None): |
1988 | + """ |
1989 | + In case an IVO or STV, with an Intermission or Intersection partner and set as Synchronized, is being opened: |
1990 | + set the Counterpart Invoice Status to Draft automatically |
1991 | + """ |
1992 | + if context is None: |
1993 | + context = {} |
1994 | + if isinstance(ids, (int, long)): |
1995 | + ids = [ids] |
1996 | + inv_fields = ['type', 'is_debit_note', 'synced', 'partner_type', 'counterpart_inv_status'] |
1997 | + for inv in self.browse(cr, uid, ids, fields_to_fetch=inv_fields, context=context): |
1998 | + is_ivo_or_stv = inv.type == 'out_invoice' and not inv.is_debit_note |
1999 | + if is_ivo_or_stv and inv.synced and inv.partner_type in ('intermission', 'section') and not inv.counterpart_inv_status: |
2000 | + self.write(cr, uid, inv.id, {'counterpart_inv_status': 'draft'}, context=context) |
2001 | + |
2002 | def action_open_invoice(self, cr, uid, ids, context=None, *args): |
2003 | """ |
2004 | Give function to use when changing invoice to open state |
2005 | @@ -1124,6 +1186,7 @@ |
2006 | if not self.action_reconcile_imported_invoice(cr, uid, ids, context): |
2007 | return False |
2008 | self.check_domain_restrictions(cr, uid, ids, context) # raises an error if one unauthorized element is used |
2009 | + self.update_counterpart_inv_status(cr, uid, ids, context=context) |
2010 | return True |
2011 | |
2012 | |
2013 | @@ -1629,6 +1692,13 @@ |
2014 | relation="account.analytic.account", string='Funding Pool', |
2015 | states={'draft': [('readonly', False)]}, |
2016 | help="Field used for import only"), |
2017 | + 'from_supply': fields.related('invoice_id', 'from_supply', type='boolean', string='From Supply', readonly=True, store=False), |
2018 | + 'synced': fields.related('invoice_id', 'synced', type='boolean', string='Synchronized', readonly=True, store=False), |
2019 | + 'invoice_type': fields.related('invoice_id', 'type', string='Invoice Type', type='selection', readonly=True, store=False, |
2020 | + selection=[('out_invoice', 'Customer Invoice'), |
2021 | + ('in_invoice', 'Supplier Invoice'), |
2022 | + ('out_refund', 'Customer Refund'), |
2023 | + ('in_refund', 'Supplier Refund')]), |
2024 | } |
2025 | |
2026 | _defaults = { |
2027 | @@ -1661,6 +1731,26 @@ |
2028 | if abs(qty) >= too_big_amount or abs(pu) >= too_big_amount or abs(discount) >= too_big_amount or abs(subtotal) >= too_big_amount: |
2029 | raise osv.except_osv(_('Error'), _('Line "%s": one of the numbers entered is more than 10 digits.') % inv_line.name) |
2030 | |
2031 | + def _check_automated_invoice(self, cr, uid, invoice_id, context=None): |
2032 | + """ |
2033 | + Prevents the creation of manual inv. lines if the related invoice has been generated via Sync. or |
2034 | + by a Supply workflow (for Intermission/Intersection partners) |
2035 | + """ |
2036 | + if context is None: |
2037 | + context = {} |
2038 | + if self._name == 'wizard.account.invoice.line': |
2039 | + # no check on Direct Invoice |
2040 | + return True |
2041 | + inv_obj = self.pool.get('account.invoice') |
2042 | + if invoice_id: |
2043 | + inv_fields = ['from_supply', 'synced', 'type', 'is_inkind_donation', 'partner_type'] |
2044 | + inv = inv_obj.browse(cr, uid, invoice_id, fields_to_fetch=inv_fields, context=context) |
2045 | + ivi_or_si_synced = inv.type == 'in_invoice' and not inv.is_inkind_donation and inv.synced |
2046 | + intermission_or_section_from_supply = inv.partner_type in ('intermission', 'section') and inv.from_supply |
2047 | + if context.get('from_inv_form') and (ivi_or_si_synced or intermission_or_section_from_supply): |
2048 | + raise osv.except_osv(_('Error'), _('This document has been generated via a Supply workflow or via synchronization. ' |
2049 | + 'You can\'t add lines manually.')) |
2050 | + |
2051 | def create(self, cr, uid, vals, context=None): |
2052 | """ |
2053 | Give a line_number to invoice line. |
2054 | @@ -1671,6 +1761,7 @@ |
2055 | """ |
2056 | if not context: |
2057 | context = {} |
2058 | + self._check_automated_invoice(cr, uid, vals.get('invoice_id'), context=context) |
2059 | # Create new number with invoice sequence |
2060 | if vals.get('invoice_id') and self._name in ['account.invoice.line']: |
2061 | invoice = self.pool.get('account.invoice').browse(cr, uid, vals['invoice_id']) |
2062 | @@ -1766,9 +1857,10 @@ |
2063 | |
2064 | def unlink(self, cr, uid, ids, context=None): |
2065 | """ |
2066 | - If invoice is a Direct Invoice and is in draft state: |
2067 | - - compute total amount (check_total field) |
2068 | - - write total to the register line |
2069 | + - If invoice is a Direct Invoice and is in draft state: |
2070 | + - compute total amount (check_total field) |
2071 | + - write total to the register line |
2072 | + - Raise error msg if the related inv. has been generated via Sync. or by a Supply workflow (for Intermission/Intersection partners) |
2073 | """ |
2074 | if not context: |
2075 | context = {} |
2076 | @@ -1776,16 +1868,25 @@ |
2077 | ids = [ids] |
2078 | # Fetch all invoice_id to check |
2079 | direct_invoice_ids = [] |
2080 | + invoice_ids = [] |
2081 | abst_obj = self.pool.get('account.bank.statement.line') |
2082 | for invl in self.browse(cr, uid, ids): |
2083 | - if invl.invoice_id and invl.invoice_id.is_direct_invoice and invl.invoice_id.state == 'draft': |
2084 | - direct_invoice_ids.append(invl.invoice_id.id) |
2085 | - # find account_bank_statement_lines and used this to delete the account_moves and associated records |
2086 | - absl_ids = abst_obj.search(cr, uid, |
2087 | - [('invoice_id','=',invl.invoice_id.id)], |
2088 | - order='NO_ORDER') |
2089 | - if absl_ids: |
2090 | - abst_obj.unlink_moves(cr, uid, absl_ids, context) |
2091 | + if invl.invoice_id and invl.invoice_id.id not in invoice_ids: |
2092 | + invoice = invl.invoice_id |
2093 | + invoice_ids.append(invoice.id) # check each invoice only once |
2094 | + is_ivi_or_si = invoice.type == 'in_invoice' and not invoice.is_inkind_donation |
2095 | + if (is_ivi_or_si and invoice.synced) or (invoice.from_supply and invoice.partner_type in ('intermission', 'section')): |
2096 | + # will be displayed when trying to delete lines manually / merge lines / or split invoices |
2097 | + raise osv.except_osv(_('Error'), _("This document has been generated via a Supply workflow or via synchronization. " |
2098 | + "Existing lines can't be deleted.")) |
2099 | + if invoice.is_direct_invoice and invoice.state == 'draft': |
2100 | + direct_invoice_ids.append(invoice.id) |
2101 | + # find account_bank_statement_lines and use this to delete the account_moves and associated records |
2102 | + absl_ids = abst_obj.search(cr, uid, |
2103 | + [('invoice_id', '=', invoice.id)], |
2104 | + order='NO_ORDER') |
2105 | + if absl_ids: |
2106 | + abst_obj.unlink_moves(cr, uid, absl_ids, context) |
2107 | # Normal behaviour |
2108 | res = super(account_invoice_line, self).unlink(cr, uid, ids, context) |
2109 | # See all direct invoice |
2110 | |
2111 | === modified file 'bin/addons/account_override/report/report_open_invoices.py' |
2112 | --- bin/addons/account_override/report/report_open_invoices.py 2017-08-04 15:15:29 +0000 |
2113 | +++ bin/addons/account_override/report/report_open_invoices.py 2019-07-30 10:04:49 +0000 |
2114 | @@ -71,10 +71,10 @@ |
2115 | bg_id = context['background_id'] |
2116 | self.percent = 0.05 # 5% of the process |
2117 | bg_obj.update_percent(self.cr, self.uid, [bg_id], self.percent) |
2118 | - state = context.get('paid_invoice') and 'paid' or 'open' |
2119 | + states = context.get('paid_invoice') and ['paid', 'inv_close'] or ['open'] |
2120 | for type in ['si_di', 'sr', 'donation', 'ivi', 'stv', 'cr', 'dn', 'ivo']: |
2121 | # determine the domain to use according to the report type and the doc type |
2122 | - domain = [('state', '=', state)] |
2123 | + domain = [('state', 'in', states)] |
2124 | if context.get('paid_invoice') and beginning_date and ending_date: |
2125 | domain += [('date_invoice', '>=', beginning_date), ('date_invoice', '<=', ending_date)] |
2126 | if type == 'si_di': |
2127 | |
2128 | === modified file 'bin/addons/account_voucher/report/account_voucher_sales_receipt_view.xml' |
2129 | --- bin/addons/account_voucher/report/account_voucher_sales_receipt_view.xml 2011-01-14 00:11:01 +0000 |
2130 | +++ bin/addons/account_voucher/report/account_voucher_sales_receipt_view.xml 2019-07-30 10:04:49 +0000 |
2131 | @@ -7,7 +7,7 @@ |
2132 | <field name="model">sale.receipt.report</field> |
2133 | <field name="type">tree</field> |
2134 | <field name="arch" type="xml"> |
2135 | - <tree colors="blue:state in ('draft');gray:state in ('cancel','paid');black:state in ('proforma','proforma2')" string="Sales Receipt Analysis"> |
2136 | + <tree colors="blue:state in ('draft');gray:state in ('cancel','paid','inv_close');black:state in ('proforma','proforma2')" string="Sales Receipt Analysis"> |
2137 | <field name="date" invisible="1"/> |
2138 | <field name="user_id" invisible="1"/> |
2139 | <field name="year" invisible="1"/> |
2140 | @@ -112,4 +112,4 @@ |
2141 | <menuitem action="action_sale_receipt_report_all" id="menu_action_sale_receipt_report_all" parent="account.menu_finance_statistic_report_statement" sequence="3"/> |
2142 | |
2143 | </data> |
2144 | -</openerp> |
2145 | \ No newline at end of file |
2146 | +</openerp> |
2147 | |
2148 | === modified file 'bin/addons/analytic_distribution/account_invoice_refund.py' |
2149 | --- bin/addons/analytic_distribution/account_invoice_refund.py 2018-05-14 12:41:04 +0000 |
2150 | +++ bin/addons/analytic_distribution/account_invoice_refund.py 2019-07-30 10:04:49 +0000 |
2151 | @@ -43,8 +43,10 @@ |
2152 | # in case of a DI refund from a register line use the dir_invoice_id in context |
2153 | doc_to_refund_id = context.get('dir_invoice_id', False) or (context.get('active_ids') and context['active_ids'][0]) |
2154 | if doc_to_refund_id: |
2155 | - source_type = obj_inv.read(cr, uid, doc_to_refund_id, ['type'], context=context)['type'] |
2156 | - if source_type in ('in_invoice', 'in_refund'): |
2157 | + source = obj_inv.read(cr, uid, doc_to_refund_id, ['type', 'is_intermission'], context=context) |
2158 | + if source['is_intermission']: |
2159 | + args = [('type', '=', 'intermission')] |
2160 | + elif source['type'] in ('in_invoice', 'in_refund'): |
2161 | args = [('type', '=', 'purchase_refund')] |
2162 | if user.company_id.instance_id: |
2163 | args.append(('is_current_instance','=',True)) |
2164 | @@ -72,7 +74,7 @@ |
2165 | jtype = isinstance(context['journal_type'], list) and context['journal_type'][0] or context['journal_type'] |
2166 | if jtype in ('sale', 'sale_refund'): |
2167 | jtype = 'sale_refund' |
2168 | - else: |
2169 | + elif jtype != 'intermission': # for IVO/IVI keep using the Interm. journal |
2170 | jtype = 'purchase_refund' |
2171 | user = self.pool.get('res.users').browse(cr, uid, uid, context=context) |
2172 | for field in res['fields']: |
2173 | @@ -86,13 +88,32 @@ |
2174 | _columns = { |
2175 | 'date': fields.date('Posting date'), |
2176 | 'document_date': fields.date('Document Date', required=True), |
2177 | + 'is_intermission': fields.boolean("Wizard opened from an Intermission Voucher", readonly=True) |
2178 | } |
2179 | |
2180 | + def _get_refund(self, cr, uid, context=None): |
2181 | + """ |
2182 | + Returns the default value for the 'filter_refund' field depending on the context |
2183 | + """ |
2184 | + if context is None: |
2185 | + context = {} |
2186 | + if context.get('is_intermission', False): |
2187 | + return 'modify' |
2188 | + return 'refund' # note that only the "Refund" option is available in DI |
2189 | + |
2190 | + def _get_is_intermission(self, cr, uid, context=None): |
2191 | + """ |
2192 | + Returns True if the wizard has been opened from an Intermission Voucher |
2193 | + """ |
2194 | + if context is None: |
2195 | + context = {} |
2196 | + return context.get('is_intermission', False) |
2197 | + |
2198 | _defaults = { |
2199 | 'document_date': _get_document_date, |
2200 | - #UTP-961: refund DI: only refund option is available |
2201 | - 'filter_refund': 'refund', |
2202 | + 'filter_refund': _get_refund, |
2203 | 'journal_id': _get_journal, # US-193 |
2204 | + 'is_intermission': _get_is_intermission, |
2205 | } |
2206 | |
2207 | def _hook_fields_for_modify_refund(self, cr, uid, *args): |
2208 | |
2209 | === modified file 'bin/addons/analytic_distribution/account_invoice_view.xml' |
2210 | --- bin/addons/analytic_distribution/account_invoice_view.xml 2018-02-23 14:35:29 +0000 |
2211 | +++ bin/addons/analytic_distribution/account_invoice_view.xml 2019-07-30 10:04:49 +0000 |
2212 | @@ -120,10 +120,16 @@ |
2213 | <xpath expr="//separator[@string='Taxes']" position="replace" /> |
2214 | <xpath expr="//field[@name='invoice_line_tax_id']" position="replace"> |
2215 | <field name="vat_ok" invisible="1" /> |
2216 | + <field name="synced" invisible="1" /> |
2217 | <group colspan="4" col="4" attrs="{'invisible': [('vat_ok', '=', False)]}"> |
2218 | <separator colspan="4" string="Taxes"/> |
2219 | - <field colspan="4" name="invoice_line_tax_id" context="{'type':parent.type}" domain="[('parent_id','=',False),('company_id', '=', parent.company_id)]" |
2220 | - nolabel="1"/> |
2221 | + <field colspan="4" |
2222 | + name="invoice_line_tax_id" |
2223 | + context="{'type': parent.type}" |
2224 | + domain="[('parent_id', '=', False), ('company_id', '=', parent.company_id)]" |
2225 | + nolabel="1" |
2226 | + attrs="{'readonly': [('invoice_type', '=', 'in_invoice'), ('synced', '=', True)]}" |
2227 | + /> |
2228 | </group> |
2229 | </xpath> |
2230 | </data> |
2231 | |
2232 | === modified file 'bin/addons/analytic_distribution/wizard/analytic_distribution_wizard.py' |
2233 | --- bin/addons/analytic_distribution/wizard/analytic_distribution_wizard.py 2019-04-08 13:21:57 +0000 |
2234 | +++ bin/addons/analytic_distribution/wizard/analytic_distribution_wizard.py 2019-07-30 10:04:49 +0000 |
2235 | @@ -511,10 +511,10 @@ |
2236 | if el.purchase_line_id and el.purchase_line_id.state not in ['draft', 'validated_n', 'validated']: |
2237 | res[el.id] = False |
2238 | # verify invoice state |
2239 | - if el.invoice_id and el.invoice_id.state in ['open', 'paid']: |
2240 | + if el.invoice_id and el.invoice_id.state in ['open', 'paid', 'inv_close']: |
2241 | res[el.id] = False |
2242 | # verify invoice line state |
2243 | - if el.invoice_line_id and el.invoice_line_id.invoice_id and el.invoice_line_id.invoice_id.state in ['open', 'paid']: |
2244 | + if el.invoice_line_id and el.invoice_line_id.invoice_id and el.invoice_line_id.invoice_id.state in ['open', 'paid', 'inv_close']: |
2245 | res[el.id] = False |
2246 | # verify commitment state |
2247 | if el.commitment_id and el.commitment_id.state in ['done']: |
2248 | @@ -764,10 +764,10 @@ |
2249 | if wiz.purchase_line_id and wiz.purchase_line_id.state not in ['draft', 'validated_n', 'validated']: |
2250 | raise osv.except_osv(_('Error'), _('You cannot change the distribution.')) |
2251 | # Verify that invoice is in good state if necessary |
2252 | - if wiz.invoice_id and wiz.invoice_id.state in ['open', 'paid']: |
2253 | + if wiz.invoice_id and wiz.invoice_id.state in ['open', 'paid', 'inv_close']: |
2254 | raise osv.except_osv(_('Error'), _('You cannot change the distribution.')) |
2255 | # Verify that invoice from invoice line is in good state if necessary |
2256 | - if wiz.invoice_line_id and wiz.invoice_line_id.invoice_id and wiz.invoice_line_id.invoice_id.state in ['open', 'paid']: |
2257 | + if wiz.invoice_line_id and wiz.invoice_line_id.invoice_id and wiz.invoice_line_id.invoice_id.state in ['open', 'paid', 'inv_close']: |
2258 | raise osv.except_osv(_('Error'), _('You cannot change the distribution.')) |
2259 | # Verify that commitment is in good state if necessary |
2260 | if wiz.commitment_id and wiz.commitment_id.state in ['done']: |
2261 | |
2262 | === modified file 'bin/addons/finance/__openerp__.py' |
2263 | --- bin/addons/finance/__openerp__.py 2017-11-07 09:20:43 +0000 |
2264 | +++ bin/addons/finance/__openerp__.py 2019-07-30 10:04:49 +0000 |
2265 | @@ -35,7 +35,6 @@ |
2266 | "demo_xml" : [], |
2267 | "update_xml" : [ |
2268 | 'board_account_view.xml', |
2269 | - 'account_invoice_workflow.xml', |
2270 | 'account_view.xml', |
2271 | 'account_invoice_view.xml', |
2272 | 'account_analytic_line_view.xml', |
2273 | |
2274 | === removed file 'bin/addons/finance/account_invoice_workflow.xml' |
2275 | --- bin/addons/finance/account_invoice_workflow.xml 2014-03-14 15:47:48 +0000 |
2276 | +++ bin/addons/finance/account_invoice_workflow.xml 1970-01-01 00:00:00 +0000 |
2277 | @@ -1,13 +0,0 @@ |
2278 | -<?xml version="1.0" encoding="utf-8"?> |
2279 | -<openerp> |
2280 | - <data> |
2281 | - |
2282 | - <!-- Invoice workflow --> |
2283 | - <record id="account.act_open" model="workflow.activity"> |
2284 | - <field name="wkf_id" ref="account.wkf"/> |
2285 | - <field name="action">action_open_invoice() |
2286 | - write({'state':'open'})</field> |
2287 | - </record> |
2288 | - |
2289 | - </data> |
2290 | -</openerp> |
2291 | |
2292 | === modified file 'bin/addons/msf_audittrail/audittrail_invoice_data.yml' |
2293 | --- bin/addons/msf_audittrail/audittrail_invoice_data.yml 2019-05-13 09:18:37 +0000 |
2294 | +++ bin/addons/msf_audittrail/audittrail_invoice_data.yml 2019-07-30 10:04:49 +0000 |
2295 | @@ -9,7 +9,8 @@ |
2296 | # Create the rule |
2297 | fields = ['date_invoice', 'state', 'account_id', 'address_invoice_id', 'amount_to_pay', 'analytic_distribution_id', |
2298 | 'check_total', 'comment', 'currency_id', 'fiscal_position', 'name', 'origin', 'partner_id', |
2299 | - 'payment_ids', 'period_id', 'reference', 'reference_type', 'tax_line'] |
2300 | + 'payment_ids', 'period_id', 'reference', 'reference_type', 'tax_line', 'synced', 'counterpart_inv_number', |
2301 | + 'counterpart_inv_status'] |
2302 | |
2303 | fields_ids = self.pool.get('ir.model.fields').search(cr, uid, [('model', '=' ,'account.invoice'), ('name', 'in', fields)], context=context) |
2304 | |
2305 | |
2306 | === modified file 'bin/addons/msf_outgoing/msf_outgoing.py' |
2307 | --- bin/addons/msf_outgoing/msf_outgoing.py 2019-07-25 13:39:42 +0000 |
2308 | +++ bin/addons/msf_outgoing/msf_outgoing.py 2019-07-30 10:04:49 +0000 |
2309 | @@ -369,7 +369,8 @@ |
2310 | 'backshipment_id': fields.function(_vals_get, method=True, type='many2one', relation='shipment', string='Draft Shipment', multi='get_vals',), |
2311 | # added by Quentin https://bazaar.launchpad.net/~unifield-team/unifield-wm/trunk/revision/426.20.14 |
2312 | 'parent_id': fields.many2one('shipment', string='Parent shipment'), |
2313 | - 'invoice_id': fields.many2one('account.invoice', string='Related invoice'), |
2314 | + # TODO check if really deprecated ? |
2315 | + 'invoice_id': fields.many2one('account.invoice', string='Related invoice (deprecated)'), |
2316 | 'additional_items_ids': fields.one2many('shipment.additionalitems', 'shipment_id', string='Additional Items'), |
2317 | 'picking_ids': fields.one2many( |
2318 | 'stock.picking', |
2319 | @@ -1579,6 +1580,7 @@ |
2320 | 'fiscal_position': partner.property_account_position.id, |
2321 | 'date_invoice': context.get('date_inv', False) or today, |
2322 | 'user_id': uid, |
2323 | + 'from_supply': True, |
2324 | } |
2325 | |
2326 | cur_id = shipment.pack_family_memory_ids[0].currency_id.id |
2327 | @@ -1613,32 +1615,7 @@ |
2328 | if is_stv and partner.partner_type == 'internal': |
2329 | continue |
2330 | |
2331 | - if is_ivo or is_stv: |
2332 | - origin_inv = 'origin' in invoice_vals and invoice_vals['origin'] or False |
2333 | - fo = move and move.sale_line_id and move.sale_line_id.order_id or False |
2334 | - new_origin = origin_inv and fo and "%s:%s" % (origin_inv, fo.name) |
2335 | - new_origin = new_origin and new_origin[:64] # keep only 64 characters (because of the JE ref size) |
2336 | - if new_origin: |
2337 | - invoice_vals.update({'origin': new_origin}) |
2338 | - name_inv = 'name' in invoice_vals and invoice_vals['name'] or False |
2339 | - new_name_inv = name_inv and fo and fo.client_order_ref and "%s : %s" % (fo.client_order_ref, name_inv) |
2340 | - if new_name_inv: |
2341 | - invoice_vals.update({'name': new_name_inv}) |
2342 | - |
2343 | - invoice_id = invoice_obj.create(cr, uid, invoice_vals, |
2344 | - context=context) |
2345 | - |
2346 | - # Change currency for the intermission invoice |
2347 | - if shipment.partner_id2.partner_type == 'intermission': |
2348 | - company_currency = company.currency_id and company.currency_id.id or False |
2349 | - if not company_currency: |
2350 | - raise osv.except_osv(_('Warning'), _('No company currency found!')) |
2351 | - wiz_account_change = self.pool.get('account.change.currency').create(cr, uid, {'currency_id': company_currency}, context=context) |
2352 | - self.pool.get('account.change.currency').change_currency(cr, uid, [wiz_account_change], context={'active_id': invoice_id}) |
2353 | - |
2354 | - # Link the invoice to the shipment |
2355 | - self.write(cr, uid, [shipment.id], {'invoice_id': invoice_id}, context=context) |
2356 | - |
2357 | + invoice_id_by_fo = {} |
2358 | # For each stock moves, create an invoice line |
2359 | for pack in shipment.pack_family_memory_ids: |
2360 | for move in pack.move_lines: |
2361 | @@ -1648,6 +1625,41 @@ |
2362 | if move.sale_line_id and move.sale_line_id.order_id.order_policy != 'picking': |
2363 | continue |
2364 | |
2365 | + # create 1 FO = 1 Invoice |
2366 | + order_id = move.sale_line_id and move.sale_line_id.order_id or False |
2367 | + if order_id not in invoice_id_by_fo: |
2368 | + new_invoice_vals = invoice_vals.copy() |
2369 | + if is_ivo or is_stv: |
2370 | + new_invoice_vals.update({'synced': True, }) # add "synced" tag for STV and IVO created from Supply flow |
2371 | + origin_inv = 'origin' in new_invoice_vals and new_invoice_vals['origin'] or False |
2372 | + fo = move and move.sale_line_id and move.sale_line_id.order_id or False |
2373 | + new_origin = origin_inv and fo and "%s:%s" % (origin_inv, fo.name) |
2374 | + new_origin = new_origin and new_origin[:64] # keep only 64 characters (because of the JE ref size) |
2375 | + if new_origin: |
2376 | + new_invoice_vals.update({'origin': new_origin}) |
2377 | + name_inv = 'name' in new_invoice_vals and new_invoice_vals['name'] or False |
2378 | + new_name_inv = name_inv and fo and fo.client_order_ref and "%s : %s" % (fo.client_order_ref, name_inv) |
2379 | + if new_name_inv: |
2380 | + new_invoice_vals.update({'name': new_name_inv}) |
2381 | + # this one does not work (check with new pps process US-5859) |
2382 | + #new_invoice_vals['picking_id'] = pack.draft_packing_id and pack.draft_packing_id.id or False |
2383 | + |
2384 | + invoice_id = invoice_obj.create(cr, uid, new_invoice_vals, |
2385 | + context=context) |
2386 | + |
2387 | + # Change currency for the intermission invoice |
2388 | + if shipment.partner_id2.partner_type == 'intermission': |
2389 | + company_currency = company.currency_id and company.currency_id.id or False |
2390 | + if not company_currency: |
2391 | + raise osv.except_osv(_('Warning'), _('No company currency found!')) |
2392 | + wiz_account_change = self.pool.get('account.change.currency').create(cr, uid, {'currency_id': company_currency}, context=context) |
2393 | + self.pool.get('account.change.currency').change_currency(cr, uid, [wiz_account_change], context={'active_id': invoice_id}) |
2394 | + |
2395 | + invoice_id_by_fo[order_id] = invoice_id |
2396 | + |
2397 | + invoice_id = invoice_id_by_fo[order_id] |
2398 | + |
2399 | + |
2400 | origin = move.picking_id.name or '' |
2401 | if move.picking_id.origin: |
2402 | origin += ':' + move.picking_id.origin |
2403 | @@ -1714,7 +1726,6 @@ |
2404 | 'analytic_distribution_id': distrib_id, |
2405 | }, context=context) |
2406 | |
2407 | - self.pool.get('shipment').write(cr, uid, [shipment.id], {'invoice_id': invoice_id}, context=context) |
2408 | if move.sale_line_id: |
2409 | sale_obj.write(cr, uid, [move.sale_line_id.order_id.id], {'invoice_ids': [(4, invoice_id)], }) |
2410 | sale_line_obj.write(cr, uid, [move.sale_line_id.id], {'invoiced': True, |
2411 | |
2412 | === modified file 'bin/addons/msf_profile/data/patches.xml' |
2413 | --- bin/addons/msf_profile/data/patches.xml 2019-07-24 09:13:25 +0000 |
2414 | +++ bin/addons/msf_profile/data/patches.xml 2019-07-30 10:04:49 +0000 |
2415 | @@ -429,6 +429,7 @@ |
2416 | <field name="method">us_6111_nr_field_closed_mar_2018</field> |
2417 | </record> |
2418 | |
2419 | +<<<<<<< TREE |
2420 | <!-- UF14.0 --> |
2421 | <record id="us_5952_delivered_closed_outs_to_delivered_state" model="patch.scripts"> |
2422 | <field name="method">us_5952_delivered_closed_outs_to_delivered_state</field> |
2423 | @@ -439,5 +440,16 @@ |
2424 | </record> |
2425 | |
2426 | |
2427 | +======= |
2428 | + <!-- UF14.0 --> |
2429 | + <record id="us_6075_set_paid_invoices_as_closed" model="patch.scripts"> |
2430 | + <field name="method">us_6075_set_paid_invoices_as_closed</field> |
2431 | + </record> |
2432 | + |
2433 | + <record id="us_6076_set_inv_as_from_supply" model="patch.scripts"> |
2434 | + <field name="method">us_6076_set_inv_as_from_supply</field> |
2435 | + </record> |
2436 | + |
2437 | +>>>>>>> MERGE-SOURCE |
2438 | </data> |
2439 | </openerp> |
2440 | |
2441 | === modified file 'bin/addons/msf_profile/i18n/fr_MF.po' |
2442 | --- bin/addons/msf_profile/i18n/fr_MF.po 2019-07-26 15:23:04 +0000 |
2443 | +++ bin/addons/msf_profile/i18n/fr_MF.po 2019-07-30 10:04:49 +0000 |
2444 | @@ -4239,12 +4239,6 @@ |
2445 | msgid "Account tax charts" |
2446 | msgstr "Compte - Plans de taxes" |
2447 | |
2448 | -#. module: account |
2449 | -#: model:ir.actions.act_window,name:account.action_account_state_open |
2450 | -#: model:ir.model,name:account.model_account_state_open |
2451 | -msgid "Account State Open" |
2452 | -msgstr "Compte - Statut Ouvert" |
2453 | - |
2454 | #. module: base |
2455 | #: selection:res.config.users,context_tz:0 |
2456 | #: selection:res.users,context_tz:0 |
2457 | @@ -7017,11 +7011,6 @@ |
2458 | "Vous pouvez en créer un à partir du menu :\n" |
2459 | "Configuration/Comptabilité Financière/Comptes/Journaux." |
2460 | |
2461 | -#. module: account |
2462 | -#: view:account.state.open:0 |
2463 | -msgid "Are you sure you want to open this invoice ?" |
2464 | -msgstr "Etes-vous sûr de vouloir ouvrir cette facture ?" |
2465 | - |
2466 | #. modules: stock_move_tracking, stock, stock_override |
2467 | #: selection:report.stock.move,type:0 |
2468 | #: selection:stock.location,chained_picking_type:0 |
2469 | @@ -8768,6 +8757,8 @@ |
2470 | #: selection:wizard.import.product.line,state:0 |
2471 | #: selection:product.mass.update,state:0 |
2472 | #: selection:stock.expired.damaged.report,state:0 |
2473 | +#: selection:account.invoice,counterpart_inv_status:0 |
2474 | +#: selection:wizard.account.invoice,counterpart_inv_status:0 |
2475 | #, python-format |
2476 | msgid "Draft" |
2477 | msgstr "Brouillon" |
2478 | @@ -10378,6 +10369,7 @@ |
2479 | #: selection:sale.donation.stock.moves,partner_type:0 |
2480 | #: selection:sale.loan.stock.moves,partner_type:0 |
2481 | #: selection:stock.picking,partner_type:0 |
2482 | +<<<<<<< TREE |
2483 | #: selection:sale.order,partner_type:0 |
2484 | #: view:res.partner:0 |
2485 | #: selection:res.partner,partner_type:0 |
2486 | @@ -10386,6 +10378,10 @@ |
2487 | #: selection:purchase.order.change.currency,partner_type:0 |
2488 | #: selection:sale.order.change.currency,partner_type:0 |
2489 | #: selection:stock.picking,partner_type_stock_picking:0 |
2490 | +======= |
2491 | +#: selection:account.invoice,partner_type:0 |
2492 | +#: selection:account.invoice.line,partner_type:0 |
2493 | +>>>>>>> MERGE-SOURCE |
2494 | #: code:addons/msf_supply_doc_export/wizard/supplier_performance_wizard.py:32 |
2495 | #: field:supplier.performance.wizard,partner_type_intermission:0 |
2496 | msgid "Intermission" |
2497 | @@ -11219,7 +11215,7 @@ |
2498 | |
2499 | #. module: account |
2500 | #: help:account.invoice.refund,filter_refund:0 |
2501 | -msgid "Refund invoice base on this type. You can not Modify and Cancel if the invoice is already reconciled" |
2502 | +msgid "Refund invoice based on this type. You can not Modify and Cancel if the invoice is already reconciled" |
2503 | msgstr "Facture d'Avoirs basée sur ce type. Vous ne pouvez pas Modifier ni Annuler si la facture est déjà lettrée." |
2504 | |
2505 | #. module: base |
2506 | @@ -12182,7 +12178,7 @@ |
2507 | msgid "No envoi.ini file found in given ZIP file!" |
2508 | msgstr "Pas de fichier envoi.ini trouvé dans le fichier ZP donné!" |
2509 | |
2510 | -#. modules: msf_processes, account, register_accounting |
2511 | +#. modules: msf_processes, account, register_accounting, account_override |
2512 | #: view:account.invoice:0 |
2513 | #: selection:account.invoice,type:0 |
2514 | #: selection:account.invoice.report,type:0 |
2515 | @@ -12196,6 +12192,7 @@ |
2516 | #: code:addons/register_accounting/account_bank_statement.py:2735 |
2517 | #: view:wizard.account.invoice:0 |
2518 | #: selection:wizard.account.invoice,type:0 |
2519 | +#: selection:account.invoice.line,invoice_type:0 |
2520 | #, python-format |
2521 | msgid "Supplier Invoice" |
2522 | msgstr "Facture Fournisseur" |
2523 | @@ -13288,7 +13285,7 @@ |
2524 | msgid "Automatic entry" |
2525 | msgstr "Ecriture Automatique" |
2526 | |
2527 | -#. modules: msf_order_date, purchase, msf_partner, stock_override, purchase_override, msf_config_locations, sale, account_override, analytic_distribution, msf_outgoing, msf_supply_doc_export |
2528 | +#. modules: msf_order_date, purchase, msf_partner, stock_override, purchase_override, msf_config_locations, sale, account_override, analytic_distribution, msf_outgoing, msf_supply_doc_export, account |
2529 | #: selection:shipment,partner_type:0 |
2530 | #: selection:purchase.order.merged.line,po_partner_type_stored:0 |
2531 | #: selection:sale.loan.stock.moves,partner_type:0 |
2532 | @@ -13306,6 +13303,8 @@ |
2533 | #: selection:sale.donation.stock.moves,partner_type:0 |
2534 | #: selection:sale.order.change.currency,partner_type:0 |
2535 | #: selection:stock.picking,partner_type_stock_picking:0 |
2536 | +#: selection:account.invoice,partner_type:0 |
2537 | +#: selection:account.invoice.line,partner_type:0 |
2538 | #: code:addons/msf_supply_doc_export/wizard/supplier_performance_wizard.py:30 |
2539 | #: field:supplier.performance.wizard,partner_type_external:0 |
2540 | msgid "External" |
2541 | @@ -14897,8 +14896,9 @@ |
2542 | msgid "BARBADOS DOLLAR" |
2543 | msgstr "BARBADOS DOLLAR" |
2544 | |
2545 | -#. modules: account, register_accounting |
2546 | +#. modules: account, register_accounting, account_override |
2547 | #: selection:account.invoice,type:0 |
2548 | +#: selection:account.invoice.line,invoice_type:0 |
2549 | #: selection:account.invoice.report,type:0 |
2550 | #: report:account.invoice2:0 |
2551 | #: selection:report.invoice.created,type:0 |
2552 | @@ -15362,11 +15362,6 @@ |
2553 | msgid "Destination not compatible with account" |
2554 | msgstr "Destination not compatible with account" |
2555 | |
2556 | -#. module: account |
2557 | -#: model:ir.model,name:account.model_account_invoice_cancel |
2558 | -msgid "Cancel the Selected Invoices" |
2559 | -msgstr "Annuler les Factures Sélectionnées" |
2560 | - |
2561 | #. modules: account, register_accounting |
2562 | #: view:account.bank.statement:0 |
2563 | #: view:account.bank.statement:0 |
2564 | @@ -16841,8 +16836,12 @@ |
2565 | msgid "%s update%s" |
2566 | msgstr "%s update%s" |
2567 | |
2568 | +<<<<<<< TREE |
2569 | #. modules: msf_budget, sales_followup, account, product_attributes, register_accounting, unifield_setup, object_query, order_types, mission_stock, msf_accrual, procurement_report, msf_partner, res_currency_tables, salr, sourcing, tender_flow, msf_doc_import, finance, msf_order_date, stock, product, stock_override |
2570 | #: view:account.state.open:0 |
2571 | +======= |
2572 | +#. modules: msf_budget, sales_followup, account, product_attributes, register_accounting, unifield_setup, object_query, order_types, mission_stock, msf_accrual, procurement_report, msf_partner, res_currency_tables, salr, sourcing, tender_flow, msf_doc_import, finance, stock, product, stock_override |
2573 | +>>>>>>> MERGE-SOURCE |
2574 | #: selection:mission.stock.wizard,split_stock:0 |
2575 | #: selection:mission.stock.wizard,with_valuation:0 |
2576 | #: view:wizard.accrual.reversal:0 |
2577 | @@ -17414,12 +17413,13 @@ |
2578 | msgid "Warning!" |
2579 | msgstr "Avertissement!" |
2580 | |
2581 | -#. modules: purchase, sale |
2582 | +#. modules: purchase, sale, account_override |
2583 | #: code:addons/purchase/purchase_workflow.py:549 |
2584 | #: code:addons/sale/sale_workflow.py:529 |
2585 | +#: code:addons/account_override/invoice.py:829 |
2586 | #, python-format |
2587 | -msgid "You can't use taxes with an intermission partner." |
2588 | -msgstr "Vous ne pouvez pas utiliser de taxes avec un partenaire intermission." |
2589 | +msgid "Taxes are forbidden with Intermission and Intersection partners." |
2590 | +msgstr "Les taxes sont interdites avec les partenaires Intermission et Intersection." |
2591 | |
2592 | #. module: account |
2593 | #: model:ir.actions.act_window,name:account.action_account_fiscal_position_form |
2594 | @@ -18873,8 +18873,9 @@ |
2595 | msgid "Number of Packs" |
2596 | msgstr "Nombre de Colis" |
2597 | |
2598 | -#. module: account |
2599 | +#. module: account, account_override |
2600 | #: code:addons/account/invoice.py:652 |
2601 | +#: code:addons/account_override/invoice.py:421 |
2602 | #, python-format |
2603 | msgid "Can't find any account journal of %s type for this company.\n" |
2604 | "\n" |
2605 | @@ -20404,8 +20405,9 @@ |
2606 | msgid "Red color" |
2607 | msgstr "Red color" |
2608 | |
2609 | -#. module: base |
2610 | +#. module: base, account |
2611 | #: selection:res.request,state:0 |
2612 | +#: code:addons/account/invoice.py:477 |
2613 | msgid "closed" |
2614 | msgstr "fermé/fermée" |
2615 | |
2616 | @@ -21129,7 +21131,7 @@ |
2617 | msgid "Free 1 Lines" |
2618 | msgstr "Option 1 Lignes" |
2619 | |
2620 | -#. modules: account_override, msf_outgoing, purchase_override, stock_override, sale, msf_order_date, purchase, msf_partner, msf_supply_doc_export |
2621 | +#. modules: account_override, msf_outgoing, purchase_override, stock_override, sale, msf_order_date, purchase, msf_partner, msf_supply_doc_export, account |
2622 | #: field:account.account,has_partner_type_section:0 |
2623 | #: selection:shipment,partner_type:0 |
2624 | #: selection:purchase.order.merged.line,po_partner_type_stored:0 |
2625 | @@ -21137,6 +21139,8 @@ |
2626 | #: selection:sale.loan.stock.moves,partner_type:0 |
2627 | #: selection:stock.picking,partner_type:0 |
2628 | #: selection:sale.order,partner_type:0 |
2629 | +#: selection:account.invoice,partner_type:0 |
2630 | +#: selection:account.invoice.line,partner_type:0 |
2631 | #: view:res.partner:0 |
2632 | #: selection:res.partner,partner_type:0 |
2633 | #: selection:purchase.order,partner_type:0 |
2634 | @@ -25234,8 +25238,12 @@ |
2635 | msgid "Europe/Bucharest" |
2636 | msgstr "Europe/Bucharest" |
2637 | |
2638 | +<<<<<<< TREE |
2639 | #. modules: msf_budget, account, account_payment, product_attributes, register_accounting, unifield_setup, object_query, order_types, mission_stock, msf_accrual, procurement_report, stock, msf_partner, salr, sourcing, tender_flow, msf_doc_import, finance, msf_supply_doc_export, product, stock_override, msf_order_date |
2640 | #: view:account.state.open:0 |
2641 | +======= |
2642 | +#. modules: msf_budget, account, account_payment, product_attributes, register_accounting, unifield_setup, object_query, order_types, mission_stock, msf_accrual, procurement_report, stock, msf_partner, salr, sourcing, tender_flow, msf_doc_import, finance, msf_supply_doc_export, product, stock_override |
2643 | +>>>>>>> MERGE-SOURCE |
2644 | #: view:account.payment.make.payment:0 |
2645 | #: selection:mission.stock.wizard,split_stock:0 |
2646 | #: selection:mission.stock.wizard,with_valuation:0 |
2647 | @@ -27110,6 +27118,8 @@ |
2648 | #: field:purchase.report,invoiced:0 |
2649 | #: view:account.invoice:0 |
2650 | #: selection:account.direct.invoice.wizard,state:0 |
2651 | +#: selection:account.invoice,counterpart_inv_status:0 |
2652 | +#: selection:wizard.account.invoice,counterpart_inv_status:0 |
2653 | msgid "Paid" |
2654 | msgstr "Payé" |
2655 | |
2656 | @@ -27898,12 +27908,6 @@ |
2657 | msgid "Ratio" |
2658 | msgstr "Ratio" |
2659 | |
2660 | -#. module: account |
2661 | -#: code:addons/account/wizard/account_state_open.py:37 |
2662 | -#, python-format |
2663 | -msgid "Invoice is already reconciled" |
2664 | -msgstr "La Facture est déjà lettrée" |
2665 | - |
2666 | #. module: account_mcdb |
2667 | #: view:account.analytic.line:0 |
2668 | msgid "Have been reallocated?" |
2669 | @@ -30251,15 +30255,28 @@ |
2670 | msgid "Certificate attached ?" |
2671 | msgstr "Certificat attaché ?" |
2672 | |
2673 | +<<<<<<< TREE |
2674 | #. modules: msf_supply_doc_export, sourcing, consumption_calculation, sale, sales_followup, msf_supply_doc_export, purchase |
2675 | +======= |
2676 | +#. modules: msf_supply_doc_export, sourcing, consumption_calculation, sale, sales_followup, msf_supply_doc_export, account_override,account,register_accounting |
2677 | +>>>>>>> MERGE-SOURCE |
2678 | #: field:po.follow.up,closed_ok:0 |
2679 | #: selection:real.average.consumption,state:0 |
2680 | #: selection:po.follow.up,state:0 |
2681 | #: selection:sale.order.leave.close,order_state:0 |
2682 | #: field:ir.followup.location.wizard,closed_ok:0 |
2683 | #: selection:sale.order.line,sale_order_state:0 |
2684 | +<<<<<<< TREE |
2685 | #: selection:sale.order.line,state_to_display:0 |
2686 | #: selection:purchase.order.line,state_to_display:0 |
2687 | +======= |
2688 | +#: selection:account.invoice,state:0 |
2689 | +#: selection:account.invoice.report,state:0 |
2690 | +#: selection:report.invoice.created,state:0 |
2691 | +#: view:account.invoice:0 |
2692 | +#: selection:wizard.account.invoice,state:0 |
2693 | +#: selection:account.invoice,counterpart_inv_status:0 |
2694 | +>>>>>>> MERGE-SOURCE |
2695 | msgid "Closed" |
2696 | msgstr "Fermé" |
2697 | |
2698 | @@ -33691,7 +33708,6 @@ |
2699 | msgstr "Importer PCM Ã partir de feuilles Excel" |
2700 | |
2701 | #. modules: account, sale |
2702 | -#: view:account.state.open:0 |
2703 | #: model:ir.actions.act_window,name:sale.action_view_sale_open_invoice |
2704 | #: view:sale.open.invoice:0 |
2705 | msgid "Open Invoice" |
2706 | @@ -33780,11 +33796,6 @@ |
2707 | "* a basic mechanism to easily plug various automated payment.\n" |
2708 | " " |
2709 | |
2710 | -#. module: account |
2711 | -#: view:account.invoice.cancel:0 |
2712 | -msgid "Cancel Invoices" |
2713 | -msgstr "Annuler les Factures" |
2714 | - |
2715 | #. module: base |
2716 | #: field:partner.sms.send,text:0 |
2717 | msgid "SMS Message" |
2718 | @@ -41110,12 +41121,6 @@ |
2719 | msgid "Sync Flag" |
2720 | msgstr "Sync Flag" |
2721 | |
2722 | -#. module: account |
2723 | -#: view:account.invoice.cancel:0 |
2724 | -#: model:ir.actions.act_window,name:account.action_account_invoice_cancel |
2725 | -msgid "Cancel Selected Invoices" |
2726 | -msgstr "Annuler les Factures Sélectionnées" |
2727 | - |
2728 | #. module: account_override |
2729 | #: code:addons/account_override/account.py:624 |
2730 | #, python-format |
2731 | @@ -47194,7 +47199,11 @@ |
2732 | msgid "Metadata" |
2733 | msgstr "Métadonnées" |
2734 | |
2735 | +<<<<<<< TREE |
2736 | #. modules: msf_order_date, purchase, msf_outgoing, msf_partner, stock_override, purchase_override, sale, account_override, analytic_distribution, product_attributes, msf_supply_doc_export |
2737 | +======= |
2738 | +#. modules: msf_order_date, purchase, msf_outgoing, msf_partner, stock_override, purchase_override, sale, account_override, analytic_distribution, msf_supply_doc_export, account |
2739 | +>>>>>>> MERGE-SOURCE |
2740 | #: field:account.account,has_partner_type_esc:0 |
2741 | #: view:account.commitment:0 |
2742 | #: selection:sale.order,partner_type:0 |
2743 | @@ -47210,7 +47219,12 @@ |
2744 | #: selection:sale.order.change.currency,partner_type:0 |
2745 | #: selection:stock.picking,partner_type:0 |
2746 | #: selection:stock.picking,partner_type_stock_picking:0 |
2747 | +<<<<<<< TREE |
2748 | #: model:product.international.status,name:product_attributes.int_2 |
2749 | +======= |
2750 | +#: selection:account.invoice,partner_type:0 |
2751 | +#: selection:account.invoice.line,partner_type:0 |
2752 | +>>>>>>> MERGE-SOURCE |
2753 | #: code:addons/msf_supply_doc_export/wizard/supplier_performance_wizard.py:31 |
2754 | #: field:supplier.performance.wizard,partner_type_esc:0 |
2755 | msgid "ESC" |
2756 | @@ -51967,9 +51981,11 @@ |
2757 | msgid "Search Donation" |
2758 | msgstr "Rechercher Donation" |
2759 | |
2760 | -#. module: sale |
2761 | +#. modules: sale, account_override, account |
2762 | #: report:addons/sale/report/sale_donation_stock_moves_report_xls.mako:127 |
2763 | #: field:sale.donation.stock.moves,partner_type:0 |
2764 | +#: field:account.invoice,partner_type:0 |
2765 | +#: field:account.invoice.line,partner_type:0 |
2766 | msgid "Partner Type" |
2767 | msgstr "Type de Partenaire" |
2768 | |
2769 | @@ -56903,8 +56919,9 @@ |
2770 | msgid "Kit Composition List" |
2771 | msgstr "Liste de composition du Kit" |
2772 | |
2773 | -#. modules: account, register_accounting |
2774 | +#. modules: account, register_accounting, account_override |
2775 | #: selection:account.invoice,type:0 |
2776 | +#: selection:account.invoice.line,invoice_type:0 |
2777 | #: selection:account.invoice.report,type:0 |
2778 | #: selection:report.invoice.created,type:0 |
2779 | #: selection:wizard.account.invoice,type:0 |
2780 | @@ -58894,7 +58911,6 @@ |
2781 | #: code:addons/account/wizard/account_invoice_state.py:44 |
2782 | #: code:addons/account/wizard/account_invoice_state.py:68 |
2783 | #: code:addons/account/wizard/account_report_balance_sheet.py:55 |
2784 | -#: code:addons/account/wizard/account_state_open.py:37 |
2785 | #: code:addons/account/wizard/account_subscription_generate.py:50 |
2786 | #: code:addons/account/wizard/account_subscription_generate.py:52 |
2787 | #: code:addons/account/wizard/account_subscription_generate.py:60 |
2788 | @@ -63350,6 +63366,18 @@ |
2789 | msgid "Cannot delete invoice(s) that are already opened or paid !" |
2790 | msgstr "Impossible de supprimer des factures qui sont déjà ouvertes ou payées !" |
2791 | |
2792 | +#. module: account |
2793 | +#: code:addons/account/invoice.py:472 |
2794 | +#, python-format |
2795 | +msgid "Cannot delete invoice(s) generated by a Supply workflow!" |
2796 | +msgstr "Impossible de supprimer des factures générées par un flux \"Supply\" !" |
2797 | + |
2798 | +#. module: account |
2799 | +#: code:addons/account/invoice.py:474 |
2800 | +#, python-format |
2801 | +msgid "Cannot delete invoice(s) set as \"Synchronized\"!" |
2802 | +msgstr "Impossible de supprimer des factures marquées comme \"Synchronisées\" !" |
2803 | + |
2804 | #. module: stock |
2805 | #: view:physical.inventory:0 |
2806 | msgid "Counting sheet" |
2807 | @@ -63994,11 +64022,6 @@ |
2808 | msgid "Select your report" |
2809 | msgstr "Sélectionner votre rapport" |
2810 | |
2811 | -#. module: account |
2812 | -#: view:account.state.open:0 |
2813 | -msgid "(Invoice should be unreconciled if you want to open it)" |
2814 | -msgstr "(Une facture doit être déléttrée pour pouvoir l'ouvrir" |
2815 | - |
2816 | #. modules: procurement_auto, procurement_cycle |
2817 | #: help:stock.warehouse.automatic.supply,frequence_id:0 |
2818 | #: help:stock.warehouse.order.cycle,frequence_id:0 |
2819 | @@ -66333,8 +66356,9 @@ |
2820 | msgid "Remove all Instances" |
2821 | msgstr "Supprimer toutes les instances" |
2822 | |
2823 | -#. module: analytic_distribution |
2824 | +#. modules: analytic_distribution, account_override |
2825 | #: view:account.invoice.line:0 |
2826 | +#: view:account.invoice:0 |
2827 | msgid "Change analytic distribution" |
2828 | msgstr "Changer la distribution analytique" |
2829 | |
2830 | @@ -68392,7 +68416,7 @@ |
2831 | #. module: account_override |
2832 | #: view:account.invoice:0 |
2833 | msgid "You are about to cancel this invoice. Do you want to proceed?" |
2834 | -msgstr "You are about to cancel this invoice. Do you want to proceed?" |
2835 | +msgstr "Vous êtes sur le point d'annuler cette facture. Voulez-vous continuer ?" |
2836 | |
2837 | #. module: procurement |
2838 | #: help:procurement.order,name:0 |
2839 | @@ -72046,7 +72070,6 @@ |
2840 | msgstr "Seuls les Produits de Kit peuvent être utilisés pour les Kits." |
2841 | |
2842 | #. modules: sales_followup, account, purchase_override, procurement_request, res_currency_tables, sync_client, documents_done, product, kit, base, purchase_followup, sale, stock, msf_profile |
2843 | -#: view:account.invoice.cancel:0 |
2844 | #: view:account.invoice.confirm:0 |
2845 | #: view:base.language.install:0 |
2846 | #: view:base.module.import:0 |
2847 | @@ -73705,6 +73728,7 @@ |
2848 | #: code:addons/account_override/invoice.py:1484 |
2849 | #: code:addons/account_override/invoice.py:1772 |
2850 | #: code:addons/account_override/invoice.py:1775 |
2851 | +#: code:addons/account_override/account_invoice_sync.py:0 |
2852 | #: code:addons/account_reconciliation/account_move_line.py:236 |
2853 | #: code:addons/account_reconciliation/account_move_line.py:256 |
2854 | #: code:addons/account_reconciliation/account_move_line.py:258 |
2855 | @@ -74686,6 +74710,13 @@ |
2856 | #: code:addons/stock/wizard/stock_reception_wizard.py:110 |
2857 | #: field:export.report.stock.move,error:0 |
2858 | #: selection:export.report.stock.move,state:0 |
2859 | +#: code:addons/account/invoice.py:1342 |
2860 | +#: code:addons/account/invoice.py:1344 |
2861 | +#: code:addons/account/report/account_liquidity_balance.py:71 |
2862 | +#: code:addons/account/wizard/account_report_liquidity_balance.py:71 |
2863 | +#: code:addons/account/wizard/account_report_liquidity_balance.py:73 |
2864 | +#: code:addons/account/wizard/account_report_liquidity_balance.py:75 |
2865 | +#: code:addons/account_override/period.py:148 |
2866 | #, python-format, python-format |
2867 | msgid "Error" |
2868 | msgstr "Erreur" |
2869 | @@ -78305,8 +78336,13 @@ |
2870 | #: selection:purchase.order,rfq_state:0 |
2871 | #: view:tender:0 |
2872 | #: selection:tender,state:0 |
2873 | +<<<<<<< TREE |
2874 | #: selection:sale.order.line,state_to_display:0 |
2875 | #: selection:purchase.order.line,state_to_display:0 |
2876 | +======= |
2877 | +#: selection:account.invoice,counterpart_inv_status:0 |
2878 | +#: selection:wizard.account.invoice,counterpart_inv_status:0 |
2879 | +>>>>>>> MERGE-SOURCE |
2880 | #: field:po.follow.up,cancel_ok:0 |
2881 | #, python-format |
2882 | msgid "Cancelled" |
2883 | @@ -88425,7 +88461,12 @@ |
2884 | #: selection:wizard.import.cheque,state:0 |
2885 | #: selection:wizard.import.invoice,state:0 |
2886 | #: selection:wizard.register.creation,state:0 |
2887 | +<<<<<<< TREE |
2888 | #: code:addons/sale/report/sale_loan_stock_moves_report.py:92 |
2889 | +======= |
2890 | +#: selection:account.invoice,counterpart_inv_status:0 |
2891 | +#: selection:wizard.account.invoice,counterpart_inv_status:0 |
2892 | +>>>>>>> MERGE-SOURCE |
2893 | #, python-format |
2894 | msgid "Open" |
2895 | msgstr "Ouvert" |
2896 | @@ -88796,10 +88837,17 @@ |
2897 | |
2898 | #. module: account_override |
2899 | #: code:addons/account_override/invoice.py:747 |
2900 | +#: code:addons/account_override/account_invoice_sync.py:230 |
2901 | #, python-format |
2902 | msgid "No Intermission journal found for the current instance." |
2903 | msgstr "Pas de journal Intermission trouvé pour l'instance actuelle." |
2904 | |
2905 | +#. module: account_override |
2906 | +#: code:addons/account_override/account_invoice_sync.py:209 |
2907 | +#, python-format |
2908 | +msgid "No Purchase journal found for the current instance." |
2909 | +msgstr "Pas de journal des Achats trouvé pour l'instance actuelle." |
2910 | + |
2911 | #. module: msf_profile |
2912 | #: field:email.configuration,smtp_server:0 |
2913 | msgid "SMTP Server" |
2914 | @@ -94758,6 +94806,24 @@ |
2915 | msgid "Can not %s invoice which is already reconciled, invoice should be unreconciled first. You can only Refund this invoice" |
2916 | msgstr "Ne peut %s une facture qui est déjà lettrée, le lettrage de la facture devrait d'abord être annulé. Vous ne pouvez que Rembourser cette facture" |
2917 | |
2918 | +#. module: account |
2919 | +#: code:addons/account/wizard/account_invoice_refund.py:161 |
2920 | +#, python-format |
2921 | +msgid "Cannot %s an Intermission Voucher which is already reconciled, it should be unreconciled first." |
2922 | +msgstr "Ne peut %s un Bon Intermission qui est déjà lettré, le lettrage du bon devrait d'abord être annulé." |
2923 | + |
2924 | +#. module: account |
2925 | +#: code:addons/account/wizard/account_invoice_refund.py:0 |
2926 | +#, python-format |
2927 | +msgid "modify" |
2928 | +msgstr "modifier" |
2929 | + |
2930 | +#. module: account |
2931 | +#: code:addons/account/wizard/account_invoice_refund.py:0 |
2932 | +#, python-format |
2933 | +msgid "cancel" |
2934 | +msgstr "annuler" |
2935 | + |
2936 | #. modules: return_claim, msf_outgoing, stock_override, kit, msf_doc_import |
2937 | #: selection:assign.to.kit.line,integrity_status:0 |
2938 | #: selection:kit.selection.line,integrity_status:0 |
2939 | @@ -97423,7 +97489,7 @@ |
2940 | msgid "Document Date" |
2941 | msgstr "Date du Document" |
2942 | |
2943 | -#. modules: msf_order_date, purchase, msf_outgoing, stock_move_tracking, msf_partner, stock_override, purchase_override, msf_config_locations, sale, account_override, stock_batch_recall, specific_rules, msf_doc_import, stock, msf_supply_doc_export |
2944 | +#. modules: msf_order_date, purchase, msf_outgoing, stock_move_tracking, msf_partner, stock_override, purchase_override, msf_config_locations, sale, account_override, stock_batch_recall, specific_rules, msf_doc_import, stock, msf_supply_doc_export, account |
2945 | #: field:account.account,has_partner_type_internal:0 |
2946 | #: selection:stock.location.configuration.wizard,location_type:0 |
2947 | #: selection:stock.remove.location.wizard,location_usage:0 |
2948 | @@ -97452,6 +97518,8 @@ |
2949 | #: selection:stock.picking,fake_type:0 |
2950 | #: selection:stock.picking,partner_type:0 |
2951 | #: selection:stock.picking,partner_type_stock_picking:0 |
2952 | +#: selection:account.invoice,partner_type:0 |
2953 | +#: selection:account.invoice.line,partner_type:0 |
2954 | #: code:addons/msf_supply_doc_export/wizard/supplier_performance_wizard.py:28 |
2955 | #: field:supplier.performance.wizard,partner_type_internal:0 |
2956 | #, python-format |
2957 | @@ -101145,12 +101213,13 @@ |
2958 | msgid "On " |
2959 | msgstr "Allumé " |
2960 | |
2961 | -#. modules: account, register_accounting |
2962 | +#. modules: account, register_accounting, account_override |
2963 | #: selection:account.invoice,type:0 |
2964 | #: selection:account.invoice.report,type:0 |
2965 | #: model:process.process,name:account.process_process_invoiceprocess0 |
2966 | #: selection:report.invoice.created,type:0 |
2967 | #: selection:wizard.account.invoice,type:0 |
2968 | +#: selection:account.invoice.line,invoice_type:0 |
2969 | msgid "Customer Invoice" |
2970 | msgstr "Bon client" |
2971 | |
2972 | @@ -107371,6 +107440,7 @@ |
2973 | msgid "Stop report" |
2974 | msgstr "Arrêter le rapport" |
2975 | |
2976 | +<<<<<<< TREE |
2977 | #. module: stock |
2978 | #: code:addons/stock/stock.py:1780 |
2979 | #, python-format |
2980 | @@ -107481,3 +107551,199 @@ |
2981 | #: report:addons/sale/report/sale_loan_stock_moves_report_xls.mako:175 |
2982 | msgid "Line State" |
2983 | msgstr "État de la Ligne" |
2984 | +======= |
2985 | +#. module: account |
2986 | +#: code:addons/account/wizard/account_invoice_refund.py:148 |
2987 | +#, python-format |
2988 | +msgid "Can not %s invoice which is already reconciled, invoice should be unreconciled first." |
2989 | +msgstr "Ne peut %s une facture qui est déjà lettrée, le lettrage de la facture devrait d'abord être annulé." |
2990 | + |
2991 | +#. module: account |
2992 | +#: code:addons/account/invoice.py:480 |
2993 | +#, python-format |
2994 | +msgid "Invoice '%s' is %s." |
2995 | +msgstr "La facture '%s' est %s." |
2996 | + |
2997 | +#. module: account |
2998 | +#: code:addons/account/wizard/account_invoice_refund.py:153 |
2999 | +#, python-format |
3000 | +msgid "It is not possible to refund a Closed invoice" |
3001 | +msgstr "Il n'est pas possible de rembourser une facture fermée" |
3002 | + |
3003 | +#. module: account |
3004 | +#: code:addons/account/invoice.py:474 |
3005 | +#, python-format |
3006 | +msgid "paid" |
3007 | +msgstr "réglée" |
3008 | + |
3009 | +#. module: account |
3010 | +#: field:account.invoice.refund,is_intermission:0 |
3011 | +msgid "Wizard opened from an Intermission Voucher" |
3012 | +msgstr "Assistant ouvert depuis un Bon Intermission" |
3013 | + |
3014 | +#. module: account_override |
3015 | +#: code:addons/account_override/invoice.py:1739 |
3016 | +#, python-format |
3017 | +msgid "This document has been generated via a Supply workflow or via synchronization. You can't add lines manually." |
3018 | +msgstr "Ce document a été généré via un flux \"Supply\" ou via la synchronisation. Vous ne pouvez pas ajouter de lignes manuellement." |
3019 | + |
3020 | +#. module: account_override |
3021 | +#: code:addons/account_override/invoice.py:1868 |
3022 | +#, python-format |
3023 | +msgid "This document has been generated via a Supply workflow or via synchronization. Existing lines can't be deleted." |
3024 | +msgstr "Ce document a été généré via un flux \"Supply\" ou via la synchronisation. Les lignes existantes ne peuvent pas être supprimées." |
3025 | + |
3026 | +#. module: account_override |
3027 | +#: code:addons/account_override/invoice.py:848 |
3028 | +#, python-format |
3029 | +msgid "Synchronized invoices are allowed only with Intermission and Intersection partners." |
3030 | +msgstr "Les factures synchronisées ne sont autorisées qu'avec les partenaires Intermission et Intersection." |
3031 | + |
3032 | +#. module: account |
3033 | +#: code:addons/account/invoice.py:683 |
3034 | +#, python-format |
3035 | +msgid "Synchronization is allowed only with Intermission and Intersection partners." |
3036 | +msgstr "La synchronisation n'est autorisée qu'avec les partenaires Intermission et Intersection." |
3037 | + |
3038 | +#. module: account_override |
3039 | +#: view:account.invoice:0 |
3040 | +msgid "Are you sure you want to validate this invoice without synchronization?" |
3041 | +msgstr "Etes-vous sûr de vouloir valider cette facture sans synchronisation ?" |
3042 | + |
3043 | +#. modules: account_override, account, register_accounting |
3044 | +#: view:account.invoice:0 |
3045 | +msgid "Counterpart Invoice" |
3046 | +msgstr "Facture de Contrepartie" |
3047 | + |
3048 | +#. modules: account_override, register_accounting |
3049 | +#: field:account.invoice,counterpart_inv_number:0 |
3050 | +#: field:wizard.account.invoice,counterpart_inv_number:0 |
3051 | +msgid "Counterpart Invoice Number" |
3052 | +msgstr "Numéro de la Facture de Contrepartie" |
3053 | + |
3054 | +#. modules: account_override, register_accounting |
3055 | +#: field:account.invoice,counterpart_inv_status:0 |
3056 | +#: field:wizard.account.invoice,counterpart_inv_status:0 |
3057 | +msgid "Counterpart Invoice Status" |
3058 | +msgstr "Etat de la Facture de Contrepartie" |
3059 | + |
3060 | +#. modules: account_override, register_accounting |
3061 | +#: field:account.invoice,synced:0 |
3062 | +#: field:wizard.account.invoice,synced:0 |
3063 | +#: field:account.invoice.line,synced:0 |
3064 | +msgid "Synchronized" |
3065 | +msgstr "Synchronisé" |
3066 | + |
3067 | +#. modules: account_override, register_accounting |
3068 | +#: field:account.invoice,from_supply:0 |
3069 | +#: field:wizard.account.invoice,from_supply:0 |
3070 | +#: field:account.invoice.line,from_supply:0 |
3071 | +msgid "From Supply" |
3072 | +msgstr "De la \"Supply\"" |
3073 | + |
3074 | +#. module: account_override |
3075 | +#: field:account.invoice.line,invoice_type:0 |
3076 | +msgid "Invoice Type" |
3077 | +msgstr "Type de Facture" |
3078 | + |
3079 | +#. modules: account_override, register_accounting |
3080 | +#: help:account.invoice,from_supply:0 |
3081 | +#: help:wizard.account.invoice,from_supply:0 |
3082 | +msgid "Internal field indicating whether the document is related to a Supply workflow" |
3083 | +msgstr "Champ interne indiquant si le document est lié à un flux \"Supply\"" |
3084 | + |
3085 | +#. module: account_override |
3086 | +#: code:addons/account_override/account_invoice_sync.py:120 |
3087 | +#, python-format |
3088 | +msgid "Account code %s not found." |
3089 | +msgstr "Code comptable %s non trouvé." |
3090 | + |
3091 | +#. module: account_override |
3092 | +#: code:addons/account_override/account_invoice_sync.py:189 |
3093 | +#, python-format |
3094 | +msgid "Impossible to retrieve the currency." |
3095 | +msgstr "Impossible de récupérer la devise." |
3096 | + |
3097 | +#. module: account_override |
3098 | +#: code:addons/account_override/account_invoice_sync.py:117 |
3099 | +#, python-format |
3100 | +msgid "Impossible to retrieve the account code at line level." |
3101 | +msgstr "Impossible de récupérer le code comptable au niveau d'une ligne." |
3102 | + |
3103 | +#. module: account_override |
3104 | +#: code:addons/account_override/account_invoice_sync.py:193 |
3105 | +#, python-format |
3106 | +msgid "Currency %s not found or inactive." |
3107 | +msgstr "Devise %s non trouvée ou inactive." |
3108 | + |
3109 | +#. module: account_override |
3110 | +#: code:addons/account_override/account_invoice_sync.py:123 |
3111 | +#, python-format |
3112 | +msgid "Error when retrieving the account at line level." |
3113 | +msgstr "Erreur lors de la récupération du compte au niveau d'une ligne." |
3114 | + |
3115 | +#. module: account_override |
3116 | +#: code:addons/account_override/account_invoice_sync.py:235 |
3117 | +#, python-format |
3118 | +msgid "The Intermission counterpart account is missing in the Company form or is inactive." |
3119 | +msgstr "Il manque le compte de Contrepartie Intermission dans le formulaire de la Société, ou bien ce compte est inactif." |
3120 | + |
3121 | +#. module: account_override |
3122 | +#: code:addons/account_override/account_invoice_sync.py:186 |
3123 | +#, python-format |
3124 | +msgid "Impossible to retrieve the journal type, or the journal type is incorrect." |
3125 | +msgstr "Impossible de récupérer le type de journal, ou le type de journal est incorrect." |
3126 | + |
3127 | +#. module: account_override |
3128 | +#: code:addons/account_override/account_invoice_sync.py:100 |
3129 | +#, python-format |
3130 | +msgid "Impossible to retrieve the line description." |
3131 | +msgstr "Impossible de récupérer la description de la ligne." |
3132 | + |
3133 | +#. module: account_override |
3134 | +#: code:addons/account_override/account_invoice_sync.py:128 |
3135 | +#, python-format |
3136 | +msgid "The account \"%s - %s\" is inactive." |
3137 | +msgstr "Le compte \"%s - %s\" est inactif." |
3138 | + |
3139 | +#. module: account_override |
3140 | +#: code:addons/account_override/account_invoice_sync.py:135 |
3141 | +#, python-format |
3142 | +msgid "Unit of Measure %s not found." |
3143 | +msgstr "Unité de Mesure %s non trouvée." |
3144 | + |
3145 | +#. module: account_override |
3146 | +#: code:addons/account_override/account_invoice_sync.py:109 |
3147 | +#, python-format |
3148 | +msgid "Product %s not found." |
3149 | +msgstr "Produit %s non trouvé." |
3150 | + |
3151 | +#. module: account_override |
3152 | +#: code:addons/account_override/account_invoice_sync.py:181 |
3153 | +#, python-format |
3154 | +msgid "The partner %s doesn't exist or is inactive." |
3155 | +msgstr "Le partenaire %s n'existe pas ou est inactif." |
3156 | + |
3157 | +#. module: account_override |
3158 | +#: code:addons/account_override/account_invoice_sync.py:113 |
3159 | +#, python-format |
3160 | +msgid "The product %s is inactive." |
3161 | +msgstr "Le produit %s est inactif." |
3162 | + |
3163 | +#. module: account_override |
3164 | +#: code:addons/account_override/account_invoice_sync.py:214 |
3165 | +#, python-format |
3166 | +msgid "Account Payable not found or inactive for the partner %s." |
3167 | +msgstr "Compte Fournisseur non trouvé ou inactif pour le partenaire %s." |
3168 | + |
3169 | +#. module: account |
3170 | +#: code:addons/account/wizard/account_invoice_refund.py:158 |
3171 | +#, python-format |
3172 | +msgid "Cannot Cancel / Modify if the account can't be reconciled." |
3173 | +msgstr "Impossible d'Annuler / Modifier si le compte n'est pas lettrable." |
3174 | + |
3175 | +#. module: account_override |
3176 | +#: view:account.invoice:0 |
3177 | +msgid "This invoice will sync to its counterpart instance." |
3178 | +msgstr "Cette facture sera synchronisée à l'instance de Contrepartie." |
3179 | +>>>>>>> MERGE-SOURCE |
3180 | |
3181 | === modified file 'bin/addons/msf_profile/msf_profile.py' |
3182 | --- bin/addons/msf_profile/msf_profile.py 2019-07-24 09:13:25 +0000 |
3183 | +++ bin/addons/msf_profile/msf_profile.py 2019-07-30 10:04:49 +0000 |
3184 | @@ -67,6 +67,46 @@ |
3185 | cr.execute("update ir_cron set function='send_backup_bg' where function='send_backup' and model='msf.instance.cloud'") |
3186 | return True |
3187 | |
3188 | + # UF14.0 |
3189 | + def us_6075_set_paid_invoices_as_closed(self, cr, uid, *a, **b): |
3190 | + cr.execute('''SELECT i.id, i.number |
3191 | + FROM account_invoice i |
3192 | + LEFT JOIN account_move_line l ON i.move_id=l.move_id |
3193 | + LEFT JOIN account_move_line rec_line ON rec_line.reconcile_id = l.reconcile_id |
3194 | + LEFT JOIN account_journal j ON j.id = rec_line.journal_id AND j.type in ('cash', 'bank', 'cheque') |
3195 | + WHERE i.state='paid' |
3196 | + AND l.reconcile_id is not null |
3197 | + AND l.account_id=i.account_id |
3198 | + AND l.is_counterpart |
3199 | + GROUP BY i.id, i.number |
3200 | + HAVING min(j.id) IS NULL |
3201 | + ORDER BY i.id |
3202 | + ''') |
3203 | + inv_ids = [] |
3204 | + inv_name = [] |
3205 | + for x in cr.fetchall(): |
3206 | + inv_ids.append(x[0]) |
3207 | + inv_name.append(x[1]) |
3208 | + if inv_ids: |
3209 | + self._logger.warn('%d Invoices change state from Paid to Close: %s' % (len(inv_ids), ', '.join(inv_name))) |
3210 | + cr.execute("update account_invoice set state='inv_close' where state='paid' and id in %s", (tuple(inv_ids), )) |
3211 | + return True |
3212 | + |
3213 | + def us_6076_set_inv_as_from_supply(self, cr, uid, *a, **b): |
3214 | + """ |
3215 | + Set the new tag from_supply to True in the related account.invoices |
3216 | + """ |
3217 | + update_inv = """ |
3218 | + UPDATE account_invoice |
3219 | + SET from_supply = 't' |
3220 | + WHERE picking_id IS NOT NULL |
3221 | + OR id IN (SELECT DISTINCT (invoice_id) FROM shipment WHERE invoice_id IS NOT NULL); |
3222 | + """ |
3223 | + cr.execute(update_inv) |
3224 | + self._logger.warn('Tag from_supply set to True in %s account.invoice(s).' % (cr.rowcount,)) |
3225 | + return True |
3226 | + |
3227 | + |
3228 | # UF13.1 |
3229 | def us_3413_align_in_partner_to_po(self,cr, uid, *a, **b): |
3230 | cr.execute("select p.name, p.id, po.partner_id, p.partner_id from stock_picking p, purchase_order po where p.type='in' and po.id = p.purchase_id and ( p.partner_id != po.partner_id or p.partner_id2 != po.partner_id) order by p.name") |
3231 | |
3232 | === modified file 'bin/addons/msf_sync_data_server/data/sync_server.message_rule.csv' |
3233 | --- bin/addons/msf_sync_data_server/data/sync_server.message_rule.csv 2019-02-16 16:57:55 +0000 |
3234 | +++ bin/addons/msf_sync_data_server/data/sync_server.message_rule.csv 2019-07-30 10:04:49 +0000 |
3235 | @@ -15,6 +15,8 @@ |
3236 | msf_sync_data_server.validated_claim_create_claim,TRUE,TRUE,"['category_return_claim', 'creation_date_return_claim', 'description_return_claim', 'follow_up_return_claim', 'name', 'picking_id_return_claim/shipment_ref', 'po_id_return_claim/name', 'po_so_return_claim', 'goods_expected', 'processor_origin', 'state', 'type_return_claim', 'origin_claim', 'event_ids_return_claim/name', 'event_ids_return_claim/creation_date_claim_event', 'event_ids_return_claim/from_picking_wizard_claim_event', 'event_ids_return_claim/replacement_picking_expected_claim_event', 'event_ids_return_claim/type_claim_event', 'event_ids_return_claim/description_claim_event', 'product_line_ids_return_claim/price_unit_claim_product_line', 'product_line_ids_return_claim/qty_claim_product_line', 'product_line_ids_return_claim/product_id_claim_product_line/id', 'product_line_ids_return_claim/product_id_claim_product_line/name', 'product_line_ids_return_claim/price_currency_claim_product_line/id', 'product_line_ids_return_claim/price_currency_claim_product_line/name', 'product_line_ids_return_claim/uom_id_claim_product_line/id', 'product_line_ids_return_claim/uom_id_claim_product_line/name', 'product_line_ids_return_claim/type_check', 'product_line_ids_return_claim/expiry_date_claim_product_line']","[('state', '=', 'in_progress'), ('partner_id_return_claim.partner_type', 'in', ['internal', 'intermission', 'intersection']), ('type_return_claim', '=', 'supplier'), ('old_version', '=', False)]",partner_id_return_claim,MISSION,return.claim.validated_claim_create_claim,return.claim,Validated Claim creates Claim,28,,Valid |
3237 | msf_sync_data_server.origin_claim_close_claim,TRUE,TRUE,"['name', 'state', 'partner_id_return_claim/name', 'partner_id_return_claim/partner_type']","[('state', '=', 'done'), ('partner_id_return_claim.partner_type', '=', 'internal'), ('type_return_claim', '=', 'supplier'), ('old_version', '=', False)]",partner_id_return_claim,MISSION,return.claim.origin_claim_close_claim,return.claim,Original Closed Claim close counterpart Claim,29,,Valid |
3238 | msf_sync_data_server.goods_expecting_picking_from_claim_creates_fo,TRUE,TRUE,"['name', 'claim_name', 'purchase_id/name', 'purchase_id/delivery_requested_date','purchase_id/details', 'purchase_id/notes', 'purchase_id/categ', 'purchase_id/order_type', 'purchase_id/priority', 'purchase_id/loan_duration', 'purchase_id/analytic_distribution_id/id', 'purchase_id/is_a_counterpart', 'purchase_id/pricelist_id/name', 'purchase_id/stock_take_date', 'move_lines/product_id/name', 'move_lines/purchase_line_id/id', 'move_lines/purchase_line_id/sync_local_id', 'move_lines/name', 'move_lines/comment', 'move_lines/product_qty', 'move_lines/product_uom/name', 'move_lines/price_unit', 'move_lines/line_number']","['&', '&', ('state', '=', 'assigned'), ('partner_id.partner_type', '=', 'internal'), ('claim', '=', True), ('claim_name', '!=', False), '|', ('name', 'like', 'replacement'), ('name', 'like', 'missing')]",partner_id,MISSION,stock.picking.goods_expecting_picking_from_claim_creates_fo,stock.picking,IN-replacement/-missing created by Claim creates FO,30,,Valid |
3239 | +msf_sync_data_server.create_account_invoice,TRUE,TRUE,"['number', 'document_date', 'date_invoice', 'journal_id/type', 'name', 'origin', 'from_supply', 'state', 'currency_id/name', 'invoice_line/name', 'invoice_line/quantity', 'invoice_line/uos_id/name', 'invoice_line/price_unit', 'invoice_line/discount', 'invoice_line/account_id/code', 'invoice_line/product_id/id', 'invoice_line/product_id/default_code']","[('type', '=', 'out_invoice'), ('is_debit_note', '=', False), ('state', '!=', 'draft'), ('number', '!=', False), ('synced', '=', True), ('partner_type', 'in', ('intermission', 'section'))]",partner_id,MISSION,account.invoice.create_invoice_from_sync,account.invoice,Account Invoice Creation,40,,Valid |
3240 | +msf_sync_data_server.update_counterpart_inv,TRUE,TRUE,"['number', 'state', 'counterpart_inv_number']","[('synced', '=', True), ('partner_type', 'in', ('intermission', 'section')), ('number', '!=', False), ('state', 'in', ['open', 'paid', 'inv_close', 'cancel'])]",partner_id,MISSION,account.invoice.update_counterpart_inv,account.invoice,Account Invoice State Update,42,,Valid |
3241 | msf_sync_data_server.create_batch_object,FALSE,TRUE,"['name', 'xmlid_name', 'prefix', 'product_id/id', 'product_id/default_code', 'partner_id/id', 'date', 'ref','life_date','sequence_id','type']","[('name', '=', False)]",partner_id,MISSION,stock.picking.create_batch_number,stock.production.lot,Create Batch Object,1001,,Valid |
3242 | msf_sync_data_server.create_asset_object,TRUE,TRUE,"['name', 'xmlid_name', 'arrival_date', 'asset_type_id/id', 'partner_id/id', 'brand', 'comment', 'description', 'hq_ref', 'international_po', 'invo_certif_depreciation', 'invo_currency/id', 'invo_date', 'invo_donator_code', 'invo_num', 'invo_supplier', 'invo_value', 'local_ref', 'model', 'orig_mission_code', 'product_id/id', 'product_id/default_code', 'project_po', 'receipt_place', 'serial_nb', 'type', 'year']","[('name', '=', False)]",partner_id,MISSION,stock.picking.create_asset,product.asset,Create Asset Object,1002,,Valid |
3243 | msf_sync_data_server.reset_ref_by_recovery_mode,TRUE,TRUE,['name'],"[('name', '=', False)]",partner_id,MISSION,sale.order.reset_ref_by_recovery_mode,sale.order,Reset Due to Recovery,1003,,Valid |
3244 | |
3245 | === modified file 'bin/addons/product_attributes/product_attributes.py' |
3246 | --- bin/addons/product_attributes/product_attributes.py 2019-07-22 12:08:20 +0000 |
3247 | +++ bin/addons/product_attributes/product_attributes.py 2019-07-30 10:04:49 +0000 |
3248 | @@ -1584,7 +1584,7 @@ |
3249 | # Check if the product is in an invoice |
3250 | has_invoice_line = invoice_obj.search(cr, uid, [('product_id', '=', product.id), |
3251 | ('invoice_id', '!=', False), |
3252 | - ('invoice_id.state', 'not in', ['paid', 'proforma', 'proforma2', 'cancel'])], context=context) |
3253 | + ('invoice_id.state', 'not in', ['paid', 'inv_close', 'proforma', 'proforma2', 'cancel'])], context=context) |
3254 | |
3255 | # Check if the product has stock in internal locations |
3256 | for loc_id in internal_loc: |
3257 | |
3258 | === modified file 'bin/addons/purchase/purchase_workflow.py' |
3259 | --- bin/addons/purchase/purchase_workflow.py 2019-05-14 08:00:10 +0000 |
3260 | +++ bin/addons/purchase/purchase_workflow.py 2019-07-30 10:04:49 +0000 |
3261 | @@ -502,15 +502,15 @@ |
3262 | |
3263 | def check_po_tax(self, cr, uid, ids, context=None): |
3264 | """ |
3265 | - Prevents from validating a PO with taxes when using an Intermission partner |
3266 | + Prevents from validating a PO with taxes when using an Intermission or Intersection partner |
3267 | """ |
3268 | if context is None: |
3269 | context = {} |
3270 | if isinstance(ids, (int, long)): |
3271 | ids = [ids] |
3272 | for po_line in self.browse(cr, uid, ids, fields_to_fetch=['order_id', 'taxes_id'], context=context): |
3273 | - if po_line.taxes_id and po_line.order_id.partner_type == 'intermission': |
3274 | - raise osv.except_osv(_('Error'), _("You can't use taxes with an intermission partner.")) |
3275 | + if po_line.taxes_id and po_line.order_id.partner_type in ('intermission', 'section'): |
3276 | + raise osv.except_osv(_('Error'), _("Taxes are forbidden with Intermission and Intersection partners.")) |
3277 | |
3278 | def check_origin_for_validation(self, cr, uid, ids, context=None): |
3279 | if not context: |
3280 | |
3281 | === modified file 'bin/addons/register_accounting/account_invoice_view.xml' |
3282 | --- bin/addons/register_accounting/account_invoice_view.xml 2018-05-15 08:55:26 +0000 |
3283 | +++ bin/addons/register_accounting/account_invoice_view.xml 2019-07-30 10:04:49 +0000 |
3284 | @@ -149,14 +149,14 @@ |
3285 | <field name="type" invisible="1"/> |
3286 | <field name="currency_id" attrs="{'readonly': [('is_direct_invoice', '=', True)]}"/> |
3287 | <newline/> |
3288 | - <field name="partner_id" domain="[('supplier', '=', True)]" on_change="onchange_partner_id(type,partner_id,date_invoice,payment_term, partner_bank_id,company_id,is_inkind_donation,is_intermission,is_debit_note,is_direct_invoice)" context="{'default_customer': 0, 'search_default_supplier': 1, 'default_supplier': 1}" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', '=', 'paid')]}"/> |
3289 | + <field name="partner_id" domain="[('supplier', '=', True)]" on_change="onchange_partner_id(type,partner_id,date_invoice,payment_term, partner_bank_id,company_id,is_inkind_donation,is_intermission,is_debit_note,is_direct_invoice)" context="{'default_customer': 0, 'search_default_supplier': 1, 'default_supplier': 1}" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', 'in', ['paid', 'inv_close'])]}"/> |
3290 | |
3291 | - <field domain="[('partner_id','=',partner_id)]" name="address_invoice_id" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', '=', 'paid')]}"/> |
3292 | + <field domain="[('partner_id','=',partner_id)]" name="address_invoice_id" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', 'in', ['paid', 'inv_close'])]}"/> |
3293 | <newline/> |
3294 | - <field name="document_date" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', '=', 'paid')]}"/> |
3295 | + <field name="document_date" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', 'in', ['paid', 'inv_close'])]}"/> |
3296 | <field name="date_invoice" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True)]}"/> |
3297 | <field name="register_posting_date" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True)]}"/> |
3298 | - <field name="reference" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', '=', 'paid')]}" /> |
3299 | + <field name="reference" attrs="{'readonly': [('is_direct_invoice', '=', True),('state', 'in', ['paid', 'inv_close'])]}" /> |
3300 | <newline/> |
3301 | <label string="" colspan="4"/> |
3302 | <field name="amount_total"/> |
3303 | @@ -165,11 +165,11 @@ |
3304 | <group colspan="2"/> |
3305 | <notebook colspan="4"> |
3306 | <page string="Invoice"> |
3307 | - <field name="account_id" domain="[('company_id', '=', company_id), ('restricted_area', '=', 'in_invoice')]" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3308 | + <field name="account_id" domain="[('company_id', '=', company_id), ('restricted_area', '=', 'in_invoice')]" required="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid', 'inv_close'])]}"/> |
3309 | <field name="check_total" readonly="1" invisible="1"/> |
3310 | <field colspan="4" default_get="{'check_total': check_total, 'address_invoice_id': |
3311 | address_invoice_id, 'partner_id': partner_id, 'price_type': 'price_type' in dir() and price_type or False}" |
3312 | - name="invoice_line" nolabel="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"> |
3313 | + name="invoice_line" nolabel="1" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid','inv_close'])]}"> |
3314 | <tree editable="bottom" string="Invoice lines" > |
3315 | <field name="is_corrected" invisible="1"/> |
3316 | <button name="button_open_analytic_lines" string="Have been corrected" type="object" icon="terp-mail-" attrs="{'invisible': [('is_corrected', '=', False)]}"/> |
3317 | @@ -193,23 +193,23 @@ |
3318 | </field> |
3319 | </page> |
3320 | <page string="Other Info"> |
3321 | - <field domain="[('partner_id', '=', partner_id)]" name="partner_bank_id" on_change="onchange_partner_bank(partner_bank_id)" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3322 | + <field domain="[('partner_id', '=', partner_id)]" name="partner_bank_id" on_change="onchange_partner_bank(partner_bank_id)" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid', 'inv_close'])]}"/> |
3323 | <field name="company_id" on_change="onchange_company_id(company_id,partner_id,type,invoice_line,currency_id)" |
3324 | - widget="selection" groups="base.group_multi_company" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3325 | - <newline/> |
3326 | - <field name="payment_term" widget="selection" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3327 | - <field name="name" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3328 | - <newline/> |
3329 | - <field name="origin" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3330 | - <field domain="[('partner_id','=',partner_id)]" name="address_contact_id" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3331 | - <field name="user_id" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','=','paid')]}"/> |
3332 | + widget="selection" groups="base.group_multi_company" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid', 'inv_close'])]}"/> |
3333 | + <newline/> |
3334 | + <field name="payment_term" widget="selection" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid','inv_close'])]}"/> |
3335 | + <field name="name" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid','inv_close'])]}"/> |
3336 | + <newline/> |
3337 | + <field name="origin" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid','inv_close'])]}"/> |
3338 | + <field domain="[('partner_id','=',partner_id)]" name="address_contact_id" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid','inv_close'])]}"/> |
3339 | + <field name="user_id" attrs="{'readonly': [('is_direct_invoice', '=', True),('state','in',['paid','inv_close'])]}"/> |
3340 | <separator colspan="4" string="Additional Information"/> |
3341 | <field colspan="4" name="comment" nolabel="1"/> |
3342 | </page> |
3343 | </notebook> |
3344 | <group col="4" colspan="4"> |
3345 | <field name="state" readonly="1" colspan="2"/> |
3346 | - <button name="%(action_direct_invoice_refund)d" type='action' string='Refund' states='open,paid' icon="gtk-execute" colspan="2"/> |
3347 | + <button name="%(action_direct_invoice_refund)d" type='action' string='Refund' states='open,paid,inv_close' icon="gtk-execute" colspan="2"/> |
3348 | </group> |
3349 | </form> |
3350 | </field> |
3351 | @@ -316,11 +316,15 @@ |
3352 | </field> |
3353 | <xpath expr="/form/notebook/page[@string='Invoice']/field[@name='invoice_line']" position="before" > |
3354 | <group name="import" string=" Import Lines " colspan="4" col="4" attrs="{'invisible':[('state', '!=', 'draft')]}"> |
3355 | - <button name="wizard_import_si_line" string="Import lines" icon="gtk-dnd" type="object" attrs="{'invisible':[('state', '!=', 'draft')]}"/> |
3356 | + <button name="wizard_import_si_line" string="Import lines" icon="gtk-dnd" type="object" |
3357 | + attrs="{'invisible': [('state', '!=', 'draft')], |
3358 | + 'readonly': [('type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
3359 | </group> |
3360 | </xpath> |
3361 | <field name="journal_id" position="replace"> |
3362 | - <field name="journal_id" domain="[('is_current_instance','=',True), ('type', '=', context.get('journal_type'))]"/> |
3363 | + <field name="journal_id" |
3364 | + domain="[('is_current_instance','=',True), ('type', '=', context.get('journal_type'))]" |
3365 | + attrs="{'readonly': ['|', ('state', '!=', 'draft'), '&', ('type', '=', 'in_invoice'), ('synced', '=', True)]}"/> |
3366 | <field name="vat_ok" invisible="1" /> |
3367 | </field> |
3368 | <button name="action_cancel_draft" position="replace"/> |
3369 | @@ -348,12 +352,16 @@ |
3370 | </tree> |
3371 | </field> |
3372 | </page> |
3373 | + <!-- display the Counterpart Invoice tab in SI, hide it in SR --> |
3374 | + <page string="Counterpart Invoice" attrs="{'invisible': [('type', '!=', 'in_invoice')]}"> |
3375 | + <field name="from_supply" invisible="1"/> <!-- make the field exportable --> |
3376 | + <field name="synced" readonly="1"/> <!-- SI can never be ticked as "Synced" manually --> |
3377 | + <newline/> |
3378 | + <field name="counterpart_inv_number"/> |
3379 | + <field name="counterpart_inv_status"/> |
3380 | + </page> |
3381 | </page> |
3382 | |
3383 | - <xpath expr="/form//field[@name='tax_line']" position="attributes"> |
3384 | - <attribute name="attrs">{'invisible': [('vat_ok', '=', False)]}</attribute> |
3385 | - </xpath> |
3386 | - |
3387 | <xpath expr="/form//field[@name='amount_untaxed']" position="attributes"> |
3388 | <attribute name="attrs">{'invisible': [('vat_ok', '=', False)]}</attribute> |
3389 | </xpath> |
3390 | @@ -371,26 +379,5 @@ |
3391 | </record> |
3392 | |
3393 | |
3394 | - <!-- Invoice search view --> |
3395 | - <record id="inherit_view_account_invoice_filter2" model="ir.ui.view"> |
3396 | - <field name="name">inherit.view.account.invoice.filter.2</field> |
3397 | - <field name="model">account.invoice</field> |
3398 | - <field name="type">search</field> |
3399 | - <field name="inherit_id" ref="account.view_account_invoice_filter"/> |
3400 | - <field name="priority">18</field> |
3401 | - <field name="arch" type="xml"> |
3402 | - <data> |
3403 | - <xpath expr="/search/group[1]/filter[@name='paid']" position="after"> |
3404 | - <separator orientation="vertical"/> |
3405 | - <filter name="not_imported" icon="gtk-cancel" string="Not imported" domain="[('imported_state', '=', 'not')]"/> |
3406 | - <filter name="partial" icon="terp-dolar_ok!" string="Partially imported" domain="[('imported_state', '=', 'partial')]"/> |
3407 | - <filter name="imported" icon="gtk-apply" string="Imported" domain="[('imported_state', '=', 'imported')]"/> |
3408 | - <separator orientation="vertical"/> |
3409 | - </xpath> |
3410 | - </data> |
3411 | - </field> |
3412 | - </record> |
3413 | - |
3414 | - |
3415 | </data> |
3416 | </openerp> |
3417 | |
3418 | === modified file 'bin/addons/register_accounting/wizard/down_payment.py' |
3419 | --- bin/addons/register_accounting/wizard/down_payment.py 2018-08-29 12:37:13 +0000 |
3420 | +++ bin/addons/register_accounting/wizard/down_payment.py 2019-07-30 10:04:49 +0000 |
3421 | @@ -97,7 +97,7 @@ |
3422 | raise osv.except_osv(_('Error'), _("Amounts IN can't be higher than Amounts OUT for the selected PO.")) |
3423 | |
3424 | # Cut away open and paid invoice linked to this PO |
3425 | - invoice_ids = self.pool.get('account.invoice').search(cr, uid, [('purchase_ids', 'in', [po_id]), ('state', 'in', ['paid', 'open'])]) |
3426 | + invoice_ids = self.pool.get('account.invoice').search(cr, uid, [('purchase_ids', 'in', [po_id]), ('state', 'in', ['paid', 'open', 'inv_close'])]) |
3427 | included_dp_amls = [] |
3428 | for inv in self.pool.get('account.invoice').read(cr, uid, invoice_ids, ['amount_total', 'down_payment_ids']): |
3429 | lines_amount -= inv.get('amount_total', 0.0) |
3430 | |
3431 | === modified file 'bin/addons/res_currency_tables/res_currency.py' |
3432 | --- bin/addons/res_currency_tables/res_currency.py 2018-07-30 14:02:59 +0000 |
3433 | +++ bin/addons/res_currency_tables/res_currency.py 2019-07-30 10:04:49 +0000 |
3434 | @@ -244,7 +244,7 @@ |
3435 | 'in at least one active partner form.') % keyword) |
3436 | |
3437 | # Check on account.invoice |
3438 | - if acc_inv_obj.search_exist(cr, uid, [('currency_id', 'in', ids), ('state', 'not in', ['paid', 'cancel'])], context=context): |
3439 | + if acc_inv_obj.search_exist(cr, uid, [('currency_id', 'in', ids), ('state', 'not in', ['paid', 'inv_close', 'cancel'])], context=context): |
3440 | raise osv.except_osv(_('Currency currently used!'), _('The currency you want to %s is used in at least ' |
3441 | 'one document in Draft or Open state.') % keyword) |
3442 | |
3443 | |
3444 | === modified file 'bin/addons/sale/report/sale_report.py' |
3445 | --- bin/addons/sale/report/sale_report.py 2017-10-09 21:06:10 +0000 |
3446 | +++ bin/addons/sale/report/sale_report.py 2019-07-30 10:04:49 +0000 |
3447 | @@ -46,7 +46,7 @@ |
3448 | else: |
3449 | res[report.id] = True |
3450 | for invoice in sale.invoice_ids: |
3451 | - if invoice.state != 'paid': |
3452 | + if invoice.state not in ('paid', 'inv_close'): |
3453 | res[report.id] = False |
3454 | break |
3455 | if not sale.invoice_ids: |
3456 | @@ -85,7 +85,7 @@ |
3457 | 'invoiced': fields.function(_invoiced, method=True, string='Paid', |
3458 | type='boolean', help="It indicates that an invoice has been paid."), |
3459 | 'order_type': fields.selection([('regular', 'Regular'), ('donation_exp', 'Donation before expiry'), |
3460 | - ('donation_st', 'Standard donation'), ('loan', 'Loan'),], |
3461 | + ('donation_st', 'Standard donation'), ('loan', 'Loan'),], |
3462 | string='Order Type', required=True, readonly=True, states={'draft': [('readonly', False)]}), |
3463 | 'priority': fields.selection(ORDER_PRIORITY, string='Priority', readonly=True, states={'draft': [('readonly', False)]}), |
3464 | 'categ': fields.selection(ORDER_CATEGORY, string='Order category', required=True, readonly=True, states={'draft': [('readonly', False)]}), |
3465 | |
3466 | === modified file 'bin/addons/sale/sale_order.py' |
3467 | --- bin/addons/sale/sale_order.py 2019-07-25 13:39:42 +0000 |
3468 | +++ bin/addons/sale/sale_order.py 2019-07-30 10:04:49 +0000 |
3469 | @@ -180,7 +180,7 @@ |
3470 | else: |
3471 | res[sale.id] = True |
3472 | for invoice in sale.invoice_ids: |
3473 | - if invoice.state != 'paid': |
3474 | + if invoice.state not in ('paid', 'inv_close'): |
3475 | res[sale.id] = False |
3476 | break |
3477 | if not sale.invoice_ids: |
3478 | @@ -196,9 +196,9 @@ |
3479 | for arg in args: |
3480 | if arg[1] == '=': |
3481 | if arg[2]: |
3482 | - clause += 'AND inv.state = \'paid\' OR (sale.state != \'draft\' AND (sale.order_type != \'regular\' OR part.partner_type = \'internal\'))' |
3483 | + clause += 'AND inv.state in (\'paid\', \'inv_close\') OR (sale.state != \'draft\' AND (sale.order_type != \'regular\' OR part.partner_type = \'internal\'))' |
3484 | else: |
3485 | - clause += 'AND inv.state != \'cancel\' AND sale.state != \'cancel\' AND inv.state <> \'paid\' AND sale.order_type = \'regular\'' |
3486 | + clause += 'AND inv.state != \'cancel\' AND sale.state != \'cancel\' AND inv.state not in (\'paid\', \'inv_close\') AND sale.order_type = \'regular\'' |
3487 | no_invoiced = True |
3488 | |
3489 | cursor.execute('SELECT rel.order_id ' \ |
3490 | |
3491 | === modified file 'bin/addons/sale/sale_view.xml' |
3492 | --- bin/addons/sale/sale_view.xml 2019-07-22 12:08:20 +0000 |
3493 | +++ bin/addons/sale/sale_view.xml 2019-07-30 10:04:49 +0000 |
3494 | @@ -430,7 +430,6 @@ |
3495 | <button name="manual_invoice" states="manual" string="Create Final Invoice" icon="gtk-go-forward" type="object" invisible="1"/> |
3496 | <button name="ship_cancel" states="shipping_except" string="Cancel document" icon="gtk-cancel" help="all the lines will be Cancelled where this status change is feasible" /> |
3497 | <button name="ask_resource_lines" states="draft,draft_p,validated,validated_p" string="Cancel document" type="object" icon="gtk-cancel" help="all the lines will be Cancelled where this status change is feasible" /> |
3498 | - <button name="invoice_cancel" states="invoice_except" string="Cancel document" icon="gtk-cancel" help="all the lines will be Cancelled where this status change is feasible" /> |
3499 | <button name="order_confirm" states="validated" string="Confirm document" icon="gtk-apply" invisible="True" help="all the lines will be Confirmed where this status change is feasible" /> |
3500 | <button name="do_order_confirm_method" type="object" states="validated" string="Confirm document" help="all the lines will be Confirmed where this status change is feasible" icon="gtk-apply" confirm="You are about to confirm the Field Order without going through the sourcing tool. Are you sure?" attrs="{'readonly': [('no_line', '=', True)]}"/> |
3501 | <button name="validate_lines" type="object" string="Validate document" icon="terp-check" states="draft,draft_p" attrs="{'readonly': [('no_line', '=', True)]}" help="all the lines will be Validated where this status change is feasible" /> |
3502 | |
3503 | === modified file 'bin/addons/sale/sale_workflow.py' |
3504 | --- bin/addons/sale/sale_workflow.py 2019-07-24 09:39:53 +0000 |
3505 | +++ bin/addons/sale/sale_workflow.py 2019-07-30 10:04:49 +0000 |
3506 | @@ -529,15 +529,15 @@ |
3507 | |
3508 | def check_fo_tax(self, cr, uid, ids, context=None): |
3509 | """ |
3510 | - Prevents from validating a FO with taxes when using an Intermission partner |
3511 | + Prevents from validating a FO with taxes when using an Intermission or Intersection partner |
3512 | """ |
3513 | if context is None: |
3514 | context = {} |
3515 | if isinstance(ids, (int, long)): |
3516 | ids = [ids] |
3517 | for fo_line in self.browse(cr, uid, ids, fields_to_fetch=['order_id', 'tax_id'], context=context): |
3518 | - if fo_line.tax_id and fo_line.order_id.partner_type == 'intermission': |
3519 | - raise osv.except_osv(_('Error'), _("You can't use taxes with an intermission partner.")) |
3520 | + if fo_line.tax_id and fo_line.order_id.partner_type in ('intermission', 'section'): |
3521 | + raise osv.except_osv(_('Error'), _("Taxes are forbidden with Intermission and Intersection partners.")) |
3522 | |
3523 | def action_validate(self, cr, uid, ids, context=None): |
3524 | ''' |
3525 | |
3526 | === modified file 'bin/addons/stock/stock.py' |
3527 | --- bin/addons/stock/stock.py 2019-06-17 14:48:35 +0000 |
3528 | +++ bin/addons/stock/stock.py 2019-07-30 10:04:49 +0000 |
3529 | @@ -1230,6 +1230,7 @@ |
3530 | 'company_id': picking.company_id.id, |
3531 | 'user_id':uid, |
3532 | 'picking_id': picking.id, |
3533 | + 'from_supply': True, |
3534 | } |
3535 | if picking.sale_id: |
3536 | if not partner.property_account_position.id: |
3537 | @@ -1323,6 +1324,13 @@ |
3538 | if origin_ivi: |
3539 | invoice_vals.update({'origin': origin_ivi}) |
3540 | |
3541 | + # Add "synced" tag for STV and IVO created from Supply flow |
3542 | + out_invoice = inv_type == 'out_invoice' |
3543 | + is_stv = out_invoice and not di and not inkind_donation and not intermission |
3544 | + is_ivo = out_invoice and not debit_note and not inkind_donation and intermission |
3545 | + if is_stv or is_ivo: |
3546 | + invoice_vals.update({'synced': True, }) |
3547 | + |
3548 | # Update Payment terms and due date for the Supplier Invoices and Refunds |
3549 | if is_si or inv_type == 'in_refund': |
3550 | si_payment_term = self._get_payment_term(cr, uid, picking) |
3551 | |
3552 | === modified file 'bin/addons/stock_override/stock.py' |
3553 | --- bin/addons/stock_override/stock.py 2019-06-17 14:48:35 +0000 |
3554 | +++ bin/addons/stock_override/stock.py 2019-07-30 10:04:49 +0000 |
3555 | @@ -944,6 +944,11 @@ |
3556 | if sp.type == 'out' and sp.partner_id.partner_type == 'external' and invoice_type != 'in_refund': |
3557 | res = False |
3558 | |
3559 | + # Move in on an intermission or intersection partner should not create an IVI / SI (generation of Donations shouldn't be blocked) |
3560 | + if sp.type == 'in' and sp.purchase_id and sp.purchase_id.order_type not in ('donation_st', 'donation_exp') \ |
3561 | + and sp.partner_id and sp.partner_id.partner_type in ('intermission', 'section') and invoice_type == 'in_invoice': |
3562 | + res = False |
3563 | + |
3564 | return res |
3565 | |
3566 | def _create_invoice(self, cr, uid, stock_picking): |
3567 | |
3568 | === modified file 'bin/addons/sync_so/picking.py' |
3569 | --- bin/addons/sync_so/picking.py 2019-06-17 09:06:48 +0000 |
3570 | +++ bin/addons/sync_so/picking.py 2019-07-30 10:04:49 +0000 |
3571 | @@ -316,10 +316,7 @@ |
3572 | if shipment: |
3573 | shipment_ref = shipment['name'] # shipment made |
3574 | else: |
3575 | - #UFTP-332: Check if name is really an OUT, because DPO could have PICk but no SHIP nor OUT --> do not link this PICK to IN |
3576 | shipment_ref = pick_dict.get('name', False) # the case of OUT |
3577 | - if shipment_ref and 'OUT' not in shipment_ref: |
3578 | - shipment_ref = False |
3579 | if not po_id and pick_dict.get('sale_id') and pick_dict.get('sale_id', {}).get('claim_name_goods_return'): |
3580 | po_sync_name = pick_dict.get('sale_id', {}).get('client_order_ref') |
3581 | if po_sync_name: |
3582 | @@ -756,6 +753,9 @@ |
3583 | so_po_common = self.pool.get('so.po.common') |
3584 | so_po_common.create_invalid_recovery_message(cr, uid, source, in_name, context) |
3585 | return "Recovery: the reference to " + in_name + " at " + source + " will be set to void." |
3586 | + elif 'PICK' in out_doc_name: |
3587 | + return "Msg ignored" |
3588 | + |
3589 | if message: |
3590 | self._logger.info(message) |
3591 | return message |
3592 | |
3593 | === modified file 'bin/addons/sync_so/specific_xml_id.py' |
3594 | --- bin/addons/sync_so/specific_xml_id.py 2019-03-01 13:32:06 +0000 |
3595 | +++ bin/addons/sync_so/specific_xml_id.py 2019-07-30 10:04:49 +0000 |
3596 | @@ -8,6 +8,7 @@ |
3597 | from osv import fields |
3598 | from product_nomenclature.product_nomenclature import RANDOM_XMLID_CODE_PREFIX |
3599 | import time |
3600 | +import netsvc |
3601 | |
3602 | # Note: |
3603 | # |
3604 | @@ -619,15 +620,26 @@ |
3605 | return True |
3606 | if context is None: |
3607 | context = {} |
3608 | + |
3609 | + # if unreconcile linked to paid/close invoice, then reopen SI |
3610 | + invoice_reopen = [] |
3611 | + if context.get('sync_update_execution') and 'reconcile_id' in vals and not vals['reconcile_id']: |
3612 | + move_lines = self.browse(cr, uid, ids, fields_to_fetch=['invoice', 'reconcile_id'], context=context) |
3613 | + invoice_reopen = [line.invoice.id for line in move_lines if line.reconcile_id and line.invoice and line.invoice.state in ['paid','inv_close']] |
3614 | + |
3615 | res = super(account_move_line, self).write(cr, uid, ids, vals, context=context, check=check, update_check=update_check) |
3616 | # Do workflow if line is coming from sync, is now reconciled and it has an unpaid invoice |
3617 | if context.get('sync_update_execution', False) and 'reconcile_id' in vals and vals['reconcile_id']: |
3618 | invoice_ids = [] |
3619 | - line_list = self.browse(cr, uid, ids, context=context) |
3620 | + line_list = self.browse(cr, uid, ids, fields_to_fetch=['invoice'], context=context) |
3621 | invoice_ids = [line.invoice.id for line in line_list if |
3622 | - line.invoice and line.invoice.state != 'paid'] |
3623 | + line.invoice and line.invoice.state not in ('paid','inv_close')] |
3624 | if self.pool.get('account.invoice').test_paid(cr, uid, invoice_ids): |
3625 | self.pool.get('account.invoice').confirm_paid(cr, uid, invoice_ids) |
3626 | + |
3627 | + if invoice_reopen: |
3628 | + netsvc.LocalService("workflow").trg_validate(uid, 'account.invoice', invoice_reopen, 'open_test', cr) |
3629 | + |
3630 | return res |
3631 | |
3632 | account_move_line() |
3633 | |
3634 | === modified file 'bin/addons/vertical_integration/report/report_open_invoices.py' |
3635 | --- bin/addons/vertical_integration/report/report_open_invoices.py 2013-06-11 15:17:55 +0000 |
3636 | +++ bin/addons/vertical_integration/report/report_open_invoices.py 2019-07-30 10:04:49 +0000 |
3637 | @@ -20,7 +20,6 @@ |
3638 | |
3639 | from spreadsheet_xml.spreadsheet_xml_write import SpreadsheetReport |
3640 | from report import report_sxw |
3641 | -from tools.translate import _ |
3642 | |
3643 | |
3644 | class report_open_invoices2(report_sxw.rml_parse): |
3645 | @@ -50,7 +49,7 @@ |
3646 | LEFT JOIN res_users responsible ON invoice.user_id = responsible.id |
3647 | LEFT JOIN res_currency currency ON invoice.currency_id = currency.id |
3648 | WHERE |
3649 | - invoice.state NOT IN ('paid', 'cancel') AND |
3650 | + invoice.state NOT IN ('paid', 'inv_close', 'cancel') AND |
3651 | invoice.type = %s |
3652 | ORDER BY invoice.date_invoice |
3653 | """ |