Modern XMPP Server

Enrico already wrote about the Why (and the What, Who and When), so I'll just quote his conclusion and move on to the How.

I now have an XMPP setup which has all the features of the recent fancy chat systems, and on top of that it runs, client and server, on Free Software, which can be audited, it is federated and I can self-host my own server in my own VPS if I want to, with packages supported in Debian.

This article is kept for historical reasons, but is no longer updated: the current version is at


I've decided to install prosody, mostly because it was recommended by the RTC QuickStart Guide; I've heard that similar results can be reached with ejabberd and other servers.

I'm also targetting Debian stable (+ backports); I started with jessie and then updated to stretch and then buster. I've started with prosody 0.9, but I'm currently using prosody 0.11, and this article has been updated to reflect that.

Installation and prerequisites

You will need to install the packages prosody and prosody-modules; on jessie the versions in backports were needed, but currently not on buster.

You also need to setup some TLS certificates (I used Let's Encrypt); and make them readable by the prosody user; you can see Chapter 12 of the RTC QuickStart Guide for more details.

With prosody 0.10+ you will also need to configure the location of the certificate for https with a configuration stanza such as:

https_ssl = {
    certificate = "/etc/ssl/public/";
    key = "/etc/ssl/private/";

or see the prosody documentation on certificates to see where to put certificates so that prosody is able to autodetect them.

On your firewall, you'll need to open the following TCP ports:

  • 5222 (client2server)
  • 5269 (server2server)
  • 5280 (default http port for prosody)
  • 5281 (default https port for prosody)

The latter two are needed to enable some services provided via http(s), including rich media transfers.

With just a handful of users, I didn't bother to configure LDAP or anything else, but just created users manually via:

prosodyctl adduser

In-band registration is disabled by default (and I've left it that way, to prevent my server from being used to send spim).

prosody configuration

You can then start configuring prosody by editing /etc/prosody/prosody.cfg.lua and changing a few values from the distribution defaults.

First of all, enforce the use of encryption and certificate checking both for client2server and server2server communications with:

c2s_require_encryption = true
s2s_secure_auth = true

and then, if you need to, add to the whitelist any server that you want to talk to and doesn't support secure s2s communication (but note that is no longer needed, as it doesn't support xmpp any longer):

s2s_insecure_domains = { "" }


For each virtualhost you want to configure, create a file /etc/prosody/conf.avail/ with contents like the following:

VirtualHost ""
        enabled = true
        ssl = {
            key = "/etc/ssl/private/";
            certificate = "/etc/ssl/public/";

For the domains where you also want to enable MUCs, add the follwing lines:

Component "" "muc"
        restrict_room_creation = "local"
        modules_enabled = {

the "local" configures prosody so that only local users are allowed to create new rooms (but then everybody can join them, if the room administrator allows it): this may help reduce unwanted usages of your server by random people.

Enabling the mam_muc module (on prosody 0.10 only) allows people to syncronize message history between multiple clients (XEP-0313)

You can also add the following line to enable rich media transfers via http uploads (XEP-0363):

Component "" "http_upload"

The defaults are pretty sane, but see for details on what knobs you can configure for this module; you may want e.g. to change the maximum file size limit and setup an expiry date:

Component "" "http_upload"
    http_upload_file_size_limit = 1024 * 1024 * 2
    http_upload_expire_after = 60 * 60 * 24 * 7

Don't forget to enable the virtualhost by linking the file inside /etc/prosody/conf.d/.

additional modules

Most of the other interesting XEPs are enabled by loading additional modules inside /etc/prosody/prosody.cfg.lua (under modules_enabled); to enable mod_something just add a line like:


Most of these come from the prosody-modules package (and thus from ) and some may require changing when prosody 0.10 will be available; when this is the case it is mentioned below.

mod_blocklist (XEP-0191)
To allow user-controlled blocking of users, including as an anti-spim measure.
mod_smacks (XEP-0198)
Allow clients to resume a disconnected session before a customizable timeout and prevent message loss.
mod_mam (XEP-0313)

Archive messages on the server for a limited period of time (default 1 week) and allow clients to retrieve them; this is required to syncronize message history between multiple clients.

With prosody 0.9 only an in-memory storage backend is available, which may make this module problematic on servers with many users. prosody 0.10 will fix this by adding support for an SQL backed storage with archiving capabilities.

mod_throttle_presence + mod_filter_chatstates (XEP-0352)
Filter out presence updates and chat states when the client announces (via Client State Indication) that the user isn't looking. This is useful to reduce power and bandwidth usage for "useless" traffic.
cloud_notify (XEP-0357)
Allow clients to register an “app server” that is notified about new messages

See also

Send a comment: unless requested otherwise I may add it, or some extract, to this page.

Return to Top