perf: Limit get_open_count to 1s for each count query (#32920)
If left unoptimized this wreaks havoc on database servers and has little real value. If it's valuable people will complaint about "?" and it will get fixed. This constriant on runtime should always be present.
This commit is contained in:
parent
18b032fc04
commit
7345b6b078
2 changed files with 33 additions and 20 deletions
|
|
@ -2,6 +2,7 @@
|
|||
# License: MIT. See LICENSE
|
||||
|
||||
import json
|
||||
from typing import Literal
|
||||
|
||||
from bs4 import BeautifulSoup
|
||||
|
||||
|
|
@ -251,6 +252,18 @@ def get_open_count(doctype: str, name: str, items=None):
|
|||
if frappe.flags.in_migrate or frappe.flags.in_install:
|
||||
return {"count": []}
|
||||
|
||||
# None of the count queries should take more than 1s individually
|
||||
frappe.db.set_execution_timeout(1)
|
||||
|
||||
try:
|
||||
return _get_linked_document_counts(doctype, name, items)
|
||||
except Exception as e:
|
||||
if frappe.db.is_statement_timeout(e):
|
||||
return {"count": []}
|
||||
raise
|
||||
|
||||
|
||||
def _get_linked_document_counts(doctype: str, name: str, items=None):
|
||||
doc = frappe.get_lazy_doc(doctype, name)
|
||||
doc.check_permission()
|
||||
meta = doc.meta
|
||||
|
|
@ -342,18 +355,16 @@ def get_external_links(doctype, name, links):
|
|||
return {"doctype": doctype, "count": total_count, "open_count": open_count}
|
||||
|
||||
|
||||
def get_doc_count(doctype, filters):
|
||||
return len(
|
||||
frappe.get_all(
|
||||
doctype,
|
||||
fields="name",
|
||||
filters=filters,
|
||||
limit=100,
|
||||
distinct=True,
|
||||
ignore_ifnull=True,
|
||||
order_by=None,
|
||||
def get_doc_count(doctype, filters) -> int | Literal["?"]:
|
||||
try:
|
||||
docs = frappe.get_all(
|
||||
doctype, filters=filters, limit=100, distinct=True, ignore_ifnull=True, order_by=None
|
||||
)
|
||||
)
|
||||
return len(docs)
|
||||
except Exception as e:
|
||||
if frappe.db.is_statement_timeout(e): # Skip fetching correct count if it's too slow
|
||||
return "?"
|
||||
raise
|
||||
|
||||
|
||||
def get_dynamic_link_filters(doctype, links, fieldname):
|
||||
|
|
|
|||
|
|
@ -457,18 +457,14 @@ frappe.ui.form.Dashboard = class FormDashboard {
|
|||
$.each(count.internal_links_found, function (i, d) {
|
||||
me.frm.dashboard.set_badge_count_for_internal_link(
|
||||
d.doctype,
|
||||
cint(d.open_count),
|
||||
cint(d.count),
|
||||
d.open_count,
|
||||
d.count,
|
||||
d.names
|
||||
);
|
||||
});
|
||||
|
||||
$.each(count.external_links_found, function (i, d) {
|
||||
me.frm.dashboard.set_badge_count_for_external_link(
|
||||
d.doctype,
|
||||
cint(d.open_count),
|
||||
cint(d.count)
|
||||
);
|
||||
me.frm.dashboard.set_badge_count_for_external_link(d.doctype, d.open_count, d.count);
|
||||
});
|
||||
}
|
||||
|
||||
|
|
@ -499,14 +495,20 @@ frappe.ui.form.Dashboard = class FormDashboard {
|
|||
$link
|
||||
.find(".open-notification")
|
||||
.removeClass("hidden")
|
||||
.html(open_count > 99 ? "99+" : open_count);
|
||||
.html(cint(open_count) > 99 ? "99+" : open_count);
|
||||
}
|
||||
|
||||
if (count) {
|
||||
$link
|
||||
.find(".count")
|
||||
.removeClass("hidden")
|
||||
.text(count > 99 ? "99+" : count);
|
||||
.text(cint(count) > 99 ? "99+" : count)
|
||||
.attr(
|
||||
"title",
|
||||
count != "?"
|
||||
? __("Count of linked documents")
|
||||
: __("Accurate count can not be fetched, click here to view all documents")
|
||||
);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue