diff --git a/frappe/utils/response.py b/frappe/utils/response.py index c537460713..80aeaa2ad0 100644 --- a/frappe/utils/response.py +++ b/frappe/utils/response.py @@ -6,6 +6,7 @@ import decimal import json import mimetypes import os +from typing import TYPE_CHECKING from urllib.parse import quote import werkzeug.utils @@ -22,6 +23,9 @@ from frappe import _ from frappe.core.doctype.access_log.access_log import make_access_log from frappe.utils import cint, format_timedelta +if TYPE_CHECKING: + from frappe.core.doctype.file.file import File + def report_error(status_code): """Build error. Show traceback in developer mode""" @@ -209,28 +213,27 @@ def download_backup(path): return send_private_file(path) -def download_private_file(path): +def download_private_file(path: str) -> Response: """Checks permissions and sends back private file""" - files = frappe.db.get_all("File", {"file_url": path}) can_access = False + files = frappe.get_all("File", filters={"file_url": path}, pluck="name") # this file might be attached to multiple documents # if the file is accessible from any one of those documents # then it should be downloadable - for f in files: - _file = frappe.get_doc("File", f) - can_access = _file.is_downloadable() - if can_access: - make_access_log(doctype="File", document=_file.name, file_type=os.path.splitext(path)[-1][1:]) + for fname in files: + file: "File" = frappe.get_doc("File", fname) + if can_access := file.is_downloadable(): break if not can_access: raise Forbidden(_("You don't have permission to access this file")) + make_access_log(doctype="File", document=file.name, file_type=os.path.splitext(path)[-1][1:]) return send_private_file(path.split("/private", 1)[1]) -def send_private_file(path): +def send_private_file(path: str) -> Response: path = os.path.join(frappe.local.conf.get("private_path", "private"), path.strip("/")) filename = os.path.basename(path)