refactor(treewide): formatting and ruff fixes, + manually enabled F401

Signed-off-by: Akhil Narang <me@akhilnarang.dev>
This commit is contained in:
Akhil Narang
2024-03-27 11:37:26 +05:30
parent 9eeedd8515
commit 960ef14b7a
575 changed files with 4086 additions and 6211 deletions

View File

@@ -18,7 +18,7 @@ from frappe.utils import cint, cstr, flt, get_formatted_email, today
from frappe.utils.deprecations import deprecated
from frappe.utils.user import get_users_with_role
from erpnext.accounts.party import get_dashboard_info, validate_party_accounts # noqa
from erpnext.accounts.party import get_dashboard_info, validate_party_accounts
from erpnext.controllers.website_list_for_contact import add_role_for_portal_user
from erpnext.utilities.transaction_base import TransactionBase
@@ -107,17 +107,16 @@ class Customer(TransactionBase):
self.name = set_name_from_naming_options(frappe.get_meta(self.doctype).autoname, self)
def get_customer_name(self):
if frappe.db.get_value("Customer", self.customer_name) and not frappe.flags.in_import:
count = frappe.db.sql(
"""select ifnull(MAX(CAST(SUBSTRING_INDEX(name, ' ', -1) AS UNSIGNED)), 0) from tabCustomer
where name like %s""",
"%{0} - %".format(self.customer_name),
f"%{self.customer_name} - %",
as_list=1,
)[0][0]
count = cint(count) + 1
new_customer_name = "{0} - {1}".format(self.customer_name, cstr(count))
new_customer_name = f"{self.customer_name} - {cstr(count)}"
msgprint(
_("Changed customer name to '{}' as '{}' already exists.").format(
@@ -322,9 +321,7 @@ class Customer(TransactionBase):
)
]
current_credit_limits = [
d.credit_limit for d in sorted(self.credit_limits, key=lambda k: k.company)
]
current_credit_limits = [d.credit_limit for d in sorted(self.credit_limits, key=lambda k: k.company)]
if past_credit_limits == current_credit_limits:
return
@@ -506,9 +503,7 @@ def get_loyalty_programs(doc):
) and (
not loyalty_program.customer_territory
or doc.territory
in get_nested_links(
"Territory", loyalty_program.customer_territory, doc.flags.ignore_permissions
)
in get_nested_links("Territory", loyalty_program.customer_territory, doc.flags.ignore_permissions)
):
lp_details.append(loyalty_program.name)
@@ -554,12 +549,12 @@ def check_credit_limit(customer, company, ignore_outstanding_sales_order=False,
]
if not credit_controller_users_formatted:
frappe.throw(
_("Please contact your administrator to extend the credit limits for {0}.").format(customer)
_("Please contact your administrator to extend the credit limits for {0}.").format(
customer
)
)
user_list = "<br><br><ul><li>{0}</li></ul>".format(
"<li>".join(credit_controller_users_formatted)
)
user_list = "<br><br><ul><li>{}</li></ul>".format("<li>".join(credit_controller_users_formatted))
message += _(
"Please contact any of the following users to extend the credit limits for {0}: {1}"
@@ -592,32 +587,24 @@ def send_emails(args):
message = _("Credit limit has been crossed for customer {0} ({1}/{2})").format(
args.get("customer"), args.get("customer_outstanding"), args.get("credit_limit")
)
frappe.sendmail(
recipients=args.get("credit_controller_users_list"), subject=subject, message=message
)
frappe.sendmail(recipients=args.get("credit_controller_users_list"), subject=subject, message=message)
def get_customer_outstanding(
customer, company, ignore_outstanding_sales_order=False, cost_center=None
):
def get_customer_outstanding(customer, company, ignore_outstanding_sales_order=False, cost_center=None):
# Outstanding based on GL Entries
cond = ""
if cost_center:
lft, rgt = frappe.get_cached_value("Cost Center", cost_center, ["lft", "rgt"])
cond = """ and cost_center in (select name from `tabCost Center` where
lft >= {0} and rgt <= {1})""".format(
lft, rgt
)
cond = f""" and cost_center in (select name from `tabCost Center` where
lft >= {lft} and rgt <= {rgt})"""
outstanding_based_on_gle = frappe.db.sql(
"""
f"""
select sum(debit) - sum(credit)
from `tabGL Entry` where party_type = 'Customer'
and is_cancelled = 0 and party = %s
and company=%s {0}""".format(
cond
),
and company=%s {cond}""",
(customer, company),
)
@@ -765,7 +752,7 @@ def make_address(args, is_primary_address=1, is_shipping_address=1):
if reqd_fields:
msg = _("Following fields are mandatory to create address:")
frappe.throw(
"{0} <br><br> <ul>{1}</ul>".format(msg, "\n".join(reqd_fields)),
"{} <br><br> <ul>{}</ul>".format(msg, "\n".join(reqd_fields)),
title=_("Missing Values Required"),
)

View File

@@ -3,7 +3,6 @@
import frappe
from frappe.custom.doctype.property_setter.property_setter import make_property_setter
from frappe.test_runner import make_test_records
from frappe.tests.utils import FrappeTestCase
from frappe.utils import flt
@@ -268,7 +267,6 @@ class TestCustomer(FrappeTestCase):
def test_customer_credit_limit(self):
from erpnext.accounts.doctype.sales_invoice.test_sales_invoice import create_sales_invoice
from erpnext.selling.doctype.sales_order.sales_order import make_sales_invoice
from erpnext.selling.doctype.sales_order.test_sales_order import make_sales_order
from erpnext.stock.doctype.delivery_note.test_delivery_note import create_delivery_note
@@ -412,17 +410,13 @@ def set_credit_limit(customer, company, credit_limit):
customer.credit_limits[-1].db_insert()
def create_internal_customer(
customer_name=None, represents_company=None, allowed_to_interact_with=None
):
def create_internal_customer(customer_name=None, represents_company=None, allowed_to_interact_with=None):
if not customer_name:
customer_name = represents_company
if not allowed_to_interact_with:
allowed_to_interact_with = represents_company
exisiting_representative = frappe.db.get_value(
"Customer", {"represents_company": represents_company}
)
exisiting_representative = frappe.db.get_value("Customer", {"represents_company": represents_company})
if exisiting_representative:
return exisiting_representative

View File

@@ -44,7 +44,7 @@ class InstallationNote(TransactionBase):
# end: auto-generated types
def __init__(self, *args, **kwargs):
super(InstallationNote, self).__init__(*args, **kwargs)
super().__init__(*args, **kwargs)
self.status_updater = [
{
"source_dt": "Installation Note Item",

View File

@@ -65,7 +65,7 @@ class ProductBundle(Document):
if len(invoice_links):
frappe.throw(
"This Product Bundle is linked with {0}. You will have to cancel these documents in order to delete this Product Bundle".format(
"This Product Bundle is linked with {}. You will have to cancel these documents in order to delete this Product Bundle".format(
", ".join(invoice_links)
),
title=_("Not Allowed"),
@@ -97,9 +97,7 @@ def get_new_item_code(doctype, txt, searchfield, start, page_len, filters):
query = (
frappe.qb.from_(item)
.select(item.item_code, item.item_name)
.where(
(item.is_stock_item == 0) & (item.is_fixed_asset == 0) & (item[searchfield].like(f"%{txt}%"))
)
.where((item.is_stock_item == 0) & (item.is_fixed_asset == 0) & (item[searchfield].like(f"%{txt}%")))
.limit(page_len)
.offset(start)
)

View File

@@ -125,7 +125,7 @@ class Quotation(SellingController):
self.indicator_title = "Expired"
def validate(self):
super(Quotation, self).validate()
super().validate()
self.set_status()
self.validate_uom_is_integer("stock_uom", "stock_qty")
self.validate_uom_is_integer("uom", "qty")
@@ -188,7 +188,8 @@ class Quotation(SellingController):
def is_in_sales_order(row):
in_sales_order = bool(
frappe.db.exists(
"Sales Order Item", {"quotation_item": row.name, "item_code": row.item_code, "docstatus": 1}
"Sales Order Item",
{"quotation_item": row.name, "item_code": row.item_code, "docstatus": 1},
)
)
return in_sales_order
@@ -278,7 +279,7 @@ class Quotation(SellingController):
def on_cancel(self):
if self.lost_reasons:
self.lost_reasons = []
super(Quotation, self).on_cancel()
super().on_cancel()
# update enquiry status
self.set_status(update=True)
@@ -453,12 +454,8 @@ def set_expired_status():
# if not exists any SO, set status as Expired
frappe.db.multisql(
{
"mariadb": """UPDATE `tabQuotation` SET `tabQuotation`.status = 'Expired' WHERE {cond} and not exists({so_against_quo})""".format(
cond=cond, so_against_quo=so_against_quo
),
"postgres": """UPDATE `tabQuotation` SET status = 'Expired' FROM `tabSales Order`, `tabSales Order Item` WHERE {cond} and not exists({so_against_quo})""".format(
cond=cond, so_against_quo=so_against_quo
),
"mariadb": f"""UPDATE `tabQuotation` SET `tabQuotation`.status = 'Expired' WHERE {cond} and not exists({so_against_quo})""",
"postgres": f"""UPDATE `tabQuotation` SET status = 'Expired' FROM `tabSales Order`, `tabSales Order Item` WHERE {cond} and not exists({so_against_quo})""",
},
(nowdate()),
)
@@ -543,7 +540,8 @@ def _make_customer(source_name, ignore_permissions=False, customer_group=None):
frappe.local.message_log = []
lead_link = frappe.utils.get_link_to_form("Lead", lead_name)
message = (
_("Could not auto create Customer due to the following missing mandatory field(s):") + "<br>"
_("Could not auto create Customer due to the following missing mandatory field(s):")
+ "<br>"
)
message += "<br><ul><li>" + "</li><li>".join(mandatory_fields) + "</li></ul>"
message += _("Please create Customer from Lead {0}.").format(lead_link)

View File

@@ -140,9 +140,7 @@ class TestQuotation(FrappeTestCase):
self.assertEqual(quotation.payment_schedule[0].payment_amount, 8906.00)
self.assertEqual(quotation.payment_schedule[0].due_date, quotation.transaction_date)
self.assertEqual(quotation.payment_schedule[1].payment_amount, 8906.00)
self.assertEqual(
quotation.payment_schedule[1].due_date, add_days(quotation.transaction_date, 30)
)
self.assertEqual(quotation.payment_schedule[1].due_date, add_days(quotation.transaction_date, 30))
sales_order = make_sales_order(quotation.name)
@@ -175,9 +173,7 @@ class TestQuotation(FrappeTestCase):
def test_so_from_expired_quotation(self):
from erpnext.selling.doctype.quotation.quotation import make_sales_order
frappe.db.set_single_value(
"Selling Settings", "allow_sales_order_creation_for_expired_quotation", 0
)
frappe.db.set_single_value("Selling Settings", "allow_sales_order_creation_for_expired_quotation", 0)
quotation = frappe.copy_doc(test_records[0])
quotation.valid_till = add_days(nowdate(), -1)
@@ -186,9 +182,7 @@ class TestQuotation(FrappeTestCase):
self.assertRaises(frappe.ValidationError, make_sales_order, quotation.name)
frappe.db.set_single_value(
"Selling Settings", "allow_sales_order_creation_for_expired_quotation", 1
)
frappe.db.set_single_value("Selling Settings", "allow_sales_order_creation_for_expired_quotation", 1)
make_sales_order(quotation.name)
@@ -646,7 +640,7 @@ class TestQuotation(FrappeTestCase):
).insert()
if not frappe.db.exists("Item Tax Template", "Vat Template - _TC"):
doc = frappe.get_doc(
frappe.get_doc(
{
"doctype": "Item Tax Template",
"name": "Vat Template",
@@ -668,9 +662,7 @@ class TestQuotation(FrappeTestCase):
item_doc.append("taxes", {"item_tax_template": "Vat Template - _TC"})
item_doc.save()
quotation = make_quotation(
item_code="_Test Item Tax Template QTN", qty=1, rate=100, do_not_submit=1
)
quotation = make_quotation(item_code="_Test Item Tax Template QTN", qty=1, rate=100, do_not_submit=1)
self.assertFalse(quotation.taxes)
quotation.append_taxes_from_item_tax_template()

View File

@@ -182,7 +182,7 @@ class SalesOrder(SellingController):
# end: auto-generated types
def __init__(self, *args, **kwargs):
super(SalesOrder, self).__init__(*args, **kwargs)
super().__init__(*args, **kwargs)
def onload(self) -> None:
if frappe.db.get_single_value("Stock Settings", "enable_stock_reservation"):
@@ -193,7 +193,7 @@ class SalesOrder(SellingController):
self.set_onload("has_reserved_stock", True)
def validate(self):
super(SalesOrder, self).validate()
super().validate()
self.validate_delivery_date()
self.validate_proj_cust()
self.validate_po()
@@ -234,7 +234,9 @@ class SalesOrder(SellingController):
for d in self.get("items"):
if d.delivery_date and getdate(self.po_date) > getdate(d.delivery_date):
frappe.throw(
_("Row #{0}: Expected Delivery Date cannot be before Purchase Order Date").format(d.idx)
_("Row #{0}: Expected Delivery Date cannot be before Purchase Order Date").format(
d.idx
)
)
if self.po_no and self.customer and not self.skip_delivery_note:
@@ -249,9 +251,9 @@ class SalesOrder(SellingController):
frappe.db.get_single_value("Selling Settings", "allow_against_multiple_purchase_orders")
):
frappe.msgprint(
_("Warning: Sales Order {0} already exists against Customer's Purchase Order {1}").format(
frappe.bold(so[0][0]), frappe.bold(self.po_no)
),
_(
"Warning: Sales Order {0} already exists against Customer's Purchase Order {1}"
).format(frappe.bold(so[0][0]), frappe.bold(self.po_no)),
alert=True,
)
else:
@@ -261,14 +263,15 @@ class SalesOrder(SellingController):
).format(
frappe.bold(so[0][0]),
frappe.bold(self.po_no),
frappe.bold(_("'Allow Multiple Sales Orders Against a Customer's Purchase Order'")),
frappe.bold(
_("'Allow Multiple Sales Orders Against a Customer's Purchase Order'")
),
get_link_to_form("Selling Settings", "Selling Settings"),
)
)
def validate_for_items(self):
for d in self.get("items"):
# used for production plan
d.transaction_date = self.transaction_date
@@ -298,7 +301,9 @@ class SalesOrder(SellingController):
(d.prevdoc_docname, self.order_type),
)
if not res:
frappe.msgprint(_("Quotation {0} not of type {1}").format(d.prevdoc_docname, self.order_type))
frappe.msgprint(
_("Quotation {0} not of type {1}").format(d.prevdoc_docname, self.order_type)
)
def validate_delivery_date(self):
if self.order_type == "Sales" and not self.skip_delivery_note:
@@ -337,13 +342,16 @@ class SalesOrder(SellingController):
)
def validate_warehouse(self):
super(SalesOrder, self).validate_warehouse()
super().validate_warehouse()
for d in self.get("items"):
if (
(
frappe.get_cached_value("Item", d.item_code, "is_stock_item") == 1
or (self.has_product_bundle(d.item_code) and self.product_bundle_has_stock_item(d.item_code))
or (
self.has_product_bundle(d.item_code)
and self.product_bundle_has_stock_item(d.item_code)
)
)
and not d.warehouse
and not cint(d.delivered_by_supplier)
@@ -353,7 +361,7 @@ class SalesOrder(SellingController):
)
def validate_with_previous_doc(self):
super(SalesOrder, self).validate_with_previous_doc(
super().validate_with_previous_doc(
{
"Quotation": {"ref_dn_field": "prevdoc_docname", "compare_fields": [["company", "="]]},
"Quotation Item": {
@@ -414,7 +422,7 @@ class SalesOrder(SellingController):
def on_cancel(self):
self.ignore_linked_doctypes = ("GL Entry", "Stock Ledger Entry", "Payment Ledger Entry")
super(SalesOrder, self).on_cancel()
super().on_cancel()
# Cannot cancel closed SO
if self.status == "Closed":
@@ -437,9 +445,7 @@ class SalesOrder(SellingController):
update_coupon_code_count(self.coupon_code, "cancelled")
def update_project(self):
if (
frappe.db.get_single_value("Selling Settings", "sales_update_frequency") != "Each Transaction"
):
if frappe.db.get_single_value("Selling Settings", "sales_update_frequency") != "Each Transaction":
return
if self.project:
@@ -477,7 +483,7 @@ class SalesOrder(SellingController):
def check_modified_date(self):
mod_db = frappe.db.get_value("Sales Order", self.name, "modified")
date_diff = frappe.db.sql("select TIMEDIFF('%s', '%s')" % (mod_db, cstr(self.modified)))
date_diff = frappe.db.sql(f"select TIMEDIFF('{mod_db}', '{cstr(self.modified)}')")
if date_diff and date_diff[0][0]:
frappe.throw(_("{0} {1} has been modified. Please refresh.").format(self.doctype, self.name))
@@ -654,9 +660,9 @@ class SalesOrder(SellingController):
)
if not frappe.db.exists("BOM", {"item": item.item_code, "is_active": 1}):
frappe.throw(
_("No active BOM found for item {0}. Delivery by Serial No cannot be ensured").format(
item.item_code
)
_(
"No active BOM found for item {0}. Delivery by Serial No cannot be ensured"
).format(item.item_code)
)
reserved_items.append(item.item_code)
else:
@@ -672,9 +678,7 @@ class SalesOrder(SellingController):
def validate_reserved_stock(self):
"""Clean reserved stock flag for non-stock Item"""
enable_stock_reservation = frappe.db.get_single_value(
"Stock Settings", "enable_stock_reservation"
)
enable_stock_reservation = frappe.db.get_single_value("Stock Settings", "enable_stock_reservation")
for item in self.items:
if item.reserve_stock and (not enable_stock_reservation or not cint(item.is_stock_item)):
@@ -698,7 +702,7 @@ class SalesOrder(SellingController):
@frappe.whitelist()
def create_stock_reservation_entries(
self,
items_details: list[dict] = None,
items_details: list[dict] | None = None,
from_voucher_type: Literal["Pick List", "Purchase Receipt"] = None,
notify=True,
) -> None:
@@ -732,11 +736,7 @@ def get_unreserved_qty(item: object, reserved_qty_details: dict) -> float:
"""Returns the unreserved quantity for the Sales Order Item."""
existing_reserved_qty = reserved_qty_details.get(item.name, 0)
return (
item.stock_qty
- flt(item.delivered_qty) * item.get("conversion_factor", 1)
- existing_reserved_qty
)
return item.stock_qty - flt(item.delivered_qty) * item.get("conversion_factor", 1) - existing_reserved_qty
def get_list_context(context=None):
@@ -1175,7 +1175,7 @@ def get_events(start, end, filters=None):
conditions = get_event_conditions("Sales Order", filters)
data = frappe.db.sql(
"""
f"""
select
distinct `tabSales Order`.name, `tabSales Order`.customer_name, `tabSales Order`.status,
`tabSales Order`.delivery_status, `tabSales Order`.billing_status,
@@ -1188,9 +1188,7 @@ def get_events(start, end, filters=None):
and (`tabSales Order Item`.delivery_date between %(start)s and %(end)s)
and `tabSales Order`.docstatus < 2
{conditions}
""".format(
conditions=conditions
),
""",
{"start": start, "end": end},
as_dict=True,
update={"allDay": 0},
@@ -1264,9 +1262,7 @@ def make_purchase_order_for_default_supplier(source_name, selected_items=None, t
items_to_map = list(set(items_to_map))
if not suppliers:
frappe.throw(
_("Please set a Supplier against the Items to be considered in the Purchase Order.")
)
frappe.throw(_("Please set a Supplier against the Items to be considered in the Purchase Order."))
purchase_orders = []
for supplier in suppliers:
@@ -1332,9 +1328,7 @@ def make_purchase_order(source_name, selected_items=None, target_doc=None):
selected_items = json.loads(selected_items)
items_to_map = [
item.get("item_code")
for item in selected_items
if item.get("item_code") and item.get("item_code")
item.get("item_code") for item in selected_items if item.get("item_code") and item.get("item_code")
]
items_to_map = list(set(items_to_map))
@@ -1517,17 +1511,13 @@ def make_raw_material_request(items, company, sales_order, project=None):
for item in items.get("items"):
item["include_exploded_items"] = items.get("include_exploded_items")
item["ignore_existing_ordered_qty"] = items.get("ignore_existing_ordered_qty")
item["include_raw_materials_from_sales_order"] = items.get(
"include_raw_materials_from_sales_order"
)
item["include_raw_materials_from_sales_order"] = items.get("include_raw_materials_from_sales_order")
items.update({"company": company, "sales_order": sales_order})
raw_materials = get_items_for_material_requests(items)
if not raw_materials:
frappe.msgprint(
_("Material Request not created, as quantity for Raw Materials already available.")
)
frappe.msgprint(_("Material Request not created, as quantity for Raw Materials already available."))
return
material_request = frappe.new_doc("Material Request")

View File

@@ -306,9 +306,7 @@ class TestSalesOrder(FrappeTestCase):
def test_reserved_qty_for_partial_delivery_with_packing_list(self):
make_stock_entry(target="_Test Warehouse - _TC", qty=10, rate=100)
make_stock_entry(
item="_Test Item Home Desktop 100", target="_Test Warehouse - _TC", qty=10, rate=100
)
make_stock_entry(item="_Test Item Home Desktop 100", target="_Test Warehouse - _TC", qty=10, rate=100)
existing_reserved_qty_item1 = get_reserved_qty("_Test Item")
existing_reserved_qty_item2 = get_reserved_qty("_Test Item Home Desktop 100")
@@ -316,16 +314,12 @@ class TestSalesOrder(FrappeTestCase):
so = make_sales_order(item_code="_Test Product Bundle Item")
self.assertEqual(get_reserved_qty("_Test Item"), existing_reserved_qty_item1 + 50)
self.assertEqual(
get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20
)
self.assertEqual(get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20)
dn = create_dn_against_so(so.name)
self.assertEqual(get_reserved_qty("_Test Item"), existing_reserved_qty_item1 + 25)
self.assertEqual(
get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 10
)
self.assertEqual(get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 10)
# close so
so.load_from_db()
@@ -339,15 +333,11 @@ class TestSalesOrder(FrappeTestCase):
so.update_status("Draft")
self.assertEqual(get_reserved_qty("_Test Item"), existing_reserved_qty_item1 + 25)
self.assertEqual(
get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 10
)
self.assertEqual(get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 10)
dn.cancel()
self.assertEqual(get_reserved_qty("_Test Item"), existing_reserved_qty_item1 + 50)
self.assertEqual(
get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20
)
self.assertEqual(get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20)
so.load_from_db()
so.cancel()
@@ -363,9 +353,7 @@ class TestSalesOrder(FrappeTestCase):
def test_reserved_qty_for_over_delivery_with_packing_list(self):
make_stock_entry(target="_Test Warehouse - _TC", qty=10, rate=100)
make_stock_entry(
item="_Test Item Home Desktop 100", target="_Test Warehouse - _TC", qty=10, rate=100
)
make_stock_entry(item="_Test Item Home Desktop 100", target="_Test Warehouse - _TC", qty=10, rate=100)
# set over-delivery allowance
frappe.db.set_value("Item", "_Test Product Bundle Item", "over_delivery_receipt_allowance", 50)
@@ -376,9 +364,7 @@ class TestSalesOrder(FrappeTestCase):
so = make_sales_order(item_code="_Test Product Bundle Item")
self.assertEqual(get_reserved_qty("_Test Item"), existing_reserved_qty_item1 + 50)
self.assertEqual(
get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20
)
self.assertEqual(get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20)
dn = create_dn_against_so(so.name, 15)
@@ -387,9 +373,7 @@ class TestSalesOrder(FrappeTestCase):
dn.cancel()
self.assertEqual(get_reserved_qty("_Test Item"), existing_reserved_qty_item1 + 50)
self.assertEqual(
get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20
)
self.assertEqual(get_reserved_qty("_Test Item Home Desktop 100"), existing_reserved_qty_item2 + 20)
def test_update_child_adding_new_item(self):
so = make_sales_order(item_code="_Test Item", qty=4)
@@ -459,9 +443,7 @@ class TestSalesOrder(FrappeTestCase):
trans_item = json.dumps(
[{"item_code": "_Test Item 2", "qty": 2, "rate": 500, "docname": so.get("items")[1].name}]
)
self.assertRaises(
frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name
)
self.assertRaises(frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name)
# remove last added item
trans_item = json.dumps(
@@ -500,9 +482,7 @@ class TestSalesOrder(FrappeTestCase):
trans_item = json.dumps(
[{"item_code": "_Test Item", "rate": 200, "qty": 2, "docname": so.items[0].name}]
)
self.assertRaises(
frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name
)
self.assertRaises(frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name)
def test_update_child_with_precision(self):
from frappe.custom.doctype.property_setter.property_setter import make_property_setter
@@ -532,15 +512,11 @@ class TestSalesOrder(FrappeTestCase):
trans_item = json.dumps(
[{"item_code": "_Test Item", "rate": 200, "qty": 7, "docname": so.items[0].name}]
)
self.assertRaises(
frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name
)
self.assertRaises(frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name)
# add new item
trans_item = json.dumps([{"item_code": "_Test Item", "rate": 100, "qty": 2}])
self.assertRaises(
frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name
)
self.assertRaises(frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name)
def test_update_child_qty_rate_with_workflow(self):
from frappe.model.workflow import apply_workflow
@@ -558,9 +534,7 @@ class TestSalesOrder(FrappeTestCase):
trans_item = json.dumps(
[{"item_code": "_Test Item", "rate": 150, "qty": 2, "docname": so.items[0].name}]
)
self.assertRaises(
frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name
)
self.assertRaises(frappe.ValidationError, update_child_qty_rate, "Sales Order", trans_item, so.name)
frappe.set_user("Administrator")
user2 = "test2@example.com"
@@ -818,9 +792,7 @@ class TestSalesOrder(FrappeTestCase):
frappe.set_user("Administrator")
frappe.permissions.remove_user_permission("Warehouse", "_Test Warehouse 1 - _TC", test_user.name)
frappe.permissions.remove_user_permission(
"Warehouse", "_Test Warehouse 2 - _TC1", test_user_2.name
)
frappe.permissions.remove_user_permission("Warehouse", "_Test Warehouse 2 - _TC1", test_user_2.name)
frappe.permissions.remove_user_permission("Company", "_Test Company 1", test_user_2.name)
def test_block_delivery_note_against_cancelled_sales_order(self):
@@ -939,9 +911,7 @@ class TestSalesOrder(FrappeTestCase):
from erpnext.selling.doctype.sales_order.sales_order import update_status as so_update_status
# make items
po_item = make_item(
"_Test Item for Drop Shipping", {"is_stock_item": 1, "delivered_by_supplier": 1}
)
po_item = make_item("_Test Item for Drop Shipping", {"is_stock_item": 1, "delivered_by_supplier": 1})
dn_item = make_item("_Test Regular Item", {"is_stock_item": 1})
so_items = [
@@ -1224,17 +1194,13 @@ class TestSalesOrder(FrappeTestCase):
new_so = frappe.copy_doc(so)
new_so.save(ignore_permissions=True)
self.assertEqual(
new_so.get("items")[0].rate, flt((price_list_rate * 25) / 100 + price_list_rate)
)
self.assertEqual(new_so.get("items")[0].rate, flt((price_list_rate * 25) / 100 + price_list_rate))
new_so.items[0].margin_rate_or_amount = 25
new_so.payment_schedule = []
new_so.save()
new_so.submit()
self.assertEqual(
new_so.get("items")[0].rate, flt((price_list_rate * 25) / 100 + price_list_rate)
)
self.assertEqual(new_so.get("items")[0].rate, flt((price_list_rate * 25) / 100 + price_list_rate))
def test_terms_auto_added(self):
so = make_sales_order(do_not_save=1)
@@ -1304,9 +1270,7 @@ class TestSalesOrder(FrappeTestCase):
def test_advance_payment_entry_unlink_against_sales_order(self):
from erpnext.accounts.doctype.payment_entry.test_payment_entry import get_payment_entry
frappe.db.set_single_value(
"Accounts Settings", "unlink_advance_payment_on_cancelation_of_order", 0
)
frappe.db.set_single_value("Accounts Settings", "unlink_advance_payment_on_cancelation_of_order", 0)
so = make_sales_order()
@@ -1359,9 +1323,7 @@ class TestSalesOrder(FrappeTestCase):
so = make_sales_order()
# disable unlinking of payment entry
frappe.db.set_single_value(
"Accounts Settings", "unlink_advance_payment_on_cancelation_of_order", 0
)
frappe.db.set_single_value("Accounts Settings", "unlink_advance_payment_on_cancelation_of_order", 0)
# create a payment entry against sales order
pe = get_payment_entry("Sales Order", so.name, bank_account="_Test Bank - _TC")
@@ -1492,7 +1454,7 @@ class TestSalesOrder(FrappeTestCase):
Second Sales Order should not add on to Blanket Orders Ordered Quantity.
"""
bo = make_blanket_order(blanket_order_type="Selling", quantity=10, rate=10)
make_blanket_order(blanket_order_type="Selling", quantity=10, rate=10)
so = make_sales_order(item_code="_Test Item", qty=5, against_blanket_order=1)
so_doc = frappe.get_doc("Sales Order", so.get("name"))
@@ -1713,7 +1675,10 @@ class TestSalesOrder(FrappeTestCase):
wo.submit()
make_stock_entry(
item_code="_Test Item", target="Work In Progress - _TC", qty=4, basic_rate=100 # Stock RM
item_code="_Test Item",
target="Work In Progress - _TC",
qty=4,
basic_rate=100, # Stock RM
)
make_stock_entry(
item_code="_Test Item Home Desktop 100", # Stock RM
@@ -1821,10 +1786,6 @@ class TestSalesOrder(FrappeTestCase):
def test_delivered_item_material_request(self):
"SO -> MR (Manufacture) -> WO. Test if WO Qty is updated in SO."
from erpnext.manufacturing.doctype.work_order.work_order import (
make_stock_entry as make_se_from_wo,
)
from erpnext.stock.doctype.material_request.material_request import raise_work_orders
so = make_sales_order(
item_list=[
@@ -1832,9 +1793,7 @@ class TestSalesOrder(FrappeTestCase):
]
)
make_stock_entry(
item_code="_Test FG Item", target="Work In Progress - _TC", qty=4, basic_rate=100
)
make_stock_entry(item_code="_Test FG Item", target="Work In Progress - _TC", qty=4, basic_rate=100)
dn = make_delivery_note(so.name)
dn.items[0].qty = 4
@@ -1859,7 +1818,8 @@ class TestSalesOrder(FrappeTestCase):
if not frappe.db.exists("Item", product_bundle):
bundle_item = make_item(product_bundle, {"is_stock_item": 0})
bundle_item.append(
"item_defaults", {"company": "_Test Company", "default_warehouse": "_Test Warehouse - _TC"}
"item_defaults",
{"company": "_Test Company", "default_warehouse": "_Test Warehouse - _TC"},
)
bundle_item.save(ignore_permissions=True)
@@ -1929,7 +1889,8 @@ class TestSalesOrder(FrappeTestCase):
if not frappe.db.exists("Item", product_bundle):
bundle_item = make_item(product_bundle, {"is_stock_item": 0})
bundle_item.append(
"item_defaults", {"company": "_Test Company", "default_warehouse": "_Test Warehouse - _TC"}
"item_defaults",
{"company": "_Test Company", "default_warehouse": "_Test Warehouse - _TC"},
)
bundle_item.save(ignore_permissions=True)
@@ -2202,9 +2163,7 @@ def create_dn_against_so(so, delivered_qty=0, do_not_submit=False):
def get_reserved_qty(item_code="_Test Item", warehouse="_Test Warehouse - _TC"):
return flt(
frappe.db.get_value("Bin", {"item_code": item_code, "warehouse": warehouse}, "reserved_qty")
)
return flt(frappe.db.get_value("Bin", {"item_code": item_code, "warehouse": warehouse}, "reserved_qty"))
test_dependencies = ["Currency Exchange"]
@@ -2217,9 +2176,7 @@ def make_sales_order_workflow():
doc.save()
return doc
frappe.get_doc(dict(doctype="Role", role_name="Test Junior Approver")).insert(
ignore_if_duplicate=True
)
frappe.get_doc(dict(doctype="Role", role_name="Test Junior Approver")).insert(ignore_if_duplicate=True)
frappe.get_doc(dict(doctype="Role", role_name="Test Approver")).insert(ignore_if_duplicate=True)
frappe.cache().hdel("roles", frappe.session.user)

View File

@@ -3,7 +3,6 @@
import json
from typing import Dict, Optional
import frappe
from frappe.utils import cint
@@ -198,16 +197,14 @@ def get_items(start, page_length, price_list, item_group, pos_profile, search_te
@frappe.whitelist()
def search_for_serial_or_batch_or_barcode_number(search_value: str) -> Dict[str, Optional[str]]:
def search_for_serial_or_batch_or_barcode_number(search_value: str) -> dict[str, str | None]:
return scan_barcode(search_value)
def get_conditions(search_term):
condition = "("
condition += """item.name like {search_term}
or item.item_name like {search_term}""".format(
search_term=frappe.db.escape("%" + search_term + "%")
)
or item.item_name like {search_term}""".format(search_term=frappe.db.escape("%" + search_term + "%"))
condition += add_search_fields_condition(search_term)
condition += ")"
@@ -219,7 +216,7 @@ def add_search_fields_condition(search_term):
search_fields = frappe.get_all("POS Search Fields", fields=["fieldname"])
if search_fields:
for field in search_fields:
condition += " or item.`{0}` like {1}".format(
condition += " or item.`{}` like {}".format(
field["fieldname"], frappe.db.escape("%" + search_term + "%")
)
return condition
@@ -249,10 +246,8 @@ def item_group_query(doctype, txt, searchfield, start, page_len, filters):
cond = cond % tuple(item_groups)
return frappe.db.sql(
""" select distinct name from `tabItem Group`
where {condition} and (name like %(txt)s) limit {page_len} offset {start}""".format(
condition=cond, start=start, page_len=page_len
),
f""" select distinct name from `tabItem Group`
where {cond} and (name like %(txt)s) limit {page_len} offset {start}""",
{"txt": "%%%s%%" % txt},
)
@@ -297,13 +292,13 @@ def get_past_order_list(search_term, status, limit=20):
if search_term and status:
invoices_by_customer = frappe.db.get_all(
"POS Invoice",
filters={"customer": ["like", "%{}%".format(search_term)], "status": status},
filters={"customer": ["like", f"%{search_term}%"], "status": status},
fields=fields,
page_length=limit,
)
invoices_by_name = frappe.db.get_all(
"POS Invoice",
filters={"name": ["like", "%{}%".format(search_term)], "status": status},
filters={"name": ["like", f"%{search_term}%"], "status": status},
fields=fields,
page_length=limit,
)

View File

@@ -85,7 +85,7 @@ def get_opp_by_lead_source(from_date, to_date, company):
* x["probability"]
/ 100
)
}
},
)
for x in opportunities
]
@@ -137,7 +137,7 @@ def get_pipeline_data(from_date, to_date, company):
* x["probability"]
/ 100
)
}
},
)
for x in opportunities
]

View File

@@ -27,8 +27,8 @@ def get_columns(filters):
party_type = filters.get("party_type")
party_type_value = get_party_group(party_type)
return [
"{party_type}:Link/{party_type}".format(party_type=party_type),
"{party_value_type}::150".format(party_value_type=frappe.unscrub(str(party_type_value))),
f"{party_type}:Link/{party_type}",
f"{frappe.unscrub(str(party_type_value))}::150",
"Address Line 1",
"Address Line 2",
"City",
@@ -109,7 +109,7 @@ def get_party_details(party_type, party_list, doctype, party_details):
["Dynamic Link", "link_doctype", "=", party_type],
["Dynamic Link", "link_name", "in", party_list],
]
fields = ["`tabDynamic Link`.link_name"] + field_map.get(doctype, [])
fields = ["`tabDynamic Link`.link_name", *field_map.get(doctype, [])]
records = frappe.get_list(doctype, filters=filters, fields=fields, as_list=True)
for d in records:

View File

@@ -77,10 +77,8 @@ def get_data_by_time(filters, common_columns):
out = []
for year in range(from_year, to_year + 1):
for month in range(
from_month if year == from_year else 1, (to_month + 1) if year == to_year else 13
):
key = "{year}-{month:02d}".format(year=year, month=month)
for month in range(from_month if year == from_year else 1, (to_month + 1) if year == to_year else 13):
key = f"{year}-{month:02d}"
data = customers_in.get(key)
new = data["new"] if data else [0, 0.0]
repeat = data["repeat"] if data else [0, 0.0]
@@ -147,7 +145,7 @@ def get_data_by_territory(filters, common_columns):
for ld in loop_data:
if ld["parent_territory"]:
parent_data = [x for x in data if x["territory"] == ld["parent_territory"]][0]
parent_data = next(x for x in data if x["territory"] == ld["parent_territory"])
for key in parent_data.keys():
if key not in ["indent", "territory", "parent_territory", "bold"]:
parent_data[key] += ld[key]
@@ -165,15 +163,12 @@ def get_customer_stats(filters, tree_view=False):
customers_in = {}
for si in frappe.db.sql(
"""select territory, posting_date, customer, base_grand_total from `tabSales Invoice`
f"""select territory, posting_date, customer, base_grand_total from `tabSales Invoice`
where docstatus=1 and posting_date <= %(to_date)s
{company_condition} order by posting_date""".format(
company_condition=company_condition
),
{company_condition} order by posting_date""",
filters,
as_dict=1,
):
key = si.territory if tree_view else si.posting_date.strftime("%Y-%m")
new_or_repeat = "new" if si.customer not in customers else "repeat"
customers_in.setdefault(key, {"new": [0, 0.0], "repeat": [0, 0.0]})

View File

@@ -77,7 +77,6 @@ def get_columns(customer_naming_type):
def get_details(filters):
sql_query = """SELECT
c.name, c.customer_name,
ccl.bypass_credit_limit_check,

View File

@@ -51,7 +51,10 @@ def get_columns(filters=None):
def fetch_item_prices(
customer: str = None, price_list: str = None, selling_price_list: str = None, items: list = None
customer: str | None = None,
price_list: str | None = None,
selling_price_list: str | None = None,
items: list | None = None,
):
price_list_map = frappe._dict()
ip = qb.DocType("Item Price")
@@ -59,10 +62,10 @@ def fetch_item_prices(
or_conditions = []
if items:
and_conditions.append(ip.item_code.isin([x.item_code for x in items]))
and_conditions.append(ip.selling == True)
and_conditions.append(ip.selling is True)
or_conditions.append(ip.customer == None)
or_conditions.append(ip.price_list == None)
or_conditions.append(ip.customer is None)
or_conditions.append(ip.price_list is None)
if customer:
or_conditions.append(ip.customer == customer)

View File

@@ -40,19 +40,17 @@ def get_sales_details(doctype):
DATEDIFF(CURRENT_DATE, max(so.transaction_date)) as 'days_since_last_order'"""
return frappe.db.sql(
"""select
f"""select
cust.name,
cust.customer_name,
cust.territory,
cust.customer_group,
count(distinct(so.name)) as 'num_of_order',
sum(base_net_total) as 'total_order_value', {0}
from `tabCustomer` cust, `tab{1}` so
sum(base_net_total) as 'total_order_value', {cond}
from `tabCustomer` cust, `tab{doctype}` so
where cust.name = so.customer and so.docstatus = 1
group by cust.name
order by 'days_since_last_order' desc """.format(
cond, doctype
),
order by 'days_since_last_order' desc """,
as_list=1,
)
@@ -62,11 +60,9 @@ def get_last_sales_amt(customer, doctype):
if doctype == "Sales Order":
cond = "transaction_date"
res = frappe.db.sql(
"""select base_net_total from `tab{0}`
where customer = %s and docstatus = 1 order by {1} desc
limit 1""".format(
doctype, cond
),
f"""select base_net_total from `tab{doctype}`
where customer = %s and docstatus = 1 order by {cond} desc
limit 1""",
customer,
)

View File

@@ -128,7 +128,6 @@ def get_columns(filters):
def get_data(filters):
data = []
company_list = get_descendants_of("Company", filters.get("company"))
@@ -181,9 +180,7 @@ def get_item_details():
details = frappe.db.get_all("Item", fields=["name", "item_name", "item_group"])
item_details = {}
for d in details:
item_details.setdefault(
d.name, frappe._dict({"item_name": d.item_name, "item_group": d.item_group})
)
item_details.setdefault(d.name, frappe._dict({"item_name": d.item_name, "item_group": d.item_group}))
return item_details
@@ -240,14 +237,13 @@ def get_chart_data(data):
for row in data:
item_key = row.get("item_code")
if not item_key in item_wise_sales_map:
if item_key not in item_wise_sales_map:
item_wise_sales_map[item_key] = 0
item_wise_sales_map[item_key] = flt(item_wise_sales_map[item_key]) + flt(row.get("amount"))
item_wise_sales_map = {
item: value
for item, value in (sorted(item_wise_sales_map.items(), key=lambda i: i[1], reverse=True))
item: value for item, value in (sorted(item_wise_sales_map.items(), key=lambda i: i[1], reverse=True))
}
for key in item_wise_sales_map:

View File

@@ -53,9 +53,7 @@ def get_columns(group_by: Literal["Lost Reason", "Competitor"]):
]
def get_data(
company: str, from_date: str, to_date: str, group_by: Literal["Lost Reason", "Competitor"]
):
def get_data(company: str, from_date: str, to_date: str, group_by: Literal["Lost Reason", "Competitor"]):
"""Return quotation value grouped by lost reason or competitor"""
if group_by == "Lost Reason":
fieldname = "lost_reason"

View File

@@ -82,9 +82,7 @@ def get_descendants_of(doctype, group_name):
).run()[0]
# get all children of group node
query = (
qb.from_(group_doc).select(group_doc.name).where((group_doc.lft >= lft) & (group_doc.rgt <= rgt))
)
query = qb.from_(group_doc).select(group_doc.name).where((group_doc.lft >= lft) & (group_doc.rgt <= rgt))
child_nodes = []
for x in query.run():
@@ -108,7 +106,9 @@ def get_customers_or_items(doctype, txt, searchfield, start, page_len, filters):
)
elif item[0] == "Item Group":
if item[3] != "":
filter_list.append([doctype, "item_group", "in", get_descendants_of("Item Group", item[3])])
filter_list.append(
[doctype, "item_group", "in", get_descendants_of("Item Group", item[3])]
)
if searchfield and txt:
filter_list.append([doctype, searchfield, "like", "%%%s%%" % txt])
@@ -132,9 +132,7 @@ def get_conditions(filters):
conditions.company = filters.company or frappe.defaults.get_user_default("company")
conditions.end_date = filters.period_end_date or frappe.utils.today()
conditions.start_date = filters.period_start_date or frappe.utils.add_months(
conditions.end_date, -1
)
conditions.start_date = filters.period_start_date or frappe.utils.add_months(conditions.end_date, -1)
return conditions

View File

@@ -81,9 +81,7 @@ def get_data():
bundled_item_map = get_packed_items(sales_orders)
item_with_product_bundle = get_items_with_product_bundle(
[row.item_code for row in sales_order_entry]
)
item_with_product_bundle = get_items_with_product_bundle([row.item_code for row in sales_order_entry])
materials_request_dict = {}
@@ -129,7 +127,9 @@ def get_data():
"description": item.description,
"sales_order_no": so.name,
"date": so.transaction_date,
"material_request": ",".join(material_requests_against_so.get("material_requests", [])),
"material_request": ",".join(
material_requests_against_so.get("material_requests", [])
),
"customer": so.customer,
"territory": so.territory,
"so_qty": item.qty,

View File

@@ -48,9 +48,7 @@ def get_chart_data(data, conditions, filters):
return {
"data": {
"labels": labels,
"datasets": [
{"name": _(filters.get("period")) + " " + _("Quoted Amount"), "values": datapoints}
],
"datasets": [{"name": _(filters.get("period")) + " " + _("Quoted Amount"), "values": datapoints}],
},
"type": "line",
"lineOptions": {"regionFill": 1},

View File

@@ -13,7 +13,7 @@ def execute(filters=None):
return Analytics(filters).run()
class Analytics(object):
class Analytics:
def __init__(self, filters=None):
self.filters = frappe._dict(filters or {})
self.date_field = (
@@ -87,9 +87,7 @@ class Analytics(object):
{"label": _(period), "fieldname": scrub(period), "fieldtype": "Float", "width": 120}
)
self.columns.append(
{"label": _("Total"), "fieldname": "total", "fieldtype": "Float", "width": 120}
)
self.columns.append({"label": _("Total"), "fieldname": "total", "fieldtype": "Float", "width": 120})
def get_data(self):
if self.filters.tree_type in ["Customer", "Supplier"]:
@@ -129,9 +127,7 @@ class Analytics(object):
""" select s.order_type as entity, s.{value_field} as value_field, s.{date_field}
from `tab{doctype}` s where s.docstatus = 1 and s.company = %s and s.{date_field} between %s and %s
and ifnull(s.order_type, '') != '' order by s.order_type
""".format(
date_field=self.date_field, value_field=value_field, doctype=self.filters.doc_type
),
""".format(date_field=self.date_field, value_field=value_field, doctype=self.filters.doc_type),
(self.filters.company, self.filters.from_date, self.filters.to_date),
as_dict=1,
)
@@ -166,7 +162,6 @@ class Analytics(object):
self.entity_names.setdefault(d.entity, d.entity_name)
def get_sales_transactions_based_on_items(self):
if self.filters["value_quantity"] == "Value":
value_field = "base_net_amount"
else:
@@ -178,9 +173,7 @@ class Analytics(object):
from `tab{doctype} Item` i , `tab{doctype}` s
where s.name = i.parent and i.docstatus = 1 and s.company = %s
and s.{date_field} between %s and %s
""".format(
date_field=self.date_field, value_field=value_field, doctype=self.filters.doc_type
),
""".format(date_field=self.date_field, value_field=value_field, doctype=self.filters.doc_type),
(self.filters.company, self.filters.from_date, self.filters.to_date),
as_dict=1,
)
@@ -221,14 +214,12 @@ class Analytics(object):
value_field = "qty"
self.entries = frappe.db.sql(
"""
select i.item_group as entity, i.{value_field} as value_field, s.{date_field}
from `tab{doctype} Item` i , `tab{doctype}` s
f"""
select i.item_group as entity, i.{value_field} as value_field, s.{self.date_field}
from `tab{self.filters.doc_type} Item` i , `tab{self.filters.doc_type}` s
where s.name = i.parent and i.docstatus = 1 and s.company = %s
and s.{date_field} between %s and %s
""".format(
date_field=self.date_field, value_field=value_field, doctype=self.filters.doc_type
),
and s.{self.date_field} between %s and %s
""",
(self.filters.company, self.filters.from_date, self.filters.to_date),
as_dict=1,
)
@@ -294,7 +285,7 @@ class Analytics(object):
total += amount
row["total"] = total
out = [row] + out
out = [row, *out]
self.data = out
@@ -330,9 +321,7 @@ class Analytics(object):
from_date, to_date = getdate(self.filters.from_date), getdate(self.filters.to_date)
increment = {"Monthly": 1, "Quarterly": 3, "Half-Yearly": 6, "Yearly": 12}.get(
self.filters.range, 1
)
increment = {"Monthly": 1, "Quarterly": 3, "Half-Yearly": 6, "Yearly": 12}.get(self.filters.range, 1)
if self.filters.range in ["Monthly", "Quarterly"]:
from_date = from_date.replace(day=1)
@@ -342,7 +331,7 @@ class Analytics(object):
from_date = from_date + relativedelta(from_date, weekday=MO(-1))
self.periodic_daterange = []
for dummy in range(1, 53):
for _dummy in range(1, 53):
if self.filters.range == "Weekly":
period_end_date = add_days(from_date, 6)
else:
@@ -370,10 +359,8 @@ class Analytics(object):
self.depth_map = frappe._dict()
self.group_entries = frappe.db.sql(
"""select name, lft, rgt , {parent} as parent
from `tab{tree}` order by lft""".format(
tree=self.filters.tree_type, parent=parent
),
f"""select name, lft, rgt , {parent} as parent
from `tab{self.filters.tree_type}` order by lft""",
as_dict=1,
)
@@ -387,12 +374,10 @@ class Analytics(object):
self.depth_map = frappe._dict()
self.group_entries = frappe.db.sql(
""" select * from (select "Order Types" as name, 0 as lft,
f""" select * from (select "Order Types" as name, 0 as lft,
2 as rgt, '' as parent union select distinct order_type as name, 1 as lft, 1 as rgt, "Order Types" as parent
from `tab{doctype}` where ifnull(order_type, '') != '') as b order by lft, name
""".format(
doctype=self.filters.doc_type
),
from `tab{self.filters.doc_type}` where ifnull(order_type, '') != '') as b order by lft, name
""",
as_dict=1,
)

View File

@@ -61,7 +61,7 @@ def get_conditions(filters):
def get_data(conditions, filters):
data = frappe.db.sql(
"""
f"""
SELECT
so.transaction_date as date,
soi.delivery_date as delivery_date,
@@ -91,9 +91,7 @@ def get_data(conditions, filters):
{conditions}
GROUP BY soi.name
ORDER BY so.transaction_date ASC, soi.item_code ASC
""".format(
conditions=conditions
),
""",
filters,
as_dict=1,
)
@@ -167,7 +165,7 @@ def prepare_data(data, so_elapsed_time, filters):
if filters.get("group_by_so"):
so_name = row["sales_order"]
if not so_name in sales_order_map:
if so_name not in sales_order_map:
# create an entry
row_copy = copy.deepcopy(row)
sales_order_map[so_name] = row_copy
@@ -176,7 +174,9 @@ def prepare_data(data, so_elapsed_time, filters):
so_row = sales_order_map[so_name]
so_row["required_date"] = max(getdate(so_row["delivery_date"]), getdate(row["delivery_date"]))
so_row["delay"] = (
min(so_row["delay"], row["delay"]) if row["delay"] and so_row["delay"] else so_row["delay"]
min(so_row["delay"], row["delay"])
if row["delay"] and so_row["delay"]
else so_row["delay"]
)
# sum numeric columns

View File

@@ -75,16 +75,14 @@ def get_entries(filters):
entries = frappe.db.sql(
"""
SELECT
name, customer, territory, {0} as posting_date, base_net_total as amount,
name, customer, territory, {} as posting_date, base_net_total as amount,
sales_partner, commission_rate, total_commission
FROM
`tab{1}`
`tab{}`
WHERE
{2} and docstatus = 1 and sales_partner is not null
{} and docstatus = 1 and sales_partner is not null
and sales_partner != '' order by name desc, sales_partner
""".format(
date_field, filters.get("doctype"), conditions
),
""".format(date_field, filters.get("doctype"), conditions),
filters,
as_dict=1,
)
@@ -97,15 +95,15 @@ def get_conditions(filters, date_field):
for field in ["company", "customer", "territory"]:
if filters.get(field):
conditions += " and {0} = %({1})s".format(field, field)
conditions += f" and {field} = %({field})s"
if filters.get("sales_partner"):
conditions += " and sales_partner = %(sales_partner)s"
if filters.get("from_date"):
conditions += " and {0} >= %(from_date)s".format(date_field)
conditions += f" and {date_field} >= %(from_date)s"
if filters.get("to_date"):
conditions += " and {0} <= %(to_date)s".format(date_field)
conditions += f" and {date_field} <= %(to_date)s"
return conditions

View File

@@ -94,8 +94,8 @@ def get_columns(filters, period_list, partner_doctype):
]
for period in period_list:
target_key = "target_{}".format(period.key)
variance_key = "variance_{}".format(period.key)
target_key = f"target_{period.key}"
variance_key = f"variance_{period.key}"
columns.extend(
[
@@ -169,9 +169,7 @@ def prepare_data(
for d in sales_users_data:
key = (d.parent, d.item_group)
dist_data = get_periodwise_distribution_data(
d.distribution_id, period_list, filters.get("period")
)
dist_data = get_periodwise_distribution_data(d.distribution_id, period_list, filters.get("period"))
if key not in rows:
rows.setdefault(key, {"total_target": 0, "total_achieved": 0, "total_variance": 0})
@@ -182,8 +180,8 @@ def prepare_data(
if p_key not in details:
details[p_key] = 0
target_key = "target_{}".format(p_key)
variance_key = "variance_{}".format(p_key)
target_key = f"target_{p_key}"
variance_key = f"variance_{p_key}"
details[target_key] = (d.get(target_qty_amt_field) * dist_data.get(p_key)) / 100
details[variance_key] = 0
details["total_target"] += details[target_key]

View File

@@ -8,6 +8,4 @@ from erpnext.selling.report.sales_partner_target_variance_based_on_item_group.it
def execute(filters=None):
data = []
return get_data_column(filters, "Sales Partner")

View File

@@ -110,9 +110,7 @@ def get_entries(filters):
{cond} and dt.name = dt_item.parent and dt.docstatus = 1
and dt.sales_partner is not null and dt.sales_partner != ''
order by dt.name desc, dt.sales_partner
""".format(
date_field=date_field, doctype=filters.get("doctype"), cond=conditions
),
""".format(date_field=date_field, doctype=filters.get("doctype"), cond=conditions),
filters,
as_dict=1,
)
@@ -125,13 +123,13 @@ def get_conditions(filters, date_field):
for field in ["company", "customer", "territory", "sales_partner"]:
if filters.get(field):
conditions += " and dt.{0} = %({1})s".format(field, field)
conditions += f" and dt.{field} = %({field})s"
if filters.get("from_date"):
conditions += " and dt.{0} >= %(from_date)s".format(date_field)
conditions += f" and dt.{date_field} >= %(from_date)s"
if filters.get("to_date"):
conditions += " and dt.{0} <= %(to_date)s".format(date_field)
conditions += f" and dt.{date_field} <= %(to_date)s"
if not filters.get("show_return_entries"):
conditions += " and dt_item.qty > 0.0"
@@ -142,10 +140,7 @@ def get_conditions(filters, date_field):
if filters.get("item_group"):
lft, rgt = frappe.get_cached_value("Item Group", filters.get("item_group"), ["lft", "rgt"])
conditions += """ and dt_item.item_group in (select name from
`tabItem Group` where lft >= %s and rgt <= %s)""" % (
lft,
rgt,
)
conditions += f""" and dt_item.item_group in (select name from
`tabItem Group` where lft >= {lft} and rgt <= {rgt})"""
return conditions

View File

@@ -103,16 +103,15 @@ def get_entries(filters):
entries = frappe.db.sql(
"""
select
dt.name, dt.customer, dt.territory, dt.%s as posting_date,dt.base_net_total as base_net_amount,
dt.name, dt.customer, dt.territory, dt.{} as posting_date,dt.base_net_total as base_net_amount,
st.commission_rate,st.sales_person, st.allocated_percentage, st.allocated_amount, st.incentives
from
`tab%s` dt, `tabSales Team` st
`tab{}` dt, `tabSales Team` st
where
st.parent = dt.name and st.parenttype = %s
and dt.docstatus = 1 %s order by dt.name desc,st.sales_person
"""
% (date_field, filters["doc_type"], "%s", conditions),
tuple([filters["doc_type"]] + values),
st.parent = dt.name and st.parenttype = {}
and dt.docstatus = 1 {} order by dt.name desc,st.sales_person
""".format(date_field, filters["doc_type"], "%s", conditions),
tuple([filters["doc_type"], *values]),
as_dict=1,
)
@@ -125,18 +124,18 @@ def get_conditions(filters, date_field):
for field in ["company", "customer", "territory"]:
if filters.get(field):
conditions.append("dt.{0}=%s".format(field))
conditions.append(f"dt.{field}=%s")
values.append(filters[field])
if filters.get("sales_person"):
conditions.append("st.sales_person = '{0}'".format(filters.get("sales_person")))
conditions.append("st.sales_person = '{}'".format(filters.get("sales_person")))
if filters.get("from_date"):
conditions.append("dt.{0}>=%s".format(date_field))
conditions.append(f"dt.{date_field}>=%s")
values.append(filters["from_date"])
if filters.get("to_date"):
conditions.append("dt.{0}<=%s".format(date_field))
conditions.append(f"dt.{date_field}<=%s")
values.append(filters["to_date"])
return " and ".join(conditions), values

View File

@@ -156,27 +156,26 @@ def get_entries(filters):
entries = frappe.db.sql(
"""
SELECT
dt.name, dt.customer, dt.territory, dt.%s as posting_date, dt_item.item_code,
dt.name, dt.customer, dt.territory, dt.{} as posting_date, dt_item.item_code,
st.sales_person, st.allocated_percentage, dt_item.warehouse,
CASE
WHEN dt.status = "Closed" THEN dt_item.%s * dt_item.conversion_factor
WHEN dt.status = "Closed" THEN dt_item.{} * dt_item.conversion_factor
ELSE dt_item.stock_qty
END as stock_qty,
CASE
WHEN dt.status = "Closed" THEN (dt_item.base_net_rate * dt_item.%s * dt_item.conversion_factor)
WHEN dt.status = "Closed" THEN (dt_item.base_net_rate * dt_item.{} * dt_item.conversion_factor)
ELSE dt_item.base_net_amount
END as base_net_amount,
CASE
WHEN dt.status = "Closed" THEN ((dt_item.base_net_rate * dt_item.%s * dt_item.conversion_factor) * st.allocated_percentage/100)
WHEN dt.status = "Closed" THEN ((dt_item.base_net_rate * dt_item.{} * dt_item.conversion_factor) * st.allocated_percentage/100)
ELSE dt_item.base_net_amount * st.allocated_percentage/100
END as contribution_amt
FROM
`tab%s` dt, `tab%s Item` dt_item, `tabSales Team` st
`tab{}` dt, `tab{} Item` dt_item, `tabSales Team` st
WHERE
st.parent = dt.name and dt.name = dt_item.parent and st.parenttype = %s
and dt.docstatus = 1 %s order by st.sales_person, dt.name desc
"""
% (
st.parent = dt.name and dt.name = dt_item.parent and st.parenttype = {}
and dt.docstatus = 1 {} order by st.sales_person, dt.name desc
""".format(
date_field,
qty_field,
qty_field,
@@ -186,7 +185,7 @@ def get_entries(filters):
"%s",
conditions,
),
tuple([filters["doc_type"]] + values),
tuple([filters["doc_type"], *values]),
as_dict=1,
)
@@ -199,23 +198,21 @@ def get_conditions(filters, date_field):
for field in ["company", "customer", "territory"]:
if filters.get(field):
conditions.append("dt.{0}=%s".format(field))
conditions.append(f"dt.{field}=%s")
values.append(filters[field])
if filters.get("sales_person"):
lft, rgt = frappe.get_value("Sales Person", filters.get("sales_person"), ["lft", "rgt"])
conditions.append(
"exists(select name from `tabSales Person` where lft >= {0} and rgt <= {1} and name=st.sales_person)".format(
lft, rgt
)
f"exists(select name from `tabSales Person` where lft >= {lft} and rgt <= {rgt} and name=st.sales_person)"
)
if filters.get("from_date"):
conditions.append("dt.{0}>=%s".format(date_field))
conditions.append(f"dt.{date_field}>=%s")
values.append(filters["from_date"])
if filters.get("to_date"):
conditions.append("dt.{0}<=%s".format(date_field))
conditions.append(f"dt.{date_field}<=%s")
values.append(filters["to_date"])
items = get_items(filters)

View File

@@ -8,6 +8,4 @@ from erpnext.selling.report.sales_partner_target_variance_based_on_item_group.it
def execute(filters=None):
data = []
return get_data_column(filters, "Territory")

View File

@@ -107,7 +107,7 @@ def get_opportunities(filters):
conditions = ""
if filters.get("transaction_date"):
conditions = " WHERE transaction_date between {0} and {1}".format(
conditions = " WHERE transaction_date between {} and {}".format(
frappe.db.escape(filters["transaction_date"][0]),
frappe.db.escape(filters["transaction_date"][1]),
)
@@ -120,12 +120,10 @@ def get_opportunities(filters):
conditions += " company = %(company)s"
return frappe.db.sql(
"""
f"""
SELECT name, territory, opportunity_amount
FROM `tabOpportunity` {0}
""".format(
conditions
),
FROM `tabOpportunity` {conditions}
""",
filters,
as_dict=1,
) # nosec
@@ -141,10 +139,8 @@ def get_quotations(opportunities):
"""
SELECT `name`,`base_grand_total`, `opportunity`
FROM `tabQuotation`
WHERE docstatus=1 AND opportunity in ({0})
""".format(
", ".join(["%s"] * len(opportunity_names))
),
WHERE docstatus=1 AND opportunity in ({})
""".format(", ".join(["%s"] * len(opportunity_names))),
tuple(opportunity_names),
as_dict=1,
) # nosec
@@ -160,10 +156,8 @@ def get_sales_orders(quotations):
"""
SELECT so.`name`, so.`base_grand_total`, soi.prevdoc_docname as quotation
FROM `tabSales Order` so, `tabSales Order Item` soi
WHERE so.docstatus=1 AND so.name = soi.parent AND soi.prevdoc_docname in ({0})
""".format(
", ".join(["%s"] * len(quotation_names))
),
WHERE so.docstatus=1 AND so.name = soi.parent AND soi.prevdoc_docname in ({})
""".format(", ".join(["%s"] * len(quotation_names))),
tuple(quotation_names),
as_dict=1,
) # nosec
@@ -179,10 +173,8 @@ def get_sales_invoice(sales_orders):
"""
SELECT si.name, si.base_grand_total, sii.sales_order
FROM `tabSales Invoice` si, `tabSales Invoice Item` sii
WHERE si.docstatus=1 AND si.name = sii.parent AND sii.sales_order in ({0})
""".format(
", ".join(["%s"] * len(so_names))
),
WHERE si.docstatus=1 AND si.name = sii.parent AND sii.sales_order in ({})
""".format(", ".join(["%s"] * len(so_names))),
tuple(so_names),
as_dict=1,
) # nosec