Set up PostfixAdmin on Ubuntu 26.04

When you host mail for virtual users, you need a reliable way to manage domains, mailboxes, and aliases without editing database rows by hand. Postfix Admin is a web-based interface for managing a Postfix-based mail server.
This is the first post in the Setting up and configuring a mail server series. It covers the required DNS records and shows how to install and configure Postfix Admin, Nginx with a free Let’s Encrypt certificate, PHP, and MySQL.
This tutorial was written for Ubuntu 26.04, however the same steps with small modifications should work on any newer version of Ubuntu .
Prerequisites
As the prerequisites to follow this series, you will need:
- An Ubuntu 26.04 server. The server hostname
must be a FQDN. In this series we will use
mail.linuxize.com. - A user with sudo privileges .
DNS settings
You need to set up the following DNS records for your mail system to work:
- A record, to point your system’s FQDN (hostname) to your mail server IPv4 address.
mail.linuxize.com. 3600 IN A 23.45.67.89- MX record, to specify which mail server is responsible for accepting email messages on behalf of a recipient’s domain. In our case we want all emails sent to
@linuxize.comemail addresses to be accepted by themail.linuxize.commail server.
linuxize.com. 3600 IN MX 0 mail.linuxize.com.- SPF record, which is used to verify which mail servers are approved to send email on behalf of a given domain. In the example below we are approving the domain mail servers (mx) and if the SPF check fails, the result will be a soft failure (~all):
linuxize.com. 3600 IN TXT "v=spf1 mx ~all"Reverse DNS (PTR)
Reverse DNS (PTR) is an IP address to domain name mapping, the exact opposite of DNS which maps domain names to IP addresses.
Most email servers will perform a reverse DNS lookup on the IP address that is attempting to connect to them and may not accept emails from the server if the PTR record is not set.
In most cases, PTR entries can be set through your hosting provider web interface. If you do not see that option, contact the support team and ask them to set up the correct PTR record for you.
You can use the dig command to find out the reverse DNS of a given IP address.
dig -x 23.45.67.8923.45.67.89.in-addr.arpa domain name pointer mail.linuxize.com.Create a system user
Since we are configuring a mail server with virtual users we need one system user which will be the owner of all mailboxes and will be used by the virtual users to access their email messages on the server.
The following commands will create a new group
and user named vmail, set the user’s home directory to /var/mail/vmail, and grant the web server read access so PostfixAdmin can create per-mailbox subfolders during user creation:
sudo groupadd -g 5000 vmail
sudo useradd -u 5000 -g vmail -s /usr/sbin/nologin -d /var/mail/vmail -m vmail
sudo chmod 770 /var/mail/vmail
sudo setfacl -m u:www-data:rgo /var/mail/vmailAll virtual mailboxes will be stored in the /var/mail/vmail directory.
Install Nginx PHP and MySQL
Postfix Admin is a PHP based application. To be able to access the PostfixAdmin web interface we need to install a web server and PHP.
Run the following command to install Nginx, MySQL, PHP and all required PHP modules:
sudo apt update
sudo apt install -y nginx mysql-server php-fpm php-cli php-mysql php-mbstring php-xml php-curl php-zip php-intl php-gd php-bcmath php-readline php-sqlite3 acl gitAfter the installation finishes, confirm the PHP-FPM service and socket so the Nginx server block points at the right path:
php -v
systemctl list-units 'php*-fpm.service'
ls -l /run/php/On Ubuntu 26.04 the symlink /run/php/php-fpm.sock points at the active versioned socket, for example /run/php/php8.5-fpm.sock. Use the symlink in Nginx so the configuration stays valid across PHP minor upgrades.
PostfixAdmin 4.x manages its PHP libraries with Composer, so install Composer next:
sudo apt install -y composerIf composer is missing on a minimal Ubuntu image, enable the Universe repository and try again:
sudo apt install -y software-properties-common
sudo add-apt-repository -y universe
sudo apt update
sudo apt install -y composerDownload and Configure Postfix Admin
At the time of writing, 4.0.1 is the latest stable version of Postfix Admin.
Download the Postfix Admin release tarball from GitHub using the following wget command :
cd /tmp
wget https://github.com/postfixadmin/postfixadmin/archive/refs/tags/v4.0.1.tar.gz -O postfixadmin-4.0.1.tar.gzOnce the download is completed extract the archive
and move
the Postfix Admin source files to the /var/www directory:
tar xzf postfixadmin-4.0.1.tar.gz
sudo mv postfixadmin-4.0.1 /var/www/postfixadmin
cd /var/www/postfixadminThe repository ships with an install.sh helper that runs Composer and creates the templates_c directory used by the Smarty cache. Run the helper as your regular sudo user so Composer does not run as root, then hand ownership to www-data and tighten permissions:
sudo chown -R "$(id -un):$(id -gn)" /var/www/postfixadmin
/bin/bash install.sh
sudo chown -R www-data:www-data /var/www/postfixadmin
sudo find /var/www/postfixadmin -type d -exec chmod 755 {} \;
sudo find /var/www/postfixadmin -type f -exec chmod 644 {} \;
sudo chmod 750 /var/www/postfixadmin/templates_cIf Composer reports ext-sqlite3 missing, install php-sqlite3 and rerun install.sh. PostfixAdmin still resolves dev platform requirements when no composer.lock is present, even with --no-dev.
Postfix Admin will use a MySQL database to store information about users, domains, and the application configuration.
Log in to the MySQL shell :
sudo mysqlCreate a new MySQL user and database using the following commands:
CREATE DATABASE postfixadmin CHARACTER SET utf8mb4;
CREATE USER 'postfixadmin'@'localhost' IDENTIFIED BY 'postfixadmin_db_password';
GRANT ALL PRIVILEGES ON postfixadmin.* TO 'postfixadmin'@'localhost';
FLUSH PRIVILEGES;
EXIT;postfixadmin_db_password with a long random password. Do not reuse example passwords, and do not commit real passwords or generated setup hashes to version control.Instead of editing the default Postfix Admin configuration we will copy it to a new file named config.local.php which will overwrite the default application settings:
sudo cp /var/www/postfixadmin/config.inc.php /var/www/postfixadmin/config.local.phpPostfixAdmin 4.x protects the setup page with a password hash. Generate a hash from a temporary plain text password and copy the output:
php -r 'echo password_hash("replace-with-setup-password", PASSWORD_DEFAULT), PHP_EOL;'Open the file with your text editor:
sudo nano /var/www/postfixadmin/config.local.phpSet or verify the following values, pasting the generated hash into setup_password:
<?php
$CONF['configured'] = true;
$CONF['database_type'] = 'mysqli';
$CONF['database_host'] = 'localhost';
$CONF['database_user'] = 'postfixadmin';
$CONF['database_password'] = 'postfixadmin_db_password';
$CONF['database_name'] = 'postfixadmin';
$CONF['setup_password'] = 'paste-generated-hash-here';
$CONF['admin_email'] = 'Support <admin@linuxize.com>';
$CONF['default_aliases'] = array(
'abuse' => 'admin@linuxize.com',
'hostmaster' => 'admin@linuxize.com',
'postmaster' => 'admin@linuxize.com',
'webmaster' => 'admin@linuxize.com'
);
$CONF['encrypt'] = 'ARGON2I';
$CONF['dovecotpw'] = "/usr/bin/doveadm pw";
$CONF['domain_path'] = 'YES';
$CONF['domain_in_mailbox'] = 'NO';
?>
Save and close the file.
The ARGON2I setting stores Dovecot-compatible password hashes natively, so PostfixAdmin does not need to call doveadm from the web app to hash passwords. The default aliases are created automatically when a new domain is added, so the target admin mailbox should exist before you add domains.
Configure Nginx for Postfix Admin
Create a server block dedicated to PostfixAdmin and point its document root at the public/ directory inside the unpacked tree:
sudo nano /etc/nginx/sites-available/mail.linuxize.comPaste the following configuration:
server {
listen 80;
server_name mail.linuxize.com;
root /var/www/postfixadmin/public;
index index.php index.html;
location / {
try_files $uri $uri/ /index.php;
}
location ~ \.php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/php-fpm.sock;
}
location ~ /\. {
deny all;
}
}If /run/php/php-fpm.sock does not exist on your system, replace it with the versioned path you saw earlier, for example /run/php/php8.5-fpm.sock.
Enable the site, test the configuration, and reload the Nginx service for the changes to take effect:
sudo ln -s /etc/nginx/sites-available/mail.linuxize.com /etc/nginx/sites-enabled/
sudo nginx -t
sudo systemctl reload nginxInstall free Let’s Encrypt SSL Certificate
We are going to use the SSL certificate to access our Postfix Admin installation and to enable Dovecot and Postfix SSL/TLS encryption later in the series.
We have a tutorial about how to install a Let’s Encrypt SSL certificate
on Nginx. The most important point here is to generate an SSL certificate for your server hostname (FQDN), in our case mail.linuxize.com:
sudo certbot --nginx -d mail.linuxize.comAfter issuance, verify that the redirect to HTTPS works and that the certificate is valid:
sudo nginx -t
curl -I https://mail.linuxize.com/
sudo certbot certificatesRun the PostfixAdmin Setup
Open the setup page in your browser:
https://mail.linuxize.com/setup.phpThe page shows a setup summary, a hosting environment check, and a database update check. Once both checks pass, log in with the plain text setup password you used to generate the hash earlier in this tutorial. PostfixAdmin will then create or update the database schema for you.
Use the same page to create your first super-admin account. The mailbox you choose here is the account you will use to log in to PostfixAdmin and manage domains, users, and aliases.
If you prefer the command line, run the postfixadmin-cli tool as www-data:
cd /var/www/postfixadmin
sudo -u www-data php scripts/postfixadmin-cli admin add admin@linuxize.com --superadmin 1 --active 1 --password 'replace-with-long-password' --password2 'replace-with-long-password'The output should look something like this:
Welcome to Postfixadmin-CLI v0.2
---------------------------------------------------------------
The admin admin@linuxize.com has been added!
---------------------------------------------------------------At this point you can log in to your Postfix Admin installation at https://mail.linuxize.com/, using the super-admin account you just created. From there, add your first virtual domain and create the mailboxes that the rest of the series will deliver mail to.

Troubleshooting
Composer reports a missing ext-sqlite3 extension
Install php-sqlite3 and rerun the helper:
sudo apt install -y php-sqlite3
cd /var/www/postfixadmin
/bin/bash install.shNginx returns 502 Bad Gateway
The fastcgi_pass socket does not match the running PHP-FPM service. Check the active socket and update the server block:
ls -l /run/php/
systemctl list-units 'php*-fpm.service'The setup page reports a database connection error
Confirm that the MySQL user, password, and database name in config.local.php match the values you created earlier, and that the user has privileges on the postfixadmin database.
Conclusion
You have installed and configured Postfix Admin on Ubuntu 26.04. In the next part of this series we will continue with the Postfix and Dovecot installation and configuration.
Linuxize Weekly Newsletter
A quick weekly roundup of new tutorials, news, and tips.
About the authors

Dejan Panovski
Dejan Panovski is the founder of Linuxize, an RHCSA-certified Linux system administrator and DevOps engineer based in Skopje, Macedonia. Author of 800+ Linux tutorials with 20+ years of experience turning complex Linux tasks into clear, reliable guides.
View author page