fix: Erase invalid default apps

and ignore at runtime in /apps handlers
This commit is contained in:
Ankush Menat 2026-05-01 13:25:54 +05:30
parent 1bdda7a803
commit d9f8b24853
3 changed files with 23 additions and 0 deletions

View file

@ -53,6 +53,8 @@ def get_apps():
def get_route(app_name): def get_route(app_name):
if app_name not in frappe.get_installed_apps():
return "/apps" # Invalid defaults
apps = frappe.get_hooks("add_to_apps_screen", app_name=app_name) apps = frappe.get_hooks("add_to_apps_screen", app_name=app_name)
app = next((app for app in apps if app.get("name") == app_name), None) app = next((app for app in apps if app.get("name") == app_name), None)
return app.get("route") if app and app.get("route") else "/apps" return app.get("route") if app and app.get("route") else "/apps"
@ -89,6 +91,9 @@ def get_default_path():
@frappe.whitelist() @frappe.whitelist()
def set_app_as_default(app_name: str): def set_app_as_default(app_name: str):
if app_name not in frappe.get_installed_apps():
frappe.throw(_("App {} is not installed").format(frappe.bold(app_name)))
if frappe.db.get_value("User", frappe.session.user, "default_app") == app_name: if frappe.db.get_value("User", frappe.session.user, "default_app") == app_name:
frappe.db.set_value("User", frappe.session.user, "default_app", "") frappe.db.set_value("User", frappe.session.user, "default_app", "")
else: else:

View file

@ -466,6 +466,21 @@ class TestUser(IntegrationTestCase):
sorted(m.get("module_name") for m in get_modules_from_all_apps()), sorted(m.get("module_name") for m in get_modules_from_all_apps()),
) )
def test_default_app(self):
from frappe.apps import get_default_path
with test_user(roles=["System Manager"]) as user:
user.default_app = "next_erp"
user.save()
self.assertFalse(user.default_app)
frappe.set_user(user.name)
user.db_set("default_app", "next_erp")
user.reload()
self.assertTrue(user.default_app)
get_default_path() # defaults will also trigger hooks logic
@IntegrationTestCase.change_settings("System Settings", reset_password_link_expiry_duration=1) @IntegrationTestCase.change_settings("System Settings", reset_password_link_expiry_duration=1)
def test_reset_password_link_expiry(self): def test_reset_password_link_expiry(self):
new_password = "new_password" new_password = "new_password"

View file

@ -248,6 +248,9 @@ class User(Document):
if self.language == "Loading...": if self.language == "Loading...":
self.language = None self.language = None
if self.default_app and self.default_app not in frappe.get_installed_apps():
self.default_app = ""
if (self.name not in ["Administrator", "Guest"]) and (not self.get_social_login_userid("frappe")): if (self.name not in ["Administrator", "Guest"]) and (not self.get_social_login_userid("frappe")):
self.set_social_login_userid("frappe", frappe.generate_hash(length=39)) self.set_social_login_userid("frappe", frappe.generate_hash(length=39))