django-ledger 0.7.4__py3-none-any.whl → 0.7.5__py3-none-any.whl
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Potentially problematic release.
This version of django-ledger might be problematic. Click here for more details.
- django_ledger/__init__.py +1 -1
- django_ledger/contrib/django_ledger_graphene/bank_account/schema.py +1 -1
- django_ledger/forms/bank_account.py +16 -12
- django_ledger/forms/data_import.py +70 -33
- django_ledger/io/io_core.py +945 -127
- django_ledger/io/io_generator.py +7 -3
- django_ledger/io/ofx.py +37 -16
- django_ledger/migrations/0020_remove_bankaccountmodel_django_ledg_cash_ac_59a8af_idx_and_more.py +44 -0
- django_ledger/migrations/0021_alter_bankaccountmodel_account_model_and_more.py +33 -0
- django_ledger/models/bank_account.py +14 -11
- django_ledger/models/customer.py +3 -13
- django_ledger/models/data_import.py +690 -35
- django_ledger/models/entity.py +39 -24
- django_ledger/models/journal_entry.py +18 -8
- django_ledger/models/mixins.py +17 -3
- django_ledger/models/vendor.py +2 -2
- django_ledger/settings.py +18 -22
- django_ledger/templates/django_ledger/bank_account/tags/bank_accounts_table.html +2 -2
- django_ledger/templates/django_ledger/data_import/data_import_job_txs.html +1 -1
- django_ledger/templates/django_ledger/data_import/import_job_create.html +11 -2
- django_ledger/templates/django_ledger/data_import/tags/data_import_job_txs_imported.html +1 -1
- django_ledger/templates/django_ledger/data_import/tags/data_import_job_txs_table.html +5 -2
- django_ledger/templatetags/django_ledger.py +12 -12
- django_ledger/views/bank_account.py +1 -1
- django_ledger/views/data_import.py +60 -134
- {django_ledger-0.7.4.dist-info → django_ledger-0.7.5.dist-info}/METADATA +17 -17
- {django_ledger-0.7.4.dist-info → django_ledger-0.7.5.dist-info}/RECORD +31 -29
- {django_ledger-0.7.4.dist-info → django_ledger-0.7.5.dist-info}/WHEEL +1 -1
- {django_ledger-0.7.4.dist-info → django_ledger-0.7.5.dist-info}/top_level.txt +1 -0
- {django_ledger-0.7.4.dist-info → django_ledger-0.7.5.dist-info}/AUTHORS.md +0 -0
- {django_ledger-0.7.4.dist-info → django_ledger-0.7.5.dist-info}/LICENSE +0 -0
django_ledger/models/entity.py
CHANGED
|
@@ -1518,8 +1518,10 @@ class EntityModelAbstract(MP_Node,
|
|
|
1518
1518
|
return coa_model, coa_model.create_account(**account_model_kwargs)
|
|
1519
1519
|
|
|
1520
1520
|
# ### LEDGER MANAGEMENT ####
|
|
1521
|
-
def get_ledgers(self, posted: bool =
|
|
1522
|
-
|
|
1521
|
+
def get_ledgers(self, posted: Optional[bool] = None):
|
|
1522
|
+
if posted is not None:
|
|
1523
|
+
return self.ledgermodel_set.filter(posted=posted)
|
|
1524
|
+
return self.ledgermodel_set.all()
|
|
1523
1525
|
|
|
1524
1526
|
# ### JOURNAL ENTRY MANAGEMENT ####
|
|
1525
1527
|
def get_journal_entries(self, ledger_model: LedgerModel, posted: bool = True):
|
|
@@ -1983,55 +1985,68 @@ class EntityModelAbstract(MP_Node,
|
|
|
1983
1985
|
name: str,
|
|
1984
1986
|
account_type: str,
|
|
1985
1987
|
active=False,
|
|
1986
|
-
|
|
1988
|
+
account_model: Optional[AccountModel] = None,
|
|
1987
1989
|
coa_model: Optional[Union[ChartOfAccountModel, UUID, str]] = None,
|
|
1988
1990
|
bank_account_model_kwargs: Optional[Dict] = None,
|
|
1989
1991
|
commit: bool = True):
|
|
1990
1992
|
|
|
1991
1993
|
"""
|
|
1992
|
-
|
|
1993
|
-
|
|
1994
|
+
Create a bank account entry for the entity model with specified attributes and validation.
|
|
1995
|
+
|
|
1996
|
+
This method creates a new instance of `BankAccountModel`, validates the
|
|
1997
|
+
given inputs, and saves it to the database if `commit` is set to True.
|
|
1994
1998
|
|
|
1995
1999
|
Parameters
|
|
1996
2000
|
----------
|
|
1997
|
-
name: str
|
|
1998
|
-
|
|
1999
|
-
account_type:
|
|
2000
|
-
|
|
2001
|
-
|
|
2002
|
-
|
|
2003
|
-
|
|
2004
|
-
|
|
2005
|
-
|
|
2006
|
-
|
|
2007
|
-
|
|
2008
|
-
|
|
2009
|
-
|
|
2010
|
-
|
|
2001
|
+
name : str
|
|
2002
|
+
The name of the bank account to be created.
|
|
2003
|
+
account_type : str
|
|
2004
|
+
The account type. It must be one of the valid types defined in
|
|
2005
|
+
`BankAccountModel.VALID_ACCOUNT_TYPES`.
|
|
2006
|
+
active : bool, optional
|
|
2007
|
+
A flag indicating whether the account is active. Defaults to False.
|
|
2008
|
+
account_model : Optional[AccountModel], optional
|
|
2009
|
+
An optional pre-existing account model instance to link to the bank
|
|
2010
|
+
account.
|
|
2011
|
+
coa_model : Optional[Union[ChartOfAccountModel, UUID, str]], optional
|
|
2012
|
+
The chart of account model or an identifier to filter accounts. Can
|
|
2013
|
+
accept a UUID, string, or `ChartOfAccountModel`.
|
|
2014
|
+
bank_account_model_kwargs : Optional[Dict], optional
|
|
2015
|
+
Additional keyword arguments to initialize the `BankAccountModel`
|
|
2016
|
+
instance. Defaults to an empty dictionary.
|
|
2017
|
+
commit : bool, optional
|
|
2018
|
+
Flag indicating whether to save the created bank account to the
|
|
2019
|
+
database. Defaults to True.
|
|
2011
2020
|
|
|
2012
2021
|
Returns
|
|
2013
2022
|
-------
|
|
2014
|
-
|
|
2015
|
-
The newly created
|
|
2023
|
+
BankAccountModel
|
|
2024
|
+
The newly created and optionally saved instance of the bank account model.
|
|
2016
2025
|
"""
|
|
2017
2026
|
|
|
2018
2027
|
if bank_account_model_kwargs is None:
|
|
2019
2028
|
bank_account_model_kwargs = dict()
|
|
2029
|
+
|
|
2020
2030
|
if account_type not in BankAccountModel.VALID_ACCOUNT_TYPES:
|
|
2021
2031
|
raise EntityModelValidationError(
|
|
2022
2032
|
_(f'Invalid Account Type: choices are {BankAccountModel.VALID_ACCOUNT_TYPES}'))
|
|
2033
|
+
|
|
2023
2034
|
account_model_qs = self.get_coa_accounts(coa_model=coa_model, active=True)
|
|
2024
2035
|
account_model_qs = account_model_qs.with_roles(
|
|
2025
|
-
roles=
|
|
2036
|
+
roles=[
|
|
2037
|
+
BankAccountModel.ACCOUNT_TYPE_ROLE_MAPPING[account_type]
|
|
2038
|
+
]
|
|
2026
2039
|
).is_role_default()
|
|
2040
|
+
|
|
2027
2041
|
bank_account_model = BankAccountModel(
|
|
2028
2042
|
name=name,
|
|
2029
2043
|
entity_model=self,
|
|
2030
2044
|
account_type=account_type,
|
|
2031
2045
|
active=active,
|
|
2032
|
-
|
|
2046
|
+
account_model=account_model_qs.get() if not account_model else account_model,
|
|
2033
2047
|
**bank_account_model_kwargs
|
|
2034
2048
|
)
|
|
2049
|
+
|
|
2035
2050
|
bank_account_model.clean()
|
|
2036
2051
|
if commit:
|
|
2037
2052
|
bank_account_model.save()
|
|
@@ -2668,7 +2683,7 @@ class EntityModelAbstract(MP_Node,
|
|
|
2668
2683
|
|
|
2669
2684
|
if cash_account:
|
|
2670
2685
|
if isinstance(cash_account, BankAccountModel):
|
|
2671
|
-
cash_account = cash_account.
|
|
2686
|
+
cash_account = cash_account.account_model
|
|
2672
2687
|
self.validate_account_model_for_coa(account_model=cash_account, coa_model=coa_model)
|
|
2673
2688
|
self.validate_account_model_for_role(cash_account, roles_module.ASSET_CA_CASH)
|
|
2674
2689
|
else:
|
|
@@ -452,6 +452,18 @@ class JournalEntryModelAbstract(CreateUpdateMixIn):
|
|
|
452
452
|
pass
|
|
453
453
|
return self.ledger.entity.slug
|
|
454
454
|
|
|
455
|
+
@property
|
|
456
|
+
def entity_model(self) -> EntityModel:
|
|
457
|
+
"""
|
|
458
|
+
Provides access to the `EntityModel` related to the JournalEntryModel.
|
|
459
|
+
|
|
460
|
+
Returns
|
|
461
|
+
-------
|
|
462
|
+
EntityModel
|
|
463
|
+
The `EntityModel` instance linked to the instance LedgerModel.
|
|
464
|
+
"""
|
|
465
|
+
return self.ledger.entity
|
|
466
|
+
|
|
455
467
|
@property
|
|
456
468
|
def entity_last_closing_date(self) -> Optional[date]:
|
|
457
469
|
"""
|
|
@@ -1236,7 +1248,7 @@ class JournalEntryModelAbstract(CreateUpdateMixIn):
|
|
|
1236
1248
|
|
|
1237
1249
|
# todo: add entity_model as parameter on all functions...
|
|
1238
1250
|
# todo: outsource this function to EntityStateModel...?...
|
|
1239
|
-
def _get_next_state_model(self, raise_exception: bool = True) -> EntityStateModel:
|
|
1251
|
+
def _get_next_state_model(self, raise_exception: bool = True) -> Optional[EntityStateModel]:
|
|
1240
1252
|
"""
|
|
1241
1253
|
Retrieves or creates the next state model for the Journal Entry.
|
|
1242
1254
|
|
|
@@ -1250,12 +1262,12 @@ class JournalEntryModelAbstract(CreateUpdateMixIn):
|
|
|
1250
1262
|
EntityStateModel
|
|
1251
1263
|
The state model with an incremented sequence.
|
|
1252
1264
|
"""
|
|
1253
|
-
entity_model =
|
|
1265
|
+
entity_model = self.entity_model
|
|
1254
1266
|
fy_key = entity_model.get_fy_for_date(dt=self.timestamp)
|
|
1255
1267
|
|
|
1256
1268
|
try:
|
|
1257
1269
|
LOOKUP = {
|
|
1258
|
-
'entity_model_id__exact': self.
|
|
1270
|
+
'entity_model_id__exact': self.entity_uuid,
|
|
1259
1271
|
'entity_unit_id__exact': self.entity_unit_id,
|
|
1260
1272
|
'fiscal_year': fy_key,
|
|
1261
1273
|
'key__exact': EntityStateModel.KEY_JOURNAL_ENTRY
|
|
@@ -1279,6 +1291,7 @@ class JournalEntryModelAbstract(CreateUpdateMixIn):
|
|
|
1279
1291
|
}
|
|
1280
1292
|
state_model = EntityStateModel.objects.create(**LOOKUP)
|
|
1281
1293
|
return state_model
|
|
1294
|
+
|
|
1282
1295
|
except IntegrityError as e:
|
|
1283
1296
|
if raise_exception:
|
|
1284
1297
|
raise e
|
|
@@ -1570,11 +1583,7 @@ class JournalEntryModelAbstract(CreateUpdateMixIn):
|
|
|
1570
1583
|
str
|
|
1571
1584
|
The URL for updating or viewing journal entry details.
|
|
1572
1585
|
"""
|
|
1573
|
-
return
|
|
1574
|
-
'entity_slug': self.entity_slug,
|
|
1575
|
-
'ledger_pk': self.ledger_id,
|
|
1576
|
-
'je_pk': self.uuid
|
|
1577
|
-
})
|
|
1586
|
+
return self.get_absolute_url()
|
|
1578
1587
|
|
|
1579
1588
|
def get_journal_entry_list_url(self) -> str:
|
|
1580
1589
|
"""
|
|
@@ -1764,6 +1773,7 @@ def journalentrymodel_presave(instance: JournalEntryModel, **kwargs):
|
|
|
1764
1773
|
raise JournalEntryValidationError(
|
|
1765
1774
|
message=_(f'Cannot add Journal Entries to locked LedgerModel {instance.ledger_id}')
|
|
1766
1775
|
)
|
|
1776
|
+
instance.generate_je_number(commit=False)
|
|
1767
1777
|
|
|
1768
1778
|
|
|
1769
1779
|
pre_save.connect(journalentrymodel_presave, sender=JournalEntryModel)
|
django_ledger/models/mixins.py
CHANGED
|
@@ -23,6 +23,7 @@ from django.utils.encoding import force_str
|
|
|
23
23
|
from django.utils.translation import gettext_lazy as _
|
|
24
24
|
from markdown import markdown
|
|
25
25
|
|
|
26
|
+
from django_ledger.io import ASSET_CA_CASH, LIABILITY_CL_ST_NOTES_PAYABLE, LIABILITY_LTL_MORTGAGE_PAYABLE
|
|
26
27
|
from django_ledger.io.io_core import validate_io_timestamp, check_tx_balance, get_localtime, get_localdate
|
|
27
28
|
from django_ledger.models.utils import lazy_loader
|
|
28
29
|
|
|
@@ -1102,7 +1103,7 @@ class MarkdownNotesMixIn(models.Model):
|
|
|
1102
1103
|
super().clean()
|
|
1103
1104
|
|
|
1104
1105
|
|
|
1105
|
-
class
|
|
1106
|
+
class FinancialAccountInfoMixin(models.Model):
|
|
1106
1107
|
"""
|
|
1107
1108
|
Implements functionality used to add bank account details to base Django Models.
|
|
1108
1109
|
|
|
@@ -1122,10 +1123,23 @@ class BankAccountInfoMixIn(models.Model):
|
|
|
1122
1123
|
|
|
1123
1124
|
ACCOUNT_CHECKING = 'checking'
|
|
1124
1125
|
ACCOUNT_SAVINGS = 'savings'
|
|
1126
|
+
ACCOUNT_CREDIT_CARD = 'credit_card'
|
|
1127
|
+
ACCOUNT_MORTGAGE = 'mortgage'
|
|
1128
|
+
|
|
1129
|
+
ACCOUNT_TYPE_ROLE_MAPPING = {
|
|
1130
|
+
ACCOUNT_CHECKING: ASSET_CA_CASH,
|
|
1131
|
+
ACCOUNT_SAVINGS: ASSET_CA_CASH,
|
|
1132
|
+
ACCOUNT_CREDIT_CARD: LIABILITY_CL_ST_NOTES_PAYABLE,
|
|
1133
|
+
ACCOUNT_MORTGAGE: LIABILITY_LTL_MORTGAGE_PAYABLE
|
|
1134
|
+
}
|
|
1135
|
+
|
|
1125
1136
|
ACCOUNT_TYPE_CHOICES = [
|
|
1126
1137
|
(ACCOUNT_CHECKING, _('Checking')),
|
|
1127
|
-
(ACCOUNT_SAVINGS, _('Savings'))
|
|
1138
|
+
(ACCOUNT_SAVINGS, _('Savings')),
|
|
1139
|
+
(ACCOUNT_CREDIT_CARD, _('Credit Card')),
|
|
1140
|
+
(ACCOUNT_MORTGAGE, _('Mortgage')),
|
|
1128
1141
|
]
|
|
1142
|
+
|
|
1129
1143
|
VALID_ACCOUNT_TYPES = tuple(atc[0] for atc in ACCOUNT_TYPE_CHOICES)
|
|
1130
1144
|
|
|
1131
1145
|
account_number = models.CharField(max_length=30, null=True, blank=True,
|
|
@@ -1139,7 +1153,7 @@ class BankAccountInfoMixIn(models.Model):
|
|
|
1139
1153
|
aba_number = models.CharField(max_length=30, null=True, blank=True, verbose_name=_('ABA Number'))
|
|
1140
1154
|
swift_number = models.CharField(max_length=30, null=True, blank=True, verbose_name=_('SWIFT Number'))
|
|
1141
1155
|
account_type = models.CharField(choices=ACCOUNT_TYPE_CHOICES,
|
|
1142
|
-
max_length=
|
|
1156
|
+
max_length=20,
|
|
1143
1157
|
default=ACCOUNT_CHECKING,
|
|
1144
1158
|
verbose_name=_('Account Type'))
|
|
1145
1159
|
|
django_ledger/models/vendor.py
CHANGED
|
@@ -18,7 +18,7 @@ from django.db import models, transaction, IntegrityError
|
|
|
18
18
|
from django.db.models import Q, F, QuerySet
|
|
19
19
|
from django.utils.translation import gettext_lazy as _
|
|
20
20
|
|
|
21
|
-
from django_ledger.models.mixins import ContactInfoMixIn, CreateUpdateMixIn,
|
|
21
|
+
from django_ledger.models.mixins import ContactInfoMixIn, CreateUpdateMixIn, FinancialAccountInfoMixin, TaxInfoMixIn
|
|
22
22
|
from django_ledger.models.utils import lazy_loader
|
|
23
23
|
from django_ledger.settings import DJANGO_LEDGER_DOCUMENT_NUMBER_PADDING, DJANGO_LEDGER_VENDOR_NUMBER_PREFIX
|
|
24
24
|
|
|
@@ -131,7 +131,7 @@ class VendorModelManager(models.Manager):
|
|
|
131
131
|
|
|
132
132
|
|
|
133
133
|
class VendorModelAbstract(ContactInfoMixIn,
|
|
134
|
-
|
|
134
|
+
FinancialAccountInfoMixin,
|
|
135
135
|
TaxInfoMixIn,
|
|
136
136
|
CreateUpdateMixIn):
|
|
137
137
|
"""
|
django_ledger/settings.py
CHANGED
|
@@ -31,30 +31,26 @@ logger.info(f'Django Ledger GraphQL Enabled: {DJANGO_LEDGER_GRAPHQL_SUPPORT_ENAB
|
|
|
31
31
|
|
|
32
32
|
## MODEL ABSTRACTS ##
|
|
33
33
|
DJANGO_LEDGER_ACCOUNT_MODEL = getattr(settings, 'DJANGO_LEDGER_ACCOUNT_MODEL', 'django_ledger.AccountModel')
|
|
34
|
-
DJANGO_LEDGER_CHART_OF_ACCOUNTS_MODEL = getattr(settings, 'DJANGO_LEDGER_ACCOUNT_MODEL', 'django_ledger.
|
|
35
|
-
DJANGO_LEDGER_TRANSACTION_MODEL = getattr(settings, 'DJANGO_LEDGER_TRANSACTION_MODEL', 'django_ledger.
|
|
36
|
-
DJANGO_LEDGER_JOURNAL_ENTRY_MODEL = getattr(settings, 'DJANGO_LEDGER_JOURNAL_ENTRY_MODEL', 'django_ledger.
|
|
34
|
+
DJANGO_LEDGER_CHART_OF_ACCOUNTS_MODEL = getattr(settings, 'DJANGO_LEDGER_ACCOUNT_MODEL', 'django_ledger.ChartOfAccountModel')
|
|
35
|
+
DJANGO_LEDGER_TRANSACTION_MODEL = getattr(settings, 'DJANGO_LEDGER_TRANSACTION_MODEL', 'django_ledger.TransactionModel')
|
|
36
|
+
DJANGO_LEDGER_JOURNAL_ENTRY_MODEL = getattr(settings, 'DJANGO_LEDGER_JOURNAL_ENTRY_MODEL', 'django_ledger.JournalEntryModel')
|
|
37
37
|
DJANGO_LEDGER_LEDGER_MODEL = getattr(settings, 'DJANGO_LEDGER_LEDGER_MODEL', 'django_ledger.LedgerModel')
|
|
38
|
-
DJANGO_LEDGER_ENTITY_MODEL = getattr(settings, 'DJANGO_LEDGER_ENTITY_MODEL', 'django_ledger.
|
|
38
|
+
DJANGO_LEDGER_ENTITY_MODEL = getattr(settings, 'DJANGO_LEDGER_ENTITY_MODEL', 'django_ledger.EntityModel')
|
|
39
39
|
DJANGO_LEDGER_ENTITY_STATE_MODEL = getattr(settings, 'DJANGO_LEDGER_ENTITY_STATE_MODEL', 'django_ledger.EntityStateModel')
|
|
40
|
-
|
|
41
|
-
|
|
42
|
-
|
|
43
|
-
|
|
44
|
-
|
|
45
|
-
|
|
46
|
-
|
|
47
|
-
|
|
48
|
-
|
|
49
|
-
|
|
50
|
-
|
|
51
|
-
|
|
52
|
-
|
|
53
|
-
|
|
54
|
-
DJANGO_LEDGER_ITEM_TRANSACTION_MODEL = getattr(settings, 'DJANGO_LEDGER_ITEM_TRANSACTION_MODEL', 'django_ledger.ItemTransactionModelAbstract')
|
|
55
|
-
DJANGO_LEDGER_ITEM_MODEL = getattr(settings, 'DJANGO_LEDGER_ITEM_MODEL', 'django_ledger.ItemModelAbstract')
|
|
56
|
-
DJANGO_LEDGER_STAGED_TRANSACTION_MODEL = getattr(settings, 'DJANGO_LEDGER_STAGED_TRANSACTION_MODEL', 'django_ledger.StagedTransactionModelAbstract')
|
|
57
|
-
DJANGO_LEDGER_IMPORT_JOB_MODEL = getattr(settings, 'DJANGO_LEDGER_IMPORT_JOB_MODEL', 'django_ledger.ImportJobModelAbstract')
|
|
40
|
+
DJANGO_LEDGER_ENTITY_UNIT_MODEL = getattr(settings, 'DJANGO_LEDGER_ENTITY_UNIT_MODEL', 'django_ledger.EntityUnitModel')
|
|
41
|
+
DJANGO_LEDGER_ESTIMATE_MODEL = getattr(settings, 'DJANGO_LEDGER_ESTIMATE_MODEL', 'django_ledger.EstimateModel')
|
|
42
|
+
DJANGO_LEDGER_BILL_MODEL = getattr(settings, 'DJANGO_LEDGER_BILL_MODEL', 'django_ledger.BillModel')
|
|
43
|
+
DJANGO_LEDGER_INVOICE_MODEL = getattr(settings, 'DJANGO_LEDGER_INVOICE_MODEL', 'django_ledger.InvoiceModel')
|
|
44
|
+
DJANGO_LEDGER_PURCHASE_ORDER_MODEL = getattr(settings, 'DJANGO_LEDGER_PURCHASE_ORDER_MODEL', 'django_ledger.PurchaseOrderModel')
|
|
45
|
+
DJANGO_LEDGER_CUSTOMER_MODEL = getattr(settings, 'DJANGO_LEDGER_CUSTOMER_MODEL', 'django_ledger.CustomerModel')
|
|
46
|
+
DJANGO_LEDGER_VENDOR_MODEL = getattr(settings, 'DJANGO_LEDGER_VENDOR_MODEL', 'django_ledger.VendorModel')
|
|
47
|
+
DJANGO_LEDGER_BANK_ACCOUNT_MODEL = getattr(settings, 'DJANGO_LEDGER_BANK_ACCOUNT_MODEL', 'django_ledger.BankAccountModel')
|
|
48
|
+
DJANGO_LEDGER_CLOSING_ENTRY_MODEL = getattr(settings, 'DJANGO_LEDGER_CLOSING_ENTRY_MODEL', 'django_ledger.ClosingEntryModel')
|
|
49
|
+
DJANGO_LEDGER_UNIT_OF_MEASURE_MODEL = getattr(settings, 'DJANGO_LEDGER_UNIT_OF_MEASURE_MODEL', 'django_ledger.UnitOfMeasureModel')
|
|
50
|
+
DJANGO_LEDGER_ITEM_TRANSACTION_MODEL = getattr(settings, 'DJANGO_LEDGER_ITEM_TRANSACTION_MODEL', 'django_ledger.ItemTransactionModel')
|
|
51
|
+
DJANGO_LEDGER_ITEM_MODEL = getattr(settings, 'DJANGO_LEDGER_ITEM_MODEL', 'django_ledger.ItemModel')
|
|
52
|
+
DJANGO_LEDGER_STAGED_TRANSACTION_MODEL = getattr(settings, 'DJANGO_LEDGER_STAGED_TRANSACTION_MODEL', 'django_ledger.StagedTransactionModel')
|
|
53
|
+
DJANGO_LEDGER_IMPORT_JOB_MODEL = getattr(settings, 'DJANGO_LEDGER_IMPORT_JOB_MODEL', 'django_ledger.ImportJobModel')
|
|
58
54
|
|
|
59
55
|
DJANGO_LEDGER_USE_CLOSING_ENTRIES = getattr(settings, 'DJANGO_LEDGER_USE_CLOSING_ENTRIES', True)
|
|
60
56
|
DJANGO_LEDGER_DEFAULT_CLOSING_ENTRY_CACHE_TIMEOUT = getattr(settings,
|
|
@@ -9,7 +9,7 @@
|
|
|
9
9
|
<th class="has-text-centered">Account Number</th>
|
|
10
10
|
<th class="has-text-centered">Routing Number</th>
|
|
11
11
|
<th class="has-text-centered">Type</th>
|
|
12
|
-
<th class="has-text-centered">
|
|
12
|
+
<th class="has-text-centered">Account</th>
|
|
13
13
|
<th class="has-text-centered">Active</th>
|
|
14
14
|
<th class="has-text-centered">Actions</th>
|
|
15
15
|
</tr>
|
|
@@ -21,7 +21,7 @@
|
|
|
21
21
|
<td>{{ bank_acc.account_number | last_four }}</td>
|
|
22
22
|
<td>{{ bank_acc.routing_number | last_four }}</td>
|
|
23
23
|
<td>{{ bank_acc.get_account_type_display }}</td>
|
|
24
|
-
<td>{{ bank_acc.
|
|
24
|
+
<td>{{ bank_acc.account_model }}</td>
|
|
25
25
|
<td>
|
|
26
26
|
{% if bank_acc.active %}
|
|
27
27
|
<span class="icon has-text-success">{% icon 'ant-design:check-circle-filled' 24 %}</span>
|
|
@@ -12,7 +12,7 @@
|
|
|
12
12
|
</div>
|
|
13
13
|
<div class="column is-12">
|
|
14
14
|
<h2 class="is-size-2">{% trans 'Imported Transactions' %}</h2>
|
|
15
|
-
{% data_import_job_txs_imported
|
|
15
|
+
{% data_import_job_txs_imported import_job %}
|
|
16
16
|
</div>
|
|
17
17
|
<div class="column is-12 has-text-centered">
|
|
18
18
|
<a class="button is-dark"
|
|
@@ -13,12 +13,21 @@
|
|
|
13
13
|
enctype="multipart/form-data"
|
|
14
14
|
method="post">
|
|
15
15
|
{% csrf_token %}
|
|
16
|
-
|
|
16
|
+
|
|
17
|
+
<div class="field mb-4">
|
|
17
18
|
<div class="control">
|
|
18
19
|
{{ form.description }}
|
|
19
20
|
</div>
|
|
20
21
|
</div>
|
|
21
|
-
|
|
22
|
+
|
|
23
|
+
<div class="field mb-4">
|
|
24
|
+
{{ form.bank_account_model.help_text }}
|
|
25
|
+
<div class="control">
|
|
26
|
+
{{ form.bank_account_model }}
|
|
27
|
+
</div>
|
|
28
|
+
</div>
|
|
29
|
+
|
|
30
|
+
<div class="field mb-4">
|
|
22
31
|
<div class="control">
|
|
23
32
|
<div id="file-js-django-ledger" class="file has-name">
|
|
24
33
|
<label class="file-label">
|
|
@@ -28,7 +28,7 @@
|
|
|
28
28
|
<td>{{ imported_tx.account_model }}</td>
|
|
29
29
|
<td>{{ imported_tx.transaction_model }}</td>
|
|
30
30
|
<td class="has-text-centered">
|
|
31
|
-
<a href="{% url 'django_ledger:je-detail' entity_slug=entity_slug ledger_pk=imported_tx.transaction_model.journal_entry.ledger_id je_pk=imported_tx.transaction_model.journal_entry_id %}"
|
|
31
|
+
<a href="{% url 'django_ledger:je-detail' entity_slug=import_job_model.entity_slug ledger_pk=imported_tx.transaction_model.journal_entry.ledger_id je_pk=imported_tx.transaction_model.journal_entry_id %}"
|
|
32
32
|
class="button is-small is-primary">{% trans 'View JE' %}</a>
|
|
33
33
|
</td>
|
|
34
34
|
</tr>
|
|
@@ -3,17 +3,20 @@
|
|
|
3
3
|
|
|
4
4
|
|
|
5
5
|
<form method="post">
|
|
6
|
+
|
|
6
7
|
{{ staged_txs_formset.non_form_errors }}
|
|
7
8
|
{% if staged_txs_formset.errors %}
|
|
8
9
|
{{ staged_txs_formset.errors }}
|
|
9
10
|
{% endif %}
|
|
10
11
|
{{ staged_txs_formset.management_form }}
|
|
12
|
+
|
|
11
13
|
{% csrf_token %}
|
|
12
14
|
|
|
13
15
|
<div class="table-container">
|
|
14
16
|
<table class="table is-narrow is-fullwidth is-bordered is-striped django-ledger-table-bottom-margin-75">
|
|
15
17
|
<thead>
|
|
16
18
|
<tr class="has-text-centered is-error">
|
|
19
|
+
<th></th>
|
|
17
20
|
<th>Dated Posted</th>
|
|
18
21
|
<th>Description</th>
|
|
19
22
|
<th>Amount</th>
|
|
@@ -27,11 +30,11 @@
|
|
|
27
30
|
</tr>
|
|
28
31
|
</thead>
|
|
29
32
|
|
|
30
|
-
|
|
31
33
|
<tbody>
|
|
32
34
|
|
|
33
35
|
{% for txf in staged_txs_formset %}
|
|
34
36
|
<tr class="{% if txf.instance.is_children %}has-background-primary{% elif txf.instance.has_children %}has-background-primary-light{% endif %}">
|
|
37
|
+
<td>{{ forloop.counter }}</td>
|
|
35
38
|
{% for hidden_field in txf.hidden_fields %}{{ hidden_field }}{% endfor %}
|
|
36
39
|
{% if txf.instance.is_children %}
|
|
37
40
|
<td class="has-background-primary-light" style="border: 0px"></td>
|
|
@@ -59,7 +62,7 @@
|
|
|
59
62
|
{{ txf.account_model }}
|
|
60
63
|
</td>
|
|
61
64
|
<td>{{ txf.unit_model }}{% if txf.instance.is_children %}
|
|
62
|
-
|
|
65
|
+
<span class="content is-small">{{ txf.instance.unit_model.name }}</span>
|
|
63
66
|
{% endif %}
|
|
64
67
|
</td>
|
|
65
68
|
<td class="has-text-centered">{{ txf.tx_import }}</td>
|
|
@@ -11,17 +11,17 @@ from random import randint
|
|
|
11
11
|
from typing import Union
|
|
12
12
|
|
|
13
13
|
from django import template
|
|
14
|
-
from django.
|
|
14
|
+
from django.core.exceptions import ValidationError
|
|
15
|
+
from django.db.models import Sum
|
|
15
16
|
from django.urls import reverse
|
|
16
17
|
from django.utils.formats import number_format
|
|
17
|
-
from rfc3986.exceptions import ValidationError
|
|
18
18
|
|
|
19
19
|
from django_ledger import __version__
|
|
20
20
|
from django_ledger.forms.app_filters import EntityFilterForm, ActivityFilterForm
|
|
21
21
|
from django_ledger.forms.feedback import BugReportForm, RequestNewFeatureForm
|
|
22
|
-
from django_ledger.io import
|
|
22
|
+
from django_ledger.io import ROLES_ORDER_ALL
|
|
23
23
|
from django_ledger.io.io_core import validate_activity, get_localdate
|
|
24
|
-
from django_ledger.models import
|
|
24
|
+
from django_ledger.models import BillModel, InvoiceModel, JournalEntryModel
|
|
25
25
|
from django_ledger.settings import (
|
|
26
26
|
DJANGO_LEDGER_FINANCIAL_ANALYSIS, DJANGO_LEDGER_CURRENCY_SYMBOL,
|
|
27
27
|
DJANGO_LEDGER_SPACED_CURRENCY_SYMBOL)
|
|
@@ -191,19 +191,18 @@ def data_import_job_list_table(context):
|
|
|
191
191
|
@register.inclusion_tag('django_ledger/data_import/tags/data_import_job_txs_table.html', takes_context=True)
|
|
192
192
|
def data_import_job_txs_pending(context, staged_txs_formset):
|
|
193
193
|
return {
|
|
194
|
-
'entity_slug':
|
|
195
|
-
'
|
|
194
|
+
'entity_slug': staged_txs_formset.IMPORT_JOB_MODEL.entity_slug,
|
|
195
|
+
'import_job_model': staged_txs_formset.IMPORT_JOB_MODEL,
|
|
196
196
|
'staged_txs_formset': staged_txs_formset
|
|
197
197
|
}
|
|
198
198
|
|
|
199
199
|
|
|
200
200
|
@register.inclusion_tag('django_ledger/data_import/tags/data_import_job_txs_imported.html', takes_context=True)
|
|
201
|
-
def data_import_job_txs_imported(context,
|
|
202
|
-
imported_txs = [stx for stx in staged_txs_qs if stx.is_imported()]
|
|
201
|
+
def data_import_job_txs_imported(context, import_job_model):
|
|
203
202
|
return {
|
|
204
|
-
'entity_slug':
|
|
205
|
-
'
|
|
206
|
-
'imported_txs':
|
|
203
|
+
'entity_slug': import_job_model.entity_slug,
|
|
204
|
+
'import_job_model': import_job_model,
|
|
205
|
+
'imported_txs': import_job_model.stagedtransactionmodel_set.all().is_imported()
|
|
207
206
|
}
|
|
208
207
|
|
|
209
208
|
|
|
@@ -236,7 +235,8 @@ def transactions_table(object_type: Union[JournalEntryModel, BillModel, InvoiceM
|
|
|
236
235
|
transaction_model_qs = object_type.get_transaction_queryset(annotated=True).order_by('-timestamp')
|
|
237
236
|
else:
|
|
238
237
|
raise ValidationError(
|
|
239
|
-
'Cannot handle object of type {} to get transaction model queryset'.format(type(object_type))
|
|
238
|
+
'Cannot handle object of type {} to get transaction model queryset'.format(type(object_type))
|
|
239
|
+
)
|
|
240
240
|
|
|
241
241
|
total_credits = sum(tx.amount for tx in transaction_model_qs if tx.is_credit())
|
|
242
242
|
total_debits = sum(tx.amount for tx in transaction_model_qs if tx.is_debit())
|
|
@@ -24,7 +24,7 @@ class BankAccountModelModelBaseView(DjangoLedgerSecurityMixIn):
|
|
|
24
24
|
def get_queryset(self):
|
|
25
25
|
if self.queryset is None:
|
|
26
26
|
entity_model: EntityModel = self.get_authorized_entity_instance()
|
|
27
|
-
self.queryset = entity_model.bankaccountmodel_set.select_related('
|
|
27
|
+
self.queryset = entity_model.bankaccountmodel_set.select_related('account_model', 'entity_model')
|
|
28
28
|
return super().get_queryset()
|
|
29
29
|
|
|
30
30
|
|