mirror of
https://github.com/frappe/erpnext.git
synced 2026-05-27 08:54:45 +00:00
Merge pull request #45267 from frappe/mergify/bp/version-15-hotfix/pr-45211
refactor: allow users to configure interval for Semi-Auto payment reconciliation (backport #45211)
This commit is contained in:
@@ -40,9 +40,13 @@
|
|||||||
"show_payment_schedule_in_print",
|
"show_payment_schedule_in_print",
|
||||||
"currency_exchange_section",
|
"currency_exchange_section",
|
||||||
"allow_stale",
|
"allow_stale",
|
||||||
|
"column_break_yuug",
|
||||||
|
"stale_days",
|
||||||
"section_break_jpd0",
|
"section_break_jpd0",
|
||||||
"auto_reconcile_payments",
|
"auto_reconcile_payments",
|
||||||
"stale_days",
|
"auto_reconciliation_job_trigger",
|
||||||
|
"reconciliation_queue_size",
|
||||||
|
"column_break_resa",
|
||||||
"invoicing_settings_tab",
|
"invoicing_settings_tab",
|
||||||
"accounts_transactions_settings_section",
|
"accounts_transactions_settings_section",
|
||||||
"over_billing_allowance",
|
"over_billing_allowance",
|
||||||
@@ -489,6 +493,28 @@
|
|||||||
"fieldname": "create_pr_in_draft_status",
|
"fieldname": "create_pr_in_draft_status",
|
||||||
"fieldtype": "Check",
|
"fieldtype": "Check",
|
||||||
"label": "Create in Draft Status"
|
"label": "Create in Draft Status"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_yuug",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"fieldname": "column_break_resa",
|
||||||
|
"fieldtype": "Column Break"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"default": "15",
|
||||||
|
"description": "Interval should be between 1 to 59 MInutes",
|
||||||
|
"fieldname": "auto_reconciliation_job_trigger",
|
||||||
|
"fieldtype": "Int",
|
||||||
|
"label": "Auto Reconciliation Job Trigger"
|
||||||
|
},
|
||||||
|
{
|
||||||
|
"default": "5",
|
||||||
|
"description": "Documents Processed on each trigger. Queue Size should be between 5 and 100",
|
||||||
|
"fieldname": "reconciliation_queue_size",
|
||||||
|
"fieldtype": "Int",
|
||||||
|
"label": "Reconciliation Queue Size"
|
||||||
}
|
}
|
||||||
],
|
],
|
||||||
"icon": "icon-cog",
|
"icon": "icon-cog",
|
||||||
@@ -496,7 +522,7 @@
|
|||||||
"index_web_pages_for_search": 1,
|
"index_web_pages_for_search": 1,
|
||||||
"issingle": 1,
|
"issingle": 1,
|
||||||
"links": [],
|
"links": [],
|
||||||
"modified": "2024-07-26 06:48:52.714630",
|
"modified": "2025-01-13 17:38:39.661320",
|
||||||
"modified_by": "Administrator",
|
"modified_by": "Administrator",
|
||||||
"module": "Accounts",
|
"module": "Accounts",
|
||||||
"name": "Accounts Settings",
|
"name": "Accounts Settings",
|
||||||
|
|||||||
@@ -10,6 +10,7 @@ from frappe.custom.doctype.property_setter.property_setter import make_property_
|
|||||||
from frappe.model.document import Document
|
from frappe.model.document import Document
|
||||||
from frappe.utils import cint
|
from frappe.utils import cint
|
||||||
|
|
||||||
|
from erpnext.accounts.utils import sync_auto_reconcile_config
|
||||||
from erpnext.stock.utils import check_pending_reposting
|
from erpnext.stock.utils import check_pending_reposting
|
||||||
|
|
||||||
|
|
||||||
@@ -27,6 +28,7 @@ class AccountsSettings(Document):
|
|||||||
allow_multi_currency_invoices_against_single_party_account: DF.Check
|
allow_multi_currency_invoices_against_single_party_account: DF.Check
|
||||||
allow_stale: DF.Check
|
allow_stale: DF.Check
|
||||||
auto_reconcile_payments: DF.Check
|
auto_reconcile_payments: DF.Check
|
||||||
|
auto_reconciliation_job_trigger: DF.Int
|
||||||
automatically_fetch_payment_terms: DF.Check
|
automatically_fetch_payment_terms: DF.Check
|
||||||
automatically_process_deferred_accounting_entry: DF.Check
|
automatically_process_deferred_accounting_entry: DF.Check
|
||||||
book_asset_depreciation_entry_automatically: DF.Check
|
book_asset_depreciation_entry_automatically: DF.Check
|
||||||
@@ -51,6 +53,7 @@ class AccountsSettings(Document):
|
|||||||
over_billing_allowance: DF.Currency
|
over_billing_allowance: DF.Currency
|
||||||
post_change_gl_entries: DF.Check
|
post_change_gl_entries: DF.Check
|
||||||
receivable_payable_remarks_length: DF.Int
|
receivable_payable_remarks_length: DF.Int
|
||||||
|
reconciliation_queue_size: DF.Int
|
||||||
role_allowed_to_over_bill: DF.Link | None
|
role_allowed_to_over_bill: DF.Link | None
|
||||||
round_row_wise_tax: DF.Check
|
round_row_wise_tax: DF.Check
|
||||||
show_balance_in_coa: DF.Check
|
show_balance_in_coa: DF.Check
|
||||||
@@ -90,6 +93,8 @@ class AccountsSettings(Document):
|
|||||||
if clear_cache:
|
if clear_cache:
|
||||||
frappe.clear_cache()
|
frappe.clear_cache()
|
||||||
|
|
||||||
|
self.validate_and_sync_auto_reconcile_config()
|
||||||
|
|
||||||
def validate_stale_days(self):
|
def validate_stale_days(self):
|
||||||
if not self.allow_stale and cint(self.stale_days) <= 0:
|
if not self.allow_stale and cint(self.stale_days) <= 0:
|
||||||
frappe.msgprint(
|
frappe.msgprint(
|
||||||
@@ -114,3 +119,17 @@ class AccountsSettings(Document):
|
|||||||
def validate_pending_reposts(self):
|
def validate_pending_reposts(self):
|
||||||
if self.acc_frozen_upto:
|
if self.acc_frozen_upto:
|
||||||
check_pending_reposting(self.acc_frozen_upto)
|
check_pending_reposting(self.acc_frozen_upto)
|
||||||
|
|
||||||
|
def validate_and_sync_auto_reconcile_config(self):
|
||||||
|
if self.has_value_changed("auto_reconciliation_job_trigger"):
|
||||||
|
if (
|
||||||
|
cint(self.auto_reconciliation_job_trigger) > 0
|
||||||
|
and cint(self.auto_reconciliation_job_trigger) < 60
|
||||||
|
):
|
||||||
|
sync_auto_reconcile_config(self.auto_reconciliation_job_trigger)
|
||||||
|
else:
|
||||||
|
frappe.throw(_("Cron Interval should be between 1 and 59 Min"))
|
||||||
|
|
||||||
|
if self.has_value_changed("reconciliation_queue_size"):
|
||||||
|
if cint(self.reconciliation_queue_size) < 5 or cint(self.reconciliation_queue_size) > 100:
|
||||||
|
frappe.throw(_("Queue Size should be between 5 and 100"))
|
||||||
|
|||||||
@@ -210,7 +210,7 @@ def trigger_reconciliation_for_queued_docs():
|
|||||||
|
|
||||||
docs_to_trigger = []
|
docs_to_trigger = []
|
||||||
unique_filters = set()
|
unique_filters = set()
|
||||||
queue_size = 5
|
queue_size = frappe.db.get_single_value("Accounts Settings", "reconciliation_queue_size") or 5
|
||||||
|
|
||||||
fields = ["company", "party_type", "party", "receivable_payable_account", "default_advance_account"]
|
fields = ["company", "party_type", "party", "receivable_payable_account", "default_advance_account"]
|
||||||
|
|
||||||
|
|||||||
@@ -2250,3 +2250,38 @@ def run_ledger_health_checks():
|
|||||||
doc.general_and_payment_ledger_mismatch = True
|
doc.general_and_payment_ledger_mismatch = True
|
||||||
doc.checked_on = run_date
|
doc.checked_on = run_date
|
||||||
doc.save()
|
doc.save()
|
||||||
|
|
||||||
|
|
||||||
|
def sync_auto_reconcile_config(auto_reconciliation_job_trigger: int = 15):
|
||||||
|
auto_reconciliation_job_trigger = auto_reconciliation_job_trigger or frappe.db.get_single_value(
|
||||||
|
"Accounts Settings", "auto_reconciliation_job_trigger"
|
||||||
|
)
|
||||||
|
method = "erpnext.accounts.doctype.process_payment_reconciliation.process_payment_reconciliation.trigger_reconciliation_for_queued_docs"
|
||||||
|
|
||||||
|
sch_event = frappe.get_doc(
|
||||||
|
"Scheduler Event", {"scheduled_against": "Process Payment Reconciliation", "method": method}
|
||||||
|
)
|
||||||
|
if frappe.db.get_value("Scheduled Job Type", {"method": method}):
|
||||||
|
frappe.get_doc(
|
||||||
|
"Scheduled Job Type",
|
||||||
|
{
|
||||||
|
"method": method,
|
||||||
|
},
|
||||||
|
).update(
|
||||||
|
{
|
||||||
|
"cron_format": f"0/{auto_reconciliation_job_trigger} * * * *",
|
||||||
|
"scheduler_event": sch_event.name,
|
||||||
|
}
|
||||||
|
).save()
|
||||||
|
else:
|
||||||
|
frappe.get_doc(
|
||||||
|
{
|
||||||
|
"doctype": "Scheduled Job Type",
|
||||||
|
"method": method,
|
||||||
|
"scheduler_event": sch_event.name,
|
||||||
|
"cron_format": f"0/{auto_reconciliation_job_trigger} * * * *",
|
||||||
|
"create_log": True,
|
||||||
|
"stopped": False,
|
||||||
|
"frequency": "Cron",
|
||||||
|
}
|
||||||
|
).save()
|
||||||
|
|||||||
@@ -412,7 +412,6 @@ scheduler_events = {
|
|||||||
"cron": {
|
"cron": {
|
||||||
"0/15 * * * *": [
|
"0/15 * * * *": [
|
||||||
"erpnext.manufacturing.doctype.bom_update_log.bom_update_log.resume_bom_cost_update_jobs",
|
"erpnext.manufacturing.doctype.bom_update_log.bom_update_log.resume_bom_cost_update_jobs",
|
||||||
"erpnext.accounts.doctype.process_payment_reconciliation.process_payment_reconciliation.trigger_reconciliation_for_queued_docs",
|
|
||||||
],
|
],
|
||||||
"0/30 * * * *": [
|
"0/30 * * * *": [
|
||||||
"erpnext.utilities.doctype.video.video.update_youtube_data",
|
"erpnext.utilities.doctype.video.video.update_youtube_data",
|
||||||
|
|||||||
@@ -388,3 +388,4 @@ erpnext.patches.v15_0.enable_allow_existing_serial_no
|
|||||||
erpnext.patches.v15_0.update_cc_in_process_statement_of_accounts
|
erpnext.patches.v15_0.update_cc_in_process_statement_of_accounts
|
||||||
erpnext.patches.v15_0.update_asset_status_to_work_in_progress
|
erpnext.patches.v15_0.update_asset_status_to_work_in_progress
|
||||||
erpnext.patches.v15_0.migrate_checkbox_to_select_for_reconciliation_effect
|
erpnext.patches.v15_0.migrate_checkbox_to_select_for_reconciliation_effect
|
||||||
|
erpnext.patches.v15_0.sync_auto_reconcile_config
|
||||||
|
|||||||
26
erpnext/patches/v15_0/sync_auto_reconcile_config.py
Normal file
26
erpnext/patches/v15_0/sync_auto_reconcile_config.py
Normal file
@@ -0,0 +1,26 @@
|
|||||||
|
import frappe
|
||||||
|
|
||||||
|
from erpnext.accounts.utils import sync_auto_reconcile_config
|
||||||
|
|
||||||
|
|
||||||
|
def execute():
|
||||||
|
"""
|
||||||
|
Set default Cron Interval and Queue size
|
||||||
|
"""
|
||||||
|
frappe.db.set_single_value("Accounts Settings", "auto_reconciliation_job_trigger", 15)
|
||||||
|
frappe.db.set_single_value("Accounts Settings", "reconciliation_queue_size", 5)
|
||||||
|
|
||||||
|
# Create Scheduler Event record if it doesn't exist
|
||||||
|
method = "erpnext.accounts.doctype.process_payment_reconciliation.process_payment_reconciliation.trigger_reconciliation_for_queued_docs"
|
||||||
|
if not frappe.db.get_all(
|
||||||
|
"Scheduler Event", {"scheduled_against": "Process Payment Reconciliation", "method": method}
|
||||||
|
):
|
||||||
|
frappe.get_doc(
|
||||||
|
{
|
||||||
|
"doctype": "Scheduler Event",
|
||||||
|
"scheduled_against": "Process Payment Reconciliation",
|
||||||
|
"method": method,
|
||||||
|
}
|
||||||
|
).save()
|
||||||
|
|
||||||
|
sync_auto_reconcile_config(15)
|
||||||
Reference in New Issue
Block a user