How to install and configure ABillS billing system

On the test, I will install Ubuntu Server 16.04 LTS into a clean system (I chose standart system utilities and OpenSSH server when installing the system).

Switch to root user:

sudo su

Before starting the installation, update the system and restart:

apt-get update
apt-get upgrade
apt-get dist-upgrade

Install the necessary components:

sudo su
apt-get install -yq mysql-server mysql-client libmysqlclient-dev apache2 apache2-utils libexpat1 ssl-cert build-essential rrdtool librrdtool-oo-perl arping curl

Go to the /usr directory and download the latest version from the site

cd /usr

Unzip the downloaded archive from ABillS:

tar zxvf abills-0.80.04.tgz

Create the necessary directories and set the rights:

mkdir /var/log/httpd/
mkdir /usr/abills/var/db/rrd/
mkdir /usr/abills/backup
mkdir -p /usr/abills/var/log
touch /usr/abills/var/log/abills.log
mkdir /usr/abills/var/log/nas_logs/
touch /usr/abills/var/log/nas_logs/nas.log
ls -l /usr/abills/
chown -Rf www-data:www-data /usr/abills/cgi-bin
chown -Rf www-data:www-data /usr/abills/Abills/templates
chown -Rf www-data:www-data /usr/abills/backup
touch /usr/abills/var/log/sql_errors
chown nobody /usr/abills/var/log/sql_errors
chmod 666 /usr/abills/var/log/sql_errors

Copy the abills web configuration to the Apache2 directory:

cp /usr/abills/misc/apache/abills_httpd.conf /etc/apache2/sites-enabled/

At the beginning of the configuration, add your ServerName, for example:


Make sure the configuration is correct:

sudo apachectl -t

Create a certificate (specify the host name in the Common name):

/usr/abills/misc/ apache

Or install certbot: Installing Certbot in Ubuntu

We activate the necessary Apache2 modules:

a2enmod ssl
a2enmod rewrite
a2enmod suexec
a2enmod include
a2enmod cgi

And restart Apache2 to apply the changes:

/etc/init.d/apache2 restart

Connect to mysql server:

mysql --default-character-set=utf8 -u root -p

Create a user and a database (where sqlpassword – specify your password):

use mysql;
GRANT ALL ON abills.* TO `abills`@localhost IDENTIFIED BY "sqlpassword"; 
flush privileges;

Import the mysql database data:

mysql --default-character-set=utf8 -u root -p -D abills < /usr/abills/db/abills.sql

In case of an error, execute the command below and repeat the database import:

sed -i -e "1 s/^/SET SQL_MODE='NO_ENGINE_SUBSTITUTION,NO_AUTO_VALUE_ON_ZERO';/;" /usr/abills/db/abills.sql

See also – The solution of error “ERROR 1067 (42000) at line 211: Invalid default value for ‘blablabla’”

Install the necessary perl modules:

cd /usr/abills/misc/
perl apt-get -batch

If some modules are not installed, install:

apt-get install -yq cpanminus build-essential

In the future, you can check whether all the necessary perl modules are installed:

cd /usr/abills/misc/
./ test

We also run a script that will help find errors:

cd /usr/abills/misc/

Install the necessary libraries for building freeradius:

apt-get install -yq libmysqlclient-dev libgdbm3 libgdbm-dev make gcc build-essential snmp libpcap-dev libperl-dev libtalloc-dev
find /usr/lib/ | grep /usr/lib/x86_64-linux-gnu/ /usr/lib/x86_64-linux-gnu/
ln -s /usr/lib/x86_64-linux-gnu/ /usr/lib/x86_64-linux-gnu/

Let’s see the new version of freeradius here and install:

cd /tmp
tar zxvf freeradius-server-2.2.10.tar.gz
cd freeradius-server-2.2.10
./configure --prefix=/usr/local/freeradius --with-rlm-perl-lib-dir=/usr/lib/x86_64-linux-gnu/ --with-dhcp=yes --with-openssl=no > /dev/null
make install
ln -s /usr/local/freeradius/sbin/radiusd /usr/sbin/radiusd

Create an autorun script:

nano /etc/init.d/radiusd

Paste the contents into it:

# Start/stop the FreeRADIUS daemon.
# Provides:          radiusd
# Required-Start:    $remote_fs $network $syslog
# Should-Start:      $time mysql slapd postgresql samba krb5-kdc
# Required-Stop:     $remote_fs $syslog
# Default-Start:     2 3 4 5
# Default-Stop:      0 1 6
# Short-Description: Radius Daemon
# Description:       Extensible, configurable radius daemon
set -e
. /lib/lsb/init-functions
DESCR="FreeRADIUS daemon"
test -f $PROGRAM || exit 0
# /var/run may be a tmpfs
if [ ! -d /var/run/radiusd ]; then
 mkdir -p /var/run/radiusd
 chown freerad:freerad /var/run/radiusd
export PATH="${PATH:+$PATH:}/usr/sbin:/sbin"
case "$1" in
                log_daemon_msg "Starting $DESCR" "$PROG"
                start-stop-daemon --start --quiet --pidfile $PIDFILE --exec $PROGRAM || ret=$?
                log_end_msg $ret
                exit $ret
                log_daemon_msg "Stopping $DESCR" "$PROG"
                if [ -f "$PIDFILE" ] ; then
                  start-stop-daemon --stop --retry=TERM/30/KILL/5 --quiet --pidfile $PIDFILE || ret=$?
                  log_end_msg $ret
                  log_action_cont_msg "$PIDFILE not found"
                  log_end_msg 0
                $0 stop
                $0 start
                echo "Usage: $0 start|stop|restart|force-reload"
                exit 1
exit 0

We make it executable and include it in autorun:

chmod +x /etc/init.d/radiusd
update-rc.d radiusd defaults
update-rc.d radiusd enable

Create the ABillS configuration files:

cp /usr/abills/misc/freeradius/v2/radiusd.conf /usr/local/freeradius/etc/raddb/radiusd.conf
rm /usr/local/freeradius/etc/raddb/sites-enabled/*
cp /usr/abills/misc/freeradius/v2/users_perl /usr/local/freeradius/etc/raddb/users
cp /usr/abills/misc/freeradius/v2/default_rlm_perl /usr/local/freeradius/etc/raddb/sites-enabled/abills_default
cp /usr/abills/misc/freeradius/v2/perl /usr/local/freeradius/etc/raddb/modules/

Open the FreeRADIUS configuration file:

nano /usr/local/freeradius/etc/raddb/radiusd.conf

And change the following:

prefix = /usr/local/freeradius
user = freerad
group = freerad

You can also instead of * specify the IP on which FreeRADIUS will work, otherwise it will be on everyone:

listen {
        ipaddr = *

We will clean clients.conf as we will store the access server in the mysql database:

echo '' > /usr/local/freeradius/etc/raddb/clients.conf
cp /usr/abills/misc/freeradius/v2/sql.conf /usr/local/freeradius/etc/raddb/

Open the connection parameters file with mysql database:

nano /usr/local/freeradius/etc/raddb/sql.conf

And indicate the true ones, for example:

sql {
        database = "mysql"
        driver = "rlm_sql_${database}"
        server = ""
        #port = 3306
        login = "abills"
        password = "sqlpassword"
        radius_db = "abills"

At the very end of the file:

'%secretkey%' change to 'test12345678901234567890'

In the following configuration file, we also specify the parameters for connecting to mysql database:

cp /usr/abills/libexec/ /usr/abills/libexec/
nano /usr/abills/libexec/

Let’s create a user and group for FreeRADIUS, and also assign rights to the directories:

groupadd freerad
useradd -g freerad -s /bash/bash freerad
chown -R freerad:freerad /usr/local/freeradius/etc/raddb
mkdir /var/run/radiusd/
chown -R freerad:freerad /var/run/radiusd/
mkdir /var/log/radacct
chown freerad:freerad /var/log/radacct

We try to run FreeRADIUS in debug mode, if everything is fine, stop it with Ctrl + C:

radiusd -X

And run FreeRADIUS in normal mode:

service radiusd start

On a server with a processor of 8 cores and 5,000 clients in radiusd.conf, I specified the threads:

thread pool {
start_servers = 8
max_servers = 32
min_spare_servers = 8
max_spare_servers = 32
max_requests_per_server = 0

You can see whether FreeRADIUS is running like this:

netstat -anp | grep 1812
netstat -anp | grep 1813
ps xa |grep radiusd
nmap -sU -p 1813 localhost

You can see the installed version of FreeRADIUS like this:

/usr/local/freeradius/sbin/radiusd -v

Set up rotation of the FreeRADIUS logs:

nano /etc/logrotate.d/radiusd
/var/log/radius.log {
    rotate 2

Let’s add tasks to cron:

nano /etc/crontab
*/5  *      *    *     *   root   /usr/abills/libexec/billd -all > /dev/null 2>&1
1     0     *    *     *   root    /usr/abills/libexec/periodic daily NO_ADM_REPORT=1 > /dev/null 2>&1
1     1     *    *     *   root    /usr/abills/libexec/periodic monthly NO_ADM_REPORT=1 > /dev/null 2>&1
1     3     *    *     *   root    /usr/abills/libexec/periodic backup > /dev/null 2>&1

See also help:

/usr/abills/libexec/periodic help

Create a file for the logs and assign the rights:

touch /usr/abills/var/log/sql_errors && chmod 666 /usr/abills/var/log/sql_errors

Create symbolic links to gzip and mysqldump to create database backups:

ln -s /bin/gzip /usr/bin/gzip
ln -s /usr/bin/mysqldump /usr/local/bin/mysqldump

The ABillS administrator web interface can be opened at (standard login – abills, password – abills):
For users:

In the web interface, through the menu “Settings” – “Access Server” add the access server and the pool of IP addresses for it.
In the RADIUS Parameters field, you can specify the transmitted parameters, for example:


Session-Timeout can be increased since by default it is 604800 (week) and after this time the session is forcibly terminated and rises upon the next DHCP request or unclassified packet.
You can disable the transfer of radius Session-Timeout (then specify session-timeout in the accel-ppp configuration for example, or better not to specify it at all):


Add tariff fees: “Setup” – “Internet” – “Tariff plans”. By default, the tariff is charged for 30 days. In the “Credit” field, you can specify 0.01 so that subscribers are not disconnected when the balance is zero and the tariff is paid. If you are redirected to a page with a negative deposit notification, then in the “Negative deposit filter” field, specify the filter name, for example, NEG_DEPOSIT.

Add the client “Clients” – “Logins” – “Add”.

We will start the Internet service for the user: “Clients” – (select user) – “Information” – “Services” – “Internet”.

If a negative deposit filter is used, then in Clients> Groups we note which groups are allowed to take a loan.

We will check by running the radtest utility specifying the username and password of an existing user:

apt-get install freeradius-utils
radtest test 123456 0 secretpass 0

In the file /usr/abills/libexec/ we indicate which IPs the administrators are allowed to connect to (it is better to specify in the Settings – Administrators – Access tab):


You can specify the session time in the web admin interface:

$conf{web_session_timeout} = 86000;

To give users with a negative balance in guest mode the same IP as the working one (in this case, unknown people will not get IP):


In order to select some IP Pool by default when adding a service (where 1 is the pool id, you can see it in Settings – Access Server – IP POOLs):


To prevent subscribers who have not used the service for several months from adding a few charges (who has a monthly rate), you can add an option to the configuration (when paying or installing a loan, the current date will be set in the Activation field):


You can check the integrity of the database as follows:

sudo apt-get install libsql-translator-perl
cd /usr/abills/misc/db_check/
sudo ./ --help

Check for not created tables:

/usr/abills/misc/db_check/ SHOW_CREATE

You can import the missing tables:

mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/Dv.sql
mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/Tags.sql
mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/config_variables.sql
mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/Dhcphosts.sql
mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/Equipment.sql
mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/Equipment_models.sql
mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/Ipn.sql
mysql -u root --default-character-set=utf8 -D abills < /usr/abills/db/Snmputils.sql

You can check if the script works correctly (I met the error “Table ‘abills.dv_main’ doesn’t exist”, then I fixed it by filling Dv.sql into the database):

/usr/abills/libexec/billd -all DEBUG=1
/usr/abills/libexec/billd -all DEBUG=10
/usr/abills/libexec/billd -all DEBUG=10 > billd_debug.txt

In the ABillS interface, select “Settings” – “Administrators”, opposite the desired administrator stash “Rights” and check the necessary rights.

In “Settings” – “Other” – “Paths” we indicate the paths to the programs.

To authorize unknown clients in guest mode, in Settings> Access Server> IP POOLs, create a guest pool and bind it to the access server.

If the problem is with payment systems, then look at the logs:

grep UID /usr/abills/var/log/paysys_check.log

Zap all in billing is used to clean the session table, but not to complete them; you can use the script to complete all sessions.

To prevent search systems from indexing billing pages, I recommend adding the /usr/abills/cgi-bin/robots.txt file with the following contents:

User-agent: *
Disallow: /

Let’s see the database statistics:

mysql -u root

See also my articles:

Leave a comment

Leave a Reply