[MERGE] forward port branch 11.0 up to bdc62d8031
This commit is contained in:
@@ -238,6 +238,7 @@ class AccountMove(models.Model):
|
||||
@api.multi
|
||||
def _reverse_move(self, date=None, journal_id=None, auto=False):
|
||||
self.ensure_one()
|
||||
date = date or fields.Date.today()
|
||||
with self.env.norecompute():
|
||||
reversed_move = self.copy(default={
|
||||
'date': date,
|
||||
@@ -502,8 +503,8 @@ class AccountMoveLine(models.Model):
|
||||
is_unaffected_earnings_line = fields.Boolean(string="Is Unaffected Earnings Line", compute="_compute_is_unaffected_earnings_line", help="Tells whether or not this line belongs to an unaffected earnings account")
|
||||
|
||||
_sql_constraints = [
|
||||
('credit_debit1', 'CHECK (credit*debit=0)', 'Wrong credit or debit value in accounting entry !'),
|
||||
('credit_debit2', 'CHECK (credit+debit>=0)', 'Wrong credit or debit value in accounting entry !'),
|
||||
('credit_debit1', 'CHECK (credit*debit=0)', 'Wrong credit or debit value in accounting entry! Credit or debit should be zero.'),
|
||||
('credit_debit2', 'CHECK (credit+debit>=0)', 'Wrong credit or debit value in accounting entry! Credit and debit should be positive.'),
|
||||
]
|
||||
|
||||
@api.model
|
||||
|
||||
@@ -500,17 +500,12 @@ class AccountAssetDepreciationLine(models.Model):
|
||||
@api.multi
|
||||
def create_move(self, post_move=True):
|
||||
created_moves = self.env['account.move']
|
||||
# `line.move_id` was invalidated from the cache at each iteration
|
||||
# To prevent to refetch `move_id` of all lines at each iteration just to check a UserError,
|
||||
# we use an intermediar dict which stores the information the UserError check requires.
|
||||
line_moves = {line: line.move_id for line in self}
|
||||
if self.mapped('move_id'):
|
||||
raise UserError(_('This depreciation is already linked to a journal entry! Please post or delete it.'))
|
||||
for line in self:
|
||||
if line_moves[line]:
|
||||
raise UserError(_('This depreciation is already linked to a journal entry! Please post or delete it.'))
|
||||
move_vals = self._prepare_move(line)
|
||||
move = self.env['account.move'].create(move_vals)
|
||||
line.write({'move_id': move.id, 'move_check': True})
|
||||
line_moves[line] = move
|
||||
created_moves |= move
|
||||
|
||||
if post_move and created_moves:
|
||||
|
||||
@@ -162,7 +162,7 @@
|
||||
<div class="o_row">
|
||||
<field name="end_type" attrs="{'required': [('recurrency', '=', True)]}"/>
|
||||
<field name="count" attrs="{'invisible': [('end_type', '!=', 'count')], 'required': [('recurrency', '=', True)]}"/>
|
||||
<field name="final_date" attrs="{'invisible': [('end_type', '!=', 'end_date')], 'required': [('end_type', '=', 'end_date')]}"/>
|
||||
<field name="final_date" attrs="{'invisible': [('end_type', '!=', 'end_date')], 'required': [('end_type', '=', 'end_date'), ('recurrency', '=', True)]}"/>
|
||||
</div>
|
||||
</group>
|
||||
<group attrs="{'invisible': [('rrule_type', '!=', 'weekly')]}" name="weekdays">
|
||||
@@ -182,10 +182,10 @@
|
||||
attrs="{'required': [('month_by', '=', 'date'), ('rrule_type', '=', 'monthly')],
|
||||
'invisible': [('month_by', '!=', 'date')]}"/>
|
||||
<field name="byday" string="The"
|
||||
attrs="{'required': [('month_by', '=', 'day'), ('rrule_type', '=', 'monthly')],
|
||||
attrs="{'required': [('recurrency', '=', True), ('month_by', '=', 'day'), ('rrule_type', '=', 'monthly')],
|
||||
'invisible': [('month_by', '!=', 'day')]}"/>
|
||||
<field name="week_list" nolabel="1"
|
||||
attrs="{'required': [('month_by', '=', 'day'), ('rrule_type', '=', 'monthly')],
|
||||
attrs="{'required': [('recurrency', '=', True), ('month_by', '=', 'day'), ('rrule_type', '=', 'monthly')],
|
||||
'invisible': [('month_by', '!=', 'day')]}"/>
|
||||
</div>
|
||||
</group>
|
||||
|
||||
@@ -10,6 +10,7 @@ Adds the possibility to specify the origin country of goods and the partner VAT
|
||||
'depends': ['l10n_be_intrastat'],
|
||||
'data': [
|
||||
'views/account_invoice_line_view.xml',
|
||||
'views/report_invoice.xml',
|
||||
],
|
||||
'auto_install': True,
|
||||
}
|
||||
|
||||
@@ -0,0 +1,33 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<odoo>
|
||||
<template id="report_invoice_document_intrastat_2019" inherit_id="account.report_invoice_document">
|
||||
<xpath expr="//th[@class='hidden']" position="after">
|
||||
<th class="text-right">Origin Country</th>
|
||||
</xpath>
|
||||
<xpath expr="//td[@class='hidden']" position="after">
|
||||
<td class="text-right">
|
||||
<span t-field="l.intrastat_product_origin_country_id"/>
|
||||
</td>
|
||||
</xpath>
|
||||
</template>
|
||||
<template id="report_intrastatinvoice_document_2019" inherit_id="report_intrastat.report_intrastatinvoice_document">
|
||||
<xpath expr="//th[4]" position="after">
|
||||
<th class="text-right">Origin Country</th>
|
||||
</xpath>
|
||||
<xpath expr="//td[4]" position="after">
|
||||
<td class="text-right">
|
||||
<span t-field="l.intrastat_product_origin_country_id"/>
|
||||
</td>
|
||||
</xpath>
|
||||
</template>
|
||||
<template id="report_invoice_layouted_intrastat_2019" inherit_id="sale.report_invoice_layouted">
|
||||
<xpath expr="//t[@groups='sale.group_sale_layout']//th[1]" position="after">
|
||||
<th class="text-right">Origin Country</th>
|
||||
</xpath>
|
||||
<xpath expr="//t[@groups='sale.group_sale_layout']//t[@t-as='l']//td[1]" position="after">
|
||||
<td class="text-right">
|
||||
<span t-field="l.intrastat_product_origin_country_id"/>
|
||||
</td>
|
||||
</xpath>
|
||||
</template>
|
||||
</odoo>
|
||||
@@ -2077,212 +2077,230 @@
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_04_new' model='account.account.tag'>
|
||||
<field name='name'>401.04 Ventas y/o servicios gravados realizados en zona fronteriza norte</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_05_new' model='account.account.tag'>
|
||||
<field name='name'>401.05 Ventas y/o servicios gravados realizados en zona fronteriza norte de contado</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_06_new' model='account.account.tag'>
|
||||
<field name='name'>401.06 Ventas y/o servicios gravados realizados en zona fronteriza norte a crédito</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_04' model='account.account.tag'>
|
||||
<field name='name'>401.04 Ventas y/o servicios gravados al 0%</field>
|
||||
<field name='name'>401.07 Ventas y/o servicios gravados al 0%</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_05' model='account.account.tag'>
|
||||
<field name='name'>401.05 Ventas y/o servicios gravados al 0% de contado</field>
|
||||
<field name='name'>401.08 Ventas y/o servicios gravados al 0% de contado</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_06' model='account.account.tag'>
|
||||
<field name='name'>401.06 Ventas y/o servicios gravados al 0% a crédito</field>
|
||||
<field name='name'>401.09 Ventas y/o servicios gravados al 0% a crédito</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_07' model='account.account.tag'>
|
||||
<field name='name'>401.07 Ventas y/o servicios exentos</field>
|
||||
<field name='name'>401.10 Ventas y/o servicios exentos</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_08' model='account.account.tag'>
|
||||
<field name='name'>401.08 Ventas y/o servicios exentos de contado</field>
|
||||
<field name='name'>401.11 Ventas y/o servicios exentos de contado</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_09' model='account.account.tag'>
|
||||
<field name='name'>401.09 Ventas y/o servicios exentos a crédito</field>
|
||||
<field name='name'>401.12 Ventas y/o servicios exentos a crédito</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_10' model='account.account.tag'>
|
||||
<field name='name'>401.10 Ventas y/o servicios gravados a la tasa general nacionales partes relacionadas</field>
|
||||
<field name='name'>401.13 Ventas y/o servicios gravados a la tasa general nacionales partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_11' model='account.account.tag'>
|
||||
<field name='name'>401.11 Ventas y/o servicios gravados a la tasa general extranjeros partes relacionadas</field>
|
||||
<field name='name'>401.14 Ventas y/o servicios gravados a la tasa general extranjeros partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_12' model='account.account.tag'>
|
||||
<field name='name'>401.12 Ventas y/o servicios gravados al 0% nacionales partes relacionadas</field>
|
||||
<field name='name'>401.15 Ventas y/o servicios gravados al 0% nacionales partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_13' model='account.account.tag'>
|
||||
<field name='name'>401.13 Ventas y/o servicios gravados al 0% extranjeros partes relacionadas</field>
|
||||
<field name='name'>401.16 Ventas y/o servicios gravados al 0% extranjeros partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_14' model='account.account.tag'>
|
||||
<field name='name'>401.14 Ventas y/o servicios exentos nacionales partes relacionadas</field>
|
||||
<field name='name'>401.17 Ventas y/o servicios exentos nacionales partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_15' model='account.account.tag'>
|
||||
<field name='name'>401.15 Ventas y/o servicios exentos extranjeros partes relacionadas</field>
|
||||
<field name='name'>401.18 Ventas y/o servicios exentos extranjeros partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_16' model='account.account.tag'>
|
||||
<field name='name'>401.16 Ingresos por servicios administrativos</field>
|
||||
<field name='name'>401.19 Ingresos por servicios administrativos</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_17' model='account.account.tag'>
|
||||
<field name='name'>401.17 Ingresos por servicios administrativos nacionales partes relacionadas</field>
|
||||
<field name='name'>401.20 Ingresos por servicios administrativos nacionales partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_18' model='account.account.tag'>
|
||||
<field name='name'>401.18 Ingresos por servicios administrativos extranjeros partes relacionadas</field>
|
||||
<field name='name'>401.21 Ingresos por servicios administrativos extranjeros partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_19' model='account.account.tag'>
|
||||
<field name='name'>401.19 Ingresos por servicios profesionales</field>
|
||||
<field name='name'>401.22 Ingresos por servicios profesionales</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_20' model='account.account.tag'>
|
||||
<field name='name'>401.20 Ingresos por servicios profesionales nacionales partes relacionadas</field>
|
||||
<field name='name'>401.23 Ingresos por servicios profesionales nacionales partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_21' model='account.account.tag'>
|
||||
<field name='name'>401.21 Ingresos por servicios profesionales extranjeros partes relacionadas</field>
|
||||
<field name='name'>401.24 Ingresos por servicios profesionales extranjeros partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_22' model='account.account.tag'>
|
||||
<field name='name'>401.22 Ingresos por arrendamiento</field>
|
||||
<field name='name'>401.25 Ingresos por arrendamiento</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_23' model='account.account.tag'>
|
||||
<field name='name'>401.23 Ingresos por arrendamiento nacionales partes relacionadas</field>
|
||||
<field name='name'>401.26 Ingresos por arrendamiento nacionales partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_24' model='account.account.tag'>
|
||||
<field name='name'>401.24 Ingresos por arrendamiento extranjeros partes relacionadas</field>
|
||||
<field name='name'>401.27 Ingresos por arrendamiento extranjeros partes relacionadas</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_25' model='account.account.tag'>
|
||||
<field name='name'>401.25 Ingresos por exportación</field>
|
||||
<field name='name'>401.28 Ingresos por exportación</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_26' model='account.account.tag'>
|
||||
<field name='name'>401.26 Ingresos por comisiones</field>
|
||||
<field name='name'>401.29 Ingresos por comisiones</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_27' model='account.account.tag'>
|
||||
<field name='name'>401.27 Ingresos por maquila</field>
|
||||
<field name='name'>401.30 Ingresos por maquila</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_28' model='account.account.tag'>
|
||||
<field name='name'>401.28 Ingresos por coordinados</field>
|
||||
<field name='name'>401.31 Ingresos por coordinados</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_29' model='account.account.tag'>
|
||||
<field name='name'>401.29 Ingresos por regalías</field>
|
||||
<field name='name'>401.32 Ingresos por regalías</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_30' model='account.account.tag'>
|
||||
<field name='name'>401.30 Ingresos por asistencia técnica</field>
|
||||
<field name='name'>401.33 Ingresos por asistencia técnica</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_31' model='account.account.tag'>
|
||||
<field name='name'>401.31 Ingresos por donativos</field>
|
||||
<field name='name'>401.34 Ingresos por donativos</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_32' model='account.account.tag'>
|
||||
<field name='name'>401.32 Ingresos por intereses (actividad propia)</field>
|
||||
<field name='name'>401.35 Ingresos por intereses (actividad propia)</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_33' model='account.account.tag'>
|
||||
<field name='name'>401.33 Ingresos de copropiedad</field>
|
||||
<field name='name'>401.36 Ingresos de copropiedad</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_34' model='account.account.tag'>
|
||||
<field name='name'>401.34 Ingresos por fideicomisos</field>
|
||||
<field name='name'>401.37 Ingresos por fideicomisos</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_35' model='account.account.tag'>
|
||||
<field name='name'>401.35 Ingresos por factoraje financiero</field>
|
||||
<field name='name'>401.38 Ingresos por factoraje financiero</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_36' model='account.account.tag'>
|
||||
<field name='name'>401.36 Ingresos por arrendamiento financiero</field>
|
||||
<field name='name'>401.39 Ingresos por arrendamiento financiero</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_37' model='account.account.tag'>
|
||||
<field name='name'>401.37 Ingresos de extranjeros con establecimiento en el país</field>
|
||||
<field name='name'>401.40 Ingresos de extranjeros con establecimiento en el país</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
</record>
|
||||
<record id='account_tag_401_38' model='account.account.tag'>
|
||||
<field name='name'>401.38 Otros ingresos propios</field>
|
||||
<field name='name'>401.41 Otros ingresos propios</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>A</field>
|
||||
@@ -2293,20 +2311,26 @@
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>D</field>
|
||||
</record>
|
||||
<record id='account_tag_402_02_new' model='account.account.tag'>
|
||||
<field name='name'>402.02 Devoluciones, descuentos o bonificaciones sobre ventas y/o servicios en zona fronteriza norte</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>D</field>
|
||||
</record>
|
||||
<record id='account_tag_402_02' model='account.account.tag'>
|
||||
<field name='name'>402.02 Devoluciones, descuentos o bonificaciones sobre ventas y/o servicios al 0%</field>
|
||||
<field name='name'>402.03 Devoluciones, descuentos o bonificaciones sobre ventas y/o servicios al 0%</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>D</field>
|
||||
</record>
|
||||
<record id='account_tag_402_03' model='account.account.tag'>
|
||||
<field name='name'>402.03 Devoluciones, descuentos o bonificaciones sobre ventas y/o servicios exentos</field>
|
||||
<field name='name'>402.04 Devoluciones, descuentos o bonificaciones sobre ventas y/o servicios exentos</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>D</field>
|
||||
</record>
|
||||
<record id='account_tag_402_04' model='account.account.tag'>
|
||||
<field name='name'>402.04 Devoluciones, descuentos o bonificaciones de otros ingresos</field>
|
||||
<field name='name'>402.05 Devoluciones, descuentos o bonificaciones de otros ingresos</field>
|
||||
<field name='color'>4</field>
|
||||
<field name='applicability'>accounts</field>
|
||||
<field name='nature'>D</field>
|
||||
|
||||
@@ -170,7 +170,7 @@ class AcquirerAdyen(models.Model):
|
||||
'sessionValidity': tmp_date.isoformat('T')[:19] + "Z",
|
||||
'resURL': urls.url_join(base_url, AdyenController._return_url),
|
||||
'merchantReturnData': json.dumps({'return_url': '%s' % values.pop('return_url')}) if values.get('return_url', '') else False,
|
||||
'shopperEmail': values.get('partner_email', ''),
|
||||
'shopperEmail': values.get('partner_email') or values.get('billing_partner_email') or '',
|
||||
})
|
||||
values['merchantSig'] = self._adyen_generate_merchant_sig_sha256('in', values)
|
||||
|
||||
|
||||
@@ -85,9 +85,9 @@ class AccountInvoice(models.Model):
|
||||
self.currency_id = self.purchase_id.currency_id
|
||||
|
||||
vendor_ref = self.purchase_id.partner_ref
|
||||
if vendor_ref:
|
||||
self.reference = ", ".join([self.reference, vendor_ref]) if (
|
||||
self.reference and vendor_ref not in self.reference) else vendor_ref
|
||||
if vendor_ref and (not self.reference or (
|
||||
vendor_ref + ", " not in self.reference and not self.reference.endswith(vendor_ref))):
|
||||
self.reference = ", ".join([self.reference, vendor_ref]) if self.reference else vendor_ref
|
||||
|
||||
new_lines = self.env['account.invoice.line']
|
||||
for line in self.purchase_id.order_line - self.invoice_line_ids.mapped('purchase_line_id'):
|
||||
|
||||
@@ -1021,11 +1021,15 @@ class ProcurementRule(models.Model):
|
||||
if price_unit and seller and line.order_id.currency_id and seller.currency_id != line.order_id.currency_id:
|
||||
price_unit = seller.currency_id.compute(price_unit, line.order_id.currency_id)
|
||||
|
||||
return {
|
||||
res = {
|
||||
'product_qty': line.product_qty + procurement_uom_po_qty,
|
||||
'price_unit': price_unit,
|
||||
'move_dest_ids': [(4, x.id) for x in values.get('move_dest_ids', [])]
|
||||
}
|
||||
orderpoint_id = values.get('orderpoint_id')
|
||||
if orderpoint_id:
|
||||
res['orderpoint_id'] = orderpoint_id.id
|
||||
return res
|
||||
|
||||
@api.multi
|
||||
def _prepare_purchase_order_line(self, product_id, product_qty, product_uom, values, po, partner):
|
||||
|
||||
@@ -170,7 +170,7 @@ class Route(models.Model):
|
||||
@api.onchange('warehouse_selectable')
|
||||
def _onchange_warehouse_selectable(self):
|
||||
if not self.warehouse_selectable:
|
||||
self.warehouse_ids = []
|
||||
self.warehouse_ids = [(5, 0, 0)]
|
||||
|
||||
def write(self, values):
|
||||
'''when a route is deactivated, deactivate also its pull and push rules'''
|
||||
|
||||
@@ -1186,6 +1186,7 @@ var AbstractFieldBinary = AbstractField.extend({
|
||||
}
|
||||
},
|
||||
on_clear: function () {
|
||||
this.$('.o_input_file').val('');
|
||||
this.set_filename('');
|
||||
this._setValue(false);
|
||||
this._render();
|
||||
|
||||
@@ -1718,6 +1718,35 @@ QUnit.module('basic_fields', {
|
||||
list.destroy();
|
||||
});
|
||||
|
||||
QUnit.test("binary fields input value is empty whean clearing after uploading", function (assert) {
|
||||
assert.expect(2);
|
||||
|
||||
var form = createView({
|
||||
View: FormView,
|
||||
model: 'partner',
|
||||
data: this.data,
|
||||
arch: '<form string="Partners">' +
|
||||
'<field name="document" filename="foo"/>' +
|
||||
'<field name="foo"/>' +
|
||||
'</form>',
|
||||
res_id: 1,
|
||||
});
|
||||
|
||||
form.$buttons.find('.btn:contains("Edit")').click();
|
||||
// // We need to convert the input type since we can't programmatically set the value of a file input
|
||||
form.$('.o_input_file').attr('type', 'text').val('coucou.txt');
|
||||
|
||||
assert.strictEqual(form.$('.o_input_file').val(), 'coucou.txt',
|
||||
"input value should be changed to \"coucou.txt\"");
|
||||
|
||||
form.$('.o_field_binary_file > .o_clear_file_button').click();
|
||||
|
||||
assert.strictEqual(form.$('.o_input_file').val(), '',
|
||||
"input value should be empty");
|
||||
|
||||
form.destroy();
|
||||
});
|
||||
|
||||
QUnit.test('field text in editable list view', function (assert) {
|
||||
assert.expect(1);
|
||||
|
||||
|
||||
@@ -1392,6 +1392,7 @@ var LinkDialog = Dialog.extend({
|
||||
}
|
||||
|
||||
this.data.range = range.create(sc, so, ec, eo);
|
||||
$(editable).data("range", this.data.range);
|
||||
this.data.range.select();
|
||||
} else {
|
||||
nodes = dom.ancestor(sc, dom.isAnchor).childNodes;
|
||||
|
||||
@@ -5,6 +5,7 @@ var FormView = require('web.FormView');
|
||||
var testUtils = require('web.test_utils');
|
||||
var core = require('web.core');
|
||||
var web_editor = require('web_editor.editor');
|
||||
var LinkDialog = require('web_editor.widget').LinkDialog;
|
||||
|
||||
var _t = core._t;
|
||||
|
||||
@@ -324,4 +325,64 @@ QUnit.test('html_frame saving in edit mode (editor and content fully loaded)', f
|
||||
|
||||
});
|
||||
|
||||
QUnit.test('discard on link dialog should select content of link in web_editor', function (assert) {
|
||||
var done = assert.async();
|
||||
assert.expect(5);
|
||||
|
||||
var form = testUtils.createView({
|
||||
View: FormView,
|
||||
model: 'mass.mailing',
|
||||
data: this.data,
|
||||
arch: '<form string="Partners">' +
|
||||
'<field name="body"/>' +
|
||||
'</form>',
|
||||
res_id: 1,
|
||||
});
|
||||
|
||||
form.$buttons.find('.o_form_button_edit').click();
|
||||
|
||||
assert.strictEqual(form.$('.note-editable').html(), '<div class="field_body">yep</div>',
|
||||
"should have rendered the field correctly in edit");
|
||||
|
||||
var $fieldEdit = form.$('.oe_form_field[name="body"]');
|
||||
var $editable = $fieldEdit.find('.field_body');
|
||||
|
||||
// create range, default startoffset:0, endOffset:length of element
|
||||
var range = document.createRange();
|
||||
var selection = window.getSelection();
|
||||
range.selectNodeContents($editable[0].childNodes[0]);
|
||||
selection.removeAllRanges();
|
||||
selection.addRange(range);
|
||||
|
||||
var content = selection.getRangeAt(range);
|
||||
assert.strictEqual(content.startOffset, 0, "selection starts at index 0");
|
||||
assert.strictEqual(content.endOffset, 3, "selection ends at index 3");
|
||||
|
||||
var defLinkDialog = $.Deferred();
|
||||
testUtils.patch(LinkDialog, {
|
||||
init: function () {
|
||||
this._super.apply(this, arguments);
|
||||
this.opened(defLinkDialog.resolve.bind(defLinkDialog));
|
||||
}
|
||||
});
|
||||
|
||||
// click on 'link' button
|
||||
$fieldEdit.find('.note-toolbar button[data-event="showLinkDialog"]').click();
|
||||
|
||||
defLinkDialog.then(function () {
|
||||
$('.modal .modal-footer .btn-default').click(); // click on 'discard'
|
||||
|
||||
var content = selection.getRangeAt(range);
|
||||
assert.strictEqual(content.startOffset, 0,
|
||||
"selection should remain same after discarding modal, starts at index 0");
|
||||
assert.strictEqual(content.endOffset, 3,
|
||||
"selection should remain same after discarding modal, ends at index 3");
|
||||
|
||||
testUtils.unpatch(LinkDialog);
|
||||
form.destroy();
|
||||
done();
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
});
|
||||
|
||||
@@ -93,7 +93,7 @@ class Website(Home):
|
||||
if request.env['res.users'].browse(request.uid).has_group('base.group_user'):
|
||||
redirect = b'/web?' + request.httprequest.query_string
|
||||
else:
|
||||
redirect = '/'
|
||||
redirect = '/my'
|
||||
return http.redirect_with_hash(redirect)
|
||||
return response
|
||||
|
||||
@@ -443,3 +443,8 @@ class WebsiteBinary(http.Controller):
|
||||
if unique:
|
||||
kw['unique'] = unique
|
||||
return Binary().content_image(**kw)
|
||||
|
||||
@http.route(['/favicon.ico'], type='http', auth='public', website=True)
|
||||
def favicon(self, **kw):
|
||||
# when opening a pdf in chrome, chrome tries to open the default favicon url
|
||||
return self.content_image(model='website', id=str(request.website.id), field='favicon', **kw)
|
||||
|
||||
@@ -0,0 +1,11 @@
|
||||
Mexico, 2018-12-05
|
||||
|
||||
I hereby agree to the terms of the Odoo Individual Contributor License
|
||||
Agreement v1.0.
|
||||
|
||||
I declare that I am authorized and able to make this agreement and sign this
|
||||
declaration.
|
||||
|
||||
Signed,
|
||||
|
||||
Luis Arturo Íñiguez Hernández luis.iniguezh@gmail.com https://github.com/luisiniguezh
|
||||
@@ -0,0 +1,11 @@
|
||||
Italy, 2019-06-04
|
||||
|
||||
I hereby agree to the terms of the Odoo Individual Contributor License
|
||||
Agreement v1.0.
|
||||
|
||||
I declare that I am authorized and able to make this agreement and sign this
|
||||
declaration.
|
||||
|
||||
Signed,
|
||||
|
||||
Michele Zaccheddu michelezak93@gmail.com https://github.com/MicheleZak
|
||||
@@ -737,3 +737,11 @@ class IrActionsActClient(models.Model):
|
||||
for record in self:
|
||||
params = record.params
|
||||
record.params_store = repr(params) if isinstance(params, dict) else params
|
||||
|
||||
def _get_default_form_view(self):
|
||||
doc = super(IrActionsActClient, self)._get_default_form_view()
|
||||
params = doc.find(".//field[@name='params']")
|
||||
params.getparent().remove(params)
|
||||
params_store = doc.find(".//field[@name='params_store']")
|
||||
params_store.getparent().remove(params_store)
|
||||
return doc
|
||||
|
||||
@@ -719,7 +719,7 @@ class IrModelFields(models.Model):
|
||||
else:
|
||||
if column_rename:
|
||||
raise UserError(_('Can only rename one field at a time!'))
|
||||
column_rename = (obj._table, item.name, vals['name'], item.index)
|
||||
column_rename = (obj._table, item.name, vals['name'], item.index, item.store)
|
||||
|
||||
# We don't check the 'state', because it might come from the context
|
||||
# (thus be set for multiple fields) and will be ignored anyway.
|
||||
@@ -737,10 +737,11 @@ class IrModelFields(models.Model):
|
||||
|
||||
if column_rename:
|
||||
# rename column in database, and its corresponding index if present
|
||||
table, oldname, newname, index = column_rename
|
||||
self._cr.execute('ALTER TABLE "%s" RENAME COLUMN "%s" TO "%s"' % (table, oldname, newname))
|
||||
if index:
|
||||
self._cr.execute('ALTER INDEX "%s_%s_index" RENAME TO "%s_%s_index"' % (table, oldname, table, newname))
|
||||
table, oldname, newname, index, stored = column_rename
|
||||
if stored:
|
||||
self._cr.execute('ALTER TABLE "%s" RENAME COLUMN "%s" TO "%s"' % (table, oldname, newname))
|
||||
if index:
|
||||
self._cr.execute('ALTER INDEX "%s_%s_index" RENAME TO "%s_%s_index"' % (table, oldname, table, newname))
|
||||
|
||||
if column_rename or patched_models:
|
||||
# setup models, this will reload all manual fields in registry
|
||||
|
||||
@@ -109,7 +109,7 @@
|
||||
</group>
|
||||
<group string="Advanced Properties" groups="base.group_no_one">
|
||||
<field name="related"/>
|
||||
<field name="depends"/>
|
||||
<field name="depends" attrs="{'required': [('compute', 'not in', [False, ''])]}"/>
|
||||
<field name="compute" widget="ace" options="{'mode': 'python'}"/>
|
||||
</group>
|
||||
<div groups="base.group_no_one">
|
||||
@@ -295,7 +295,7 @@
|
||||
</group>
|
||||
<group string="Advanced Properties" groups="base.group_no_one">
|
||||
<field name="related"/>
|
||||
<field name="depends" attrs="{'required': [('compute', '!=', False)] }"/>
|
||||
<field name="depends" attrs="{'required': [('compute', 'not in', [False, ''])]}"/>
|
||||
<field name="compute" widget="ace" options="{'mode': 'python'}"/>
|
||||
</group>
|
||||
<div groups="base.group_no_one">
|
||||
|
||||
@@ -0,0 +1,13 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
from odoo import api, SUPERUSER_ID
|
||||
|
||||
|
||||
# TO REMOVE in master
|
||||
def uninstall_test_pylint(cr):
|
||||
env = api.Environment(cr, SUPERUSER_ID, {})
|
||||
env['ir.module.module'].search([
|
||||
('name', '=', 'test_pylint'),
|
||||
('state', '=', 'installed')
|
||||
]).write({'state': 'uninstalled'})
|
||||
@@ -0,0 +1,12 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
{
|
||||
'name': 'test-lint',
|
||||
'version': '0.1',
|
||||
'category': 'Tests',
|
||||
'description': """A module to test Odoo code with various linters.""",
|
||||
'maintainer': 'Odoo SA',
|
||||
'depends': ['base'],
|
||||
'installable': True,
|
||||
'auto_install': False,
|
||||
'pre_init_hook': 'uninstall_test_pylint'
|
||||
}
|
||||
@@ -0,0 +1,2 @@
|
||||
from . import test_pylint
|
||||
from . import test_ecmascript
|
||||
@@ -0,0 +1,48 @@
|
||||
# -*- coding: utf-8 -*-
|
||||
# Part of Odoo. See LICENSE file for full copyright and licensing details.
|
||||
|
||||
import logging
|
||||
import os
|
||||
import re
|
||||
import subprocess
|
||||
from unittest import skipIf
|
||||
from odoo.tests.common import TransactionCase
|
||||
from odoo import tools
|
||||
from odoo.modules import get_modules, get_module_path
|
||||
|
||||
MAX_ES_VERSION = 'es5'
|
||||
|
||||
_logger = logging.getLogger(__name__)
|
||||
|
||||
try:
|
||||
es_check = tools.misc.find_in_path('es-check')
|
||||
except IOError:
|
||||
es_check = None
|
||||
|
||||
|
||||
@skipIf(es_check is None, "es-check tool not found on this system")
|
||||
class TestECMAScriptVersion(TransactionCase):
|
||||
|
||||
longMessage = True
|
||||
|
||||
def test_ecmascript_version(self):
|
||||
""" Test that there is no unsupported ecmascript in javascript files """
|
||||
|
||||
black_re = re.compile(r'summernote.+(intro\.js|outro.js)$')
|
||||
|
||||
mod_paths = [get_module_path(m) for m in get_modules()]
|
||||
files_to_check = []
|
||||
for p in mod_paths:
|
||||
for dp, _, file_names in os.walk(p):
|
||||
if 'static/test' in dp:
|
||||
continue
|
||||
for fn in file_names:
|
||||
fullpath_name = os.path.join(dp, fn)
|
||||
if fullpath_name.endswith('.js') and not black_re.search(fullpath_name):
|
||||
files_to_check.append(fullpath_name)
|
||||
|
||||
_logger.info('Testing %s js files', len(files_to_check))
|
||||
cmd = [es_check, MAX_ES_VERSION] + files_to_check
|
||||
process = subprocess.Popen(cmd, stdout=subprocess.PIPE, stderr=subprocess.PIPE)
|
||||
out, err = process.communicate()
|
||||
self.assertEqual(process.returncode, 0, msg=out)
|
||||
@@ -3,7 +3,7 @@
|
||||
'name': 'test-eval',
|
||||
'version': '0.1',
|
||||
'category': 'Tests',
|
||||
'description': """A module to test Odoo with pylint.""",
|
||||
'description': """Deprecated empty module in favor of test-lint.""",
|
||||
'maintainer': 'Odoo SA',
|
||||
'depends': ['base'],
|
||||
'installable': True,
|
||||
|
||||
@@ -1 +0,0 @@
|
||||
from . import test_pylint
|
||||
Reference in New Issue
Block a user