SRV records for XMPP over TLS

XMPP Servers: | Servers Category |
---|---|
XMPP Clients: | Clients Category |
User Guides: | User Guide Category |
This artical will walk you through implementing XEP-0368: SRV records for XMPP over TLS on a Prosody version 0.10 XMPP server, running on Ubuntu version 16.04 LTS server. This will allow users to connect to the XMPP server while connecting through a restrictive firewall that blocks port 5222. This also adds that ability for a client to connect directly a TLS port instead of a STARTTLS port, this allows for a slightly quicker connection (in theory).[1]
Overview[edit | edit source]
The concept of the XEP-0368 standard is to allow users to connect to the xmpp server via port 443, but still allow HTTPS traffic to flow over the same port. This is accomplished by installing the program sslh that will sit in front of both the web server and the xmpp server and splits the connection between them.
- When a client connects via port
5222
, they connect viaSTARTTLS
directly toXMPP Server
port. - When a client connects via port
5223
, they connect via directTLS
directly toXMPP Server
port. - When a client connects via port
443
, they connect viaTLS
tosslh
that will then redirect the connection toXMPP Server
port5223
.
Install SSLH from Source[edit | edit source]
You must install sslh with ALPN support; sslh version 1.18 or greater.[2]
To start out with, you must install the below prerequisites, on ubuntu[2], use the following command:<syntaxhighlight lang="bash"> apt install git libwrap0-dev libconfig8-dev libpcre3-dev </syntaxhighlight>
After you have installed the prerequisites, download the git repository for sslh
<syntaxhighlight lang="bash">
mkdir -p /var/src && cd /var/src/
git clone --depth=1 https://github.com/yrutschle/sslh.git
</syntaxhighlight>And findlay, go into into the source sslh
directory to compile and install the code.<syntaxhighlight lang="bash">
cd /var/src/sslh/
make install
</syntaxhighlight>After the software is installed, copy the init file to start sslh.<syntaxhighlight lang="bash">
cp scripts/etc.init.d.sslh /etc/init.d/sslh
</syntaxhighlight>
Configuring SSLH for XMPP and HTTPS Traffic[edit | edit source]
You must create and/or update the /etc/sslh.cfg
file.
The host entry, that is currently im.example.org
, must be changed to you XMPP server's DNS Host Name.<syntaxhighlight lang="c">
verbose: 0;
foreground: false;
inetd: false;
numeric: false;
transparent: false;
timeout: 2;
user: "nobody";
pidfile: "/var/run/sslh.pid";
syslog_facility: "auth";
- Change hostname with your external address name. Note: It should not be resolving to 127.0.0.1
listen: (
{ host: "im.example.com"; port: "443"; }
);
protocols: (
#{ name: "ssh"; service: "ssh"; host: "localhost"; port: "22"; keepalive: true; fork: true; }, { name: "http"; host: "localhost"; port: "443"; log_level: 0;},
# just match ALPN { name: "tls"; host: "localhost"; port: "5223"; alpn_protocols: [ "xmpp-client" ]; log_level: 1;}, { name: "tls"; host: "localhost"; port: "443"; alpn_protocols: [ "h2", "http/1.1", "spdy/1", "spdy/2", "spdy/3" ]; log_level: 0; },
# just match SNI { name: "tls"; host: "localhost"; port: "5223"; probe: "builtin"; sni_hostnames: [ "example.com" ]; log_level: 1;}, { name: "tls"; host: "localhost"; port: "5223"; probe: "builtin"; sni_hostnames: [ "example2.com" ]; log_level: 1;}, { name: "tls"; host: "localhost"; port: "5223"; probe: "builtin"; sni_hostnames: [ "example3.com" ]; log_level: 1;}, { name: "tls"; host: "localhost"; port: "443"; probe: "builtin"; sni_hostnames: [ "im.example.com" ]; log_level: 0; }, { name: "tls"; host: "localhost"; port: "443"; probe: "builtin"; sni_hostnames: [ "im.example2.com" ]; log_level: 0; }, { name: "tls"; host: "localhost"; port: "443"; probe: "builtin"; sni_hostnames: [ "im.example3.com" ]; log_level: 0; },
# catch anything else TLS { name: "tls"; host: "localhost"; port: "443"; log_level: 0;},
# Jabber { name: "regex"; host: "localhost"; port: "5222"; regex_patterns: [ "jabber" ]; log_level: 1;}, { name: "regex"; host: "localhost"; port: "443"; regex_patterns: [ "jabber" ]; log_level: 0;},
# Catch-all { name: "regex"; host: "localhost"; port: "443"; regex_patterns: [ "" ]; log_level: 0;}
);
on-timeout: "timeout";
</syntaxhighlight>Once complete, you must also set RUN=yes
in the /etc/default/sslh
file.
Web Server Changes[edit | edit source]
Since SSLH needs to use port 443 on the server's network interface, you must set your web server to listen to the loopback interface for any host that is using port 443.
Using Nginx[edit | edit source]
When using nginx, you must change all entries that are listening on the https port (443) to use the localhost interface and not the same interface SSLH is attached to.
In the below example, the IPv4 host is changed to localhost
, and the IPv6 host is changed to ::1
.
<syntaxhighlight lang="nginx">
server { listen localhost:443 ssl http2; listen [::1]:443 ssl http2; server_name im.example.com; server_name conference.example.com; server_name upload.example.com;
</syntaxhighlight>
This must be done for EVERY entry within nginx.
Changes to be made on the XMPP Server[edit | edit source]
ejabberd Changes[edit | edit source]
By default, ejabberd should already be configured to allow XEP-0368 connects. You may confirm that required sections are enabled.
Default XMPP client port <syntaxhighlight lang="erlang"> listen:
- port: 5222 ip: "::" module: ejabberd_c2s starttls_required: true shaper: c2s_shaper access: c2s
</syntaxhighlight>
Direct-TLS XMPP client port <syntaxhighlight lang="erlang">
- port: 5223 ip: "::" module: ejabberd_c2s tls: true shaper: c2s_shaper access: c2s
</syntaxhighlight>
Prosody Changes[edit | edit source]
Prosody needs to allow connections from clients via TLS (not STARTTLS). This is done by enabling legacy SSL support by adding the below line in the global section of your prosody.cfg.lua:
<syntaxhighlight lang="lua"> legacy_ssl_ports = 5223; </syntaxhighlight>
DNS Changes[edit | edit source]
And finally, we need to make the required DNS Changes.
In this example, the XMPP host (im.example.org
) is listening for clients on ports 5223
, 5222
, and 443
.<syntaxhighlight lang="text">
- Clients will try in the following order, 5223/tls, 5222/xmpp, 443/tls
_xmpps-client._tcp.example.org. 86400 IN SRV 5 1 5223 im.example.org.
_xmpp-client._tcp.example.org. 86400 IN SRV 10 1 5222 im.example.org.
_xmpps-client._tcp.example.org. 86400 IN SRV 15 1 443 im.example.org.
_xmpp-client._tcp.example.org. 86400 IN SRV 20 1 443 im.example.org.
</syntaxhighlight>The client will first try to connect to port 5223
, if it is unable to, it will then try port 5222
, if it is unable to, it will then try port 443
.
Testing[edit | edit source]
References[edit | edit source]
- ↑ "XEP-0368: SRV records for XMPP over TLS § Introduction". 2017-03-09. Retrieved 2017-08-05.
- ↑ 2.0 2.1 "Installing Prosody § XMPP over HTTPS". Retrieved 2017-08-05.
- ↑ "XEP-0368: SRV records for XMPP over TLS § Requirements". 2017-03-09. Retrieved 2017-08-05.