Files
tryton/account.py
T

274 lines
10 KiB
Python
Raw Normal View History

2009-01-02 17:54:34 +01:00
#This file is part of Tryton. The COPYRIGHT file at the top level of
#this repository contains the full copyright notices and license terms.
2012-09-24 22:17:32 +02:00
from trytond.model import fields
2011-08-21 11:20:30 +02:00
from trytond.pyson import Eval
2012-09-24 22:17:32 +02:00
from trytond.pool import Pool, PoolMeta
2012-09-29 15:34:34 +02:00
__all__ = ['FiscalYear', 'Period', 'Move', 'Reconciliation']
2012-09-24 22:17:32 +02:00
__metaclass__ = PoolMeta
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
class FiscalYear:
__name__ = 'account.fiscalyear'
2009-01-02 17:54:34 +01:00
out_invoice_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Customer Invoice Sequence', required=True,
domain=[
('code', '=', 'account.invoice'),
['OR',
('company', '=', Eval('company')),
2012-03-27 10:43:07 +02:00
('company', '=', None),
2010-01-20 10:57:08 +01:00
],
],
2011-08-04 16:57:16 +02:00
context={
'code': 'account.invoice',
'company': Eval('company'),
},
depends=['company'])
2009-01-02 17:54:34 +01:00
in_invoice_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Supplier Invoice Sequence', required=True,
domain=[
('code', '=', 'account.invoice'),
['OR',
('company', '=', Eval('company')),
2012-03-27 10:43:07 +02:00
('company', '=', None),
2010-01-20 10:57:08 +01:00
],
],
2011-08-04 16:57:16 +02:00
context={
'code': 'account.invoice',
'company': Eval('company'),
},
depends=['company'])
2009-01-02 17:54:34 +01:00
out_credit_note_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Customer Credit Note Sequence', required=True,
domain=[
('code', '=', 'account.invoice'),
['OR',
('company', '=', Eval('company')),
2012-03-27 10:43:07 +02:00
('company', '=', None),
2010-01-20 10:57:08 +01:00
],
],
2011-08-04 16:57:16 +02:00
context={
'code': 'account.invoice',
'company': Eval('company'),
}, depends=['company'])
2009-01-02 17:54:34 +01:00
in_credit_note_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Supplier Credit Note Sequence', required=True,
domain=[
('code', '=', 'account.invoice'),
['OR',
('company', '=', Eval('company')),
2012-03-27 10:43:07 +02:00
('company', '=', None),
2010-01-20 10:57:08 +01:00
],
],
2011-08-04 16:57:16 +02:00
context={
'code': 'account.invoice',
'company': Eval('company'),
}, depends=['company'])
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
@classmethod
def __setup__(cls):
super(FiscalYear, cls).__setup__()
cls._error_messages.update({
'change_invoice_sequence': 'You can not change '
'invoice sequence in fiscal year "%s" because there are '
'already posted invoices in this fiscal year.',
'different_invoice_sequence': 'Fiscal year "%(first)s" and '
'"%(second)s" have the same invoice sequence.',
2013-02-16 22:06:26 +01:00
})
2009-01-02 17:54:34 +01:00
@classmethod
def validate(cls, years):
super(FiscalYear, cls).validate(years)
for year in years:
year.check_invoice_sequences()
2012-09-24 22:17:32 +02:00
def check_invoice_sequences(self):
for sequence in ('out_invoice_sequence', 'in_invoice_sequence',
'out_credit_note_sequence', 'in_credit_note_sequence'):
fiscalyears = self.search([
(sequence, '=', getattr(self, sequence).id),
('id', '!=', self.id),
])
if fiscalyears:
self.raise_user_error('different_invoice_sequences', {
'first': self.rec_name,
'second': fiscalyears[0].rec_name,
})
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
@classmethod
def write(cls, fiscalyears, vals):
Invoice = Pool().get('account.invoice')
2010-04-08 14:15:58 +02:00
2009-01-02 17:54:34 +01:00
for sequence in ('out_invoice_sequence', 'in_invoice_sequence',
'out_credit_note_sequence', 'in_credit_note_sequence'):
if vals.get(sequence):
2012-09-24 22:17:32 +02:00
for fiscalyear in fiscalyears:
if (getattr(fiscalyear, sequence)
and (getattr(fiscalyear, sequence).id !=
vals[sequence])):
if Invoice.search([
('invoice_date', '>=',
fiscalyear.start_date),
('invoice_date', '<=',
fiscalyear.end_date),
('number', '!=', None),
('type', '=', sequence[:-9]),
]):
cls.raise_user_error('change_invoice_sequence',
(fiscalyear.rec_name,))
2012-09-24 22:17:32 +02:00
super(FiscalYear, cls).write(fiscalyears, vals)
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
class Period:
__name__ = 'account.period'
2009-01-02 17:54:34 +01:00
out_invoice_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Customer Invoice Sequence',
domain=[('code', '=', 'account.invoice')],
context={'code': 'account.invoice'},
states={
2011-08-21 11:20:30 +02:00
'invisible': Eval('type') != 'standard',
2011-08-04 16:57:16 +02:00
},
depends=['type'])
2009-01-02 17:54:34 +01:00
in_invoice_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Supplier Invoice Sequence',
domain=[('code', '=', 'account.invoice')],
context={'code': 'account.invoice'},
states={
2011-08-21 11:20:30 +02:00
'invisible': Eval('type') != 'standard',
2011-08-04 16:57:16 +02:00
},
depends=['type'])
2009-01-02 17:54:34 +01:00
out_credit_note_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Customer Credit Note Sequence',
domain=[('code', '=', 'account.invoice')],
context={'code': 'account.invoice'},
states={
2011-08-21 11:20:30 +02:00
'invisible': Eval('type') != 'standard',
2011-08-04 16:57:16 +02:00
},
depends=['type'])
2009-01-02 17:54:34 +01:00
in_credit_note_sequence = fields.Many2One('ir.sequence.strict',
2011-08-04 16:57:16 +02:00
'Supplier Credit Note Sequence',
domain=[('code', '=', 'account.invoice')],
context={'code': 'account.invoice'},
states={
2011-08-21 11:20:30 +02:00
'invisible': Eval('type') != 'standard',
2011-08-04 16:57:16 +02:00
},
depends=['type'])
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
@classmethod
def __setup__(cls):
super(Period, cls).__setup__()
cls._error_messages.update({
'change_invoice_sequence': 'You can not change the invoice '
'sequence in period "%s" because there is already an '
'invoice posted in this period',
'different_invoice_sequence': 'Period "%(first)s" and '
'"%(second)s" have the same invoice sequence.',
'different_period_fiscalyear_company': 'Period "%(period)s" '
'must have the same company as its fiscal year '
'(%(fiscalyear)s).'
2013-02-16 22:06:26 +01:00
})
2009-01-02 17:54:34 +01:00
@classmethod
def validate(cls, periods):
super(Period, cls).validate(periods)
for period in periods:
period.check_invoice_sequences()
2012-09-24 22:17:32 +02:00
def check_invoice_sequences(self):
for sequence_name in ('out_invoice_sequence', 'in_invoice_sequence',
'out_credit_note_sequence', 'in_credit_note_sequence'):
sequence = getattr(self, sequence_name)
2013-01-22 16:40:44 +01:00
if not sequence:
continue
periods = self.search([
(sequence_name, '=', sequence.id),
('fiscalyear', '!=', self.fiscalyear.id),
])
if periods:
self.raise_user_error('different_invoice_sequence', {
'first': self.rec_name,
'second': periods[0].rec_name,
})
2012-09-24 22:17:32 +02:00
if (sequence.company
and sequence.company != self.fiscalyear.company):
self.raise_user_error('different_period_fiscalyear_company', {
'period': self.rec_name,
'fiscalyear': self.fiscalyear.rec_name,
})
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
@classmethod
2013-01-06 22:18:13 +01:00
def create(cls, vlist):
2012-09-24 22:17:32 +02:00
FiscalYear = Pool().get('account.fiscalyear')
2013-01-06 22:18:13 +01:00
vlist = [v.copy() for v in vlist]
for vals in vlist:
if vals.get('fiscalyear'):
fiscalyear = FiscalYear(vals['fiscalyear'])
for sequence in ('out_invoice_sequence', 'in_invoice_sequence',
'out_credit_note_sequence', 'in_credit_note_sequence'):
if not vals.get(sequence):
vals[sequence] = getattr(fiscalyear, sequence).id
return super(Period, cls).create(vlist)
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
@classmethod
def write(cls, periods, vals):
Invoice = Pool().get('account.invoice')
2009-01-02 17:54:34 +01:00
2012-09-24 22:17:32 +02:00
for sequence_name in ('out_invoice_sequence', 'in_invoice_sequence',
2009-01-02 17:54:34 +01:00
'out_credit_note_sequence', 'in_credit_note_sequence'):
2012-09-24 22:17:32 +02:00
if vals.get(sequence_name):
for period in periods:
sequence = getattr(period, sequence_name)
if (sequence and
sequence.id != vals[sequence]):
if Invoice.search([
('invoice_date', '>=', period.start_date),
('invoice_date', '<=', period.end_date),
('number', '!=', None),
('type', '=', sequence_name[:-9]),
]):
cls.raise_user_error('change_invoice_sequence',
(period.rec_name,))
2012-09-24 22:17:32 +02:00
super(Period, cls).write(periods, vals)
2012-03-25 00:17:27 +01:00
2013-01-22 16:40:44 +01:00
def get_invoice_sequence(self, invoice_type):
sequence = getattr(self, invoice_type + '_sequence')
if sequence:
return sequence
return getattr(self.fiscalyear, invoice_type + '_sequence')
2012-03-25 00:17:27 +01:00
2012-09-29 15:34:34 +02:00
class Move:
__name__ = 'account.move'
@classmethod
def _get_origin(cls):
return super(Move, cls)._get_origin() + ['account.invoice']
2012-09-24 22:17:32 +02:00
class Reconciliation:
__name__ = 'account.move.reconciliation'
2012-03-25 00:17:27 +01:00
2012-09-24 22:17:32 +02:00
@classmethod
2013-01-06 22:18:13 +01:00
def create(cls, vlist):
2012-09-24 22:17:32 +02:00
Invoice = Pool().get('account.invoice')
2013-01-06 22:18:13 +01:00
reconciliations = super(Reconciliation, cls).create(vlist)
move_ids = set()
for reconciliation in reconciliations:
move_ids |= set(l.move.id for l in reconciliation.lines)
2012-09-24 22:17:32 +02:00
invoices = Invoice.search([
2012-03-25 00:17:27 +01:00
('move', 'in', list(move_ids)),
])
2012-09-24 22:17:32 +02:00
Invoice.process(invoices)
2013-01-06 22:18:13 +01:00
return reconciliations
2012-03-25 00:17:27 +01:00
2012-09-24 22:17:32 +02:00
@classmethod
def delete(cls, reconciliations):
Invoice = Pool().get('account.invoice')
2012-03-25 00:17:27 +01:00
move_ids = set(l.move.id for r in reconciliations for l in r.lines)
2012-09-24 22:17:32 +02:00
invoices = Invoice.search([
2012-03-25 00:17:27 +01:00
('move', 'in', list(move_ids)),
])
2012-09-24 22:17:32 +02:00
super(Reconciliation, cls).delete(reconciliations)
Invoice.process(invoices)