Many people communicate on a day to day basis using tools like Google Hangouts, Skype, Whatsapp and what have you. What do most of these tools have in common? Well, though they're meant to communicate, they're only open as long as you communicate with other people who make use of the same proprietary solution, i.e. they don't support open standards like XMPP or SIP. Google used to support XMPP in Google Talk, however XMPP isn't supported anymore since they moved to the current Google Hangouts.
Anyway, the good news is: we can do it ourselves…, oh, Yes We Can
Let's build a solution that allows us to chat, transfer files, phone and videophone without having to use a proprietary tool and without having to get an additional contract with a service provider or telco.
We'll use the ejabberd software as backend XMPP-solution as it is an open source, scalable, robust and secure solution that is available through the default Debian Wheezy software repository. In addition to the server we chose to install Jitsi on the clients as Jitsi is an open source XMPP-client that is full featured. Also, Jitsi packages are available for many desktop platforms and packages for mobile devices are being developed.
First we have to plan which domain we'll use for our XMPP-server. Assuming we chose the domain 'example.com' to be configured on our XMPP-server named 'jabber', then the identity of our XMPP-users, which is called 'JID', would become user1@example.com, user2@example.com etc. Just like e-mail, that is. Also just like e-mail, we have to tell DNS how the XMPP-clients and external XMPP-servers can reach our server. In order to prepare DNS, add SRV-records like so to the 'example.com' domain (assuming an A-record for 'jabber.example.com' already exists):
_xmpp-client._tcp 900 IN SRV 5 0 5222 jabber.example.com. _xmpp-server._tcp 900 IN SRV 5 0 5269 jabber.example.com. _jabber._tcp 900 IN SRV 5 0 5269 jabber.example.com.
You can check your new entries like so:
dig -t srv _xmpp-client._tcp.example.com
After installation of the ejabberd server, several TCP-ports will be opened up on the server. It's advisable to only allow external traffic to and from the following ports (as long as you don't change the default values):
Installation of the ejabberd server is rather easy as a pre-compiled software package is available through the default Debian Wheezy software repository. So, just install the server:
apt-get install ejabberd
During the installation process a basic setup is stored in the ejabberd database (this is a mnesia-database as ejabberd is written in Erlang). Let's customize the newly created ejabberd configuration. The main configuration file is /etc/ejabberd/ejabberd.cfg When you take a look at this file you'll notice that comments start with '% %' characters, and lines finish with a ‘.’ character. Ok, first we have to tell ejabberd that we want to override the initial configuration. Uncomment the 'override_acls.'-directive:
... %% %% Remove the Access Control Lists before new ones are added. %% override_acls. ...
Then configure the admin-user:
... %% Admin user {acl, admin, {user, "fred", "example.com"}}. ...
Check the hostname of the server.
... %% Hostname {hosts, ["example.com"]}. ...
If you want to serve more domains, you can configure a hosts-directive like so:
... %% hosts: Domains served by ejabberd. %% You can define one or several, for example: {hosts, ["example.net", "example.com", "example.org"]}. ...
Now let's adjust the default XMPP client-listener (c2s) so that ejabberd also supports IPv6. In addition, we want TLS to be required for all of the client connections. The self-signed certificate '/etc/ejabberd/ejabberd.pem' has been created by debconf. Of course you could use your own certificate instead.
... {listen, [ {5222, ejabberd_c2s, [ inet6, {access, c2s}, {shaper, c2s_shaper}, {max_stanza_size, 65536}, %%zlib, starttls, starttls_required, {certfile, "/etc/ejabberd/ejabberd.pem"} ]}, ...
Now we want to also allow inter XMPP-server traffic (s2s) over IPv6. Here we don't have to add a starttls-directive as tls is enabled by default for s2s traffic.
... {5269, ejabberd_s2s_in, [ inet6, {shaper, s2s_shaper}, {max_stanza_size, 131072} ]}, ...
and further below we can modify these optione:
... %% %% Outgoing S2S options %% %% Preferred address families (which to try first) and connect timeout %% in milliseconds. %% %%{outgoing_s2s_options, [ipv4, ipv6], 10000}. {outgoing_s2s_options, [ipv6, ipv4], 5000}. ...
If you change the name/location of the certificate, don't forget to check the server to server-directive around line numer 206 of the configuration file:
... %% %% s2s_certfile: Specify a certificate file. %% {s2s_certfile, "/etc/ejabberd/ejabberd.pem"}. ...
Fine, now we're done. Let's restart the server and check if things are OK. Ejabberd logfiles are stored in /var/log/ejabberd
service ejabberd restart
Check the status of ejabberd:
ejabberdctl status
or check if the listeners have come up:
netstat -nalp |egrep '5222|5269'
If you encounter any UUP's (i.e. Unidentified Unsolved Problems), you might want to increase the ejabberd server's loglevel from 4 to 5:
... {loglevel, 5}. ...
Most of the ejabberd server administration can be done through the 'ejabberdctl' tool. Try:
ejabberdctl help help
You can create and register a new user like so:
ejabberdctl register fred jabber.example.com 'h1spassw00rd' ejabberdctl register user2 jabber.example.com 'h1spassw00rd' ejabberdctl register user3 jabber.example.com 'h1spassw00rd'
Look who is connected to your server:
ejabberdctl connected_users ejabberdctl connected_users_info
There is also 'Web Admin', a small admin webinterface you can check out at:
http://jabber.example.com:5280/admin
More information on 'Web Admin' is available at http://www.process-one.net/docs/ejabberd/guide_en.html#htoc75
However, we prefer the cli anyway
For conferencing by using a central-server, with all clients connected to this in a star-topology, a bridge is available from jitsi. It is named 'video-bridge'.
Get the software from https://download.jitsi.org/jitsi-videobridge/linux/
Create a useraccount:
groupadd jitsi useradd -d /opt/jitsi-videobridge-linux-x64 -s /bin/bash -g jitsi jitsi chown -R jitsi.jitsi /opt/jitsi-videobridge-linux-x64
Add an entry to /etc/hosts
... 1.2.3.4 yourhostname.example.com yourhostname jitsi-videobridge.jabber.example.com ...
Install software from the debian-repository:
apt-get install unzip default-jre-headless
Install the video-bridge:
su - jitsi unzip /tmp/jitsi-videobridge-linux-x64-65.zip mv jitsi-videobridge-linux-x64-65/lib . mv jitsi-videobridge-linux-x64-65/jvb.sh . mv jitsi-videobridge-linux-x64-65/jitsi-videobridge.jar jitsi-videobridge-v65.jar
Create a start-script /opt/jitsi-videobridge-linux-x64/start-bridge with content:
#!/bin/bash HOME="/opt/jitsi-videobridge-linux-x64-63" ${HOME}/jvb.sh --secret=VerySecretpw --domain='jabber.example.com' --host='localhost' --port=5275
Set the properties:
chmod 700 start-bridge
Now we have to make some additions/changes to the /etc/ejabberd/ejabberd.cfg
Add a listener in the ejabberd Use the same port as mentioned above.
... {5275, ejabberd_service, [ {host, "jitsi-videobridge.jabber.example.com", [{password, "VerySecretpw"}]} ]}, ...
Raise the traffic-shaper values in ejabberd
... %% %% The "normal2" shaper limits traffic speed to 300.000 B/s while using the jitsi-videobridge %% {shaper, normal2, {maxrate, 100000}}. ...
Activate the trafficshaper, at the paragraph 'ACCESS RULES' and replace normal for normal2:
... %% For all users except admins used "normal" shaper {access, c2s_shaper, [{none, admin}, {normal2, all}]}. ...
Restart ejabberd.
Check for the Listener-port to open.
Start the bridge by running the start-bridge script as the user jitsi:
nohup ./start-bridge &
Use the client from http://www.jitsi.org