Easy Digital Downloads on Ubuntu 24.04 on Azure User Guide
Overview
Easy Digital Downloads is an open source ecommerce platform for selling digital products: ebooks, software, plugins, themes, music, photography, design assets and documents. It provides a complete shopping cart and checkout, secure file delivery with access control, discount codes, customer records and purchase histories, and detailed sales and earnings reporting. Because it runs on WordPress, the storefront is an ordinary WordPress site, so you keep the familiar admin, the theme ecosystem and the REST API alongside the commerce features.
This cloudimg image installs WordPress 7.0.2 and Easy Digital Downloads 3.6.9 on a LAMP stack drawn entirely from Ubuntu 24.04 noble universe, with no third party APT repositories. Easy Digital Downloads is already activated, so the Checkout, Receipt, Order History, Confirmation and Products pages exist the moment the instance boots.
What is included:
- Easy Digital Downloads 3.6.9, activated, at
/var/www/html/wordpress/wp-content/plugins/easy-digital-downloads - WordPress 7.0.2 from the official wordpress.org release at
/var/www/html/wordpress - Apache 2.4.58 with mod_rewrite enabled, virtual host at
/etc/apache2/sites-available/easy-digital-downloads.conf - MySQL 8.0.46 with an
edddatabase and anedduseraccount, both given a unique password on first boot - PHP 8.3.6 with the curl, gd, mbstring, xml, zip, imagick, intl, bcmath and mysqli extensions
- WP CLI 2.12.0 at
/usr/local/bin/wp easy-digital-downloads-firstboot.service, which generates every credential uniquely per instance- Apache and MySQL enabled and starting automatically on boot
- 24/7 cloudimg support
Key facts:
| Item | Value |
|---|---|
| Platform | Ubuntu 24.04 LTS, Azure Gen2 |
| Default SSH user | azureuser |
| Store administrator | cloudimg |
| Web root | /var/www/html/wordpress |
| Credentials file | /stage/scripts/easy-digital-downloads-credentials.log (mode 0600, root only) |
| HTTP port | 80 |
Prerequisites
Before deploying you need:
- An active Azure subscription
- An active Azure Marketplace subscription for this offer
- An SSH key pair for the
azureuseraccount - A virtual network and subnet in your target region
- A network security group allowing inbound TCP 22 and TCP 80
Recommended VM size: Standard_B2s (2 vCPU, 4 GB RAM) is sufficient for a small to medium catalogue. Move to a D2s_v3 or larger for high traffic stores or large download libraries.
Step 1: Deploy the Virtual Machine
Option A: Azure Portal
- Go to Create a resource and search the Marketplace for this cloudimg offer
- Select the plan and choose Create
- Pick your subscription, resource group and region
- Set the VM size to Standard_B2s
- Set the authentication type to SSH public key and the username to azureuser
- On the Networking tab, allow inbound SSH (22) and HTTP (80)
- Select Review + create, then Create
Option B: Azure CLI
az vm create \
--resource-group my-resource-group \
--name my-edd-vm \
--image cloudimg:easy-digital-downloads-ubuntu-24-04:default:latest \
--size Standard_B2s \
--admin-username azureuser \
--generate-ssh-keys \
--public-ip-sku Standard \
--location eastus
Step 2: Connect via SSH
From your own workstation, look up the public IP address of the instance and connect to it:
az vm show --resource-group my-resource-group --name my-edd-vm \
--show-details --query publicIps --output tsv
ssh azureuser@<vm-ip>
Step 3: Verify the Stack
Confirm both services are running and listening:
sudo systemctl is-active apache2 mysql
sudo ss -tln | grep -E ':80 |:3306 '
Check the versions of each component:
apache2 -v | head -1
php -v | head -1
mysql --version

Confirm WordPress and Easy Digital Downloads are installed and the plugin is active:
sudo -u www-data wp core version --path=/var/www/html/wordpress
sudo -u www-data wp plugin list --path=/var/www/html/wordpress --fields=name,status,version

Step 4: Retrieve Your Store Credentials
Every credential on this instance is generated on first boot and written to a file readable only by root. Nothing is shared between instances and nothing is baked into the image.
sudo cat /stage/scripts/easy-digital-downloads-credentials.log
The file contains:
| Key | Meaning |
|---|---|
EDD_URL |
The public storefront address |
EDD_ADMIN_URL |
The WordPress admin sign in address |
EDD_DOWNLOADS_URL |
Direct link to your digital products list |
WP_ADMIN_USER |
The store administrator username (cloudimg) |
WP_ADMIN_PASSWORD |
The store administrator password, unique to this instance |
WP_DB_NAME, WP_DB_USER, WP_DB_PASSWORD |
The WordPress database and its account |
MYSQL_ROOT_PASSWORD |
The MySQL root password, unique to this instance |
Confirm the first boot service completed and the file is protected:
sudo systemctl is-active easy-digital-downloads-firstboot.service
sudo ls -l /stage/scripts/easy-digital-downloads-credentials.log
sudo ls -l /var/lib/cloudimg/easy-digital-downloads-firstboot.done

Step 5: Sign In to Your Store
Browse to http://<vm-ip>/wp-admin/ and sign in as cloudimg with the WP_ADMIN_PASSWORD from Step 4.

After signing in you land on the WordPress dashboard, with the Downloads and Store Reports entries added by Easy Digital Downloads in the left menu.

The site address is resolved automatically on first boot, and the image derives its address from the host you browse it on. That means the storefront works on the public IP straight away, and it keeps working unchanged if you later point a domain name at the instance.
Step 6: Review Your Digital Products
Choose Downloads in the left menu. This is your product catalogue. A newly deployed store is empty, and every product you add appears here with its price, categories, net sales and net revenue.

Easy Digital Downloads creates its store pages when it activates, which happens on first boot. Confirm they exist:
sudo -u www-data wp post list --post_type=page --path=/var/www/html/wordpress --fields=post_title,post_name --format=table

Step 7: Create Your First Digital Product
In the admin, choose Downloads then Add Download. Give the product a name, set a price in the Download Prices panel, and attach the file the customer receives in the Download Files panel. Publish it when you are ready to sell.
You can also create a product from the command line, which is useful for bulk imports and automation:
sudo -u www-data wp post create --post_type=download \
--post_title='Starter Icon Pack' --post_status=publish \
--path=/var/www/html/wordpress
sudo -u www-data wp post list --post_type=download --path=/var/www/html/wordpress --fields=ID,post_title,post_status
Files attached to a product are delivered through Easy Digital Downloads rather than served directly, so a customer cannot share a working download URL with someone who has not paid.
Step 8: Configure Payments and Store Settings
Choose Downloads then Settings to set your store country, currency, and the payment gateways you want to accept. Easy Digital Downloads supports Stripe and PayPal in the core plugin, and test mode is available so you can place an order end to end before you take real money.

Choose Downloads then Reports to track sales, earnings, average order value, refunds, taxes and file downloads over any date range.

Step 9: View the Public Storefront
Browse to http://<vm-ip>/ to see the storefront your customers will use.

Confirm both the storefront and the sign in page answer:
curl -sf -o /dev/null -w 'storefront: HTTP %{http_code}\n' http://127.0.0.1/
curl -sf -o /dev/null -w 'sign in: HTTP %{http_code}\n' http://127.0.0.1/wp-login.php
Server Components
| Component | Version | Path |
|---|---|---|
| Easy Digital Downloads | 3.6.9 | /var/www/html/wordpress/wp-content/plugins/easy-digital-downloads |
| WordPress | 7.0.2 | /var/www/html/wordpress |
| Apache HTTP Server | 2.4.58 | /etc/apache2 |
| MySQL | 8.0.46 | /var/lib/mysql |
| PHP | 8.3.6 | /etc/php/8.3 |
| WP CLI | 2.12.0 | /usr/local/bin/wp |
Filesystem Layout
| Mount point | Size | Purpose |
|---|---|---|
/ |
29 GB | Root filesystem, including the web root and the MySQL data directory |
/boot |
881 MB | Operating system kernel files |
/boot/efi |
105 MB | UEFI boot partition (Gen2 Hyper V) |
/mnt |
7.8 GB | Azure temporary resource disk, cleared on deallocation |
Key directories:
| Path | Purpose |
|---|---|
/var/www/html/wordpress |
WordPress and Easy Digital Downloads |
/var/www/html/wordpress/wp-content/uploads |
Media library and product files |
/var/www/html/wordpress/wp-config.php |
Database credentials and site configuration |
/etc/apache2/sites-available/easy-digital-downloads.conf |
Apache virtual host |
/var/log/apache2/edd-access.log, edd-error.log |
Apache logs for the store |
/var/lib/mysql |
MySQL data directory |
Scripts and Log Files
| Path | Purpose |
|---|---|
/usr/local/sbin/easy-digital-downloads-firstboot.sh |
Generates every per instance credential on first boot |
/etc/systemd/system/easy-digital-downloads-firstboot.service |
The systemd unit that runs it once |
/stage/scripts/easy-digital-downloads-credentials.log |
The generated credentials, mode 0600 root only |
/var/lib/cloudimg/easy-digital-downloads-firstboot.done |
Sentinel proving first boot completed |
/var/log/easy-digital-downloads-firstboot.log |
First boot log |
On Startup
The first time the instance boots, easy-digital-downloads-firstboot.service runs once and does the following:
- Generates a MySQL root password, a WordPress database password and a store administrator password, each unique to this instance
- Creates the
edddatabase and theedduseraccount - Writes
wp-config.phpwith those credentials - Installs WordPress and creates the
cloudimgadministrator - Activates Easy Digital Downloads, which creates the store pages
- Writes the credentials file with mode 0600 owned by root
- Writes its sentinel file so it never runs again
Because the image ships with no database and no configuration file, there is no default password to change and no shared credential between customers.
Managing the Services
sudo systemctl status apache2 --no-pager
sudo systemctl restart apache2
sudo systemctl restart mysql
To follow the store's web logs:
sudo tail -n 20 /var/log/apache2/edd-error.log
Backups
Back up both the database and the uploaded product files. The database holds your products, orders and customers; the uploads directory holds the files your customers download.
sudo mysqldump -uroot -p"$(sudo grep '^MYSQL_ROOT_PASSWORD=' /stage/scripts/easy-digital-downloads-credentials.log | cut -d= -f2-)" edd > /var/backups/edd-$(date +%F).sql
sudo tar czf /var/backups/edd-uploads-$(date +%F).tar.gz -C /var/www/html/wordpress/wp-content uploads
Troubleshooting
The storefront does not load. Check Apache is running and listening, then read the error log:
sudo systemctl is-active apache2
sudo tail -n 20 /var/log/apache2/edd-error.log
You cannot sign in. Re read the password from the credentials file, which is authoritative for this instance. If the password has been changed and lost, reset it with WP CLI:
sudo -u www-data wp user update cloudimg --user_pass='<new-password>' --path=/var/www/html/wordpress
The credentials file only contains a placeholder comment. First boot has not finished yet. Wait a few moments and check the service:
sudo systemctl status easy-digital-downloads-firstboot.service --no-pager
sudo tail -n 20 /var/log/easy-digital-downloads-firstboot.log
Product pages return 404. Flush the permalink rules:
sudo -u www-data wp rewrite flush --hard --path=/var/www/html/wordpress
Database connection errors. Confirm MySQL is running and that WordPress can reach it:
sudo systemctl is-active mysql
sudo -u www-data wp db check --path=/var/www/html/wordpress
Security Recommendations
- Enable HTTPS before you take payments. Point a domain at the instance, then install a certificate. The site address follows the host you browse it on, so no reconfiguration is needed after the certificate is issued:
bash sudo apt-get install -y certbot python3-certbot-apache sudo certbot --apache -d <your-domain> - Restrict the network security group so port 22 is reachable only from your management network. Port 80 and 443 stay open to your customers.
- Keep WordPress, Easy Digital Downloads and your theme updated from the admin, or with
wp core update,wp plugin update --allandwp theme update --all. - Apply operating system updates regularly, for example
sudo apt-get update && sudo apt-get upgrade. - Store the credentials file contents in your own secret manager, then keep the file readable only by root.
- Turn on two factor authentication for administrator accounts with a WordPress plugin before the store goes live.
Licensing
Easy Digital Downloads is licensed under the GNU General Public License version 2 or later, and WordPress is licensed under the GNU General Public License version 2 or later. Both are free to use commercially. cloudimg provides the packaged image and commercial support separately from the upstream projects.
Support
For assistance, contact cloudimg support:
- Email: support@cloudimg.co.uk
- Response time: 24/7 with a guaranteed 24 hour response SLA
- Website: https://www.cloudimg.co.uk