Merge branch 'develop' into erpnext_form_cleanups

This commit is contained in:
Deepesh Garg
2026-02-05 09:50:22 +05:30
committed by GitHub
15 changed files with 391 additions and 236 deletions

View File

@@ -535,10 +535,12 @@ class PaymentRequest(Document):
row_number += TO_SKIP_NEW_ROW
@frappe.whitelist(allow_guest=True)
@frappe.whitelist()
def make_payment_request(**args):
"""Make payment request"""
frappe.has_permission(doctype="Payment Request", ptype="write", throw=True)
args = frappe._dict(args)
if args.dt not in ALLOWED_DOCTYPES_FOR_PAYMENT_REQUEST:
frappe.throw(_("Payment Requests cannot be created against: {0}").format(frappe.bold(args.dt)))

View File

@@ -12,56 +12,76 @@
"disabled",
"column_break_9",
"warehouse",
"utm_source",
"utm_campaign",
"utm_medium",
"company_address",
"section_break_15",
"applicable_for_users",
"accounting_tab",
"section_break_11",
"payments",
"set_grand_total_to_default_mop",
"price_list_and_currency_section",
"currency",
"column_break_bptt",
"selling_price_list",
"write_off_section",
"write_off_account",
"column_break_ukpz",
"write_off_cost_center",
"column_break_pkca",
"write_off_limit",
"income_and_expense_account",
"income_account",
"column_break_byzk",
"expense_account",
"taxes_section",
"taxes_and_charges",
"column_break_cjpp",
"tax_category",
"section_break_19",
"account_for_change_amount",
"disable_rounded_total",
"column_break_23",
"apply_discount_on",
"allow_partial_payment",
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"project",
"pos_configurations_tab",
"section_break_14",
"hide_images",
"hide_unavailable_items",
"auto_add_item_to_cart",
"validate_stock_on_save",
"print_receipt_on_order_complete",
"action_on_new_invoice",
"validate_stock_on_save",
"column_break_16",
"update_stock",
"ignore_pricing_rule",
"print_receipt_on_order_complete",
"pos_item_selector_section",
"hide_images",
"column_break_rpny",
"hide_unavailable_items",
"column_break_stcl",
"auto_add_item_to_cart",
"pos_item_details_section",
"allow_rate_change",
"column_break_hwfg",
"allow_discount_change",
"set_grand_total_to_default_mop",
"allow_partial_payment",
"section_break_15",
"applicable_for_users",
"section_break_23",
"item_groups",
"column_break_25",
"customer_groups",
"more_info_tab",
"section_break_16",
"print_format",
"letter_head",
"column_break0",
"tc_name",
"select_print_heading",
"section_break_19",
"selling_price_list",
"currency",
"write_off_account",
"write_off_cost_center",
"write_off_limit",
"account_for_change_amount",
"disable_rounded_total",
"column_break_23",
"income_account",
"expense_account",
"taxes_and_charges",
"tax_category",
"apply_discount_on",
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
"project"
"campaign_section_break",
"utm_source",
"column_break_tvls",
"utm_campaign",
"column_break_xygw",
"utm_medium"
],
"fields": [
{
@@ -130,8 +150,7 @@
},
{
"fieldname": "section_break_14",
"fieldtype": "Section Break",
"label": "Configuration"
"fieldtype": "Section Break"
},
{
"description": "Only show Items from these Item Groups",
@@ -152,6 +171,7 @@
"options": "POS Customer Group"
},
{
"collapsible": 1,
"fieldname": "section_break_16",
"fieldtype": "Section Break",
"label": "Print Settings"
@@ -191,7 +211,7 @@
{
"fieldname": "section_break_19",
"fieldtype": "Section Break",
"label": "Accounting"
"label": "Miscellaneous"
},
{
"fieldname": "selling_price_list",
@@ -427,9 +447,101 @@
},
{
"default": "0",
"description": "Applicable on POS Invoice",
"fieldname": "allow_partial_payment",
"fieldtype": "Check",
"label": "Allow Partial Payment"
},
{
"fieldname": "column_break_tvls",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_xygw",
"fieldtype": "Column Break"
},
{
"collapsible": 1,
"fieldname": "campaign_section_break",
"fieldtype": "Section Break",
"label": "Campaign"
},
{
"fieldname": "accounting_tab",
"fieldtype": "Tab Break",
"label": "Accounting"
},
{
"fieldname": "more_info_tab",
"fieldtype": "Tab Break",
"label": "More Info"
},
{
"fieldname": "pos_configurations_tab",
"fieldtype": "Tab Break",
"label": "POS Configurations"
},
{
"fieldname": "price_list_and_currency_section",
"fieldtype": "Section Break",
"label": "Price List & Currency"
},
{
"fieldname": "column_break_bptt",
"fieldtype": "Column Break"
},
{
"fieldname": "write_off_section",
"fieldtype": "Section Break",
"label": "Write Off"
},
{
"fieldname": "column_break_ukpz",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_pkca",
"fieldtype": "Column Break"
},
{
"fieldname": "income_and_expense_account",
"fieldtype": "Section Break",
"label": "Income and Expense"
},
{
"fieldname": "column_break_byzk",
"fieldtype": "Column Break"
},
{
"fieldname": "taxes_section",
"fieldtype": "Section Break",
"label": "Taxes"
},
{
"fieldname": "column_break_cjpp",
"fieldtype": "Column Break"
},
{
"fieldname": "pos_item_selector_section",
"fieldtype": "Section Break",
"label": "POS Item Selector"
},
{
"fieldname": "column_break_rpny",
"fieldtype": "Column Break"
},
{
"fieldname": "column_break_stcl",
"fieldtype": "Column Break"
},
{
"fieldname": "pos_item_details_section",
"fieldtype": "Section Break",
"label": "POS Item Details"
},
{
"fieldname": "column_break_hwfg",
"fieldtype": "Column Break"
}
],
"grid_page_length": 50,
@@ -458,7 +570,7 @@
"link_fieldname": "pos_profile"
}
],
"modified": "2025-06-24 11:19:19.834905",
"modified": "2026-02-05 03:38:13.216277",
"modified_by": "Administrator",
"module": "Accounts",
"name": "POS Profile",

View File

@@ -8,12 +8,12 @@
"email_append_to": 1,
"engine": "InnoDB",
"field_order": [
"company",
"title",
"naming_series",
"supplier",
"supplier_name",
"tax_id",
"company",
"column_break_6",
"posting_date",
"posting_time",
@@ -85,20 +85,24 @@
"taxes_and_charges_added",
"taxes_and_charges_deducted",
"total_taxes_and_charges",
"section_break_49",
"totals_section",
"grand_total",
"disable_rounded_total",
"rounding_adjustment",
"column_break8",
"use_company_roundoff_cost_center",
"in_words",
"rounded_total",
"base_totals_section",
"base_grand_total",
"base_rounding_adjustment",
"base_rounded_total",
"column_break_hcca",
"base_in_words",
"column_break8",
"grand_total",
"rounding_adjustment",
"use_company_roundoff_cost_center",
"rounded_total",
"in_words",
"base_rounded_total",
"section_break_ttrv",
"total_advance",
"column_break_peap",
"outstanding_amount",
"disable_rounded_total",
"section_tax_withholding_entry",
"tax_withholding_group",
"ignore_tax_withholding_threshold",
@@ -882,15 +886,10 @@
"options": "currency",
"print_hide": 1
},
{
"fieldname": "section_break_49",
"fieldtype": "Section Break",
"label": "Totals"
},
{
"fieldname": "base_grand_total",
"fieldtype": "Currency",
"label": "Grand Total (Company Currency)",
"label": "Grand Total",
"oldfieldname": "grand_total",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
@@ -901,7 +900,7 @@
"depends_on": "eval:!doc.disable_rounded_total",
"fieldname": "base_rounding_adjustment",
"fieldtype": "Currency",
"label": "Rounding Adjustment (Company Currency)",
"label": "Rounding Adjustment",
"no_copy": 1,
"options": "Company:company:default_currency",
"print_hide": 1,
@@ -911,7 +910,7 @@
"depends_on": "eval:!doc.disable_rounded_total",
"fieldname": "base_rounded_total",
"fieldtype": "Currency",
"label": "Rounded Total (Company Currency)",
"label": "Rounded Total",
"no_copy": 1,
"options": "Company:company:default_currency",
"print_hide": 1,
@@ -920,7 +919,7 @@
{
"fieldname": "base_in_words",
"fieldtype": "Data",
"label": "In Words (Company Currency)",
"label": "In Words",
"length": 240,
"oldfieldname": "in_words",
"oldfieldtype": "Data",
@@ -1625,8 +1624,7 @@
"hidden": 1,
"label": "Item Wise Tax Details",
"no_copy": 1,
"options": "Item Wise Tax Detail",
"print_hide": 1
"options": "Item Wise Tax Detail"
},
{
"collapsible": 1,
@@ -1661,6 +1659,28 @@
"fieldname": "override_tax_withholding_entries",
"fieldtype": "Check",
"label": "Edit Tax Withholding Entries"
},
{
"fieldname": "column_break_hcca",
"fieldtype": "Column Break"
},
{
"fieldname": "section_break_ttrv",
"fieldtype": "Section Break"
},
{
"fieldname": "column_break_peap",
"fieldtype": "Column Break"
},
{
"fieldname": "base_totals_section",
"fieldtype": "Section Break",
"label": "Totals (Company Currency)"
},
{
"fieldname": "totals_section",
"fieldtype": "Section Break",
"label": "Totals"
}
],
"grid_page_length": 50,
@@ -1668,7 +1688,7 @@
"idx": 204,
"is_submittable": 1,
"links": [],
"modified": "2026-02-03 14:23:47.937128",
"modified": "2026-02-04 16:32:19.664287",
"modified_by": "Administrator",
"module": "Accounts",
"name": "Purchase Invoice",

View File

@@ -461,27 +461,6 @@ erpnext.buying.PurchaseOrderController = class PurchaseOrderController extends (
}
}
get_items_from_open_material_requests() {
erpnext.utils.map_current_doc({
method: "erpnext.stock.doctype.material_request.material_request.make_purchase_order_based_on_supplier",
args: {
supplier: this.frm.doc.supplier,
},
source_doctype: "Material Request",
source_name: this.frm.doc.supplier,
target: this.frm,
setters: {
company: this.frm.doc.company,
},
get_query_filters: {
docstatus: ["!=", 2],
supplier: this.frm.doc.supplier,
},
get_query_method:
"erpnext.stock.doctype.material_request.material_request.get_material_requests_based_on_supplier",
});
}
validate() {
set_schedule_date(this.frm);
}

View File

@@ -9,23 +9,20 @@
"engine": "InnoDB",
"field_order": [
"supplier_section",
"company",
"title",
"naming_series",
"supplier",
"supplier_name",
"order_confirmation_no",
"order_confirmation_date",
"get_items_from_open_material_requests",
"mps",
"column_break_7",
"transaction_date",
"schedule_date",
"column_break1",
"supplier",
"company",
"is_subcontracted",
"supplier_name",
"has_unit_price_items",
"supplier_warehouse",
"amended_from",
"accounting_dimensions_section",
"cost_center",
"dimension_col_break",
@@ -79,16 +76,19 @@
"taxes_and_charges_deducted",
"total_taxes_and_charges",
"totals_section",
"grand_total",
"disable_rounded_total",
"rounding_adjustment",
"column_break4",
"in_words",
"rounded_total",
"base_totals_section",
"base_grand_total",
"base_rounding_adjustment",
"column_break_jkoz",
"base_in_words",
"base_rounded_total",
"column_break4",
"grand_total",
"rounding_adjustment",
"rounded_total",
"disable_rounded_total",
"in_words",
"section_break_tnkm",
"advance_paid",
"discount_section",
"apply_discount_on",
@@ -154,11 +154,13 @@
"auto_repeat",
"update_auto_repeat_reference",
"additional_info_section",
"is_internal_supplier",
"party_account_currency",
"represents_company",
"ref_sq",
"amended_from",
"column_break_74",
"party_account_currency",
"mps",
"is_internal_supplier",
"inter_company_order_reference",
"is_old_subcontracting_flow",
"connections_tab"
@@ -206,13 +208,6 @@
"reqd": 1,
"search_index": 1
},
{
"depends_on": "eval:doc.supplier && doc.docstatus===0 && (!(doc.items && doc.items.length) || (doc.items.length==1 && !doc.items[0].item_code))",
"description": "Fetch items based on Default Supplier.",
"fieldname": "get_items_from_open_material_requests",
"fieldtype": "Button",
"label": "Get Items from Open Material Requests"
},
{
"bold": 1,
"fetch_from": "supplier.supplier_name",
@@ -773,7 +768,7 @@
{
"fieldname": "base_grand_total",
"fieldtype": "Currency",
"label": "Grand Total (Company Currency)",
"label": "Grand Total",
"no_copy": 1,
"oldfieldname": "grand_total",
"oldfieldtype": "Currency",
@@ -785,7 +780,7 @@
"depends_on": "eval:!doc.disable_rounded_total",
"fieldname": "base_rounding_adjustment",
"fieldtype": "Currency",
"label": "Rounding Adjustment (Company Currency)",
"label": "Rounding Adjustment",
"no_copy": 1,
"options": "Company:company:default_currency",
"print_hide": 1,
@@ -794,7 +789,7 @@
{
"fieldname": "base_in_words",
"fieldtype": "Data",
"label": "In Words (Company Currency)",
"label": "In Words",
"length": 240,
"oldfieldname": "in_words",
"oldfieldtype": "Data",
@@ -804,7 +799,7 @@
{
"fieldname": "base_rounded_total",
"fieldtype": "Currency",
"label": "Rounded Total (Company Currency)",
"label": "Rounded Total",
"oldfieldname": "rounded_total",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
@@ -862,7 +857,7 @@
{
"fieldname": "advance_paid",
"fieldtype": "Currency",
"label": "Advance Paid",
"label": "Advance Paid (Company Currency)",
"no_copy": 1,
"options": "party_account_currency",
"print_hide": 1,
@@ -1301,8 +1296,21 @@
"hidden": 1,
"label": "Item Wise Tax Details",
"no_copy": 1,
"options": "Item Wise Tax Detail",
"print_hide": 1
"options": "Item Wise Tax Detail"
},
{
"fieldname": "column_break_jkoz",
"fieldtype": "Column Break"
},
{
"fieldname": "base_totals_section",
"fieldtype": "Section Break",
"label": "Totals (Company Currency)",
"options": "Company:company:default_currency"
},
{
"fieldname": "section_break_tnkm",
"fieldtype": "Section Break"
}
],
"grid_page_length": 50,
@@ -1310,7 +1318,7 @@
"idx": 105,
"is_submittable": 1,
"links": [],
"modified": "2026-02-03 14:44:55.192192",
"modified": "2026-02-04 13:01:36.628472",
"modified_by": "Administrator",
"module": "Buying",
"name": "Purchase Order",

View File

@@ -1251,10 +1251,26 @@ class JobCard(Document):
frappe.db.set_value("Workstation", self.workstation, "status", status)
def add_time_logs(self, **kwargs):
row = None
kwargs = frappe._dict(kwargs)
if not kwargs.employees and kwargs.to_time:
for row in self.time_logs:
if not row.to_time and row.from_time:
row.to_time = kwargs.to_time
row.time_in_mins = time_diff_in_minutes(row.to_time, row.from_time)
if kwargs.completed_qty:
row.completed_qty = kwargs.completed_qty
row.db_update()
else:
self.add_time_logs_for_employess(kwargs)
self.validate_time_logs(save=True)
self.save()
def add_time_logs_for_employess(self, kwargs):
row = None
update_status = False
for employee in kwargs.employees:
kwargs.employee = employee.get("employee")
if kwargs.from_time and not kwargs.to_time:
@@ -1290,9 +1306,6 @@ class JobCard(Document):
self.set_status(update_status=update_status)
self.validate_time_logs(save=True)
self.save()
def update_workstation_status(self):
status_map = {
"Open": "Off",

View File

@@ -496,7 +496,7 @@ class ProductionPlan(Document):
item_details = get_item_details(data.item_code, throw=False)
if self.combine_items:
bom_no = item_details.bom_no
bom_no = item_details.get("bom_no")
if data.get("bom_no"):
bom_no = data.get("bom_no")

View File

@@ -8,6 +8,8 @@ from frappe.utils import getdate, today
from erpnext.stock.report.stock_analytics.stock_analytics import get_period, get_period_date_ranges
WORK_ORDER_STATUS_LIST = ["Not Started", "Overdue", "Pending", "Completed", "Closed", "Stopped"]
def execute(filters=None):
columns = get_columns(filters)
@@ -16,119 +18,98 @@ def execute(filters=None):
def get_columns(filters):
columns = [{"label": _("Status"), "fieldname": "Status", "fieldtype": "Data", "width": 140}]
columns = [{"label": _("Status"), "fieldname": "status", "fieldtype": "Data", "width": 140}]
ranges = get_period_date_ranges(filters)
for _dummy, end_date in ranges:
period = get_period(end_date, filters)
columns.append({"label": _(period), "fieldname": scrub(period), "fieldtype": "Float", "width": 120})
return columns
def get_periodic_data(filters, entry):
periodic_data = {
"Not Started": {},
"Overdue": {},
"Pending": {},
"Completed": {},
"Closed": {},
"Stopped": {},
}
def get_work_orders(filters):
from_date = filters.get("from_date")
to_date = filters.get("to_date")
ranges = get_period_date_ranges(filters)
WorkOrder = frappe.qb.DocType("Work Order")
for from_date, end_date in ranges:
period = get_period(end_date, filters)
for d in entry:
if getdate(from_date) <= getdate(d.creation) <= getdate(end_date) and d.status not in [
"Draft",
"Submitted",
"Completed",
"Cancelled",
]:
if d.status in ["Not Started", "Closed", "Stopped"]:
periodic_data = update_periodic_data(periodic_data, d.status, period)
elif getdate(today()) > getdate(d.planned_end_date):
periodic_data = update_periodic_data(periodic_data, "Overdue", period)
elif getdate(today()) < getdate(d.planned_end_date):
periodic_data = update_periodic_data(periodic_data, "Pending", period)
if (
getdate(from_date) <= getdate(d.actual_end_date) <= getdate(end_date)
and d.status == "Completed"
):
periodic_data = update_periodic_data(periodic_data, "Completed", period)
return periodic_data
def update_periodic_data(periodic_data, status, period):
if periodic_data.get(status).get(period):
periodic_data[status][period] += 1
else:
periodic_data[status][period] = 1
return periodic_data
return (
frappe.qb.from_(WorkOrder)
.select(WorkOrder.creation, WorkOrder.actual_end_date, WorkOrder.planned_end_date, WorkOrder.status)
.where(
(WorkOrder.docstatus == 1)
& (WorkOrder.company == filters.get("company"))
& (
(WorkOrder.creation.between(from_date, to_date))
| (WorkOrder.actual_end_date.between(from_date, to_date))
)
)
.run(as_dict=True)
)
def get_data(filters, columns):
data = []
entry = frappe.get_all(
"Work Order",
fields=[
"creation",
"actual_end_date",
"planned_end_date",
"status",
],
filters={"docstatus": 1, "company": filters["company"]},
)
ranges = build_ranges(filters)
period_labels = [scrub(pd) for _fd, _td, pd in ranges]
periodic_data = {status: {pd: 0 for pd in period_labels} for status in WORK_ORDER_STATUS_LIST}
entries = get_work_orders(filters)
periodic_data = get_periodic_data(filters, entry)
for d in entries:
if d.status == "Completed":
if not d.actual_end_date:
continue
labels = ["Not Started", "Overdue", "Pending", "Completed", "Closed", "Stopped"]
chart_data = get_chart_data(periodic_data, columns)
ranges = get_period_date_ranges(filters)
if period := scrub(get_period_for_date(getdate(d.actual_end_date), ranges)):
periodic_data["Completed"][period] += 1
continue
for label in labels:
work = {}
work["Status"] = _(label)
for _dummy, end_date in ranges:
period = get_period(end_date, filters)
if periodic_data.get(label).get(period):
work[scrub(period)] = periodic_data.get(label).get(period)
creation_date = getdate(d.creation)
period = scrub(get_period_for_date(creation_date, ranges))
if not period:
continue
if d.status in ("Not Started", "Closed", "Stopped"):
periodic_data[d.status][period] += 1
else:
if d.planned_end_date and getdate(today()) > getdate(d.planned_end_date):
periodic_data["Overdue"][period] += 1
else:
work[scrub(period)] = 0.0
data.append(work)
periodic_data["Pending"][period] += 1
return data, chart_data
data = []
for status in WORK_ORDER_STATUS_LIST:
row = {"status": _(status)}
for _fd, _td, period in ranges:
row[scrub(period)] = periodic_data[status].get(scrub(period), 0)
data.append(row)
chart = get_chart_data(periodic_data, columns)
return data, chart
def get_period_for_date(date, ranges):
for from_date, to_date, period in ranges:
if from_date <= date <= to_date:
return period
return None
def build_ranges(filters):
ranges = []
for from_date, end_date in get_period_date_ranges(filters):
period = get_period(end_date, filters)
ranges.append((getdate(from_date), getdate(end_date), period))
return ranges
def get_chart_data(periodic_data, columns):
labels = [d.get("label") for d in columns[1:]]
period_labels = [d.get("label") for d in columns[1:]]
period_fieldnames = [d.get("fieldname") for d in columns[1:]]
not_start, overdue, pending, completed, closed, stopped = [], [], [], [], [], []
datasets = []
for status in WORK_ORDER_STATUS_LIST:
values = [periodic_data.get(status, {}).get(fieldname, 0) for fieldname in period_fieldnames]
datasets.append({"name": _(status), "values": values})
for d in labels:
not_start.append(periodic_data.get("Not Started").get(d))
overdue.append(periodic_data.get("Overdue").get(d))
pending.append(periodic_data.get("Pending").get(d))
completed.append(periodic_data.get("Completed").get(d))
closed.append(periodic_data.get("Closed").get(d))
stopped.append(periodic_data.get("Stopped").get(d))
datasets.append({"name": _("Not Started"), "values": not_start})
datasets.append({"name": _("Overdue"), "values": overdue})
datasets.append({"name": _("Pending"), "values": pending})
datasets.append({"name": _("Completed"), "values": completed})
datasets.append({"name": _("Closed"), "values": closed})
datasets.append({"name": _("Stopped"), "values": stopped})
chart = {"data": {"labels": labels, "datasets": datasets}}
chart["type"] = "line"
return chart
return {"data": {"labels": period_labels, "datasets": datasets}, "type": "line"}

View File

@@ -461,4 +461,5 @@ erpnext.patches.v15_0.create_accounting_dimensions_in_advance_taxes_and_charges
execute:frappe.delete_doc_if_exists("Workspace Sidebar", "Opening & Closing")
erpnext.patches.v16_0.migrate_transaction_deletion_task_flags_to_status # 2
erpnext.patches.v16_0.set_ordered_qty_in_quotation_item
erpnext.patches.v16_0.update_company_custom_field_in_bin
erpnext.patches.v16_0.update_company_custom_field_in_bin
erpnext.patches.v15_0.replace_http_with_https_in_sales_partner

View File

@@ -0,0 +1,10 @@
import frappe
from frappe import qb
from pypika.functions import Replace
def execute():
sp = frappe.qb.DocType("Sales Partner")
qb.update(sp).set(sp.partner_website, Replace(sp.partner_website, "http://", "https://")).where(
sp.partner_website.rlike("^http://.*")
).run()

View File

@@ -1733,13 +1733,11 @@ erpnext.TransactionController = class TransactionController extends erpnext.taxe
this.frm.set_currency_labels(
[
"advance_paid",
"base_total",
"base_net_total",
"base_total_taxes_and_charges",
"base_discount_amount",
"base_grand_total",
"base_rounded_total",
"base_in_words",
"base_taxes_and_charges_added",
"base_taxes_and_charges_deducted",
"total_amount_to_pay",
@@ -1762,17 +1760,13 @@ erpnext.TransactionController = class TransactionController extends erpnext.taxe
"net_total",
"total_taxes_and_charges",
"discount_amount",
"grand_total",
"taxes_and_charges_added",
"taxes_and_charges_deducted",
"tax_withholding_net_total",
"rounded_total",
"in_words",
"paid_amount",
"write_off_amount",
"operating_cost",
"scrap_material_cost",
"rounding_adjustment",
"raw_material_cost",
"total_cost",
"totals_section",
@@ -1829,6 +1823,19 @@ erpnext.TransactionController = class TransactionController extends erpnext.taxe
this.frm.doc.price_list_currency != company_currency
);
let taxes_fields = [
"total_taxes_and_charges",
"taxes_and_charges_deducted",
"taxes_and_charges_added",
"base_taxes_and_charges_added",
"base_taxes_and_charges_deducted",
"base_total_taxes_and_charges",
];
taxes_fields.forEach((field) => {
this.frm.toggle_display(field, this.frm.doc[field] !== 0 || this.frm.doc.docstatus !== 1);
});
let show =
cint(this.frm.doc.discount_amount) ||
(this.frm.doc.taxes || []).filter(function (d) {

View File

@@ -50,8 +50,17 @@ class SalesPartner(WebsiteGenerator):
if not self.route:
self.route = "partners/" + self.scrub(self.partner_name)
super().validate()
if self.partner_website and not self.partner_website.startswith("http"):
self.partner_website = "http://" + self.partner_website
if self.partner_website:
from urllib.parse import urlsplit, urlunsplit
# scrub http
parts = urlsplit(self.partner_website)
if not parts.netloc and parts.path:
parts = parts._replace(netloc=parts.path, path="")
if not parts.scheme or parts.scheme == "http":
parts = parts._replace(scheme="https")
self.partner_website = urlunsplit(parts)
def get_context(self, context):
address_names = frappe.db.get_all(

View File

@@ -77,17 +77,19 @@
"taxes_and_charges_added",
"taxes_and_charges_deducted",
"total_taxes_and_charges",
"section_break_46",
"totals_section",
"grand_total",
"disable_rounded_total",
"rounding_adjustment",
"column_break_50",
"in_words",
"rounded_total",
"base_totals_section",
"base_grand_total",
"base_rounding_adjustment",
"base_rounded_total",
"column_break_ugyv",
"base_in_words",
"column_break_50",
"grand_total",
"rounding_adjustment",
"rounded_total",
"in_words",
"disable_rounded_total",
"base_rounded_total",
"section_break_42",
"apply_discount_on",
"base_discount_amount",
@@ -772,15 +774,10 @@
"options": "currency",
"print_hide": 1
},
{
"fieldname": "section_break_46",
"fieldtype": "Section Break",
"label": "Totals"
},
{
"fieldname": "base_grand_total",
"fieldtype": "Currency",
"label": "Grand Total (Company Currency)",
"label": "Grand Total",
"oldfieldname": "grand_total",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
@@ -791,7 +788,7 @@
"depends_on": "eval:!doc.disable_rounded_total",
"fieldname": "base_rounding_adjustment",
"fieldtype": "Currency",
"label": "Rounding Adjustment (Company Currency)",
"label": "Rounding Adjustment",
"no_copy": 1,
"options": "Company:company:default_currency",
"print_hide": 1,
@@ -800,7 +797,7 @@
{
"fieldname": "base_in_words",
"fieldtype": "Data",
"label": "In Words (Company Currency)",
"label": "In Words",
"length": 240,
"oldfieldname": "in_words",
"oldfieldtype": "Data",
@@ -810,7 +807,7 @@
{
"fieldname": "base_rounded_total",
"fieldtype": "Currency",
"label": "Rounded Total (Company Currency)",
"label": "Rounded Total",
"oldfieldname": "rounded_total",
"oldfieldtype": "Currency",
"options": "Company:company:default_currency",
@@ -1282,8 +1279,22 @@
"hidden": 1,
"label": "Item Wise Tax Details",
"no_copy": 1,
"options": "Item Wise Tax Detail",
"print_hide": 1
"options": "Item Wise Tax Detail"
},
{
"fieldname": "totals_section",
"fieldtype": "Section Break",
"label": "Totals"
},
{
"fieldname": "base_totals_section",
"fieldtype": "Section Break",
"label": "Totals (Company Currency)",
"options": "Company:company:default_currency"
},
{
"fieldname": "column_break_ugyv",
"fieldtype": "Column Break"
}
],
"grid_page_length": 50,
@@ -1291,7 +1302,7 @@
"idx": 261,
"is_submittable": 1,
"links": [],
"modified": "2026-01-29 21:24:30.652933",
"modified": "2026-02-04 14:36:41.087460",
"modified_by": "Administrator",
"module": "Stock",
"name": "Purchase Receipt",

View File

@@ -146,7 +146,7 @@
},
{
"bold": 1,
"columns": 3,
"columns": 2,
"fieldname": "item_code",
"fieldtype": "Link",
"in_global_search": 1,
@@ -436,7 +436,6 @@
"columns": 2,
"fieldname": "net_amount",
"fieldtype": "Currency",
"in_list_view": 1,
"label": "Net Amount",
"options": "currency",
"print_hide": 1,
@@ -1141,7 +1140,7 @@
"idx": 1,
"istable": 1,
"links": [],
"modified": "2025-10-21 10:39:32.659933",
"modified": "2026-02-04 14:42:10.646809",
"modified_by": "Administrator",
"module": "Stock",
"name": "Purchase Receipt Item",

View File

@@ -522,6 +522,9 @@ class StockReconciliation(StockController):
if abs(difference_amount) > 0:
return True
float_precision = frappe.db.get_default("float_precision") or 3
item_dict["rate"] = flt(item_dict.get("rate"), float_precision)
item.valuation_rate = flt(item.valuation_rate, float_precision) if item.valuation_rate else None
if (
(item.qty is None or item.qty == item_dict.get("qty"))
and (item.valuation_rate is None or item.valuation_rate == item_dict.get("rate"))