Skip to content

feat(linux): detect Linglong sandbox via LINGLONG_APPID env - #105

Open
dengbo11 wants to merge 1 commit into
leanflutter:mainfrom
dengbo11:main
Open

feat(linux): detect Linglong sandbox via LINGLONG_APPID env#105
dengbo11 wants to merge 1 commit into
leanflutter:mainfrom
dengbo11:main

Conversation

@dengbo11

Copy link
Copy Markdown

When running inside a Linglong container the LINGLONG_APPID environment variable is set by the runtime, but was not checked by runningInSandbox(). Applications like LocalSend that pass a theme icon name to tray_manager were getting the icon name rewritten into a sandbox-internal absolute path, because the sandbox guard didn't recognise Linglong.

Adding the env-var check is consistent with the Flatpak/Snap pattern and requires no packages to guess the app's filesystem layout.

When running inside a Linglong container the LINGLONG_APPID
environment variable is set by the runtime, but was not checked
by runningInSandbox(). Applications like LocalSend that pass
a theme icon name to tray_manager were getting the icon name
rewritten into a sandbox-internal absolute path, because the
sandbox guard didn't recognise Linglong.

Adding the env-var check is consistent with the Flatpak/Snap
pattern and requires no packages to guess the app's filesystem
layout.
@dengbo11

Copy link
Copy Markdown
Author

Hi maintainers,

I encountered an issue when using tray_manager in a Flutter application (LocalSend) running inside a Linglong (如意玲珑) sandbox on deepin 25. The tray icon showed a default
application-x-desktop icon instead of the app's actual icon.

After investigation, I found that runningInSandbox() does not recognize the Linglong environment, so the icon path is treated as a non-sandbox path and gets rewritten into a sandbox-
internal absolute path that the host's tray icon provider cannot read.


What is Linglong?

Linglong (also known as Linyaps / 如意玲珑) is an open-source, cross-distribution Linux package format developed by the OpenAtom community.
Like Flatpak and Snap, it provides sandboxed application isolation via Linux kernel namespaces (mount, PID, network, etc.) and an OCI-compatible container runtime.

Key properties relevant to sandbox detection:

  • The runtime always sets the LINGLONG_APPID environment variable inside the container, containing the application's reverse-domain ID (e.g., org.localsend). This is the canonical
    way to detect a Linglong sandbox.
  • The application root inside the sandbox is /opt/apps/<APP_ID>/files/, which is not visible to host processes.
  • The host's /run/user/<uid> is mounted into the container at the same path, so files written there are host-visible.
  • Application icons from share/icons/hicolor/ are exported to the host at /var/lib/linglong/entries/share/icons/hicolor/, making them resolvable by QIcon::fromTheme().

Why this change is needed

runningInSandbox() currently checks for FLATPAK_ID, SNAP, container, and /.dockerenv — but not LINGLONG_APPID. When a Flutter app inside Linglong calls
trayManager.setIcon(iconPath):

  1. runningInSandbox() returns false → the sandbox guard is bypassed.
  2. path.joinAll prepends the Flutter asset bundle path, turning the icon path into a sandbox-internal absolute path (e.g., /opt/apps/org.localsend/files/.../logo-32-white.png).
  3. The host's tray icon provider receives this path via SNI, cannot access it, and falls back to the default icon.
  4. No IconPixmap is provided by app_indicator_set_icon_full, so there is no fallback.

This is the same class of problem that Flatpak and Snap already solve — the sandbox guard simply doesn't know about Linglong. Adding LINGLONG_APPID to the detection list is the minimal,
consistent fix.

The LINGLONG_APPID environment variable is set unconditionally by the Linglong runtime (see [container_cfg_builder.cpp:1532](https://github.com/OpenAtom-Linyaps/linyaps/blob/main/libs/
oci-cfg-generators/src/linglong/oci-cfg-generators/container_cfg_builder.cpp#L1532)), so it is a reliable detection mechanism.

With this change, application code inside Linglong can pass a theme icon name (e.g., localsend_app) or a host-visible absolute path to trayManager.setIcon(), and the icon will be
correctly resolved by the host.

Best regards

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant