Skip to main content

Resources

Securing Ubuntu network with uncomplicated firewall

It is said that the best way to improve server security is to reduce the attack surface. Network communication in any system happens with the help of logical network ports, be it TCP ports or UDP ports. One part of the attack surface is the number of open ports that are waiting for connection to be established. It is always a good idea to block all unrequired ports. Any traffic coming to these ports can be filtered, that is, allowed or blocked with the help of a filtering system.

The Linux kernel provides a built-in packet filtering mechanism called netfilter, which is used to filter the traffic coming in or going out of the system. All modern Linux firewall systems use netfilter under the hood. Iptables is a well-known and popular user interface to set up and manage filtering rules for netfilter. It is a complete firewall solution that is highly configurable and highly flexible. However, iptables need effort on the user's part to master the firewall setup. Various frontend tools have been developed to simplify the configuration of iptables. UFW is among the most popular frontend solutions to manage iptables.

Uncomplicated firewall (UFW) provides easy-to-use interface for people unfamiliar with firewall concepts. It provides a framework for managing netfilter as well as the command-line interface to manipulate the firewall. With its small command set and plain English parameters, UFW makes it quick and easy to understand and set up firewall rules. At the same time, you can use UFW to configure most of the rules possible with iptables. UFW comes preinstalled with all Ubuntu installations after version 8.04 LTS.

In this recipe, we will secure our Ubuntu server with the help of UFW and also look at some advance configurations possible with UFW.

Getting ready

You will need an access to a root account or an account with root privileges.

How to do it…

Follow these steps to secure network with uncomplicated firewall:

UFW comes preinstalled on Ubuntu systems. If it's not, you can install it with the following commands:

$ sudo apt-get udpate

$ sudo apt-get install UFW

Check the status of UFW:

$ sudo ufw status

Add a new rule to allow SSH:

$ sudo ufw allow ssh

Alternatively, you can use a port number to open a particular port:

$ sudo ufw allow 22

Allow only TCP traffic over HTTP (port 80):

$ sudo ufw allow http/tcp

Deny incoming FTP traffic:

$ sudo ufw deny ftp

Check all added rules before starting the firewall:

$ sudo ufw show added

Now enable the firewall:

$ sudo ufw enable

Check the ufw status, the verbose parameter is optional:

$ sudo ufw status verbose

Get a numbered list of added rules:

$ sudo ufw status numbered

You can also allow all ports in a range by specifying a port range:

$ sudo ufw allow 1050:5000/tcp

If you want to open all ports for a particular IP address, use the following command:

$ sudo ufw allow from 10.0.2.100

Alternatively, you can allow an entire subnet, as follows:

$ sudo ufw allow from 10.0.2.0/24

You can also allow or deny a specific port for a given IP address:

$ sudo ufw allow from 10.0.2.100 to any port 2222

$ sudo ufw deny from 10.0.2.100 to any port 5223

To specify a protocol in the preceding rule, use the following command:

$ sudo ufw deny from 10.0.2.100 proto tcp to any port 5223

Deleting rules:

$ sudo ufw delete allow ftp

Delete rules by specifying their numbers:

$ sudo ufw status numbered

$ sudo ufw delete 2

Add a new rule at a specific number:

$ sudo ufw insert 1 allow 5222/tcp # Inserts a rule at number 1

19.

If you want to reject outgoing FTP connections, you can use the following command:

$ sudo ufw reject out ftp

UFW also supports application profiles. To view all application profiles, use the following command:

$ sudo ufw app list

Get more information about the app profile using the following command:

$ sudo ufw app info OpenSSH

Allow the application profile as follows:

$ sudo ufw allow OpenSSH

Set ufw logging levels [off|low|medium|high|full] with the help of the following command:

$ sudo ufw logging medium

View firewall reports with the show parameter:

$ sudo ufw show added # list of rules added

$ sudo ufw show raw # show complete firewall

Reset ufw to its default state (all rules will be backed up by UFW):

$ sudo ufw reset

There's more…

UFW also provides various configuration files that can be used:

/etc/default/ufw: This is the main configuration file.

/etc/ufw/sysctl.conf: These are the kernel network variables. Variables in this file override variables in /etc/sysctl.conf.

/var/lib/ufw/user[6].rules or /lib/ufw/user[6].rules are the rules added via the ufw command.

/etc/ufw/before.init are the scripts to be run before the UFW initialization.

/etc/ufw/after.init are the scripts to be run after the UFW initialization.

See also

Check logging section of the UFW community page for an explanation of UFW logs at https://help.ubuntu.com/community/UFW

Check out the UFW manual pages with the following command:

$ man ufw

Creating users and connecting with XMPP client in Ubuntu

We have installed the XMPP server, Ejabberd. In this recipe, we will learn how to add new user accounts to the Ejabberd server. We will also learn how to configure the XMPP client and connect to our server.

Getting ready

Make sure that you have installed the Ejabberd server and it is running properly.

Additionally, you will need XMPP client software. You can choose from multiple free and open source clients such as pidgin, PSI, Adium, Gajim, and many more. I will be using PSI as it provides various low-level administrative features.

How to do it…

Ejabberd supports multiple methods for registering a new user account. These include adding a new user from the command line, creating a new user from the admin panel, and allowing clients to register with the server using in-band registration. Here, we will create a new user from a command line admin tool. Later in this recipe, I will briefly explain another two methods.

Follow these steps to create a user account and connect it with a XMPP client:

Use the following command to register a new user using the ejabberdctl command:

$ # ejabberdctl register username host password

$ sudo ejabberdctl register user1 ubuntu password

You can get a list of registered users with the registered_users option to ejabberdctl:

$ # ejabberdctl registered_users host

$ sudo ejabberdctl registered_users ubuntu

Now you can create a connection to the server with the XMPP client and your new account. Download and install the XMPP client tool, PSI.

Open PSI, click the General tab, and then select Account Setup. This will open the XMPP Accounts window, which looks something like this:

Click the Add button in the XMPP Accounts window. This will open another window named Add Accounts:

Now, in the Add Account window, enter the name for this connection, or you can choose to keep the name as Default. Click the Add button to open one more window.

In the newly opened window, enter the account details that we created with the ejabberdctl command:

On the Account tab, enter the full XMPP address (JID) and password for your account.

Click on the Connection tab, then click to check the Manually Specify Server Host/Port: checkbox, and then enter the server IP or FQDN and change the port to match your configuration:

Next, click the Save button to complete the account setup and then click Close to close the account setup window. Your account will be listed in the main window of Psi, as follows:

Now you are ready to connect to your XMPP server. Select the listed account and change the drop-down box at the bottom to Online. This will start the connection process and set the user status as Online.

The PSI client will show a prompt regarding self-signed certificates if you are using the default certificate provided by Ejabberd. Click Trust this certificate to proceed.

It will take a few seconds to complete the connection process. Once connected, your PSI status will change to Online:

Now click General menu to add XMPP contacts or to join a group chat or to send a message to existing contact. To change your Instant Messaging account status, click on the Status menu and select your desired option.

How it works…

The preceding example demonstrates the account creation and client setup process for connecting with the XMPP server. We have used an administrative command to create an XMPP account and then configured client software to use the existing account.

You can also create a new account from the Ejabberd web console. The web console lists all the configured hostnames under the Virtual Hosts section, and each host lists options for user and access management, and other administration tools. Both these options need the server administrator to create an account.

Additionally, XMPP supports an extension that enables a user to self-register with the server. This is called in-band registration (xep-0077), where a user can send his registration request with his desired username, password, and other details, such as email, and the server creates a new user account. This is useful with public XMPP servers where administrators cannot handle all registration requests. The Ejabberd server supports in-band registration with the mod_register plugin, which is enabled by default. From the client side, you can use any XMPP client that supports in-band registration. If you have noticed, PSI also supports in-band registration and provides an option to register a new account in the Add Account process:

There's more…

When it is an XMPP administration task, PSI is a handy tool. It provides a debug console where you can monitor all XML data transfers between the client and server, as well as send arbitrary XML stanzas to the server. You can access the XML console from right-clicking the menu of your PSI account. Once opened, check Enable checkbox to enable traffic monitoring. The XML Console looks similar to the following screenshot:

XML Console also allows the filtering of traffic based on packet type. Button Dump Ringbuf can be used to dump any traffic before opening the XML Console.

Another option is service discovery from the right-click menu. You need to log in as an administrator to see all the options under service discovery. From here, you can monitor user accounts and various services that are available on the server. The Service Discovery window looks something like this:

See also

A list of XMPP client tools at https://xmpp.org/xmpp-software/clients/

Managing Ubuntu file permissions

We have created users and groups. In this recipe, you will work with default file permissions for users and groups, as well as see how to modify those permissions.

Getting ready

Create two users, user1 and user2. Create new group editor and add user1 and user2 as members.

How to do it…

Follow these steps to manage file permissions, follow these steps:

To change groups for files and directories:

Log in with user1.

Create a new directory documents under home:

user1@ubuntu:~$ mkdir documents

Create a text file under documents:

user1@ubuntu:~$ echo "hello world"> documents/file.txt

Now log in with user2:

user1@ubuntu:~$ su user2

Try to edit the same text file. It should say Permission denied:

user2@ubuntu:/home/user1$ echo "hello again"> documents/file.txt

log in as user1 and change the group of documents to editor:

user1@ubuntu:~$ chgrp -R editor documents

Switch to user2 and try editing the same file. Now it should work:

To set permissions with chmod, follow these steps:

Create simple shell script with the following command:

$ echo 'echo "Hello World!!"'> hello.sh

Execute a shell script with the following command:

$ ./hello.sh

Set executable permission to hello.sh with the following command:

$ chmod u+x hello.sh

Check new permission with the following command:

$ ls -l

Execute hello.sh again:

To protect shared files with sticky bit, follow these steps:

Log in as user1 and set sticky bit for directory documents:

user1@ubuntu:~$ chmod +t documents

Log in as user2 and create a new file.

Try to delete any file under documents. It should fail:

How it works…

When you create a new file or directory in Ubuntu, the default permissions for files are read and write access to owner and owner's private group, along with read, write, and execute access for directories. You can check the default setting with umask -S.

In our example, we have user1 and user2. Both of them are members of the editor group. When user1 creates a file, the default permissions are limited to user1 and its private group (user1) named after the user account. This is the reason user2 sees Permission denied on editing file. By changing the group of documents to editor we allow all members of editor to read and write to files in documents.

With the chmod command, we can set permissions at a more granular level. In our example of hello.sh, we have set the executable permission for hello.sh. Similarly, we can set read permission as follows:

$chmod +r filename

To set write permission, use the following command:

$chmod +w filename

You can set more selective permissions with additional parameters before mode expression as follows:

$chmod ugo+x filename

Here, u sets the permission for user, g for group, and o for all others.

To remove permissions, replace + with -. For example, $chmod o-w filename. Alternatively, you can use the Octal format to specify permissions:

$chmod 777 filename

This gives read, write, and execute permission to user group and others, whereas the command $chmod 600 filename gives set, read, and write permissions for owner and no permission to groups and others. In Octal format [777], the first bit is used for the user or owner of the file, the second bit is for group, and the third bit is for everyone else. Check out the following table for more information:

Notation

Octal value

Permissions

-|---|---|---

0|000|000|000

Regular files, no permissions

d|r--|r--|r--

d|400|400|400

Directory, read permission to owner,

group, and others

-|rw-|r--|r--

-|644|644|644

Regular file, read and write permission

to owner and read permission to group or others

-|rwx|rwx|rwx

-|777|777|777

Regular file, all permissions to everyone

Finally, when you share files within a group of users, there are chances that someone deletes the file that is required by other users. Sticky bit can protect these file from deletion. When sticky bit is set, only the owner or a user with root privileges can delete a file.

You can set sticky bit with the command chmod as $chmod +t directoryName. Sticky bit is shown in long listing (ls -l) with symbol t or T. Additionally, sticky bit works only with directories and is ignored on ordinary files.

There's more…

Many times when working as a root user, all files and directories created are owned by root. A non-root user can't write to these directories or files. You can use the command chown to change the ownership of such files and assign them to respective users.

To change ownership of a file, use the following command:

$chown newuser filename

To change the owner as well as the group of file, use the following command:

$chown newuser:newgroup filename

You can skip changing owner and change only the group with the following command:

$chown :newgroup filename

Note that the chown command can only be used by users with root privileges.

Installing Docker in Ubuntu

In last few recipes, we learned about LXD, an operating system container service. Now, we will look at a hot new technology called Docker. Docker is an application container designed to package and run a single service. It enables developers to enclose an app with all dependencies in an isolated container environment. Docker helps developers create a reproducible environment with a simple configuration file called a Dockerfile. It also provides portability by sharing the Dockerfile, and developers can be sure that their setup will work the same on any system with the Docker runtime.

Docker is very similar to LXC. Its development started as a wrapper around the LXC API to help DevOps take advantage of containerization. It added some restrictions to allow only a single process to be running in a container, unlike a whole operating system in LXC. In subsequent versions, Docker changed its focus from LXC and started working on a new standard library for application containers, known as libcontainer.

It still uses the same base technologies, such as Linux namespaces and control groups, and shares the same kernel with the host operating system. Similarly, Docker makes use of operating system images to run containers. Docker images are a collection of multiple layers, with each layer adding something new to the base layer. This something new can include a service, such as a web server, application code, or even a new set of configurations. Each layer is independent of the layers above it and can be reused to create a new image.

Being an application container, Docker encourages the use of a microservice-based distributed architecture. Think of deploying a simple WordPress blog. With Docker, you will need to create at least two different containers, one for the MySQL server and the other for the WordPress code with PHP and the web server. You can separate PHP and web servers in their own containers. While this looks like extra effort, it makes your application much more flexible. It enables you to scale each component separately and improves application availability by separating failure points.

While both LXC and Docker use containerization technologies, their use cases are different. LXC enables you to run an entire lightweight virtual machine in a container, eliminating the inefficiencies of virtualization. Docker enables you to quickly create and share a self-dependent package with your application, which can be deployed on any system running Docker.

In this recipe, we will cover the installation of Docker on Ubuntu Server. The recipes after that will focus on various features provided by Docker.

Getting ready

You will need access to the root account or an account with sudo privileges.

How to do it…

Recently, Docker released version 1.11 of the Docker engine. We will follow the installation steps provided on the Docker site to install the latest available version:

First, add a new gpg key:

$ sudo apt-key adv --keyserver hkp://p80.pool.sks- keyservers.net:80 --recv-keys 58118E89F3A912897C070ADBF76221572C52609D

Next, add a new repository to the local installation sources. This repository is maintained by Docker and contains Docker packages for 1.7.1 and higher versions:

$ echo "deb https://apt.dockerproject.org/repo ubuntu-xenial main" | \

sudo tee /etc/apt/sources.list.d/docker.list

Next, update the apt package list and install Docker with the following commands:

$ sudo apt-get update

$ sudo apt-get install docker-engine

Once the installation completes, you can check the status of the Docker service, as follows:

$ sudo service docket status

Check the installed Docker version with docker version:

$ sudo docker version

Client:

Version: 1.11.1

API version: 1.23

...

Server:

Version: 1.11.1

API version: 1.23

...

Download a test container to test the installation. This container will simply print a welcome message and then exit:

$ sudo docker run hello-world

At this point, you need to use sudo with every Docker command. To enable a non-sudo user to use Docker, or to simply avoid the repeated use of sudo, add the respective usernames to the docker group:

$ sudo gpasswd -a ubuntu docker

Now, update group membership, and you can use Docker without the sudo command:

$ newgrp docker

How it works…

This recipe installs Docker from the official Docker repository. This way, we can be sure to get the latest version. The Ubuntu 16.04 repository also contains the package for Docker with version 1.10. If you prefer to install from the Ubuntu repository, it's an even easier task with a single command, as follows:

$ sudo apt-get install docker.io

As of writing this, Docker 1.11 is the latest stable release and the first release to have been built on Open Container Initiative standards. This version is built on runc and containerd.

There's more…

Docker provides a quick installation script, which can be used to install Docker with a single command. This scripts reads the basic details of your operating system, such as the distribution and version, and then executes all the required steps to install Docker. You can use the bootstrap script as follows:

$ sudo curl -sSL https://get.docker.com | sudo sh

Note that with this command, the script will be executed with sudo privileges. Make sure you cross-check the script's contents before executing it. You can download the script without executing it, as follows:

$ curl -sSL https://get.docker.com -o docker_install.sh

See also

The Docker installation guide: http://docs.docker.com/installation/ubuntulinux/

Operating system containers versus application containers: https://blog.risingstack.com/operating-system-containers-vs-application-containers/

What Docker adds to lxc-tools: http://stackoverflow.com/questions/17989306/what-does-docker-add-to-lxc-tools-the-userspace-lxc-tools

A curated list of Docker resources: https://github.com/veggiemonk/awesome-docker

Introduction for Cloud Computing in Ubuntu

Cloud computing has become the most important terminology in the computing sphere. It has reduced the effort and cost required to set up and operate the overall computing infrastructure. It has helped various businesses quickly start their business operations without wasting time planning their IT infrastructure, and has enabled really small teams to scale their businesses with on-demand computing power.

The term cloud is commonly used to refer to a large network of servers connected to the Internet. These servers offer a wide range of services and are available for the general public on a pay-per-use basis. Most cloud resources are available in the form of Software as a Service (SaaS), Platform as a Service (PaaS), or Infrastructure as a Service (IaaS). A SaaS is a software system hosted in the cloud. These systems are generally maintained by large organizations; a well-known example that we commonly use is Gmail and the Google Docs service. The end user can access these application through their browsers. He or she can just sign up for the service, pay the required fees, if any, and start using it without any local setup. All data is stored in the cloud and is accessible from any location.

PaaS provide a base platform to develop and run applications in the cloud. The service provider does the hard work of building and maintaining the infrastructure and provides easy-to-use APIs that enable developers to quickly develop and deploy an application. Heroku and the Google App Engine are well-known examples of PaaS services.

Similarly, IaaS provides access to computing infrastructure. This is the base layer of cloud computing and provides physical or virtual access to computing, storage, and network services. The service builds and maintains actual infrastructure, including hardware assembly, virtualization, backups, and scaling. Examples include Amazon AWS and the Google Compute Engine. Heroku is a platform service built on top of the AWS infrastructure.

These cloud services are built on top of virtualization. Virtualization is a software system that enables us to break a large physical server into multiple small virtual servers that can be used independently. One can run multiple isolated operating systems and applications on a single large hardware server. Cloud computing is a set of tools that allows the general public to utilize these virtual resources at a small cost.

Ubuntu offers a wide range of virtualization and cloud computing tools. It supports hypervisors, such as KVM, XEN, and QEMU; a free and open source cloud computing platform, OpenStack; the service orchestration tool Juju and machine provisioning tool MAAS. In this article, we will take a brief look at virtualization with KVM. We will install and set up our own cloud with OpenStack and deploy our applications with Juju.

Optimizing MySQL performance – queries in Ubuntu

MySQL performance optimizations can be divided into two parts. One is query optimization and the other is MySQL server configuration. To get optimum results, you have to work on both of these parts. Without proper configuration, queries will not provide consistent performance; on the other hand, without proper queries and a database structure, queries may take much longer to produce results.

In this recipe, we will learn how to evaluate query performance, set indexes, and identify the optimum database structure for our data.

Getting ready

You will need access to an admin account on the MySQL server.

You will need a large dataset to test queries. Various tools are available to generate test data. I will be using test data available at https://github.com/datacharmer/test_db .

How to do it…

Follow these steps to optimize MySQL performance:

The first and most basic thing is to identify key columns and add indexes to them:

mysql> alter table salaries add index (salary);

Enable the slow query log to identify long-running queries. Enter the following commands from the MySQL console:

mysql> set global log_slow_queries = 1;

mysql> set global slow_query_log_file = ‘/var/log/mysql/slow.log’;

Once you identify the slow and repeated query, execute that query on the database and record query timings. The following is a sample query:

mysql> select count(*) from salaries where salary between 30000 and 65000 and from_date > ‘1986-01-01’;

Next, use explain to view the query execution plan:

mysql> explain select count(*) from salaries where salary between 30000 and 65000 and from_date > ‘1986-01-01’;

Add required indexes, if any, and recheck the query execution plan. Your new index should be listed under possible_keys and key columns of explain output:

mysql> alter table `salaries` add index ( `from_date` ) ;

If you found that MySQL is not using a proper index or using another index than expected then you can explicitly specify the index to be used or ignored:

mysql> select * from salaries use index (salaries) where salary between 30000 and 65000 and from_date > ‘1986-01- 01’;

mysql> select * from salaries where salary between 30000 and 65000 and from_date > ‘1986-01-01’ ignore index (from_date);

Now execute the query again and check query timings for any improvements.

Analyze your data and modify the table structure. The following query will show the minimum and maximum length of data in each column. Add a small amount of buffer space to the reported maximum length and reduce additional space allocation if any:

mysql> select * from `employees` procedure analyse();

The following is the partial output for the analyse() procedure:

Check the database engines you are using. The two major engines available in MySQL are MyISAM and InnoDB:

mysql> show create table employees;

How it works…

MySQL uses SQL to accept commands for data processing. The query contains the operation, such as select, insert, and update; the target that is a table name; and conditions to match the data. The following is an example query:

select * from employee where id = 1001;

In the preceding query, select * is the operation asking MySQL to select all data for a row. The target is the employee table, and id = 1001 is a condition part.

Once a query is received, MySQL generates query execution plan for it. This step contains various steps such as parsing, preprocessing, and optimization. In parsing and pre-processing, the query is checked for any syntactical errors and the proper order of SQL grammar. The given query can be executed in multiple ways. Query optimizer selects the best possible path for query execution. Finally, the query is executed and the execution plan is stored in the query cache for later use.

The query execution plan can be retrieved from MySQL with the help of the explain query and explain extended. Explain executes the query until the generation of the query execution plan and then returns the execution plan as a result. The execution plan contains table names used in this query, key fields used to search data, the number of rows needed to be scanned, and temporary tables and file sorting used, if any. The query execution plan shows possible keys that can be used for query execution and then shows the actual key column used. Key is a column with an index on it, which can be a primary index, unique index, or non-unique index. You can check the MySQL documentation for more details on query execution plans and explain output.

If a specific column in a table is being used repeatedly, you should consider adding a proper index to that column. Indexes group similar data together, which reduces the look up time and total number of rows to be scanned. Also keep in mind that indexes use large amounts of memory, so be selective while adding indexes.

Secondly, if you have a proper index set on a required column and the query optimization plan does not recognize or use the index, you can force MySQL to use a specific index with the USE INDEX index_name statement. To ignore a specific index, use the statement IGNORE INDEX index_name.

You may get a small improvement with table maintenance commands. Optimize table is useful when a large part of the table is modified or deleted. It reorganizes table index data on physical storage and improves I/O performance. Flush table is used to reload the internal cache. Check table and Analyze table check for table errors and data distribution respectively. The improvements with these commands may not be significant for smaller tables. Reducing the extra space allocated to each column is also a good idea for reducing total physical storage used. Reduced storage will optimize I/O performance as well as cache utilization.

You should also check the storage engines used by specific tables. The two major storage engines used in MySQL are MyISAM and InnoDB. InnnoDB provides full transactional support and uses row-level locking, whereas MyISAM does not have transaction support and uses table-level locking. MyISAM is a good choice for faster reads where you have a large amount of data with limited writes on the table. MySQL does support the addition of external storage engines in the form of plugins. One popular open source storage engine is XtraDB by Percona systems.

There’s more…

If your tables are really large, you should consider partitioning them. Partitioning tables distributes related data across multiple files on disk. Partitioning on frequently used keys can give you a quick boost. MySQL supports various different types of partitioning such as hash partitions, range partitions, list partitions, key partitions, and also sub-partitions.

You can specify hash partitioning with table creation as follows:

create table employees (

id int not null,

fname varchar(30),

lname varchar(30),

store_id int

) partition by hash(store_id) partitions 4;

Alternatively, you can also partition an existing table with the following query:

mysql> alter table employees partition by hash(store_id) partitions 4;

Sharding MySQL

You can also shard your database. Sharding is a form of horizontal partitioning where you store part of the table data across multiple instances of a table. The table instance can exist on the same server under separate databases or across different servers. Each table instance contains parts of the total data, thus improving queries that need to access limited data. Sharding enables you to scale a database horizontally across multiple servers.

The best implementation strategy for sharding is to try to avoid it for as long as possible. Sharding requires additional maintenance efforts on the operations side and the use of proxy software to hide sharding from an application, or to make your application itself sharding aware. Sharding also adds limitations on queries that require access to the entire table. You will need to create cross-server joins or process data in the application layer.

See also

The MySQL optimization guide at https://dev.mysql.com/doc/refman/5.6/en/optimization.html

MySQL query execution plan information at https://dev.mysql.com/doc/refman/5.6/en/execution-plan-information.html

InnoDB storage engine at https://dev.mysql.com/doc/refman/5.6/en/innodb-storage-engine.html

Other storage engines available in MySQL at https://dev.mysql.com/doc/refman/5.6/en/storage-engines.html

Table maintenance statements at http://dev.mysql.com/doc/refman/5.6/en/table-maintenance-sql.html

MySQL test database at https://github.com/datacharmer/test_db

Ubuntu server logins with LDAP

So, we have installed and configured our own centralized auth server with LDAP. Now is the time to use LDAP to authenticate client logins. In this recipe, we will set up a separate Ubuntu server to use our LDAP server for authenticating users.

Getting ready

You will need a new Ubuntu server to be set as an LDAP client. Also, sudo privileges are needed for the initial setup.

Make sure you have followed the previous recipes and have set up your LDAP server.

How to do it…

We will need to install the LDAP client-side package on the client system. This package will install all the required tools to authenticate with the remote LDAP server:

$ sudo apt-get update

$ sudo apt-get install ldap-auth-client nscd

The installation process will ask you some questions regarding your LDAP server and its authentication details. Answer those questions as follows:

LDAP server URI: ldap://you-LDAP-server-IP: Make sure you change the protocol line from ldapi:/// to ldap://

Distinguished name of search base: Match this to the domain set on the LDAP server in the format dc=example,dc=com

LDAP version to use: 3

Make local root database admin: Yes

Does LDAP database require login: No

LDAP account for root: cn=admin,dc=example,dc=com

LDAP root account password: The password for the LDAP admin account

Next, we need to change the authentication configuration to check with the LDAP server. First, run the following command to set the name service switch file /etc/nsswitch.conf:

$ sudo auth-client-config -t nss -p lac_ldap

This will change /etc/nsswitch.conf as follows:

Next, add the following line to /etc/pam.d/common-session. This will create a local home directory for LDAP users. Edit the common-session file and add the following line at the end of the file:

session required pam_mkhomedir.so umask=0022 skel=/etc/skel

Now restart the nscd service with the following command:

$ sudo /etc/init.d/nscd restart

Now you should be able to log in with the user account created on your LDAP server. I have set up an Organizational Unit (OU) named users and created an admin user under it:

Next, change the login to the newly created LDAP user account with the su username command. You will need to enter a password that is configured on LDAP server. As this is a first-time login for this new user, our PAM settings have created a new home directory for him:

This new user is a member of the admin group on the LDAP server, so he will get sudo privileges on the local server as well.

You can always use a default login prompt to log in with LDAP users, as well as local user accounts that already exist on the server.

How it works…

Here we have configured the Ubuntu server to authenticate with our centralized LDAP system. This is not limited to the Ubuntu server and you can configure the Ubuntu desktop in a similar way as well. Using a centralized authentication makes it easy to administer hundreds of user accounts from a single place. A user can still log in as a local user if he has any local credentials.

Using centralized authentication enables you to log in from any system. You will get the same access rights and permissions from any terminal. Additionally, if the LDAP configuration supports roaming profiles then all your data will be replicated to any new system you log in from. You may have noticed the home directory for the LDAP user account is located in the /home/users directory and not in /home. This separates your account from any local users.

Finally, the groups and roles configured on the LDAP server also apply on the system you are logging in from. So, if the user is assigned admin rights on the LDAP server, he will get admin rights, including sudo privileges, on the system he is logged in from. This is because Ubuntu contains a default group named admin with sudo privileges. When a user logs in with his LDAP account, the groups and roles assigned to his LDAP account are matched with local groups and roles. You can either disable such groups from any remote systems, or set the proper access rights on the LDAP server itself.

See also

The Ubuntu community page for LDAP client authentication at https://help.ubuntu.com/community/LDAPClientAuthentication

Collaboration Tools

In this article, we will cover the following recipes:

  • Installing the VNC Server
  • Installing Hackpad, a collaborative document editor
  • Installing Mattermost – a self-hosted slack alternative
  • Installing OwnCloud, self-hosted cloud storage

Securing remote access with OpenVPN in Ubuntu

VPN enables two or more systems to communicate privately and securely over the public network or Internet. The network traffic is routed through the Internet, but is encrypted. You can use VPN to set up a secure connection between two datacenters or to access office resources from the leisure of your home. The VPN service is also used to protect your online activities, access location restricted contents, and bypass restrictions imposed by your ISP.

VPN services are implemented with a number of different protocols, such as Point-to-Point Tunneling Protocol (PPTP), Layer two tunneling protocol (L2TP), IPSec, and SSL. In this recipe, we will set up a free VPN server, OpenVPN. OpenVPN is an open source SSL VPN solution and provides a wide range of configurations. OpenVPN can be configured to use either TCP or UDP protocols. In this recipe, we will set up OpenVPN with its default UDP port 1194.

Getting ready…

You will need one server and one client system and root or equivalent access to both systems.

How to do it…

Install OpenVPN with the following command:

$ sudo apt-get update

$ sudo apt-get install openvpn easy-rsa

Now, set up your own certification authority and generate certificate and keys for the OpenVPN server.

Next, we need to edit the OpenVPN files that are owned by the root user, and the build-ca script needs root access while writing new keys. Temporarily, change to root account using sudo su:

$ sudo su

Copy the Easy-RSA directory to /etc/openvpn:

# cp -r /usr/share/easy-rsa /etc/openvpn/

Now edit /etc/openvpn/easy-rsa/vars and change the variables to match your environment:

export KEY_COUNTRY="US"

export KEY_PROVINCE="ca"

export KEY_CITY="your city"

export KEY_ORG="your Company"

export KEY_EMAIL="you@company.com"

export KEY_CN="MyVPN"

export KEY_NAME="MyVPN"

export KEY_OU="MyVPN"

Generate a Master certificate with the following commands:

# cd /etc/openvpn/easy-vars

# source vars

# ./clean-all

# ./build-ca

Next, generate a certificate and private key for the server. Replace the server name with the name of your server:

# ./build-key-server servername

Press the Enter key when prompted for the password and company name.

When asked for signing the certificate, enter y and then press the Enter key.

Build Diffie Hellman parameters for the OpenVPN server:

# ./build-dh

Copy all the generated keys and certificates to /etc/openvpn:

# cp /etc/openvpn/easy-rsa/keys/{servername.crt, servername.key, ca.crt, dh2048.pem} /etc/openvpn

Next, generate a certificate for the client with the following commands:

# cd /etc/openvpn/easy-rsa

# source vars

# ./build-key clientname

Copy the generated key, certificate, and server certificate to the client system. Use a secure transfer mechanism such as SCP:

/etc/openvpn/ca.crt

/etc/openvpn/easy-rsa/keys/clientname.crt

/etc/openvpn/easy-rsa/keys/clientname.key

Now, configure the OpenVPN server. Use the sample configuration files provided by OpenVPN:

$ gunzip -c /usr/share/doc/openvpn/examples/sample-config- files/server.conf.gz > /etc/openvpn/server.conf

Open server.conf in your favorite editor:

# nano /etc/openvpn/server.conf

Make sure that the certificate and key path are properly set:

ca ca.crt

cert servername.crt

key servername.key

dh dh2048.pen

Enable clients to redirect their web traffic through a VPN server. Uncomment the following line:

push "redirect-gateway def1 bypass-dhcp"

To protect against DNS leaks, push DNS settings to VPN clients and uncomment the following lines:

push "dhcp-option DNS 208.67.222.222"

push "dhcp-option DNS 208.67.220.220"

The preceding lines point to OpenDNS servers. You can set them to any DNS server of your choice.

Lastly, set OpenVPN to run with unprivileged user and group and uncomment the following lines:

user nobody

group nogroup

Optionally, you can enable compression on the VPN link. Search and uncomment the following line:

comp-lzo

Save the changes and exit the editor.

Next, edit /etc/sysctl to enable IP forwarding. Find and uncomment the following line by removing the hash, #, in front of it:

#net.ipv4.ip_forward=1

Update sysctl settings with the following command:

# sysctl -p

Now start the server. You should see an output similar to the following:

# service openvpn start

* Starting virtual private network daemon(s)

* Autostarting VPN 'server'

When it starts successfully, OpenVPN creates a new network interface named tun0. This can be checked with the ifconfig command:

# ifconfig tun0

tun0 Link encap:UNSPEC HWaddr 00-00-00-00-00-00-00- 00-00-00-00-00-00-00-00-00

inet addr:10.8.0.1 P-t-P:10.8.0.2 Mask:255.255.255.255

If the server does not start normally, you can check the logs at /var/log/syslog. It should list all the steps completed by the OpenVPN service.

How it works…

OpenVPN is the open source VPN solution. It is a traffic-tunneling protocol that works in client-server mode. You might already know that VPN is widely used to create a private and secure network connection between two endpoints. It is generally used to access your servers or access office systems from your home. The other popular use of VPN servers is to protect your privacy by routing your traffic through a VPN server. OpenVPN needs two primary components, namely a server and a client. The preceding recipe installs the server component. When the OpenVPN service is started on the OpenVPN host, it creates a new virtual network interface, a tun device named tun0. On the client side, OpenVPN provides the client with tools that configure the client with a similar setup by creating a tap device on the client's system.

Once the client is configured with a server hostname or IP address, a server certificate, and client keys, the client initiates a virtual network connection using a tap device on client to a tun device on the server. The provided keys and certificate are used to cross-check server authenticity and then authenticate itself. As the session is established, all network traffic on the client system is routed or tunneled via a tap network interface. All the external services that are accessed by the OpenVPN client, and you get to see the requests as if they are originated from the OpenVPN server and not from the client. Additionally, the traffic between the server and client is encrypted to provide additional security.

There's more…

In this recipe we have installed and configured OpenVPN server. To use the VPN service from your local system you will need a VPN client tool.

Following are the steps to install and configure VPN client on Ubuntu systems:

Install the OpenVPN client with a similar command the one we used to install the server:

$ sudo apt-get update

$ sudo apt-get install openvpn

Copy the sample client.conf configuration file:

$ sudo cp /usr/share/doc/openvpn/examples/sample-config- files/client.conf /etc/openvpn/

Copy the certificates and keys generated for this client:

$ scp user@yourvpnserver:/etc/openvpn/easy- rsa/keys/client1.key /etc/openvpn

You can use other tools such as SFTP or WinSCP on the Windows systems.

Now edit client.conf, enable client mode, and specify the server name or address:

client

remote your.vpnserver.com 1194

Make sure that you have set the correct path for keys copied from the server.

Now save the configuration file and start the OpenVPN server:

$ service openvpn start

This should create the tun0 network interface:

$ ifconfig tun0

Check the new routes created by VPN:

$ netstat -rn

You can test your VPN connection with any What's My IP service. You can also take a DNS leak test with online DNS leak tests.

For Windows and Mac OS systems, OpenVPN provides respective client tools. You need an OpenVPN profile with the .ovpn extension. A template can be found with the OpenVPN client you are using or on the server under OpenVPN examples. The following is the complete path:

/usr/share/doc/openvpn/examples/sample-config- files/client.conf

Note that OpenVPN provides a web-based admin interface

to manage VPN clients. This is a commercial offering that

provides an easy-to-use admin interface to manage OpenVPN

settings and client certificates.

Installing Ejabberd in Ubuntu

In this recipe, we will learn how to install the Ejabberd XMPP server. We will be using an integrated installation package that is available from the Ejabberd download site. You can also install Ejabberd from the Ubuntu package repository, but that will give you an older, and probably outdated, version.

Getting ready

You will need an Ubuntu server with root access or an account with sudo privileges.

How to do it…

The following are the steps to install Ejabberd:

Download the Ejabberd installer with the following command. We will be downloading the 64-bit package for Debian-based systems.

Make sure you get the updated link to download the latest available version:

$ wget https://www.process-one.net/downloads/downloads- action.php?file=/ejabberd/15.11/ejabberd_15.11-0_amd64.deb -O ejabberd.deb

Once the download completes, you will have an installer package with the .deb extension. Use the dpkg command to install Ejabberd from this package:

$ sudo dpkg -i ejabberd.deb

When installation completes, check the location of the Ejabberd executable:

$ whereis ejabberd

Now you can start the Ejabberd server, as follows:

$ sudo /opt/ejabberd-15.11/bin/ejabberdctl start

The start command does not create any output. You can check the server status with the ejabberdctl status command:

$ sudo /opt/ejabberd-15.11/bin/ejabberdctl status

Now your XMPP server is ready to use. Ejabberd includes a web-based admin panel. Once the server has started, you can access it at http://server_ip:5280/admin . It should ask you to log in, as shown in the following screenshot:

The admin panel is protected with a username and password. Ejabberd installation creates a default administrative user account with the username and password both set to admin.

To log in, you need a JID (XMPP ID) as a username, which is a username and hostname combination. The hostname of my server is ubuntu and the admin JID is admin@ubuntu. Once you have entered the correct username and password, an admin console will be rendered as follows:

How it works…

Ejabberd binaries are available as a Debian package. It includes a minimum Erlang runtime and all other dependencies. You can download the latest package from the Ejabberd download page.

The installer unpacks all the contents at the /opt/ejabberd-version directory. You can get an exact location of the installation with the whereis command. All executable files are generally located under the bin directory. We will mostly be working with ejabberdctl, which is a command line administrative tool. It provides various options to manage and monitor Ejabberd installation. You can see the full list of supported options by entering ejabberdctl without any options.

The following screenshot shows the partial output of executing ejabberdctl without any options:

If you have noticed, I am using sudo with each ejabberdctl command. You can avoid the use of the sudo command by switching to the ejabberd user, which is created at the time of Ejabberd installation. The installer creates a system user account, ejabberd, and sets its home directory to the Ejabberd installation directory, /opt/ejabberd-version. You will still need to use sudo to switch user accounts as the ejabberd user has no password set. Use the following command to log in as the ejabberd user:

$ sudo su ejabberd

In addition to creating the system user to run the Ejabberd process, the installer also creates an ejabberd admin account. The username and password for the administrator account is set to admin/admin. Make sure that you change this password before using your server in production. The installation process also creates a default XMPP host. The hostname is set to match your server hostname. It can be modified from the configuration file.

Once the server has started, you can access the handy web administrative console to manage most of the Ejabberd settings. You can add new users, create access control lists and set access rules, check the participating servers (node), and all hosted XMPP domains (host). Additionally, you can enable or disable Ejabberd modules separately for each domain. That means if you are using the same server to host xmpp1.example1.com and xmpp2.example2.com, you can enable a multi-user chat for xmpp1.example1.com and disable the same module for xmpp2.example2.com.

See also

Ejabberd download page at https://www.process-one.net/en/ejabberd/downloads/

Deleting a user account in Ubuntu

If you no longer need a user account, it is good idea to delete that account.

Getting ready

You will need super user or root privileges to delete a group from the Ubuntu server.

How to do it...

Follow these steps to delete the user account:

  1. Enter the following command to delete a user account:
    $ sudo deluser --remove-home john
  2. Enter your password to complete addgroup with root privileges:

How it works…

Here, we used the deluser command with the option --remove-home. This will delete the user account named john and also remove the home and mail spool directories associated with john. By default, the deluser command will delete the user without deleting the home directory.

It is a good idea to keep a backup of user files before removing the home directory and any other files. This can be done with an additional flag along with the deluser command:

$ deluser --backup --remove-home john

This will create a backup file with the name john.tar.gz in the current working directory, and then the user account and the home directory will removed.

There's more…

When called with the --group option, the deluser command will remove the group. Similarly, when called with two non-option arguments, the deluser command will try to remove a user from a specific group:

$ deluser john guest # this will remove user john from group guest

$ deluser --group guest # this will remove a group

If you want to disable the user account rather than delete it, you can do it with the following commands:

$ sudo usermod --expiredate 1 john # disable the user account john

$ sudo usermod --expiredate "" john # re-enable user account john

$ sudo usermod -e YYYY-MM-DD john # specify expiry date

Networking with LXD in Ubuntu

In this recipe, we will look at LXD network setup. By default, LXD creates an internal bridge network. Containers are set to access the Internet through Network Address Translation (NAT) but are not accessible from the Internet. We will learn to open a service on a container to the Internet, share a physical network with a host, and set a static IP address to a container.

Getting ready

As always, you will need access to the root account or an account with sudo privileges.

Make sure that you have created at least one container.

How to do it…

By default, LXD sets up a NAT network for containers. This is a private network attached to the lxdbr0 port on the host system. With this setup, containers get access to the Internet, but the containers themselves or the services running in the containers are not accessible from an outside network. To open a container to an external network, you can either set up port forwarding or use a bridge to attach the container directly to the host's network:

To set up port forwarding, use the iptables command, as follows:

$ sudo iptables -t nat -A PREROUTING -p tcp -i eth0 \

--dport 80 -j DNAT --to 10.106.147.244:80

This will forward any traffic on the host TCP port 80 to the containers' TCP port 80 with the IP 10.106.147.244. Make sure that you change the port and IP address as required.

You can also set a bridge that connects all containers directly to your local network. The bridge will use an Ethernet port to connect to the local network. To set a bridge network with the host, we first need to create a bridge on the host and then configure the container to use that bridge adapter.

To set up a bridge on the host, open the /etc/network/interfaces file and add the following lines:

auto br0

iface br0 inet dhcp

bridge_ports eth0

Make sure that you replace eth0 with the name of the interface connected to the external network.

Enable IP forwarding under sysctl. Find the following line in /etc/sysctl.conf and uncomment it:

net.ipv4.ip_forward=1

Start a new bridge interface with the ifup command:

$ sudo ifup br0

If required, you can restart the networking service, as follows:

$ sudo service networking restart

Next, we need to update the LXD configuration to use our new bridge interface. Execute a reconfiguration of the LXD daemon and choose  when asked to create a new bridge:

$ sudo dpkg-reconfigure -p medium lxd

Then on the next page, choose to use an existing bridge:

Enter the name of the newly created bridge interface:

This should configure LXD to use our own bridge network and skip the internal bridge. You can check the new configuration under the default profile:

$ lxc profile show default

Now, start a new container. It should receive the IP address from the router on your local network. Make sure that your local network has DHCP configured:

How it works…

By default, LXD sets up a private network for all containers. A separate bridge, lxdbr0, is set up and configured in the default profile. This network is shared (NAT) with the host system, and containers can access the Internet through this network. In the previous example, we used IPtables port forwarding to make the container port 80 available on the external network. This way, containers will still use the same private network, and a single application will be exposed to the external network through the host system. All incoming traffic on host port 80 will be directed to the container's port 80.

You can also set up your own bridge connected to the physical network. With this bridge, all your containers can connect to and be directly accessible over your local network. Your local DHCP will be used to assign IP addresses to containers. Once you create a bridge, you need to configure it with LXD containers either through profiles or separately with container configuration. In the previous example, we reconfigured the LXD network to set a new bridge.

LXD supports more advanced network configuration by attaching the host eth interface directly to a container. The following settings in the container configuration will set the network type to a physical network and use the host's eth0 directly inside a container. The eth0 interface will be unavailable for the host system till the container is live:

$ lxc config device add c1 eth0 nic nictype=physical parent=eth0

There's more…

LXD creates a default bridge with the name lxdbr0. The configuration file for this bridge is located at /etc/default/lxd-bridge. This file contains various configuration parameters, such as the address range for the bridge, default domain, and bridge name. An interesting parameter is the additional configuration path for dnsmasq configurations.

The LXD bridge internally uses dnsmasq for DHCP allocation. The additional configuration file can be used to set up various dnsmasq settings, such as address reservation and name resolution for containers.

Edit /etc/default/lxd-bridge to point to the dnsmasq configuration file:

# Path to an extra dnsmasq configuration file

LXD_CONFILE="/etc/default/dnsmasq.conf"

Then, create a new configuration file called /etc/default/dnsmasq.conf with the following contents:

dhcp-host=c5,10.71.225.100

server=/lxd/10.71.225.1

#interface=lxdbr0

This will reserve the IP 10.71.225.100 for the container called c5, and you can also ping containers with that name, as follows:

$ ping lxd.c5

See also

Read more about bridge configuration at https://wiki.debian.org/LXC/SimpleBridge

Find out more about LXD bridge at the following links:

https://insights.ubuntu.com/2016/04/07/lxd-networking-lxdbr0-explained/

http://askubuntu.com/questions/754323/lxd-2-0-local-networking

https://insights.ubuntu.com/2015/11/10/converting-eth0-to-br0-and-getting-all-your-lxc-or-lxd-onto-your-lan /

Read more about dnsmasq at https://wiki.debian.org/HowTo/dnsmasq

Sample dnsmasq configuration file: http://oss.segetech.com/intra/srv/dnsmasq.conf

Check the dnsmasq manual pages with the man dnsmasq command

Cloud Computing in Ubuntu

In this article, we will cover the following recipes:

  • Creating virtual machine with KVM
  • Managing virtual machines with virsh
  • Setting up your own cloud with OpenStack
  • Adding a cloud image to OpenStack
  • Launching a virtual instance with OpenStack
  • Installing Juju a service orchestration framework
  • Managing services with Juju

Setting MySQL backups in Ubuntu

In this recipe, we will learn how to back up the MySQL database.

Getting ready

You will need administrative access to the MySQL database.

How to do it…

Follow these steps to set up the backups:

Backing up the MySQL database is the same as exporting data from the server. Use the mysqldump tool to back up the MySQL database as follows:

$ mysqldump -h localhost -u admin -p mydb > mydb_backup.sql

You will be prompted for the admin account password. After providing the password, the backup process will take time depending on the size of the database.

To back up all databases, add the --all-databases flag to the preceding command:

$ mysqldump --all-databases -u admin -p alldb_backup.sql

Next, we can restore the backup created with the mysqldump tool with the following command:

$ mysqladmin -u admin -p create mydb

$ mysql -h localhost -u admin -p mydb mydb_backup.sql

To restore all databases, skip the database creation part:

$ mysql -h localhost -u admin -p alldb_backup.sql

How it works…

MySQL provides a very general tool, mysqldump, to export all data from the database server. This tool can be used with any type of database engine, be it MyISAM or InnoDB or any other. To perform an online backup of InnoDB tables, mysqldump provides the --single-transaction option. With this option set, InnoDB tables will not be locked and will be available to other applications while backup is in progress.

Oracle provides the MySQL Enterprise backup tool for MySQL Enterprise edition users. This tool includes features such as incremental and compressed backups. Alternatively, Percona provides an open source utility known as Xtrabackup. It provides incremental and compressed backups and many more features.

Some other backup methods include copying MySQL table files and the mysqlhotcopy script for InnoDB tables. For these methods to work, you may need to pause or stop the MySQL server before backup.

You can also enable replication to mirror all data to the other server. It is a mechanism to maintain multiple copies of data by automatically copying data from one system to another. In this case, the primary server is called Master and the secondary server is called Slave. This type of configuration is known as Master-Slave replication. Generally, applications communicate with the Master server for all read and write requests. The Slave is used as a backup if the Master goes down. Many times, the Master-Slave configuration is used to load balance database queries by routing all read requests to the Slave server and write requests to the Master server. Replication can also be configured in Master-Master mode, where both servers receive read-write requests from clients.

See also

MySQL backup methods at http://dev.mysql.com/doc/refman/5.6/en/backup-methods.html

Percona XtraBackup at https://www.percona.com/doc/percona- xtrabackup/2.2/index.html

MySQL binary log at http://dev.mysql.com/doc/refman/5.6/en/binary-log.html

Installing OpenLDAP on Ubuntu

This recipe covers the installation and initial configuration of LDAP. The Ubuntu package repository makes the installation easy by providing the required packages for the LDAP service.

Getting ready

You will need access to a root account or an account with sudo privileges.

How to do it…

Let's start with installing the LDAP package and helper utilities:

Update your repository using the apt-get update command and then install the OpenLDAP package, slapd:

$ sudo apt-get update

$ sudo apt-get install slapd ldap-utils

You will be asked to enter the admin password and to confirm it.

The installation process simply installs the package without any configuration. We need to start the actual configuration process with the reconfiguration of the slapd package. Use the following command to start the re-configuration process:

$ sudo dpkg-reconfigure slapd

This command will ask you a series of questions including the domain name, admin account, password, database type, and others. Match your answers as follows:

Omit LDAP server configuration – NO.

DNS Domain name – Enter your domain name. You can use any domain name. For this setup, I will be using example.com. This domain name will determine the top structure of your directory:

Organization name – Enter your organization name. I am using example as my organization.

Admin password – Enter a password for the admin account. It can be the same as the one entered during installation, or a totally different one. Make sure you note this password as it will be used to access the admin account.

Database backend – HDB

Remove the database when slapd is purged - this is about removing the database in case you uninstall the slapd package. Choose NO as you don't want the database to be deleted:

Move old database - YES

Allow the LDAPv2 protocol - unless you are planning to use some old tools, choose NO:

Once you have answered all the questions, the process will reconfigure the LDAP service. Now your LDAP service is installed and ready to use:

Now you can use utility commands to query existing data. To test whether the LDAP service is installed and running properly, use the ldapsearch -x command. You should see output similar to following screenshot:

Use ldapsearch as follows to query our newly added domain, example.com:

$ ldapsearch -x -LLL -H ldap:/// -b dc=example,dc=com dn

The following command will query the default content for example.com:

$ ldapsearch -x -LLL -b dc=example,dc=com

The ldap-utils package also provides more commands to configure the LDAP service, but it is quite a lengthy and complex task. In the next recipe, we will learn how to set up a web-based admin interface that make things a little easier.

How it works…

With the respective packages available in the Ubuntu package repository, installing OpenLDAP is quite an easy task. All we have to do is install the required binaries and then configure the LDAP system to serve our desired domain. We have installed two packages: one is slapd, the LDAP daemon, and the other is ldap-utils, which provides various commands to work with the LDAP daemon. After installation is complete, we have re-configured LDAP to match our required directory setup. We have chosen to go with LDAPv3 API and disabled LDAPv2. If you have any older systems working with LDAPv2, then you will need to enable support for old APIs.

Before we access the admin page, let's make some small changes in the configuration file. The file is located at /etc/phpldapadmin/config.php. By default, phpLDAPadmin shows warning messages for unused template files. These warning messages get shown in the main interface before the actual content. To hide them, search for hide_template_warning in the configuration file and set it to true. You will also need to uncomment the same line:

$config->custom->appearance['hide_template_warning'] = true;

The other settings should have already been set by the installation process. You can cross-check the following settings:

$servers->setValue('server','host','127.0.0.1');

$servers->setValue(

'login','bind_id',

'cn=admin,dc=example,

dc=com'

);

$servers->setValue(

'server','base',array('dc=example,dc=com')

);

Once you are done with the configuration file changes, save and close it and then access the admin interface through your browser:

Click on the login link on the left of the page to get the login dialogue box. The username (Login DN) field is already filled with details for the admin account. Make sure the details match the domain you have set up. Enter the password for the admin account and click the Authenticate button:

You should have noticed the warning on the login box saying the connection is unencrypted. This is just a reminder that you are using the admin console over a non-HTTPs connection. You can set up Apache with SSL certificates to get an encrypted, secure connection with your LDAP server. Check article 3, Working with Web Servers, for more details on how to set up SSL certificates on the Apache web server.

Once you log in to phpLDAPadmin, you can see the domain listed in the left-hand side menu. Click on the domain link to view its details.

Next, click on the small plus link (+) to expand the domain link and see its children. With the default settings, it should show only the admin account:

Along with the link for the admin account, you will see an option to create a new entry. Clicking on this link will show you a list of templates for the new entry:

While clicking on some of these templates, for example Generic:

User Account, you may notice a PHP error saying Error

trying to get non-existent value. The form rendering fails and you cannot

see the complete form the with submit button. This is a small bug and

can be fixed with a small edit.

Open /usr/share/phpldapadmin/lib/TemplateRender.php.

Search for the following line:

$default = $this->getServer()

->getValue('appearance','password_hash');

Now update the preceding command as follows:

$default = $this->getServer()

->getValue('appearance','password_hash_custom');

Now you are ready to create groups and respective user accounts on your LDAP server.

How it works…

In this recipe, we have installed a web-based administration console for the LDAP server. The ldap-utils package provides various commands to work with the LDAP server, but it is quite a complex and lengthy task. A graphical user interface gives you a better listing of all options and existing configurations, making things a little easier.

The phpLDAPadmin package is a PHP/Apache-based web application that provides a graphical interface for the LDAP server. It displays all options and configurations in an easy-to-use graphical format and passes all user actions to LDAP APIs.

There's more…

Apache directory studio is another user interface for LDAP administration. It is a desktop application based on Java. You can get more details at https://directory.apache.org/studio/ .

See also

A StackOverflow answer for the phpLDAPadmin error message at http://stackoverflow.com/a/21195761/1012809

Troubleshooting Ubuntu web server

In this recipe, we will cover some common issues with Apache and Nginx and list the basic steps for overcoming those issues. The steps mentioned here are general troubleshooting methods; you may need to change them based on your setup and environment.

Getting ready

You may need root level access to your web server system.

How to do it…

Web server problems can be grouped in a few broad categories, such as a server not working, a particular domain or virtual host is not accessible, problems with a specific module configuration, and access denied errors. The following section lists each of these problems and their possible solutions.

Web server not accessible

The first step is to check your local Internet connection. Try to access the server from another system from another network.

Check if the DNS settings point to your web server.

If your network is working properly, then try to ping to the server IP address.

On the web server, check the firewall or any other tool that may block communication.

Open a telnet connection to web server on port 80, or whatever port you have used for web server. If you see output similar to following screenshot, then your web server is working:

Make sure that the web server port is not being used by some other process:

$ sudo netstat -plutn

If required, reload or restart the web server process:

$ sudo service apache2 reload/restart

Check the Apache/Nginx logs listed under the /var/log/ directory and view the entire file in a scrollable format:

$ less /var/log/apache2/error.log

See the continuous stream of logs as they are added to the log file:

$ tail -f /var/log/nginx/error.log

You may want to run Apache with extended log levels. Find the variable LogLevel in /etc/apache2/apache2.conf and set its value to debug:

$ sudo nano /etc/apache2/apache2.conf

LogLevel debug

Run Apache in debug single process mode:

$ sudo apache2ctl -X # debug mode single worker

Virtual host not accessible

Make sure you have enabled virtual host configuration:

ubuntu@ubuntu:~$ a2query -s

example.com (enabled by site administrator)

Check the virtual host configuration for any syntax errors:

ubuntu@ubuntu:~$ sudo apache2ctl -t

Syntax OK

On Nginx, use the following command:

ubuntu@ubuntu:~$ sudo nginx -t

nginx: the configuration file /etc/nginx/nginx.conf syntax is ok

nginx: configuration file /etc/nginx/nginx.conf test is successful

Check the virtual host's details and other Apache configurations:

$ sudo apache2ctl -S

Make sure your virtual host IP and port configuration matches the one defined with NamedVirtualHost.

Check DocumentRoot - does it point to proper files?

On Apache:

DocumentRoot /var/www/html

On Nginx:

server {

root /usr/share/nginx/html;

}

Crosscheck your ServerName and ServerAlias variables - do they match your domain name?

On Apache, these settings should look similar to this:

ServerName example.com

ServerAlias www.example.com

On Nginx, the ServerName is defined as this:

server {

server_name example.com www.example.com;

}

Access denied or forbidden errors

Check directory permissions for the virtual host root directory. Are they accessible to the web server? Check the web server user and group (commonly www-data) have ready permissions. If required, you can set permissions with chown and chmod commands.

ubuntu@ubuntu:~$ ls -l /var/www/

drwxr-x--- 3 ubuntu www-data 4096 Aug 4 23:00 example.com

drwxr-xr-x 2 ubuntu www-data 4096 Aug 2 23:04 public_html

Secondly, make sure that you have properly set directory permissions in the virtual host configuration. Are they restricting file access?

Use the following commands to set directory permissions in the virtual host configuration:

AllowOverride None

Order Deny,Allow

Deny from all

Apache downloads .php files

Make sure that the mod_php module is installed and enabled:

ubuntu@ubuntu:~$ ls -l /etc/apache2/mods-available | grep php

-rw-r--r-- 1 root root 897 Jul 2 21:26 php7.0.conf

-rw-r--r-- 1 root root 59 Jul 2 21:26 php7.0.load

ubuntu@ubuntu:~$ a2query -m | grep php

php7.0 (enabled by maintainer script)

Automating common tasks with Git hooks

One of the more interesting features of Git is hooks. With hooks, you can tie an arbitrary script to various Git events. Whenever a particular event, such as a git commit or git push, occurs, the script attached to that event gets executed.

Typically, an event consists of several steps, and a script can be attached to each of these steps. The most common steps are pre-event and post-event, with pre hooks executed before the event and post hooks after the event. A pre hook, such as pre-commit, is generally used to cross-check the updates and can approve or reject an actual event. A post hook is used to execute additional activities after an event, such as start a built process when a new push is received or a notification sent.

Every Git repository consists of a .git/hooks directory with sample scripts. You can start using those hooks by removing the .sample extension from the script name. Additionally, the hook scripts belong to a single repository instance and do not get copied with the repository clone. So, if you add some hooks to your local repository and then push changes to the remote, the hooks will not get replicated on the remote. You will need to manually copy those scripts on the remote system. Built-in sample hooks generally use the shell scripts, but you can use any scripting language, such as Python or even PHP.

In this recipe, we will learn how to use Git hooks. We will create our own post-commit hook that deploys to a local web server.

Getting ready

We will need a local web server installed. I have used an Apache installation; feel free to use your favorite server:

Set up a new virtual host under Apache and enable it:

$ cd /var/www/

$ sudo mkdir git-hooks-demo

$ sudo chown ubuntu:ubuntu git-hooks-demo

$ cd git-hooks-demo

Create index.html and add the following contents to it:

$ vi index.html

Git hooks demo

Deployed Manually

Troubleshooting Ubuntu network connectivity

Networking consists of various components and services working together to enable systems to communicate with each other. A lot of times it happens that everything seems good, but we are not able to access other servers or the Internet. In this recipe, we will look at some tools provided by Ubuntu to troubleshoot the network connectivity issues.

Getting ready

As you are reading this recipe, I am assuming that you are facing a networking issue. Also, I am assuming that the problems are with a primary network adapter, eth0.

You may need access to root account or account with similar privileges.

How to do it…

Follow these steps to troubleshoot network connectivity:

Let's start with checking the network card. If it is working properly and is detected by Ubuntu. Check boot time logs and search for lines related to Ethernet, eth:

$ dmesg | grep eth

If you don't find anything in the boot logs, then most probably, your network hardware is faulty or unsupported by Ubuntu.

Next, check whether the network cable is plugged in and is working properly. You can simply check the LED indicators on the network card or use the following command:

$ sudo mii-tool

If you can see a line with link ok, then you have a working Ethernet connection.

Next, check whether a proper IP address is assigned to the eth0 Ethernet port:

$ ifconfig eth0

Check whether you can find a line that starts with inet addr. If you cannot find this line or it is listed as inet addr 169.254, then you don't have an IP address assigned.

Even if you see a line stating the IP address, make sure that it is valid for network that you are connected to.

Now assuming that you have not assigned an IP address, let's try to get dynamic IP address from the DHCP server. Make sure that eth0 is set for dynamic configuration. You should see line similar to iface eth0 inet dhcp:

$ cat /etc/network/interfaces

Execute the dhclient command to query the local DHCP server:

$ sudo dhclient -v

If you can see a line similar to bound to 10.0.2.15, then you are assigned with a new IP address. If you keep getting DHCPDISCOVER messages, this means that your DHCP server is not accessible or not assigning an IP address to this client.

Now, if you check the IP address again, you should see a newly IP address listed:

$ ifconfig eth0

Assuming that you have received a proper IP address, let's move on to the default gateway:

$ ip route

The preceding command lists our default route. In my case, it is 10.0.2.2. Let's try to ping the default gateway:

$ ping –c 5 10.0.2.2

If you get a response from the gateway, this means that your local network is working properly. If you do not get a response from gateway, you may want to check your local firewall.

Check the firewall status:

$ sudo ufw status

Check the rules or temporarily disable the firewall and retry reaching your gateway:

$ sudo ufw disable

Next, check whether we can go beyond our gateway. Try to ping an external server. I am trying to ping a public DNS server by Google:

$ ping -c 5 8.8.8.8

If you successfully receive a response, then you have a working network connection. If this does not work, then you can check the problem with the mtr command. This command will display each router between your server and the destination server:

$ mtr -r -c 1 8.8.8.8

Next, we need to check DNS servers:

$ nslookup www.ubuntu.com

If you received an IP address for Ubuntu servers, then the DNS connection is working properly. If it's not, you can try changing the DNS servers temporarily. Add the nameserver entry to /etc/resolve.conf above other nameserver, if any:

nameserver 8.8.8.8

At this point, you should be able to access the Internet. Try to ping an external server by its name:

$ ping -c 3 www.ubuntu.com

There's more…

The following are some additional commands that may come handy while working with a network:

lspci lists all pci devices. Combine it with grep to search for specific device.

Lsmod shows the status of modules in Linux kernels.

ip link lists all the available network devices with status and configuration parameters.

ip addr shows the IP addresses assigned for each device.

ip route displays routing table entries.

tracepath/traceroute lists all the routers (path) between local and remote hosts.

iptables is an administration tool for packet filtering and NAT.

dig is a DNS lookup utility.

ethtool queries and controls network drivers and hardware settings.

route views or edits the IP routing table.

telnet was the interface for telnet protocol. Now it is a simple tool to quickly check remote working ports.

Nmap is a powerful network mapping tool.

netstat displays network connections, routing tables, interface stats, and more.

ifdown and ifup start or stop the network interface. They are similar to ifconfig down or ifconfig up.

Introduction on Communication Server with XMPP in Ubuntu

Extensible Messaging and Presence Protocol (XMPP) is a communication protocol that provides near-real-time message passing between two or more entities. XMPP is based on XML and transfers data in predefined formats that are known to server as well as client systems. Being an XML-based protocol, you can easily extend XMPP to suit your requirements. It also provides various standard extensions to extend the base functionality of the XMPP server.

In this article, we will learn how to set up our own XMPP server. The main focus will be on implementing a simple chat application. In later recipes, we will also look at a Node.js and socket-based alternative to implementing the messaging server.

We will be working with a popular XMPP server Ejabberd. It is a well-known XMPP implementation supported by ProcessOne. Ejabberd is based on Erlang, a functional programming language specifically designed for soft real-time communication.