perf: fetch existing fields beforehand
This commit is contained in:
parent
7503db4160
commit
9a0636bf91
1 changed files with 29 additions and 6 deletions
|
|
@ -316,6 +316,14 @@ def create_custom_fields(custom_fields: dict, ignore_validate=False, update=True
|
|||
|
||||
:param custom_fields: example `{'Sales Invoice': [dict(fieldname='test')]}`"""
|
||||
|
||||
def process_field_update(field):
|
||||
nonlocal updated
|
||||
|
||||
updated = True
|
||||
|
||||
# handles edge case of same field being updated multiple times
|
||||
existing_custom_fields[(field.dt, field.fieldname)] = field.__dict__
|
||||
|
||||
try:
|
||||
frappe.flags.in_create_custom_fields = True
|
||||
doctypes_to_update = set()
|
||||
|
|
@ -323,10 +331,12 @@ def create_custom_fields(custom_fields: dict, ignore_validate=False, update=True
|
|||
if frappe.flags.in_setup_wizard:
|
||||
ignore_validate = True
|
||||
|
||||
existing_custom_fields = get_existing_custom_fields(custom_fields)
|
||||
|
||||
for doctypes, fields in custom_fields.items():
|
||||
if isinstance(fields, dict):
|
||||
# only one field
|
||||
fields = [fields]
|
||||
fields = (fields,)
|
||||
|
||||
if isinstance(doctypes, str):
|
||||
# only one doctype
|
||||
|
|
@ -336,19 +346,19 @@ def create_custom_fields(custom_fields: dict, ignore_validate=False, update=True
|
|||
updated = False
|
||||
|
||||
for df in fields:
|
||||
field = frappe.db.get_value("Custom Field", {"dt": doctype, "fieldname": df["fieldname"]})
|
||||
field = existing_custom_fields.get((doctype, df["fieldname"]))
|
||||
if not field:
|
||||
try:
|
||||
df = df.copy()
|
||||
df["owner"] = "Administrator"
|
||||
create_custom_field(doctype, df, ignore_validate=ignore_validate)
|
||||
updated = True
|
||||
custom_field = create_custom_field(doctype, df, ignore_validate=ignore_validate)
|
||||
process_field_update(custom_field)
|
||||
|
||||
except frappe.exceptions.DuplicateEntryError:
|
||||
pass
|
||||
|
||||
elif update:
|
||||
custom_field = frappe.get_doc("Custom Field", field)
|
||||
custom_field = frappe.get_doc({"doctype": "Custom Field", **field})
|
||||
original_values = custom_field.__dict__.copy()
|
||||
custom_field.update(df)
|
||||
|
||||
|
|
@ -357,7 +367,7 @@ def create_custom_fields(custom_fields: dict, ignore_validate=False, update=True
|
|||
custom_field.flags.ignore_validate = True
|
||||
|
||||
custom_field.save()
|
||||
updated = True
|
||||
process_field_update(custom_field)
|
||||
|
||||
if updated:
|
||||
doctypes_to_update.add(doctype)
|
||||
|
|
@ -370,6 +380,19 @@ def create_custom_fields(custom_fields: dict, ignore_validate=False, update=True
|
|||
frappe.flags.in_create_custom_fields = False
|
||||
|
||||
|
||||
def get_existing_custom_fields(custom_fields):
|
||||
doctypes_to_fetch = set()
|
||||
for doctypes in custom_fields:
|
||||
if isinstance(doctypes, str):
|
||||
doctypes = (doctypes,)
|
||||
|
||||
for doctype in doctypes:
|
||||
doctypes_to_fetch.add(doctype)
|
||||
|
||||
existing_fields = frappe.get_all("Custom Field", filters={"dt": ("in", doctypes_to_fetch)}, fields="*")
|
||||
return {(field.dt, field.fieldname): field for field in existing_fields}
|
||||
|
||||
|
||||
@frappe.whitelist()
|
||||
def rename_fieldname(custom_field: str, fieldname: str):
|
||||
frappe.only_for("System Manager")
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue