From 93f3ac5f22e38a7739c3a0c18192dc5394e9fb3c Mon Sep 17 00:00:00 2001 From: zhangkun2 Date: Mon, 2 Nov 2026 17:51:02 +0800 Subject: [PATCH] fix: inject XDG_CURRENT_DESKTOP before graphical-session-pre.target MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit - Add dde-session-environment.service (oneshot, Before=graphical-session-pre.target) to inject XDG_CURRENT_DESKTOP=DDE into systemd user manager and D-Bus activation environment early, preventing a race where xdg-desktop-portal starts before EnvironmentsManager::init() runs and FileChooser interface is missing. - Add dde-session-environment.sh script with error handling (both commands run, exit code reports failure if either fails). - Add RefuseManualStart/RefuseManualStop/CollectMode for consistency with existing services. - Install service into graphical-session-pre.target.wants/ for auto-pull. - Add comment in main.cpp explaining the relationship between the early service and EnvironmentsManager::init(). PMS: https://pms.uniontech.com/bug-view-382063.html Log: 在 graphical-session-pre.target 之前注入 XDG_CURRENT_DESKTOP=DDE,修复门户前端启动竞态 Influence: 修复冷启动后 Electron 应用选择文件夹闪退问题 --- src/dde-session/main.cpp | 6 ++++++ systemd/CMakeLists.txt | 15 +++++++++++++++ systemd/dde-session-environment.service.in | 12 ++++++++++++ systemd/dde-session-environment.sh.in | 17 +++++++++++++++++ 4 files changed, 50 insertions(+) create mode 100644 systemd/dde-session-environment.service.in create mode 100755 systemd/dde-session-environment.sh.in diff --git a/src/dde-session/main.cpp b/src/dde-session/main.cpp index db37a7c..1ad0971 100644 --- a/src/dde-session/main.cpp +++ b/src/dde-session/main.cpp @@ -90,6 +90,12 @@ int main(int argc, char *argv[]) DLogManager::registerConsoleAppender(); DLogManager::registerFileAppender(); + // XDG_CURRENT_DESKTOP=DDE is also injected early by + // dde-session-environment.service (Before=graphical-session-pre.target) + // to prevent a race where xdg-desktop-portal starts before this call. + // EnvironmentsManager::init() still runs here to set the full set of + // environment variables (QT_QPA_PLATFORM, scale factors, etc.) and to + // call qputenv() for the current process. EnvironmentsManager().init(); QString dmService = "dde-session.target"; diff --git a/systemd/CMakeLists.txt b/systemd/CMakeLists.txt index f92e2e3..0648555 100644 --- a/systemd/CMakeLists.txt +++ b/systemd/CMakeLists.txt @@ -10,6 +10,12 @@ configure_file(dde-session-shutdown.service.in configure_file(dde-keyring.service.in dde-keyring.service @ONLY) +configure_file(dde-session-environment.service.in + dde-session-environment.service + @ONLY) +configure_file(dde-session-environment.sh.in + dde-session-environment.sh + @ONLY) set(SERVICES @@ -20,11 +26,20 @@ set(SERVICES ${CMAKE_CURRENT_BINARY_DIR}/dde-session-exit-task.service ${CMAKE_CURRENT_BINARY_DIR}/dde-session-shutdown.service ${CMAKE_CURRENT_BINARY_DIR}/dde-keyring.service + ${CMAKE_CURRENT_BINARY_DIR}/dde-session-environment.service dde-session-shutdown.target dde-session.target ) install(FILES ${SERVICES} DESTINATION lib/systemd/user/) +# Install the early environment setup script +install(PROGRAMS ${CMAKE_CURRENT_BINARY_DIR}/dde-session-environment.sh + DESTINATION ${CMAKE_INSTALL_LIBEXECDIR}/deepin) + +# graphical-session-pre.target.wants - early environment injection +install(DIRECTORY DESTINATION lib/systemd/user/graphical-session-pre.target.wants/) +install_symlink(dde-session-environment.service graphical-session-pre.target.wants) + install(DIRECTORY DESTINATION lib/systemd/user/dde-session-pre.target.wants/) set(DDE_SESSION_PRE_WANTS dde-session-pre.target.wants/dde-session@x11.service diff --git a/systemd/dde-session-environment.service.in b/systemd/dde-session-environment.service.in new file mode 100644 index 0000000..4397ecd --- /dev/null +++ b/systemd/dde-session-environment.service.in @@ -0,0 +1,12 @@ +[Unit] +Description=Set DDE session environment variables early +RefuseManualStart=yes +RefuseManualStop=yes +CollectMode=inactive-or-failed + +Before=graphical-session-pre.target + +[Service] +Type=oneshot +ExecStart=@CMAKE_INSTALL_FULL_LIBEXECDIR@/deepin/dde-session-environment.sh +Slice=session.slice diff --git a/systemd/dde-session-environment.sh.in b/systemd/dde-session-environment.sh.in new file mode 100755 index 0000000..5e7c476 --- /dev/null +++ b/systemd/dde-session-environment.sh.in @@ -0,0 +1,17 @@ +#!/bin/sh +# SPDX-FileCopyrightText: 2026 UnionTech Software Technology Co., Ltd. +# +# SPDX-License-Identifier: GPL-3.0-or-later + +# Set XDG_CURRENT_DESKTOP=DDE early in the systemd user manager and D-Bus +# activation environments, before graphical-session-pre.target is reached. +# +# This ensures that xdg-desktop-portal (the front-end) can discover the DDE +# portal backend even if it starts before dde-session's full +# EnvironmentsManager::init() has run, preventing a race where FileChooser +# and other portal interfaces are missing on cold boot. + +rc=0 +systemctl --user set-environment XDG_CURRENT_DESKTOP=DDE || rc=1 +dbus-update-activation-environment XDG_CURRENT_DESKTOP=DDE || rc=1 +exit $rc