How to fix Discord's streaming window not open on Hyprland
The problem
So I hopped in a Discord voicechat to see my friends’ gaming streams. I would like to show them something so I tried to open streaming, but I couldn’t. There was nothing that popped out off my screen after clicking this button:
At that moment, I was using Flatpak Discord. I also installed Vesktop but the problem was also not solved.
Then, I decided to run Vesktop via terminal to see if any logs appeared. Just like what I expected, this was the log I encountered:
1
2
3
4
[3555:0725/195200.630261:ERROR:third_party/webrtc/modules/desktop_capture/linux/wayland/screen_capture_portal_interface.cc:54] Failed to request session: GDBus.Error:org.freedesktop.DBus.Error.NameHasNoOwner: Could not activate remote peer 'org.freedesktop.portal.Desktop': startup job failed
[3555:0725/195200.630284:ERROR:third_party/webrtc/modules/desktop_capture/linux/wayland/base_capturer_pipewire.cc:93] ScreenCastPortal failed: 3 Error during screenshare picker Failed to get sources.
(node:3555) UnhandledPromiseRejectionWarning: TypeError: Video was requested, but no video stream was provided at VesktopMain:97:5759
(node:3555) UnhandledPromiseRejectionWarning: Unhandled promise rejection. This error originated either by throwing inside of an async function without a catch block, or by rejecting a promise which was not handled with .catch(). To terminate the node process on unhandled promise rejection, use the CLI flag --unhandled-rejections=strict (see https://nodejs.org/api/cli.html#cli_unhandled_rejections_mode). (rejection id: 3
Explaination
There are three layers involved in this process:
Vesktop: The app that you press the “Share” button;
xdg-desktop-portal: The “middleman” that pops the “Choose screen” window out for you;
A portal implements certain functionalities, such as opening file pickers or screen sharing.”
—Hyprland Wiki—
graphical-session.target: The sign signals systemd that graphical session is active or not.
NOTE:
graphical-session.targetis useful since some graphical applications such aswaybar,polybar,dunstwill crash if compositor/window manager (Hyprland, KDE, GNOME) doesn’t finish its startup yet. Compositor can only run after you log in successfully;
- However, only KDE and GNOME automatically activates
graphical-session.target, but Hyprland does not.
To see the unit service config file of xdg-desktop-portal, run systemctl --user cat xdg-desktop-portal.service:
1
2
3
4
5
6
7
8
9
10
11
12
13
❯ systemctl --user cat xdg-desktop-portal.service
# /usr/lib/systemd/user/xdg-desktop-portal.service
[Unit]
Description=Portal service
PartOf=graphical-session.target
Requisite=graphical-session.target
After=graphical-session.target
[Service]
Type=dbus
BusName=org.freedesktop.portal.Desktop
ExecStart=/usr/libexec/xdg-desktop-portal
Slice=session.slice
Pay attention to Requisite=graphical-session.target. This implies that xdg-desktop-portal.service can run only if graphical-session.target is activated.
—Hyprland Wiki—
Look at the log:
1
2
3
4
Failed to request session:
GDBus.Error:org.freedesktop.DBus.Error.NameHasNoOwner: Could
not activate remote peer 'org.freedesktop.portal.Desktop': startup
job failed
xdg-desktop-portal, via the alias org.freedesktop.portal.Desktop, couldn’t be activated. Therefore, the culprit should be graphical-session.target.
Use journalctl -xe to confirm the error:
1
2
Jul 25 18:10:36 67canyouhelpmerev69 systemd[2050]: graphical-session.target - Current graphical user session is inactive.
...
Based on the result and this piece of note, I can confidently conclude that graphical-session.target’s inactivation is the culprit.
Solution
- Setup
graphical-session.target(if needed)
- Check your
graphical-session.target’s state:
1
systemctl --user status hyprland-session.target
If it prints out Unit hyprland-session.target could not be found., follow the procedure below. If not, skip to step 2.
- Create file:
1
2
mkdir -p ~/.config/systemd/user
nano ~/.config/systemd/user/hyprland-session.target
- Inside
hyprland-session.target, paste:
1
2
3
4
5
6
[Unit]
Description=Hyprland session
BindsTo=graphical-session.target
Wants=graphical-session-pre.target
After=graphical-session-pre.target
PropagatesStopTo=graphical-session.target
- Reload systemd user
1
systemctl --user daemon-reload
- Activate target and portal
1
2
3
4
5
systemctl --user start hyprland-session.target
systemctl --user status graphical-session.target #If "Active: active", proceeds
systemctl --user start xdg-desktop-portal
systemctl --user status xdg-desktop-portal #If "Active: active", you are ready to stream.
- Setup auto activation
Check if your ~/.config/hypr/conf/autostart.lua has this line or not:
1
2
3
4
5
6
7
hl.on("hyprland.start", function()
--Other cmds
hl.exec_cmd("systemctl --user start hyprland-session.target") --This line
--Other cmds
end)
If not, add it.