Friday, April 9, 2010

Michael Conigliaro RHCE Exam Experience

SkyHi @ Friday, April 09, 2010

On September 4th, 2009, I took the new 3.5 hour, single-section RHCE exam. This was my first time taking the exam, and to be perfectly honest, it was nowhere near as challenging as I thought it would be. While I don’t want to downplay the significance of the RHCE certification or give anyone the false impression that the exam is necessarily easy, I do want to emphasize that contrary to popular belief, it is quite possible to self-study your way to a perfect score. Not only was I able to breeze through the entire list of test objectives, I had time to thoroughly check and double-check all of my work with almost an hour to spare. This meant I was done long before anyone else in the room, including those who took the official Red Hat training courses. So how did I accomplish this feat?

The first thing you should know is that I had already been working professionally with Linux for ~10 years before I began studying for the exam. I doubt that so much experience is really necessary, but because the exam measures actual competency on live systems rather than your ability to memorize or “read between the lines,” I think it’s highly unlikely that someone with little or no working knowledge of Linux could successfully cram for this test. So I’d have to say that experience is an important prerequisite, but I’d also have to say that experience alone is almost certainly not enough. Considering the wide range of subject matter, it’s very likely that you’ll be tested on something you’ve never had to touch before.

In my opinion, the hardest thing about self-studying for the RHCE exam is knowing how much you need to know about each study point in the RHCE Prep Guide. In other words, when it says something like “you need to know basic configuration of x,” it’s hard to know exactly what “basic configuration” means. Although I’ve signed an NDA preventing me from revealing any details about the exam itself, I can tell you that nearly all of my study material came from two places:

  1. RHCE Red Hat Certified Engineer Linux Study Guide by Michael Jang
  2. Red Hat Deployment Guide

The rest of my study material came from search engines. I spent a lot of time comparing other people’s study notes to mine and reading anecdotes about the RHCE exam. While the result of this was usually a temporary blow to my confidence (there are a lot of horror stories out there!), I did find a few blogs and forum posts with some helpful information. Usually it was just an alternative way of doing something, but it was also nice to come across the occasional words of encouragement from a self-studied RHCE. Just knowing that other people had done it gave me a slight confidence boost (as I hope this post does for some of you).

The first thing I did was read Michael Jang’s book cover to cover, just trying to absorb what I considered to be the most important information from each chapter (i.e. concepts rather than commands). This took me a week or two. When I was done, I set up a test environment using VirtualBox. Then I decided it would help to have a condensed, single-page study guide to refer to, so I created a “wikified” version of the RHCE Prep Guide which I called my RHCE “cheat sheet”. For the next few weeks, I went through each study point on the “cheat sheet” and used my study material to test and document everything I thought I might need to know.

I found Michael Jang’s book to be a great study guide (the labs and example problems were a huge help), but I wasn’t completely happy with the amount of detail on some topics, as well as how it tends to follow the Red Hat course outlines rather than just sticking to the RHCE Prep Guide. I also found quite a few typos and just plain incorrect information, so that’s where the Red Hat Deployment Guide came in. While I was working on the RHCE “cheat sheet,” I would usually read the appropriate chapter(s) from Michael Jang’s book first, then I would supplement it with the appropriate chapter(s) from the Red Hat Deployment Guide. If I felt particularly weak in a certain area, I would also peruse the man pages and any HOWTOs I could find online. This was a long, arduous process, but it helped ensure that I wasn’t missing any important details.

For the last couple weeks, I tested myself by putting the “cheat sheet” away, doing a minimal install of CentOS in my test environment, and trying to configure everything I could without referring to any documentation whatsoever. Since the test takes place on a live system, I assumed from the beginning that the man pages would be available, but in order to save time, I wanted to make sure I could do everything off the top of my head. As a result, I ended up memorizing almost everything on the “cheat sheet,” which is probably why I was able to complete the exam so quickly.

Since I didn’t have a study partner, preparing for the troubleshooting section of the exam was a bit of a challenge. I did come across an interesting project called Trouble Maker which directly addresses this problem, but unfortunately, it has not been updated in several years and does not work on recent versions of CentOS. For a while, I actually considered writing my own trouble maker program, but I ultimately decided that this would be too much work. Luckily, I have a few friends who know enough about Linux to make a machine unbootable, so we made a game of it. I would give them my root password and challenge them to do something that would keep me from using my computer, then I would try to fix it as fast as I could.

When it was all said and done, I spent roughly six weeks (studying a few hours each day) to prepare for the RHCE. Considering how easy the exam was for me, I believe that I worked a lot harder than I needed to, but the results were clearly well worth the effort. The best advice I can give to prospective RHCEs is to take your time and practice until you can do everything in the RHCE Prep Guide off the top of your head. If you feel weak in anything, do yourself a favor and postpone the exam.


RHCE "Cheat Sheet"

SkyHi @ Friday, April 09, 2010
This document attempts to provide answers to all study points on the RHCE and RHCT Exam Preparation Guide in a single-page (and thus, printable) format. This is not a “brain dump” or an attempt to cheat the RH302 exam in any way. These are just my self-study notes. Use them at your own risk.

:!: Note: Study points last updated on 2009-08-11. This list may become out of date without notice (especially after I pass the test ;-)).
Testing Environment with Sun VirtualBox

install guest additions:

yum install gcc kernel-devel

Prerequisite skills for RHCT and RHCE

Candidates should possess the following skills, as they may be necessary in order to fulfill requirements of the RHCT and RHCE exams:
use standard command line tools (e.g., ls, cp, mv, rm, tail, cat, etc.) to create, remove, view, and investigate files and directories
use grep, sed, and awk to process text streams and files
use a terminal-based text editor, such as vim or nano, to modify text files
use input/output redirection
operator description
> redirect STDOUT to a file
2> redirect STDERR to a file
&> redirect all output to a file
2>&1 redirect all output to a pipe

use » to append instead of overwrite

understand basic principles of TCP/IP networking, including IP addresses, netmasks, and gateways for IPv4 and IPv6
use su to switch user accounts

su -

use passwd to set passwords


use tar, gzip, and bzip2

# compress (tar/gzip)
tar cvzf .tgz

# extract (tar/gzip)
tar xvzf .tgz

# compress (tar/bzip)
tar cvjf .tbz

# extract (tar/bzip)
tar xvjf .tbz

configure an email client on Red Hat Enterprise Linux

echo "message" | mail -s "subject"
mail -s "subject" <

use text and/or graphical browser to access HTTP/HTTPS URLs


use lftp to access FTP URLs
RHCT skills
Troubleshooting and System Maintenance

RHCTs should be able to:
boot systems into different run levels for troubleshooting and system maintenance

append the desired runlevel to grub's kernel line:

1-5 runs appropriate rc and init scripts
single only runs rc.sysinit
emergency skips all rc and init scripts

diagnose and correct misconfigured networking

check /etc/sysconfig/network
check /etc/sysconfig/network-scripts/ifcfg-
service network restart
chkconfig network on
netstat -r

redhat network config tool:


diagnose and correct hostname resolution problems

check /etc/nsswitch.conf
check /etc/resolv.conf
check /etc/hosts
dig @

redhat network config tool:


configure the X Window System and a desktop environment

install x:

yum groupinstall "x window system"

init respawns /etc/X11/prefdm -nodaemon to keep x running in runlevel 5
startx to start manually

xfs is supposedly required for x windows (even though i can run x fine without it…):

service xfs on
chkconfig xfs on

x environment config:


redhat display config tool:

system-config-display [--reconfig]

install gnome desktop:

yum groupinstall "gnome desktop environment"

switchdesk allows you to change your desktop environment:

yum install switchdesk

if switchdesk is not available, edit /etc/sysconfig/desktop:


add new partitions, filesystems, and swap to existing systems

manage partitions:



make filesystems:


label filesystems:


Thursday, April 8, 2010

Ubuntu install HFSprogs fro HFS+

SkyHi @ Thursday, April 08, 2010
#sudo apt-get install hfsprogs

#mkfs.hfsprogs /dev/sda3

Wednesday, April 7, 2010

Redirect To SSL Using Apache’s .htaccess

SkyHi @ Wednesday, April 07, 2010

There are plenty of times I want to require users to be accessing a site only via SSL. My first try at this was to simple create a .htaccess file that contained SSLRequireSSL, which basically tells Apache that access to a site can only be allowed if SSL is being used. This accomplished what I wanted, but it brought a side issue to requiring SSL, users often leave off (or forget) the the s in https. So after a little bit of digging around I found another approach to this. The new .htaccess file looks like this:

RewriteEngine On
RewriteCond %{SERVER_PORT} !443
RewriteRule (.*) [R]

The first line tells Apache we are going to use mod_rewrite. The second line only matches if the port being used to access the site is 443 (the port reserved for https use). If that second line matches then the third takes kicks in, which simply redirects the user to the SSL version of your URL. This still enforces the use of SSL, but saves you from trying figure why you can’t get to your site just because you forget the s in https.

UPDATE Tue 23 May 2006 @ 3:50pm : Comment #4 by Nicolás Echániz has an even better version of this that isn’t limited to checking a specific port (443) for SSL:

RewriteEngine On
RewriteCond %{HTTPS} off
RewriteRule (.*) https://%{HTTP_HOST}%{REQUEST_URI}


Apache server response codes

SkyHi @ Wednesday, April 07, 2010


Whenever a user sends a request to a server, a process called a ‘handshake’ begins where the server and your computer communicate and the server makes sure it can accommodate what your user has requested of it. This means being able to make the connection between the two computers and then completing the transfer of data.

Headers are short fragments of text which are generated by servers to hold information pertaining to each transfer as it occurs. There are four kinds of headers:


This holds information about the client (user), the server itself and the protocol being used (like http or ftp).
Entity This holds information about the data that is being transferred.


This holds information about the allowable formats and parameters for the transfer.


This is sent out by the server at the end of a transfer, and includes detailed information, in code form, on the outcome of the transfer.

Response Codes

As a web surfer you've probably become familiar with the dreaded 404 error message and the 500 internal server error.

If you get a 404 make sure your link is correct. Case does matter.A 500 Error is the result of a misconfigured CGI script or a misconfigured .htaccess file,. These are the most well-known server response codes, but there are many more. These numerical codes are grouped — the low numbers are generally ‘good’, and operate silently, while anything over 400 is definitely bad news and will be reported to the user in the form of an error message.

Error Code



Silent Response Codes that signify that a request has been received and is currently being processed.


The request has been completed and the rest of the process can continue.


The user's request to switch protocols (like from FTP to HTTP) was accepted.


Silent codes that confirm that requests have completed successfully.


Ok — the file which the client requested is available for transfer. This is the response code you want to see all of your users receiving.


When new pages are created by posted form data or by a CGI process, this is confirmation that it worked.


The client's request was accepted, though not yet processed.


The information contained in the entity header is not from the original site, but from a third party server.


If you click a link which has no target URL, this response is elicited by the server. It's silent and doesn't warn the user about anything.


This allows the server to reset any content returned by a CGI.


Partial content — the requested file wasn't downloaded entirely. This is returned when the user presses the stop button before a page is loaded, for example.


A redirection is occurring from the original request.


The requested address refers to more than one file. Depending on how the server is configured, you get an error or a choice of which page you want.


Moved Permanently — if the server is set up properly it will automatically redirect the reader to the new location of the file.


Found — page has been moved temporarily, and the new URL is available. You should be sent there by the server.


This is a "see other" SRC. Data is somewhere else and the GET method is used to retrieve it.


Not Modified — if the request header includes an 'if modified since' parameter, this code will be returned if the file has not changed since that date. Search engine robots may generate a lot of these.


Request is incomplete for some reason.


Bad Request — there is a syntax error in the request, and it is denied.


The request header did not contain the necessary authentication codes, and the client is denied access.


Payment is required. This code is not yet in operation.


Forbidden — the client is not allowed to see a certain file. This is also returned at times when the server doesn't want any more visitors.


Document not found — the requested file was not found on the server. Possibly because it was deleted, or never existed before. Often caused by misspellings of URLs.


The method you are using to access the file is not allowed.


The requested file exists but cannot be used as the client system doesn't understand the format the file is configured for.


The request must be authorised before it can take place.


Request Timeout — the server took longer than its allowed time to process the request. Often caused by heavy net traffic.


Too many concurrent requests for a single file.


The file used to be in this position, but is there no longer.


The request is missing its Content-Length header.


A certain configuration is required for this file to be delivered, but the client has not set this up.


The requested file was too big to process.


The address you entered was overly long for the server.


The filetype of the request is unsupported.


Errors have occurred in the server itself.


Internal Server Error — nasty response that is usually caused by a problem in your Perl code when a CGI program is run.


The request cannot be carried out by the server.


Bad Gateway — the server you're trying to reach is sending back errors.


Temporarily Unavailable — the service or file that is being requested is not currently available.


The gateway has timed out. Like the 408 timeout error, but this one occurs at the gateway of the server.


The HTTP protocol you are asking for is not supported.

Error code categories

Successful Client Requests:

200 OK
201 Created
202 Accepted
203 Non-Authorative Information
204 No Content
205 Reset Content
206 Partial Content

Client Request Redirected:

300 Multiple Choices
301 Moved Permanently
302 Moved Temporarily
303 See Other
304 Not Modified
305 Use Proxy

Client Request Errors:

400 Bad Request
401 Authorization Required
402 Payment Required (not used yet)
403 Forbidden
404 Not Found
405 Method Not Allowed
406 Not Acceptable (encoding)
407 Proxy Authentication Required
408 Request Timed Out
409 Conflicting Request
410 Gone
411 Content Length Required
412 Precondition Failed
413 Request Entity Too Long
414 Request URI Too Long
415 Unsupported Media Type

Server Errors:

500 Internal Server Error
501 Not Implemented
502 Bad Gateway
503 Service Unavailable
504 Gateway Timeout
505 HTTP Version Not Supported


Don’t ever put CNAME on the root domain (esp. if you want MX to work)

SkyHi @ Wednesday, April 07, 2010

I was changing name servers for one of my domains. When testing the mail setup, I kept getting mail sent to the web server rather than the mail server. It turns out that if the mail server can’t find mx records, it falls back to A (or CNAME) records. So why was the mail server falling back to using the A/CNAME record when I had a perfectly good MX record assigned to the domain? After many hours of debugging and comparing working domain with non-working ones, the only difference I found was that I has a CNAME for the domain eg. 3600 IN CNAME

Turns out that if you have a CNAME for the domain, it redirects the lookup not just for A but for every record. So from dig, it looks fine if you query the authorative name servers directly – you see the mx and cname record – but it falls flat when queried on the recursive nameserver. Indeed after looking at RFC 1034, it states that “If a CNAME RR is present at a node, no other data should be present”. So setting the CNAME on the domain also consequently redirected requests for NS and SOA records, which made the domain quite invalid, although the subdomain records still resolved. Bottom line, don’t ever put CNAME on the root domain.

I was trying to be smart and save on retyping the IP by using CNAME… but turns out I was too smart.


Tuesday, April 6, 2010

A mail server with Postfixadmin, Postfix and Dovecot on Debian Lenny ¶

SkyHi @ Tuesday, April 06, 2010

A mail server with Postfixadmin, Postfix and Dovecot on Debian Lenny

This HOWTO will explain the installation and configuration of a full featured mail server using Postfix as SMTP server, Dovecot as POP/IMAP server and Postfixadmin as management interface. As Postfixadmin need a database to maintain account and domain informations we will use MySQL (but also PostgresSQL or SQLite can be used). All the configurations were done on a Debian Lenny system.

Postfixadmin Installation

Postfixadmin is distributed as Debian package directly by the maintainer, but we need to download just the .deb file from here because there is no repository. Before installing it we will need to install some dependencies (a web server, and because we want to use it on a standalone server, also a database server). We choose to use Apache as web server and MySQL as database server, so we will need to install these packages and all the other Postfixadmin dependencies; this can be done the Debian way with the command:

aptitude install dbconfig-common wwwconfig-common  \
libapache2-mod-php5 php5 php5-imap php5-mysql \
mysql-client mysql-server postfix-mysql

we will also have to answer to the ordinary setup questions made by debconf; we can just accept the default values, but we will have to choose a password for the MySQL root administrative account.

Before installing the Postfixadmin from the .deb file we will need to create a database and a database account that will be used by Postfixadmin for its data; we can do this with the following commands:

mysqladmin -u root -p create postfixadmin
mysql -u root -p
mysql> grant create, select, insert, update, delete, lock, index, alter, drop
on postfixadmin.* to 'postfixadmin'@'localhost'
identified by 'secretandcomplexpassword';
mysql> flush privileges;
mysql> \q

(they will ask for the root account password that was given in the previous step). After this we can install the .deb file with:

dpkg -i postfixadmin_*.deb

There are two possible choices for Postfixadmin: the 2.2 stable version and the new 2.3 release candidate; this last one supports more features and is almost production ready. If you use the 2.2 stable version you will need to modify the following lines of the /etc/postfixadmin/ file to setup the access to the previously created database:

$CONF['configured'] = true;
$CONF['database_type'] = 'mysql';
$CONF['database_host'] = 'localhost';
$CONF['database_user'] = 'postfixadmin';
$CONF['database_password'] = 'secretandcomplexpassword';
$CONF['database_name'] = 'postfixadmin';

If instead you use the 2.3 development version, having dbconfig-common and wwwconfig-common installed, the previous step of the database creation is managed by the package itself and it is no more needed. Also the database access configuration inside /etc/postfixadmin/ is automatically done by debconf, so all is needed is to give to debconf the password of the MySQL root user that you setup at the beginning, and then answer to the debconf questions about the password used for the Postfixadmin dedicated database user.

After this we can proceed to populate the database, this will be done by Postfixadmin itself using the following link in a browser (we can use the same link for database upgrade when installing a new Postfixadmin version, or to reset the Postfixadmin superuser password):


Up to 2.2 version this PHP script should be run once, and then removed after its use. With the 2.3 version when it is used for the first time it would ask for a setup password, and then print an hashed value that must be put inside /etc/postfixadmin/; the browser will show the line that should replace this one:

$CONF['setup_password'] = 'changeme';

With this modification done we can re-execute the script going back to http://MY.POSTFIXADMIN.SERVER.IP/postfixadmin/setup.php; this time can use the setup password to create an administrative Postfixadmin account having full access to all management functions. It should be noted that like all Postfixadmin accounts also this one should be given in the form of an email address (i.e. something like

To check that this initial setup has been completed successfully we can see if everything is working fine going to the http://MY.POSTFIXADMIN.SERVER.IP/postfixadmin address and logging in using the superuser account we just created. After this check we can proceed doing some more specific configuration; the first one is to put proper references to our main domain in the web interface; this can be done with the following commands:

cd /etc/postfixadmin/
sed -e 's/change-this-to-your.domain.tld/' >

and to be sure we can check the file to see if all link to web pages are correct (they will be always something like

An important step is to configure the mailbox pathname that will be used by both Postfix and Dovecot, we choose to map an email account like to a mailbox pathname like, to do this we have to put the following configuration values in the /etc/postfixadmin/ file:

$CONF['domain_path'] = 'YES';
$CONF['domain_in_mailbox'] = 'NO';

Then to enable quotas we will need to modify also the following line:

$CONF['quota'] = 'YES';

and to enable the vacation support we will need to modify the following lines:

$CONF['vacation'] = 'YES';
$CONF['vacation_domain'] = ''

where is the domain used by Postfix to manage vacation email (we'll look at this in the following).

Other configuration lines that can be modified are the following:

$CONF['default_language'] = 'it';
$CONF['min_password_length'] = 6;
$CONF['aliases'] = '50';
$CONF['mailboxes'] = '50';
$CONF['maxquota'] = '50';

respectively to setup the web interface language, a minimum length for the accounts password, and the default values for limit on number of alias, mailbox and megabytes for the quota. These last three will be proposed by the management interface when creating a new domain (a 0 means no limit).

The Postfixadmin 2.3 version has a new simplified management for having the same aliases on more than on domain; this new feature need more database queries and a modified Postfix configuration, so is better to disable it; this can be done with the following line:

$CONF['alias_domain'] = 'NO';

To check if everything is working fine we can login as administrator in the web interfaces to create a new domain and some user accounts. Then we can logout and check if that those account are working by re-logging as that users.

Postfix configuration

Having user account and domain data managed by Postfixadmin, we need to configure Postfix virtual mailbox according to the data stored in MySQL. The first step is to create a base directory where to put all the virtual mailboxes; we will also need a system user that will own all the files. We can do this with the following commands:

mkdir /var/mail/vmail
useradd -d /var/mail/vmail vmail
chown vmail:vmail /var/mail/vmail/
chmod o-xr /var/mail/vmail/

Then we need to setup Postfix to use virtual mailboxes getting the informations about users, domain and pathnames from the database; this can be done adding the following lines to /etc/postfix/

virtual_alias_maps = proxy:mysql:/etc/postfix/
virtual_mailbox_domains = proxy:mysql:/etc/postfix/
virtual_mailbox_maps = proxy:mysql:/etc/postfix/
virtual_mailbox_base = /var/mail/vmail
virtual_minimum_uid = 106
virtual_transport = virtual
virtual_uid_maps = static:106
virtual_gid_maps = static:61

where 106 e 61 are the numeric uid and gid for the vmail user (these number can be different in each system so you have to check them yourself with something like getent passwd|grep vmail).

After this we need to create all the mysql_* files to tell Postfix how to access to the database to get the information it needs. The first file,, configure the access to aliases definitions and it should be something like:

user = postfixadmin
password = secretandcomplexpassword
hosts = localhost
dbname = postfixadmin
query = SELECT goto FROM alias WHERE address='%s' AND active = 1

the second file,, configure the access to domain definitions, and it should be something like:

user = postfixadmin
password = secretandcomplexpassword
hosts = localhost
dbname = postfixadmin
query = SELECT domain FROM domain WHERE domain='%s' and backupmx = '0' and active = '1'

the third file,, configure the access to mailbox pathname (relative to the base directory /var/mail/vmail), and it should be something like:

user = postfixadmin
password = secretandcomplexpassword
hosts = localhost
dbname = postfixadmin
query = SELECT maildir FROM mailbox WHERE username='%s' AND active = 1

If we want to use Postfixadmin to manage secondary mail server for some domains we will need to add to /etc/postfix/ also the following line:

relay_domains = $mydestination, proxy:mysql:/etc/postfix/

where should be something like:

user = postfixadmin
password = secretandcomplexpassword
hosts = localhost
dbname = postfixadmin
query = SELECT domain FROM domain WHERE domain='%s' and backupmx = '1' and active = '1'

To check if everything is working fine you can send an email to an user you previously created with Postfixadmin and check the mail.log file to see if it is accepted.

Postfix/Postfixadmin vacation configuration

If we want to manage vacation trough Postfixadmin we need some additional Postfix configurations. As first step we need a system user dedicated to the automatic answer management, with the lowest possible privileges; we can create it with the following commands:

groupadd -g 65501 vacation
useradd -g 65501 -u 65501 -c Vacation -s /sbin/nologin -d /nonexistent vacation

then we will need a directory for temporary files accessible only for this user, we can create it with the following commands:

mkdir /var/spool/vacation
chown -R vacation.vacation /var/spool/vacation
chmod o-xr /var/spool/vacation

The second step is to setup the vacation script, we need to put a copy (it's distributed with Postfixadmin) in the previous directory; this can be done with the following commands:

cd /usr/share/doc/postfixadmin/examples/VIRTUAL_VACATION/
zcat > /var/spool/vacation/
chmod 700 /var/spool/vacation/

to have the script working correctly we will also need some perl modules; these can be installed with the command:

aptitude install libemail-valid-perl libmime-encwords-perl libmime-perl \
libmail-sender-perl liblog-log4perl-perl

and at last we will need to setup the script to access to the database, this can be done modifying the following lines at the beginning of it (note that we are using the same values used in the Postfixadmin configuration):

our $db_type = 'mysql';
our $db_host = 'localhost';
our $db_username = 'postfixadmin';
our $db_password = 'secretandcomplexpassword';
our $db_name = 'postfixadmin';

our $vacation_domain = '';

The last step is the Postfix configuration; we will need to setup a new transport dedicates to vacation, so we need to add to /etc/postfix/ the following lines:

vacation    unix  -       n       n       -       -       pipe
flags=Rq user=vacation argv=/var/spool/vacation/ -f ${sender} -- ${recipient}

then we will need to use this transport for all mail directed to the dedicated domain, so first we need to create the /etc/postfix/transport file with the following line:       vacation:

and then add to /etc/postfix/ the following line:

transport_maps = hash:/etc/postfix/transport

This done we can tell Postfix to use the new configuration with the following commands:

postmap /etc/postfix/transport
postfix reload

Dovecot configuration

To make emails available to the users we well need a POP/IMAP server, we choose to use Dovecot, so we will need to install it, we will do the Debian way with the following command (we will install ntp also, that is needed because Dovecot could have problem if time is moving backwards); :

aptitude install dovecot-imapd dovecot-pop3d ntp

then we will need to tell Dovecot where to find the emails and how to authenticate users.

The first step is to modify the default configuration to access to the /var/mail/vmail directory as the user vmail, having mailbox in the form username/; this can be done putting the following lines in /etc/dovecot/dovecot.conf:

mail_location = maildir:/var/mail/vmail/%d/%n
mail_privileged_group = vmail
first_valid_uid = 106

where 106 is the vmail uid (as before this could be different on different installations).

The second step is to enable the user authentication over the MySQL data, this can be done removing the default PAM configuration for the userdb and passdb directives, putting instead something like the following in /etc/dovecot/dovecot.conf:

  passdb sql {
args = /etc/dovecot/dovecot-mysql.conf
userdb sql {
args = /etc/dovecot/dovecot-mysql.conf

then we will need to create the file /etc/dovecot/dovecot-mysql.conf to tell Dovecot how to access to the database; it should be something like:

driver = mysql
connect = host=localhost dbname=postfixadmin user=postfixadmin password=secretandcomplexpassword client_flags=0
default_pass_scheme = MD5
user_query = SELECT maildir, 106 AS uid, 61 AS gid FROM mailbox WHERE username = '%u'
password_query = SELECT password FROM mailbox WHERE username = '%u' AND active = '1'

where 106 and 61 are respectively the uid and gid of the user vmail.

To check if everything is working fine you can connect to the server with an email client and look at the email you previously sent.

Authenticated SMTP

This will be provided by telling Postfix to use Dovecot as authentication provider. The first step is to setup Dovecot to provide an authentication socket for Postfix; this can be done by adding the following lines to /etc/dovecot/dovecot.conf:

socket listen {
client {
path = /var/spool/postfix/private/auth
mode = 0660
user = postfix
group = postfix

after restarting Dovecot this will create the socket in the Postfix chroot as private/auth, and it should look like this:

# ls /var/spool/postfix/private/auth -l
srw-rw---- 1 postfix postfix 0 29 set 18:59 /var/spool/postfix/private/auth

The second step is to configure Postfix to use this socket, this will be done adding the following lines to /etc/postfix/

smtpd_sasl_type = dovecot
smtpd_sasl_path = private/auth

The rest is just the ordinary Postfix configuration needed to accept SASL authenticated sessions, forcing them to be done using TLS for security, so you will need to enable SASL authentication under TLS adding the following lines to /etc/postfix/

smtpd_sasl_auth_enable = yes
smtp_sasl_application_name = smtpd
smtpd_sasl_local_domain = $myhostname
broken_sasl_auth_clients = yes

and force use of TLS:

smtpd_use_tls = yes
smtpd_tls_auth_only = yes
smtpd_tls_loglevel = 1
smtpd_tls_received_header = yes
smtpd_tls_session_cache_timeout = 3600s
tls_random_source = dev:/dev/urandom

and then give relay permission to authenticated users adding the line permit_sasl_authenticated to the smtpd_recipient_restrictions parameter, that should look like:

smtpd_recipient_restrictions =

CLI script for massive account creation

Postfixadmin is a very nice web interface to manage email accounts and domain, but like all GUI or web based interfaces using it is not so practical when you have to create hundreds of accounts in a single shot. For this reason we developed a simple Python script that will do mass account creation. You can find it in the attachment.

The script is quite easy to use, it just need a CSV file with the account list; it should work with any kind of CSV file, but it was tested just with the default output of OpenOffice?.org Calc. The first line of the file should contains the column names, the script will look only to columns named user, domain, password and name (case sensitive!); they will have the meaning explained in the following table:

user user part of the email (like user in user@…)
password cleartext password
domain domain name (like '')
name full user name ('Name Surname')

It's only needed to provide at least the user, domain and password columns, and the script will fill the database tables creating accounts and domains. The email accounts will be in the form user@domain, with password password for each line present in the CSV file. It will also create all domains present in the file and, if the -A option is given, also the default accounts (abuse, hostmaster, postmaster, webmaster) for each domain.

The script requires a single argument, the name of the CSV file, and the -p option followed by the database access password (i.e., following the previous instructions, "secretandcomplexpassword"). There are some more option to set database name, database user name, database host, etc. but the default values should be good because they are the same used by the default installation of Postfixadmin. The whole list of options can be printed executing the script without arguments or with the -h option.

The script doesn't do data validation, so it is published without any warranty (under the GPL licence). This means that making a database backup before using it is strongly suggested. It will print errors if some accounts or domains are already present in the database, skipping creation (i.e. it will not overwrite them), but it will create all other accounts and domains not already present. It will also skip the creation of a duplicated account.