Beispiel #1
0
    def test_onchange_editable_compute_one2many(self):
        # create a record with a computed editable field ('edit') on lines
        record = self.env['test_new_api.compute_editable'].create({'line_ids': [(0, 0, {'value': 7})]})
        self.env.flush_all()
        line = record.line_ids
        self.assertRecordValues(line, [{'value': 7, 'edit': 7, 'count': 0}])

        # retrieve the onchange spec for calling 'onchange'
        spec = Form(record)._view['onchange']

        # The onchange on 'line_ids' should increment 'count' and keep the value
        # of 'edit' (this field should not be recomputed), whatever the order of
        # the fields in the dictionary.  This ensures that the value set by the
        # user on a computed editable field on a line is not lost.
        line_ids = [
            Command.update(line.id, {'value': 8, 'edit': 9, 'count': 0}),
            Command.create({'value': 8, 'edit': 9, 'count': 0}),
        ]
        result = record.onchange({'line_ids': line_ids}, 'line_ids', spec)
        expected = {'value': {
            'line_ids': [
                Command.clear(),
                Command.update(line.id, {'value': 8, 'edit': 9, 'count': 8}),
                Command.create({'value': 8, 'edit': 9, 'count': 8}),
            ],
        }}
        self.assertEqual(result, expected)

        # change dict order in lines, and try again
        line_ids = [
            (op, id_, dict(reversed(list(vals.items()))))
            for op, id_, vals in line_ids
        ]
        result = record.onchange({'line_ids': line_ids}, 'line_ids', spec)
        self.assertEqual(result, expected)
Beispiel #2
0
 def test_104_res_partner_recursion_indirect_cycle(self):
     """ Indirect hacky write to create cycle in children """
     p3b = self.p1.create({
         'name': 'Elmtree Grand-Child 1.2',
         'parent_id': self.p2.id
     })
     with self.assertRaises(ValidationError):
         self.p2.write({
             'child_ids': [
                 Command.update(self.p3.id, {'parent_id': p3b.id}),
                 Command.update(p3b.id, {'parent_id': self.p3.id})
             ]
         })
Beispiel #3
0
    def test_onchange_one2many_with_domain_on_related_field(self):
        """ test the value of the one2many field when defined with a domain on a related field"""
        discussion = self.env.ref('test_new_api.discussion_0')
        demo = self.user_demo

        # mimic UI behaviour, so we get subfields
        # (we need at least subfield: 'important_emails.important')
        view_info = self.Discussion.get_view(self.env.ref('test_new_api.discussion_form').id, 'form')
        field_onchange = self.Discussion._onchange_spec(view_info=view_info)
        self.assertEqual(field_onchange.get('messages'), '1')

        BODY = "What a beautiful day!"
        USER = self.env.user

        # create standalone email
        email = self.EmailMessage.create({
            'discussion': discussion.id,
            'name': "[%s] %s" % ('', USER.name),
            'body': BODY,
            'author': USER.id,
            'important': False,
            'email_to': demo.email,
        })

        # check if server-side cache is working correctly
        self.env.cache.invalidate()
        self.assertIn(email, discussion.emails)
        self.assertNotIn(email, discussion.important_emails)
        email.important = True
        self.assertIn(email, discussion.important_emails)

        # check that when trigger an onchange, we don't reset important emails
        # (force `invalidate` as but appear in onchange only when we get a cache
        # miss)
        self.env.cache.invalidate()
        self.assertEqual(len(discussion.messages), 4)
        values = {
            'name': "Foo Bar",
            'moderator': demo.id,
            'categories': [Command.link(cat.id) for cat in discussion.categories],
            'messages': [Command.link(msg.id) for msg in discussion.messages],
            'participants': [Command.link(usr.id) for usr in discussion.participants],
            'important_messages': [Command.link(msg.id) for msg in discussion.important_messages],
            'important_emails': [Command.link(eml.id) for eml in discussion.important_emails],
        }
        self.env.cache.invalidate()
        result = discussion.onchange(values, 'name', field_onchange)

        self.assertEqual(
            result['value']['important_emails'],
            [Command.clear(), Command.update(email.id, {
                'name': u'[Foo Bar] %s' % USER.name,
                'body': BODY,
                'author': USER.name_get()[0],
                'size': len(BODY),
                'important': True,
                'email_to': demo.email,
            })],
        )
Beispiel #4
0
 def create_company(self):
     self.ensure_one()
     if self.company_name:
         # Create parent company
         values = dict(name=self.company_name, is_company=True, vat=self.vat)
         values.update(self._update_fields_values(self._address_fields()))
         new_company = self.create(values)
         # Set new company as my parent
         self.write({
             'parent_id': new_company.id,
             'child_ids': [Command.update(partner_id, dict(parent_id=new_company.id)) for partner_id in self.child_ids.ids]
         })
     return True
Beispiel #5
0
 def test_write_4_one2many(self):
     """ Check that we can write on an inherited one2many field. """
     box = self.env.ref('test_inherits.box_a')
     box.write({'line_ids': [Command.create({'name': 'Line 1'})]})
     self.assertTrue(all(box.line_ids._ids))
     self.assertEqual(box.line_ids.mapped('name'), ['Line 1'])
     self.assertEqual(box.line_ids, box.unit_id.line_ids)
     box.flush()
     box.invalidate_cache(['line_ids'])
     box.write({'line_ids': [Command.create({'name': 'Line 2'})]})
     self.assertTrue(all(box.line_ids._ids))
     self.assertEqual(box.line_ids.mapped('name'), ['Line 1', 'Line 2'])
     self.assertEqual(box.line_ids, box.unit_id.line_ids)
     box.flush()
     box.invalidate_cache(['line_ids'])
     box.write({'line_ids': [Command.update(box.line_ids[0].id, {'name': 'First line'})]})
     self.assertTrue(all(box.line_ids._ids))
     self.assertEqual(box.line_ids.mapped('name'), ['First line', 'Line 2'])
     self.assertEqual(box.line_ids, box.unit_id.line_ids)
Beispiel #6
0
    def test_write_base_many2many(self):
        """ Write on many2many field. """
        rec1 = self.env['test_performance.base'].create({'name': 'X'})

        # create N tags on rec1: O(N) queries
        with self.assertQueryCount(4):
            rec1.invalidate_cache()
            rec1.write({'tag_ids': [Command.create({'name': 0})]})
        self.assertEqual(len(rec1.tag_ids), 1)

        with self.assertQueryCount(14):
            rec1.invalidate_cache()
            rec1.write({
                'tag_ids':
                [Command.create({'name': val}) for val in range(1, 12)]
            })
        self.assertEqual(len(rec1.tag_ids), 12)

        tags = rec1.tag_ids

        # update N tags: O(N) queries
        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec1.write({
                'tag_ids':
                [Command.update(tag.id, {'name': 'X'}) for tag in tags[0]]
            })
        self.assertEqual(rec1.tag_ids, tags)

        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec1.write({
                'tag_ids':
                [Command.update(tag.id, {'name': 'X'}) for tag in tags[1:]]
            })
        self.assertEqual(rec1.tag_ids, tags)

        # delete N tags: O(1) queries
        with self.assertQueryCount(__system__=8, demo=8):
            rec1.invalidate_cache()
            rec1.write(
                {'tag_ids': [Command.delete(tag.id) for tag in tags[0]]})
        self.assertEqual(rec1.tag_ids, tags[1:])

        with self.assertQueryCount(__system__=8, demo=8):
            rec1.invalidate_cache()
            rec1.write(
                {'tag_ids': [Command.delete(tag.id) for tag in tags[1:]]})
        self.assertFalse(rec1.tag_ids)
        self.assertFalse(tags.exists())

        rec1.write(
            {'tag_ids': [Command.create({'name': val}) for val in range(12)]})
        tags = rec1.tag_ids

        # unlink N tags: O(1) queries
        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec1.write(
                {'tag_ids': [Command.unlink(tag.id) for tag in tags[0]]})
        self.assertEqual(rec1.tag_ids, tags[1:])

        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec1.write(
                {'tag_ids': [Command.unlink(tag.id) for tag in tags[1:]]})
        self.assertFalse(rec1.tag_ids)
        self.assertTrue(tags.exists())

        rec2 = self.env['test_performance.base'].create({'name': 'X'})

        # link N tags from rec1 to rec2: O(1) queries
        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.link(tag.id) for tag in tags[0]]})
        self.assertEqual(rec2.tag_ids, tags[0])

        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.link(tag.id) for tag in tags[1:]]})
        self.assertEqual(rec2.tag_ids, tags)

        with self.assertQueryCount(2):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.link(tag.id) for tag in tags[1:]]})
        self.assertEqual(rec2.tag_ids, tags)

        # empty N tags in rec2: O(1) queries
        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.clear()]})
        self.assertFalse(rec2.tag_ids)
        self.assertTrue(tags.exists())

        with self.assertQueryCount(2):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.clear()]})
        self.assertFalse(rec2.tag_ids)

        # set N tags in rec2: O(1) queries
        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.set(tags.ids)]})
        self.assertEqual(rec2.tag_ids, tags)

        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.set(tags[:8].ids)]})
        self.assertEqual(rec2.tag_ids, tags[:8])

        with self.assertQueryCount(4):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.set(tags[4:].ids)]})
        self.assertEqual(rec2.tag_ids, tags[4:])

        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.set(tags.ids)]})
        self.assertEqual(rec2.tag_ids, tags)

        with self.assertQueryCount(2):
            rec1.invalidate_cache()
            rec2.write({'tag_ids': [Command.set(tags.ids)]})
        self.assertEqual(rec2.tag_ids, tags)
Beispiel #7
0
    def test_write_base_one2many(self):
        """ Write on one2many field. """
        rec1 = self.env['test_performance.base'].create({'name': 'X'})

        # create N lines on rec1: O(N) queries
        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec1.write({'line_ids': [Command.create({'value': 0})]})
        self.assertEqual(len(rec1.line_ids), 1)

        with self.assertQueryCount(15):
            rec1.invalidate_cache()
            rec1.write({
                'line_ids':
                [Command.create({'value': val}) for val in range(1, 12)]
            })
        self.assertEqual(len(rec1.line_ids), 12)

        lines = rec1.line_ids

        # update N lines: O(N) queries
        with self.assertQueryCount(6):
            rec1.invalidate_cache()
            rec1.write({
                'line_ids':
                [Command.update(line.id, {'value': 42}) for line in lines[0]]
            })
        self.assertEqual(rec1.line_ids, lines)

        with self.assertQueryCount(26):
            rec1.invalidate_cache()
            rec1.write({
                'line_ids': [
                    Command.update(line.id, {'value': 42 + line.id})
                    for line in lines[1:]
                ]
            })
        self.assertEqual(rec1.line_ids, lines)

        # delete N lines: O(1) queries
        with self.assertQueryCount(14):
            rec1.invalidate_cache()
            rec1.write(
                {'line_ids': [Command.delete(line.id) for line in lines[0]]})
        self.assertEqual(rec1.line_ids, lines[1:])

        with self.assertQueryCount(12):
            rec1.invalidate_cache()
            rec1.write(
                {'line_ids': [Command.delete(line.id) for line in lines[1:]]})
        self.assertFalse(rec1.line_ids)
        self.assertFalse(lines.exists())

        rec1.write({
            'line_ids': [Command.create({'value': val}) for val in range(12)]
        })
        lines = rec1.line_ids

        # unlink N lines: O(1) queries
        with self.assertQueryCount(14):
            rec1.invalidate_cache()
            rec1.write(
                {'line_ids': [Command.unlink(line.id) for line in lines[0]]})
        self.assertEqual(rec1.line_ids, lines[1:])

        with self.assertQueryCount(12):
            rec1.invalidate_cache()
            rec1.write(
                {'line_ids': [Command.unlink(line.id) for line in lines[1:]]})
        self.assertFalse(rec1.line_ids)
        self.assertFalse(lines.exists())

        rec1.write({
            'line_ids': [Command.create({'value': val}) for val in range(12)]
        })
        lines = rec1.line_ids
        rec2 = self.env['test_performance.base'].create({'name': 'X'})

        # link N lines from rec1 to rec2: O(1) queries
        with self.assertQueryCount(8):
            rec1.invalidate_cache()
            rec2.write(
                {'line_ids': [Command.link(line.id) for line in lines[0]]})
        self.assertEqual(rec1.line_ids, lines[1:])
        self.assertEqual(rec2.line_ids, lines[0])

        with self.assertQueryCount(8):
            rec1.invalidate_cache()
            rec2.write(
                {'line_ids': [Command.link(line.id) for line in lines[1:]]})
        self.assertFalse(rec1.line_ids)
        self.assertEqual(rec2.line_ids, lines)

        with self.assertQueryCount(4):
            rec1.invalidate_cache()
            rec2.write(
                {'line_ids': [Command.link(line.id) for line in lines[0]]})
        self.assertEqual(rec2.line_ids, lines)

        with self.assertQueryCount(4):
            rec1.invalidate_cache()
            rec2.write(
                {'line_ids': [Command.link(line.id) for line in lines[1:]]})
        self.assertEqual(rec2.line_ids, lines)

        # empty N lines in rec2: O(1) queries
        with self.assertQueryCount(13):
            rec1.invalidate_cache()
            rec2.write({'line_ids': [Command.clear()]})
        self.assertFalse(rec2.line_ids)

        with self.assertQueryCount(3):
            rec1.invalidate_cache()
            rec2.write({'line_ids': [Command.clear()]})
        self.assertFalse(rec2.line_ids)

        rec1.write({
            'line_ids': [Command.create({'value': val}) for val in range(12)]
        })
        lines = rec1.line_ids

        # set N lines in rec2: O(1) queries
        with self.assertQueryCount(8):
            rec1.invalidate_cache()
            rec2.write({'line_ids': [Command.set(lines[0].ids)]})
        self.assertEqual(rec1.line_ids, lines[1:])
        self.assertEqual(rec2.line_ids, lines[0])

        with self.assertQueryCount(6):
            rec1.invalidate_cache()
            rec2.write({'line_ids': [Command.set(lines.ids)]})
        self.assertFalse(rec1.line_ids)
        self.assertEqual(rec2.line_ids, lines)

        with self.assertQueryCount(4):
            rec1.invalidate_cache()
            rec2.write({'line_ids': [Command.set(lines.ids)]})
        self.assertEqual(rec2.line_ids, lines)
Beispiel #8
0
    def _str_to_one2many(self, model, field, records):
        name_create_enabled_fields = self._context.get(
            'name_create_enabled_fields') or {}
        prefix = field.name + '/'
        relative_name_create_enabled_fields = {
            k[len(prefix):]: v
            for k, v in name_create_enabled_fields.items()
            if k.startswith(prefix)
        }
        commands = []
        warnings = []

        if len(records) == 1 and exclude_ref_fields(records[0]) == {}:
            # only one row with only ref field, field=ref1,ref2,ref3 as in
            # m2o/m2m
            record = records[0]
            subfield, ws = self._referencing_subfield(record)
            warnings.extend(ws)
            # transform [{subfield:ref1,ref2,ref3}] into
            # [{subfield:ref1},{subfield:ref2},{subfield:ref3}]
            records = ({
                subfield: item
            } for item in record[subfield].split(','))

        def log(f, exception):
            if not isinstance(exception, Warning):
                current_field_name = self.env[
                    field.comodel_name]._fields[f].string
                arg0 = exception.args[0] % {
                    'field': '%(field)s/' + current_field_name
                }
                exception.args = (arg0, *exception.args[1:])
                raise exception
            warnings.append(exception)

        # Complete the field hierarchy path
        # E.g. For "parent/child/subchild", field hierarchy path for "subchild" is ['parent', 'child']
        parent_fields_hierarchy = self._context.get('parent_fields_hierarchy',
                                                    []) + [field.name]

        convert = self.with_context(
            name_create_enabled_fields=relative_name_create_enabled_fields,
            parent_fields_hierarchy=parent_fields_hierarchy).for_model(
                self.env[field.comodel_name])

        for record in records:
            id = None
            refs = only_ref_fields(record)
            writable = convert(exclude_ref_fields(record), log)
            if refs:
                subfield, w1 = self._referencing_subfield(refs)
                warnings.extend(w1)
                try:
                    id, _, w2 = self.db_id_for(model, field, subfield,
                                               record[subfield])
                    warnings.extend(w2)
                except ValueError:
                    if subfield != 'id':
                        raise
                    writable['id'] = record['id']

            if id:
                commands.append(Command.link(id))
                commands.append(Command.update(id, writable))
            else:
                commands.append(Command.create(writable))

        return commands, warnings
Beispiel #9
0
    def test_event_create_wtype(self):
        """ Test a single event creation with a type defining all sub records. """
        event_type = self.env['event.type'].browse(self.test_event_type.ids)

        event_values = dict(
            self.event_base_vals,
            event_type_id=event_type.id,
        )
        event = self.env['event.event'].create([event_values])
        event.write({
            'event_ticket_ids': [
                Command.update(
                    event.event_ticket_ids[0].id,
                    {
                        'start_sale_datetime':
                        self.reference_now + timedelta(hours=1)
                    },
                ),
                Command.update(
                    event.event_ticket_ids[1].id,
                    {
                        'start_sale_datetime':
                        self.reference_now + timedelta(hours=2)
                    },
                )
            ],
        })

        # check result
        self.assertEqual(event.address_id, self.env.user.company_id.partner_id)
        self.assertTrue(event.auto_confirm)
        self.assertEqual(event.country_id, self.env.user.company_id.country_id)
        self.assertEqual(event.date_tz, 'Europe/Paris')
        self.assertEqual(event.event_booth_count, 4)
        self.assertEqual(len(event.event_mail_ids), 3)
        self.assertEqual(len(event.event_ticket_ids), 2)
        self.assertTrue(event.introduction_menu)
        self.assertTrue(event.location_menu)
        self.assertTrue(event.menu_register_cta)
        self.assertEqual(
            event.message_partner_ids,
            self.env.user.partner_id + self.env.user.company_id.partner_id)
        self.assertEqual(event.note, '<p>Template note</p>')
        self.assertTrue(event.register_menu)
        self.assertEqual(len(event.question_ids), 3)
        self.assertTrue(event.seats_limited)
        self.assertEqual(event.seats_max, 30)
        self.assertEqual(event.stage_id, self.stage_def)
        self.assertEqual(event.tag_ids, self.tags)
        self.assertTrue(event.website_menu)

        # check time dependent computation: before event
        with freeze_time(self.reference_now):
            self.assertFalse(event.is_finished)
            self.assertFalse(event.is_ongoing)
            self.assertFalse(event.event_registrations_started)

        # check time dependent computation: registrations started
        with freeze_time(self.reference_now + timedelta(hours=1)):
            event.invalidate_model(
                ['is_finished', 'is_ongoing', 'event_registrations_started'])
            self.assertFalse(event.is_finished)
            self.assertFalse(event.is_ongoing)
            self.assertTrue(event.event_registrations_started)

        # check time dependent computation: during event
        with freeze_time(self.reference_now + timedelta(days=1, hours=1)):
            event.invalidate_model(
                ['is_finished', 'is_ongoing', 'event_registrations_started'])
            self.assertFalse(event.is_finished)
            self.assertTrue(event.is_ongoing)
            self.assertTrue(event.event_registrations_started)
    def test_affect_base_amount_1(self):
        tax_20_affect = self.env['account.tax'].create({
            'name': "tax_20_affect",
            'amount_type': 'percent',
            'amount': 20.0,
            'include_base_amount': True,
        })
        tax_10 = self.env['account.tax'].create({
            'name': "tax_10",
            'amount_type': 'percent',
            'amount': 10.0,
        })
        tax_5 = self.env['account.tax'].create({
            'name': "tax_5",
            'amount_type': 'percent',
            'amount': 5.0,
        })

        invoice = self.env['account.move'].create({
            'move_type': 'out_invoice',
            'partner_id': self.partner_a.id,
            'invoice_date': '2019-01-01',
            'invoice_line_ids': [
                Command.create({
                    'name': 'line1',
                    'account_id': self.company_data['default_account_revenue'].id,
                    'price_unit': 1000.0,
                    'tax_ids': [Command.set((tax_20_affect + tax_10 + tax_5).ids)],
                }),
                Command.create({
                    'name': 'line2',
                    'account_id': self.company_data['default_account_revenue'].id,
                    'price_unit': 1000.0,
                    'tax_ids': [Command.set(tax_10.ids)],
                }),
                Command.create({
                    'name': 'line3',
                    'account_id': self.company_data['default_account_revenue'].id,
                    'price_unit': 1000.0,
                    'tax_ids': [Command.set(tax_10.ids)],
                }),
                Command.create({
                    'name': 'line4',
                    'account_id': self.company_data['default_account_revenue'].id,
                    'price_unit': 2000.0,
                    'tax_ids': [Command.set((tax_20_affect + tax_10).ids)],
                }),
            ]
        })
        base_lines, tax_lines = self._dispatch_move_lines(invoice)

        tax_details = self._get_tax_details()
        self.assertTaxDetailsValues(tax_details, [
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[2].id,
                'base_amount': -200.0,
                'tax_amount': -10.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[1].id,
                'base_amount': -200.0,
                'tax_amount': -20.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[2].id,
                'base_amount': -1000.0,
                'tax_amount': -50.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[1].id,
                'base_amount': -1000.0,
                'tax_amount': -100.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[0].id,
                'base_amount': -1000.0,
                'tax_amount': -200.0,
            },
            {
                'base_line_id': base_lines[1].id,
                'tax_line_id': tax_lines[1].id,
                'base_amount': -1000.0,
                'tax_amount': -100.0,
            },
            {
                'base_line_id': base_lines[2].id,
                'tax_line_id': tax_lines[1].id,
                'base_amount': -1000.0,
                'tax_amount': -100.0,
            },
            {
                'base_line_id': base_lines[3].id,
                'tax_line_id': tax_lines[1].id,
                'base_amount': -400.0,
                'tax_amount': -40.0,
            },
            {
                'base_line_id': base_lines[3].id,
                'tax_line_id': tax_lines[1].id,
                'base_amount': -2000.0,
                'tax_amount': -200.0,
            },
            {
                'base_line_id': base_lines[3].id,
                'tax_line_id': tax_lines[3].id,
                'base_amount': -2000.0,
                'tax_amount': -400.0,
            },
        ])
        self.assertTotalAmounts(invoice, tax_details)

        # Same with a group of taxes

        tax_group = self.env['account.tax'].create({
            'name': "tax_group",
            'amount_type': 'group',
            'children_tax_ids': [Command.set((tax_20_affect + tax_10 + tax_5).ids)],
        })

        invoice.write({
            'invoice_line_ids': [Command.update(base_lines[0].id, {
                'tax_ids': [Command.set(tax_group.ids)],
            })],
        })

        base_lines, tax_lines = self._dispatch_move_lines(invoice)

        tax_details = self._get_tax_details()
        self.assertTaxDetailsValues(tax_details, [
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[4].id,
                'base_amount': -200.0,
                'tax_amount': -10.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[3].id,
                'base_amount': -200.0,
                'tax_amount': -20.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[4].id,
                'base_amount': -1000.0,
                'tax_amount': -50.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[3].id,
                'base_amount': -1000.0,
                'tax_amount': -100.0,
            },
            {
                'base_line_id': base_lines[0].id,
                'tax_line_id': tax_lines[2].id,
                'base_amount': -1000.0,
                'tax_amount': -200.0,
            },
            {
                'base_line_id': base_lines[1].id,
                'tax_line_id': tax_lines[0].id,
                'base_amount': -1000.0,
                'tax_amount': -100.0,
            },
            {
                'base_line_id': base_lines[2].id,
                'tax_line_id': tax_lines[0].id,
                'base_amount': -1000.0,
                'tax_amount': -100.0,
            },
            {
                'base_line_id': base_lines[3].id,
                'tax_line_id': tax_lines[0].id,
                'base_amount': -400.0,
                'tax_amount': -40.0,
            },
            {
                'base_line_id': base_lines[3].id,
                'tax_line_id': tax_lines[0].id,
                'base_amount': -2000.0,
                'tax_amount': -200.0,
            },
            {
                'base_line_id': base_lines[3].id,
                'tax_line_id': tax_lines[1].id,
                'base_amount': -2000.0,
                'tax_amount': -400.0,
            },
        ])
        self.assertTotalAmounts(invoice, tax_details)
    def test_zero_amount_tax(self):
        """ Ensure the tax details is generated for 0% tax. """
        zero_tax = self.env['account.tax'].create({
            'name': "zero_tax",
            'amount_type': 'percent',
            'amount': 0.0,
        })

        invoice = self.env['account.move'].create({
            'move_type': 'out_invoice',
            'partner_id': self.partner_a.id,
            'invoice_date': '2019-01-01',
            'invoice_line_ids': [
                Command.create({
                    'name': 'line1',
                    'account_id': self.company_data['default_account_revenue'].id,
                    'price_unit': 1000.0,
                    'tax_ids': [Command.set(zero_tax.ids)],
                }),
                Command.create({
                    'name': 'line2',
                    'account_id': self.company_data['default_account_revenue'].id,
                    'price_unit': 1000.0,
                    'tax_ids': [Command.set(zero_tax.ids)],
                }),
            ]
        })
        base_lines, tax_lines = self._dispatch_move_lines(invoice)

        tax_details = self._get_tax_details()
        self.assertTaxDetailsValues(
            tax_details,
            [
                {
                    'base_line_id': base_lines[0].id,
                    'tax_line_id': tax_lines[0].id,
                    'base_amount': -1000.0,
                    'tax_amount': 0.0,
                },
                {
                    'base_line_id': base_lines[1].id,
                    'tax_line_id': tax_lines[0].id,
                    'base_amount': -1000.0,
                    'tax_amount': 0.0,
                },
            ],
        )
        self.assertTotalAmounts(invoice, tax_details)

        # Same with a group of taxes

        tax_group = self.env['account.tax'].create({
            'name': "tax_group",
            'amount_type': 'group',
            'children_tax_ids': [Command.set(zero_tax.ids)],
        })

        invoice.write({
            'invoice_line_ids': [
                Command.update(base_lines[0].id, {'tax_ids': [Command.set(tax_group.ids)]}),
                Command.update(base_lines[1].id, {'tax_ids': [Command.set(tax_group.ids)]}),
            ],
        })
        base_lines, tax_lines = self._dispatch_move_lines(invoice)

        tax_details = self._get_tax_details()
        self.assertTaxDetailsValues(
            tax_details,
            [
                {
                    'base_line_id': base_lines[0].id,
                    'tax_line_id': tax_lines[0].id,
                    'base_amount': -1000.0,
                    'tax_amount': 0.0,
                },
                {
                    'base_line_id': base_lines[1].id,
                    'tax_line_id': tax_lines[0].id,
                    'base_amount': -1000.0,
                    'tax_amount': 0.0,
                },
            ],
        )
        self.assertTotalAmounts(invoice, tax_details)
Beispiel #12
0
    def test_onchange_one2many_multi(self):
        """ test the effect of multiple onchange methods on one2many fields """
        partner1 = self.env['res.partner'].create({'name': 'A partner'})
        multi = self.env['test_new_api.multi'].create({'partner': partner1.id})
        line1 = multi.lines.create({'multi': multi.id})

        field_onchange = multi._onchange_spec()
        self.assertEqual(
            field_onchange, {
                'name': '1',
                'partner': '1',
                'lines': None,
                'lines.name': None,
                'lines.partner': None,
                'lines.tags': None,
                'lines.tags.name': None,
            })

        values = multi._convert_to_write(
            {key: multi[key]
             for key in ('name', 'partner', 'lines')})
        self.assertEqual(
            values, {
                'name': partner1.name,
                'partner': partner1.id,
                'lines': [Command.set([line1.id])],
            })

        # modify 'partner'
        #   -> set 'partner' on all lines
        #   -> recompute 'name'
        #       -> set 'name' on all lines
        partner2 = self.env['res.partner'].create({'name': 'A second partner'})
        values = {
            'name':
            partner1.name,
            'partner':
            partner2.id,  # this one just changed
            'lines': [
                Command.set([line1.id]),
                Command.create({
                    'name': False,
                    'partner': False,
                    'tags': [Command.clear()]
                })
            ],
        }
        self.env.cache.invalidate()

        result = multi.onchange(values, 'partner', field_onchange)
        self.assertEqual(
            result['value'], {
                'name':
                partner2.name,
                'lines': [
                    Command.clear(),
                    Command.update(
                        line1.id, {
                            'name': partner2.name,
                            'partner': (partner2.id, partner2.name),
                            'tags': [Command.clear()],
                        }),
                    Command.create({
                        'name': partner2.name,
                        'partner': (partner2.id, partner2.name),
                        'tags': [Command.clear()],
                    }),
                ],
            })

        # do it again, but this time with a new tag on the second line
        values = {
            'name':
            partner1.name,
            'partner':
            partner2.id,  # this one just changed
            'lines': [
                Command.set([line1.id]),
                Command.create({
                    'name':
                    False,
                    'partner':
                    False,
                    'tags': [Command.clear(),
                             Command.create({'name': 'Tag'})]
                })
            ],
        }
        self.env.cache.invalidate()
        result = multi.onchange(values, 'partner', field_onchange)
        expected_value = {
            'name':
            partner2.name,
            'lines': [
                Command.clear(),
                Command.update(
                    line1.id, {
                        'name': partner2.name,
                        'partner': (partner2.id, partner2.name),
                        'tags': [Command.clear()],
                    }),
                Command.create({
                    'name':
                    partner2.name,
                    'partner': (partner2.id, partner2.name),
                    'tags': [Command.clear(),
                             Command.create({'name': 'Tag'})],
                }),
            ],
        }
        self.assertEqual(result['value'], expected_value)

        # ensure ID is not returned when asked and a many2many record is set to be created
        self.env.cache.invalidate()

        result = multi.onchange(
            values, 'partner', dict(field_onchange, **{'lines.tags.id': None}))
        self.assertEqual(result['value'], expected_value)

        # ensure inverse of one2many field is not returned
        self.env.cache.invalidate()

        result = multi.onchange(values, 'partner',
                                dict(field_onchange, **{'lines.multi': None}))
        self.assertEqual(result['value'], expected_value)
Beispiel #13
0
    def test_onchange_one2many(self):
        """ test the effect of onchange() on one2many fields """
        USER = self.env.user

        # create an independent message
        message1 = self.Message.create({'body': "ABC"})
        message2 = self.Message.create({'body': "ABC"})
        self.assertEqual(message1.name, "[%s] %s" % ('', USER.name))

        field_onchange = self.Discussion._onchange_spec()
        self.assertEqual(field_onchange.get('name'), '1')
        self.assertEqual(field_onchange.get('messages'), '1')
        self.assertItemsEqual(
            strip_prefix('messages.', field_onchange),
            ['author', 'body', 'name', 'size', 'important'],
        )

        # modify discussion name
        values = {
            'name':
            "Foo",
            'categories': [],
            'moderator':
            False,
            'participants': [],
            'messages': [
                Command.link(message1.id),
                Command.link(message2.id),
                Command.update(message2.id, {'body': "XYZ"}),
                Command.create({
                    'name': "[%s] %s" % ('', USER.name),
                    'body': "ABC",
                    'author': USER.id,
                    'size': 3,
                    'important': False,
                }),
            ],
        }
        self.env.cache.invalidate()
        result = self.Discussion.onchange(values, 'name', field_onchange)
        self.assertIn('messages', result['value'])
        self.assertEqual(
            result['value']['messages'],
            [
                Command.clear(),
                Command.update(
                    message1.id, {
                        'name': "[%s] %s" % ("Foo", USER.name),
                        'body': "ABC",
                        'author': USER.name_get()[0],
                        'size': 3,
                        'important': False,
                    }),
                Command.update(
                    message2.id,
                    {
                        'name': "[%s] %s" % ("Foo", USER.name),
                        'body': "XYZ",  # this must be sent back
                        'author': USER.name_get()[0],
                        'size': 3,
                        'important': False,
                    }),
                Command.create({
                    'name': "[%s] %s" % ("Foo", USER.name),
                    'body': "ABC",
                    'author': USER.name_get()[0],
                    'size': 3,
                    'important': False,
                }),
            ])

        # ensure onchange changing one2many without subfield works
        one_level_fields = {
            k: v
            for k, v in field_onchange.items() if k.count('.') < 1
        }
        values = dict(values, name='{generate_dummy_message}')
        result = self.Discussion.with_context(
            generate_dummy_message=True).onchange(values, 'name',
                                                  one_level_fields)
        self.assertEqual(result['value']['messages'], [
            Command.clear(),
            Command.link(message1.id),
            Command.link(message2.id),
            Command.create({}),
            Command.create({}),
        ])