Remote viewer for VM console (spice over IP)

I read a previous question asking about Spice over IP and the answer given was that it was not possible.

Is this still the case, if so is something planned to support this?

I’ve got Incus on a headless server. I would like to interact with its VMs’ consoles using a remote client on a laptop, something like the remote viewing capability of virt-manager.

I have the Incus UI running and that is a way to get a console but it would be nice if it was possible without using a browser.

At least on my client system (Arch Linux), I can just fire up a local spice client with

incus console $remote:$container --type vga

for any remote where the incus API is reachable over HTTPS.

I just had a look at how incus does that, and apparently it forwards the spice stream (which it gets over the HTTP API) to a local unix socket, and passes that local socket to the spice client (in my case, that’s “spicy” aka “spice-client-gtk” which comes with the Gnome desktop environment).

Oh that’s good, I’m using Arch as well :smile:

So if I install Incus and spice-client-gtk on my laptop then it should work… I’ll have to try that and report back.

I don’t think there is an incus-client package - that would be useful for occasions where the you want the client but not the server.

I can confirm that works perfectly :smile:

sudo pacman -S incus spice-gtk
incus remote generate-certificate

Copy ~/.config/incus/client.crt to the server and, on the server, do incus config trust add-certificate client.crt. Then, on client…

incus remote add myserver myserver.lan
incus console myserver:myvm --type vga

If you run a webserver on the Incus node it’s no big deal. You just need “websockify” and “spice-html5” and something that launches the websockify process. Either on request or permanently.

Example Apache configuration:

# Enable necessary modules
LoadModule proxy_module modules/mod_proxy.so
LoadModule proxy_wstunnel_module modules/mod_proxy_wstunnel.so
LoadModule ssl_module modules/mod_ssl.so

# Handle insecure certificates (self-signed)
SSLProxyEngine on
SSLProxyCheckPeerCN off
SSLProxyCheckPeerName off
SSLProxyCheckPeerExpire off

# spice-html5 is a Javascript SPICE client used to manage VMs:
Alias /spice /usr/share/spice-html5
<Directory /usr/share/spice-html5>
    Allow from all
    Satisfy Any
    DirectoryIndex spice.html
</Directory>

# Dynamic proxy pass based on the port query parameter
RewriteCond %{QUERY_STRING} port=(.*)
RewriteRule ^/spice_proxy/(.*) ws://127.0.0.1:%1/$1 [P]

# Fallback if no port parameter is provided (optional)
ProxyPass /spice_proxy/ ws://127.0.0.1:5901/
ProxyPassReverse /spice_proxy/ ws://127.0.0.1:5901/

Run websockify with the proper options:

/usr/bin/websockify --web /usr/share/spice-html5 5949 --unix-target=/home/incus/run/<instance-name>/qemu.spice --cert=/usr/sausalito/license/self.pem --timeout=900 --idle-timeout=900 --heartbeat=15

5949 is the port I chose to use here.

–unix-target=/home/incus/run/instance-name/qemu.spice

That ought to be the path to the running VM’s qemu.spice socket. Your path will certainly be different than mine.

–cert=/usr/sausalito/license/self.pem

The PEM file with an SSL certificate and key. Can be self signed.

–timeout=900 --idle-timeout=900 --heartbeat=15

The heartbeat is periodically sent to keep the session alive and after the timeouts expire websockify will shutdown. So you may want to adjust these as needed or set them to not expire depending on your usage case. I launch websockify from a GUI as needed and want it to shut down by itself after a period of inactivity.

Given the above Apache config the sample URL to access this would then be:

https://:443/spice/spice_auto.html?host=&port=443&path=/spice_proxy/?port=5949

You don’t have to open up port 5949 in this example, as everything is proxied through the regular Apache ports (443 for HTTPS in this case).

If you have another VM using another websockify instance on a different port? Just change the port in the above URL to access it.
The certificate related SSLProxyCheckPeer* options in the config make sure that Apache’s mod_proxy doesn’t complain about the self signed certificate used for the proxy connection between Apache and websockify.

If you install the package incus-ui-canonical then you get a web interface to Incus on :8443/ui/, which includes web access to the graphical consoles.

It doesn’t advertise what technology it uses to achieve that, but there’s a strong hint in the HTML:

<div class="spice-wrapper" style="height: calc(100vh - 271px)">
  <div id="spice-area">
    <div id="spice-screen" class="spice-screen" style="height: 800px;">
      <canvas width="1280" height="800" id="spice_surface_0" tabindex="0"></canvas>
    </div>
  </div>
</div>
1 Like