Interaction with the server
Liquidsoap starts with one or several scripts as its configuration, and then
streams forever if everything goes well. Once started, you can still interact
with it by means of the server. The server allows you to run commands. Some
are general and always available, some belong to a specific operator. For
request.queue() instances register commands to enqueue new
requests, the outputs register commands to start or stop the outputting, display
the last ten metadata chunks, etc.
The protocol of the server is a simple human-readable one. Currently it does not
have any kind of authentication and permissions. It is currently available via
two media: TCP and Unix sockets. The TCP socket provides a simple telnet-like
interface, available only on the local host by default. The Unix socket
interface (cf. the
server.socket setting) is through some sort of virtual
file. This is more constraining, which allows one to restrict the use of the
socket to some priviledged users.
You can find more details on how to configure the server in the
documentation of the settings key
server, in particular
server.telnet for the TCP interface and
server.socket for the Unix
interface. Liquidsoap also embeds some documentation about
the available server commands.
Now, we shall simply enable the Telnet interface to the server, by setting
set("server.telnet",true) or simply passing the
-t option on the
command-line. In a complete case analysis we set up a
request.queue() instance to play user requests. It had the identifier
"queue". We are now going to interact via the server to push requests into
Of course, the server isn't very user-friendly. But it is easy to write scripts to interact with Liquidsoap in that way, to implement a website or an IRC interface to your radio. However, this sort of tool is often bound to a specific usage, so we have not released any of ours. Feel free to ask the community about code that you could re-use.
Sometimes it is useful to control a variable using telnet. A simple way to
achive this is to use the
interactive.float function. For instance, in order
to dynamically the volume of a source:
The first line registers the variable volume on the telnet. Its value can be changed using the telnet command
and it can be retrieved using
Similarly, we can switch between two tracks using
switch as follows:
By default the source s1 is played. To switch to s2, you can connect on
the telnet server and type
var.set button = false.
Starting with liquidsoap version
1.3.4, you can register custom server commands
to interact with the client with applications such as implementing a
There main commands are:
server.readlineto read and write interactively
server.broadcastto control the execution of the command
Writing a partial response is done using the following syntactic sugar:
Read a value can be done 3 different ways. Most simple one is
Then you can read a fixed number of characters:
Finally, you can read until reaching a marker, which can be any string or regular expression:
You can pause and resume server commands using an API similar to Unix conditions:
server.condition()creates a condition variable
server.waitpauses a server command. See below for details
server.signal(c)resumes one waiting command
server.broadcast(c)resumes all waiting commands
server.wait is used through a syntactic sugar:
In the following, we define two commands:
wait: when executing the command, the client waits for a message. Message can be one of:
"exit": terminate command
"read": read one line from the client and print it back
- Otherwise, the client prints the received value
send <value>: when executing this command, the client sends
<value>to all waiting clients.
Example of use:
Securing the server
The command server provided by liquidsoap is very convenient for manipulating a
running instance of Liquidsoap. However, no authentication mechanism is
provided. The telnet server has no authentication and listens by default on the
127.0.0.1) network interface, which means that it is accessible to
any logged user on the machine.
Many users have expressed interest into setting up a secured access to the command server, using for instance user and password information. While we understand and share this need, we do not believe this is a task that lies into Liquidsoap's scope. An authentication mechanism is not something that should be implemented naively. Being SSH, HTTP login or any other mechanism, all these methods have been, at some point, exposed to security issues. Thus, implementing our own secure access would require a constant care about possible security issues.
Rather than doing our own home-made secure acces, we believe that our users should be able to define their own secure access to the command server, taking advantage of a mainstream authentication mechanism, for instance HTTP or SSH login. In order to give an example of this approach, we show here how to create a SSH access to the command server: we create a SSH user that, when logging through SSH, has only access to the command server.
First, we enable the unix socket for the command server in Liquidsoap:
When started, liquidsoap will create a socket file
that can be used to interact with the command server. For instance,
if your user has read and write rights on the socket file, you can do
The interface is then exactly the same has for the telnet server.
We define now a new “shell”. This shell is in fact the invokation of the socat
command. Thus, we create a
/usr/local/bin/liq_shell file with the following
We set this file as executable, and we add it in the list of shells in
Now, we create a user with the
liq_shell as its shell:
You also need to make sure that
liq-user has read and write rights
on the socket file.
Finally, when logging through ssh with
liq-user, we get:
This is an example of how you can use an existing secure access to secure the access to liquidsoap's command server. This way, you make sure that you are using a mainstream secure application, here SSH.
This example may be adapted similarly to use an online HTTP login mechanism, which is probably the most comment type of mechanism intented for the command line server.