Install Latest phpMyAdmin with LEMP on Ubuntu 20.04
You’ll get a fresh copy of phpMyAdmin that works out‑of‑the‑box with your Nginx‑PHP‑MariaDB stack, and you won’t be stuck with the ancient 4.x package from the Ubuntu repos.
Preparing the server
First make sure everything is up to date and that the LEMP components are already running. If you’re still on the default phpMyAdmin package, uninstall it – it’s tied to Apache and only pulls in old PHP extensions.
sudo apt update && sudo apt upgrade -y
sudo apt purge phpmyadmin -y # get rid of the repo version
Why? The distro version lags behind for months; pulling the latest tarball avoids compatibility headaches later on.
Install required PHP modules
phpMyAdmin needs a handful of extensions that aren’t always installed with php-fpm.
sudo apt install php-fpm php-mysql php-json php-gd php-mbstring php-zip -y
php-mysql lets phpMyAdmin talk to MariaDB, while php-mbstring and php-zip are required for import/export features. Skipping any of these will make the UI complain about missing extensions.
Grab the newest release
Head over to the official download page, copy the link for the latest tar.gz, and pull it with wget. Using the checksum guarantees you didn’t fetch a corrupted file.
cd /tmp
LATEST=$(curl -s https://www.phpmyadmin.net/downloads/ | grep -oP 'phpMyAdmin-\K[0-9.]+(?=\.tar\.gz)' | head -1)
wget "https://files.phpmyadmin.net/phpMyAdmin/${LATEST}/phpMyAdmin-${LATEST}-all-languages.tar.gz"
wget "https://files.phpmyadmin.net/phpMyAdmin/${LATEST}/phpMyAdmin-${LATEST}-all-languages.tar.gz.sha256"
# Verify
sha256sum -c phpMyAdmin-${LATEST}-all-languages.tar.gz.sha256
If the checksum fails, delete the file and try again – better safe than debugging a broken UI later.
Deploy into Nginx’s web root
I like to keep third‑party apps under /var/www. Extract the archive there and give www-data ownership.
sudo mkdir -p /var/www/phpmyadmin
sudo tar xf phpMyAdmin-${LATEST}-all-languages.tar.gz -C /var/www/phpmyadmin --strip-components=1
sudo chown -R www-data:www-data /var/www/phpmyadmin
Why the --strip-components? It removes the top‑level folder that the archive creates, so you end up with a clean /var/www/phpmyadmin directory.
Create an Nginx site block
Because phpMyAdmin isn’t a full‑blown app, a simple location block inside your existing server config works fine.
# /etc/nginx/sites-available/your-site.conf
server {
listen 80;
server_name example.com;
root /var/www/html; # whatever you use for the main site
index index.php index.html index.htm;
location /phpmyadmin/ {
alias /var/www/phpmyadmin/;
try_files $uri $uri/ =404;
fastcgi_pass unix:/run/php/php8.0-fpm.sock;
fastcgi_index index.php;
include fastcgi_params;
fastcgi_param SCRIPT_FILENAME $request_filename;
}
# other locations …
}
The alias directive points Nginx to the phpMyAdmin folder without moving it into your document root. Restart Nginx afterwards:
sudo nginx -t && sudo systemctl reload nginx
If you forget fastcgi_param SCRIPT_FILENAME, PHP will throw a “File not found” error when you try to log in.
Secure the installation
Leaving phpMyAdmin open to the world is inviting brute‑force attempts. A quick HTTP basic auth does the trick and costs almost nothing.
sudo apt install apache2-utils -y # provides htpasswd
sudo htpasswd -c /etc/nginx/.phpmyadmin.pass admin
Add this snippet inside the location /phpmyadmin/ block:
auth_basic "Restricted";
auth_basic_user_file /etc/nginx/.phpmyadmin.pass;
Now you’ll be prompted for credentials before even seeing the login screen.
Finish setup in the browser
Visit http://example.com/phpmyadmin/. The first time you load it, phpMyAdmin will ask you to create a temporary blowfish secret file. Create /var/www/phpmyadmin/config.inc.php (or use the wizard) and add:
<?php
$cfg['blowfish_secret'] = 'aRandom32CharStringHere';
Replace the placeholder with something truly random – it protects your cookies.
That’s it. You now have the newest phpMyAdmin running on a clean LEMP stack, without any leftover Apache junk or outdated distro packages.
Happy querying, and don’t forget to back up your config.inc.php before you start fiddling with users!