WP-CLI is the official command line interface for WordPress. It lets you download WordPress, create wp-config.php, run the installer and manage plugins, themes, users and the database without opening the web dashboard, which makes installations repeatable and easy to script. In this tutorial you will install WP-CLI on Ubuntu 24.04, use it to set up a new WordPress site served by Nginx and PHP-FPM with HTTPS, and learn the commands you will use to maintain it.
Prerequisites
To follow this tutorial you need:
- A server running Ubuntu 24.04 LTS, for example a CubePath VPS, with at least 1 GB of RAM.
- A non-root user with
sudoprivileges. - A LEMP stack: Nginx, MySQL 8.0 and PHP-FPM 8.3 installed and running.
- A domain name,
your_domainin this tutorial, with an A record pointing to the server, and ports 80 and 443 open in the firewall.
Step 1 - Installing the PHP extensions WordPress needs
WordPress core only needs the MySQL extension, but themes, plugins and the media library rely on several others. Install them for PHP 8.3:
sudo apt update
sudo apt install php8.3-mysql php8.3-curl php8.3-gd php8.3-mbstring php8.3-xml php8.3-zip php8.3-intl
Reload PHP-FPM so it loads the new extensions:
sudo systemctl reload php8.3-fpm
Confirm that they are active:
php -m | grep -E '^(curl|gd|intl|mbstring|mysqli|xml|zip)$'
curl
gd
intl
mbstring
mysqli
xml
zip
Step 2 - Installing WP-CLI
WP-CLI is distributed as a single PHAR file. Download the latest stable build from the official repository:
cd /tmp
curl -O https://raw.githubusercontent.com/wp-cli/builds/gh-pages/phar/wp-cli.phar
Check that the file runs before installing it:
php wp-cli.phar --info
OS: Linux 6.8.0-... x86_64
Shell: /bin/bash
PHP binary: /usr/bin/php8.3
PHP version: 8.3.6
...
WP-CLI version: 2.x.x
Make it executable and move it into your PATH as wp:
chmod +x wp-cli.phar
sudo mv wp-cli.phar /usr/local/bin/wp
Verify the installation:
wp --version
WP-CLI 2.x.x
WP-CLI can update itself later with sudo wp cli update.
Step 3 - Creating the database and user
WordPress needs its own database and a MySQL user that can only access that database. Open the MySQL console:
sudo mysql
Run the following statements. Replace your_strong_password with a strong, unique password and keep it at hand for the next step:
CREATE DATABASE wordpress DEFAULT CHARACTER SET utf8mb4 COLLATE utf8mb4_unicode_ci;
CREATE USER 'wordpress_user'@'localhost' IDENTIFIED BY 'your_strong_password';
GRANT ALL PRIVILEGES ON wordpress.* TO 'wordpress_user'@'localhost';
EXIT;
Check that the new user can log in and see the database:
mysql -u wordpress_user -p -e "SHOW DATABASES;"
+--------------------+
| Database |
+--------------------+
| information_schema |
| performance_schema |
| wordpress |
+--------------------+
Step 4 - Downloading WordPress and creating wp-config.php
The web server runs PHP as www-data, and WordPress needs to write to its own files to install plugins, themes and updates. Run WP-CLI as www-data too, so every file it creates has the right owner from the start. Never run WP-CLI as root on a live site: it warns against it because plugin code would run with root privileges.
Create the site directory and a WP-CLI cache directory in www-data's home (/var/www), both owned by www-data:
sudo mkdir -p /var/www/your_domain /var/www/.wp-cli
sudo chown www-data:www-data /var/www/your_domain /var/www/.wp-cli
Change into the site directory. All the wp commands in the rest of this tutorial run from here:
cd /var/www/your_domain
Download the latest WordPress release. Use --locale if you want another language, for example --locale=es_ES:
sudo -u www-data wp core download
Downloading WordPress 6.x.x (en_US)...
md5 hash verified: ...
Success: WordPress downloaded.
Create wp-config.php. The --prompt=dbpass option asks for the database password interactively, so it doesn't end up in your shell history:
sudo -u www-data wp config create --dbname=wordpress --dbuser=wordpress_user --dbhost=localhost --prompt=dbpass
1/10 [--dbpass=<dbpass>]:
Success: Generated 'wp-config.php' file.
WP-CLI tests the database connection before writing the file and generates unique authentication keys and salts, so a success message also confirms that the credentials work.
Disable the built-in theme and plugin file editor, which is a common target after an admin account is compromised, and restrict access to the configuration file:
sudo -u www-data wp config set DISALLOW_FILE_EDIT true --raw
sudo chmod 640 wp-config.php
Step 5 - Configuring Nginx for WordPress
Create a server block for the site:
sudo nano /etc/nginx/sites-available/your_domain
Add the following configuration:
server {
listen 80;
listen [::]:80;
server_name your_domain www.your_domain;
root /var/www/your_domain;
index index.php;
client_max_body_size 64M;
location / {
try_files $uri $uri/ /index.php?$args;
}
location ~ /\.(?!well-known) {
deny all;
}
location ~* /uploads/.*\.php$ {
deny all;
}
location ~ \.php$ {
include snippets/fastcgi-php.conf;
fastcgi_pass unix:/run/php/php8.3-fpm.sock;
}
}
The try_files line sends every request that is not a real file to index.php, which WordPress needs for permalinks. The two deny blocks block hidden files (except .well-known, which Let's Encrypt uses) and stop PHP files uploaded to the media folder from being executed. Nginx checks regular expression locations in order, so they must come before the generic \.php$ block. client_max_body_size allows media uploads up to 64 MB; raise upload_max_filesize and post_max_size in /etc/php/8.3/fpm/php.ini to the same value if you need that much.
Enable the site, test the configuration and reload Nginx:
sudo ln -s /etc/nginx/sites-available/your_domain /etc/nginx/sites-enabled/
sudo nginx -t
sudo systemctl reload nginx
Now obtain a Let's Encrypt certificate so the site is installed directly with an HTTPS URL:
sudo apt install certbot python3-certbot-nginx
sudo certbot --nginx -d your_domain -d www.your_domain
Certbot adds the certificate to the server block and redirects HTTP to HTTPS. Check that the redirect works:
curl -sI http://your_domain | grep -i '^location'
Location: https://your_domain/
Step 6 - Running the WordPress installer
The last step creates the database tables, the site title and the first administrator. Replace your_admin, admin@your_domain and the title with your own values. Avoid admin as the user name, since it is the first one attackers try:
sudo -u www-data wp core install --url=https://your_domain --title="Your Site Title" --admin_user=your_admin --admin_email=admin@your_domain
Admin password: ...
Success: WordPress installed successfully.
Because no --admin_password was given, WP-CLI generated a strong random password and printed it once. Save it in your password manager now.
Verify the installation:
sudo -u www-data wp core version
sudo -u www-data wp core verify-checksums
sudo -u www-data wp option get siteurl
6.x.x
Success: WordPress installation verifies against checksums.
https://your_domain
verify-checksums compares every core file with the official release, which is also a useful check after a suspected compromise. Open https://your_domain/wp-admin in your browser and log in with the administrator account.
Step 7 - Managing the site with WP-CLI
These are the commands you will use most often. Run them from /var/www/your_domain as www-data.
Set a clean permalink structure:
sudo -u www-data wp rewrite structure '/%postname%/'
Install and activate a plugin, then list all plugins with their update status:
sudo -u www-data wp plugin install wordfence --activate
sudo -u www-data wp plugin list
+-----------+----------+-----------+---------+
| name | status | update | version |
+-----------+----------+-----------+---------+
| akismet | inactive | none | 5.x |
| hello | inactive | none | 1.7.2 |
| wordfence | active | none | 8.x.x |
+-----------+----------+-----------+---------+
Remove the sample plugins you don't use:
sudo -u www-data wp plugin delete hello akismet
Update WordPress core, the database schema, plugins and themes:
sudo -u www-data wp core update
sudo -u www-data wp core update-db
sudo -u www-data wp plugin update --all
sudo -u www-data wp theme update --all
Export the database before any major change. Store the dump outside the web root so it can never be downloaded:
sudo mkdir -p /var/backups/wordpress
sudo chown www-data:www-data /var/backups/wordpress
sudo -u www-data wp db export /var/backups/wordpress/wordpress-$(date +%F).sql
Success: Exported to '/var/backups/wordpress/wordpress-2026-09-25.sql'.
When you move the site to a new domain, search-replace updates every URL in the database, including serialized data. Run it with --dry-run first to see how many changes it would make:
sudo -u www-data wp search-replace 'https://old_domain' 'https://your_domain' --dry-run
Reset a lost administrator password:
sudo -u www-data wp user update your_admin --prompt=user_pass
Troubleshooting
Error: Error establishing a database connection.The credentials inwp-config.phpdon't match the MySQL user, or MySQL is not running. Check withmysql -u wordpress_user -pandsudo systemctl status mysql.Warning: Failed to create directory '/var/www/.wp-cli/cache/'. The cache directory doesn't exist or isn't owned bywww-data. Create it as shown in Step 4.Error: YIKES! It looks like you're running this as root.Run WP-CLI withsudo -u www-datainstead of plainsudo.- WordPress asks for FTP credentials when installing plugins from the dashboard. The files are not owned by
www-data. Fix ownership withsudo chown -R www-data:www-data /var/www/your_domain. - Permalinks return 404. The
try_filesline is missing from the Nginxlocation /block, or Nginx was not reloaded.
Conclusion
You installed WP-CLI on Ubuntu 24.04 and used it to download, configure and install WordPress behind Nginx with HTTPS, then used it to manage plugins, updates and database exports. From here you can schedule wp db export from a cron job for daily backups, add a page cache such as Redis object caching, or script the whole installation to deploy new WordPress sites in minutes.
