Allow copying move from closed period

Closes #13361
This commit is contained in:
Cédric Krier
2024-06-26 09:39:26 +02:00
parent b1e1034db1
commit b41ee38f1a
5 changed files with 145 additions and 3 deletions
+1
View File
@@ -1,3 +1,4 @@
* Allow copying move from closed period
* Replace Accounting Party by Accounting group
Version 7.2.0 - 2024-04-29
+4
View File
@@ -81,6 +81,10 @@ class MoveTemplateKeywordValidationError(ValidationError):
pass
class CopyWarning(UserWarning):
pass
class CancelWarning(UserWarning):
pass
+4
View File
@@ -134,6 +134,10 @@ this repository contains the full copyright notices and license terms. -->
<record model="ir.message" id="msg_modify_posted_moved">
<field name="text">You cannot modify posted move "%(move)s".</field>
</record>
<record model="ir.message" id="msg_move_copy_closed_period">
<field name="text">The period of move "%(move)s" is closed.
Use the current period to copy the move?</field>
</record>
<record model="ir.message" id="msg_move_cancel_closed_period">
<field name="text">The period of move "%(move)s" is closed.
Use the current period to cancel the move?</field>
+41 -3
View File
@@ -27,9 +27,10 @@ from trytond.wizard import (
Button, StateAction, StateTransition, StateView, Wizard)
from .exceptions import (
AccountMissing, CancelDelegatedWarning, CancelWarning, DelegateLineError,
GroupLineError, JournalMissing, PeriodNotFoundError, PostError,
ReconciliationDeleteWarning, ReconciliationError, RescheduleLineError)
AccountMissing, CancelDelegatedWarning, CancelWarning, CopyWarning,
DelegateLineError, GroupLineError, JournalMissing, PeriodNotFoundError,
PostError, ReconciliationDeleteWarning, ReconciliationError,
RescheduleLineError)
_MOVE_STATES = {
'readonly': Eval('state') == 'posted',
@@ -335,14 +336,51 @@ class Move(DescriptionOriginMixin, ModelSQL, ModelView):
@classmethod
def copy(cls, moves, default=None):
pool = Pool()
Date = pool.get('ir.date')
Period = pool.get('account.period')
Warning = pool.get('res.user.warning')
if default is None:
default = {}
else:
default = default.copy()
def _check_period(origin):
period = Period(origin['period'])
if period.state == 'closed':
move = cls(origin['id'])
key = Warning.format('copy', [move])
if Warning.check(key):
raise CopyWarning(key,
gettext('account.msg_move_copy_closed_period',
move=move))
return False
else:
return True
def default_period(origin):
if not _check_period(origin):
with Transaction().set_context(company=origin['company']):
today = Date.today()
period = Period.find(origin['company'], date=today)
return period.id
else:
return origin['period']
def default_date(origin):
if not _check_period(origin):
with Transaction().set_context(company=origin['company']):
return Date.today()
else:
return origin['date']
default.setdefault('number', None)
default.setdefault('post_number', None)
default.setdefault('state', cls.default_state())
default.setdefault('post_date', None)
default.setdefault('period', default_period)
default.setdefault('date', default_date)
return super().copy(moves, default=default)
@classmethod
@@ -0,0 +1,95 @@
==================
Move Copy Scenario
==================
Imports::
>>> from decimal import Decimal
>>> from proteus import Model
>>> from trytond.modules.account.tests.tools import (
... create_chart, create_fiscalyear, get_accounts)
>>> from trytond.modules.company.tests.tools import create_company
>>> from trytond.tests.tools import (
... activate_modules, assertEqual, assertNotEqual, assertTrue)
Activate modules::
>>> config = activate_modules('account')
>>> Journal = Model.get('account.journal')
>>> Move = Model.get('account.move')
>>> Party = Model.get('party.party')
Create a company::
>>> _ = create_company()
Create a fiscal year::
>>> fiscalyear = create_fiscalyear()
>>> fiscalyear.click('create_period')
>>> period = fiscalyear.periods[0]
Create a chart of accounts::
>>> _ = create_chart()
>>> accounts = get_accounts()
Create a party::
>>> party = Party(name="Party")
>>> party.save()
Create a posted move::
>>> move = Move()
>>> move.period = period
>>> move.journal, = Journal.find([('code', '=', 'REV')])
>>> move.date = period.start_date
>>> line = move.lines.new()
>>> line.account = accounts['revenue']
>>> line.credit = Decimal(42)
>>> line = move.lines.new()
>>> line.account = accounts['receivable']
>>> line.debit = Decimal(42)
>>> line.party = party
>>> move.save()
>>> move.click('post')
>>> move.state
'posted'
Copy move on open period::
>>> copy_move, = move.duplicate()
>>> assertTrue(copy_move.number)
>>> copy_move.post_number
>>> copy_move.state
'draft'
>>> copy_move.post_date
>>> assertEqual(copy_move.period, move.period)
>>> assertEqual(copy_move.date, move.date)
>>> copy_move.delete()
Copy move on closed period::
>>> period.click('close')
>>> period.state
'closed'
>>> copy_move, = move.duplicate()
Traceback (most recent call last):
...
CopyWarning: ...
>>> config.skip_warning = True
>>> copy_move, = move.duplicate()
>>> assertTrue(copy_move.number)
>>> copy_move.post_number
>>> copy_move.state
'draft'
>>> copy_move.post_date
>>> assertNotEqual(copy_move.period, move.period)
>>> copy_move.period.state
'open'
>>> assertNotEqual(copy_move.date, move.date)