Apache HTTP Server es uno de los servidores web más usados del mundo: es estable, modular y admite configuración por directorio con archivos .htaccess, algo que muchas aplicaciones PHP siguen esperando. En este tutorial instalarás Apache en Ubuntu 24.04, abrirás el firewall, publicarás un sitio con su propio virtual host, activarás los módulos más habituales, reducirás la información que expone el servidor y lo protegerás con un certificado TLS gratuito de Let's Encrypt.
Requisitos previos
Para seguir esta guía necesitas:
- Un servidor con Ubuntu 24.04 LTS, por ejemplo un VPS de CubePath.
- Un usuario no root con privilegios
sudo. - UFW activo con SSH permitido (
sudo ufw allow OpenSSH). - Para el paso de HTTPS: un dominio (en esta guía,
your_domain) con un registro DNSAque apunte a la IP pública del servidor, y opcionalmente otro parawww.your_domain.
Notaen Rocky Linux o AlmaLinux 9 el paquete se llama
httpd, el servicio eshttpd, la configuración vive en/etc/httpd/y no existen los comandosa2ensitenia2enmod. Esta guía se centra en Ubuntu y Debian.
Paso 1: Instalar Apache
Apache está en los repositorios oficiales de Ubuntu con el nombre apache2. Actualiza el índice de paquetes e instálalo:
sudo apt update
sudo apt install apache2
El paquete arranca el servicio y lo habilita en el inicio automáticamente. Compruébalo:
sudo systemctl status apache2 --no-pager
● apache2.service - The Apache HTTP Server
Loaded: loaded (/usr/lib/systemd/system/apache2.service; enabled; preset: enabled)
Active: active (running) since Thu 2026-09-24 10:12:03 UTC; 15s ago
Consulta también la versión instalada:
apache2 -v
Server version: Apache/2.4.58 (Ubuntu)
Paso 2: Abrir el firewall
Al instalarse, Apache registra tres perfiles de aplicación en UFW:
sudo ufw app list
Available applications:
Apache
Apache Full
Apache Secure
OpenSSH
Apache abre solo el puerto 80, Apache Secure solo el 443 y Apache Full ambos. Como más adelante añadirás HTTPS, permite los dos:
sudo ufw allow 'Apache Full'
sudo ufw status
Status: active
To Action From
-- ------ ----
OpenSSH ALLOW Anywhere
Apache Full ALLOW Anywhere
OpenSSH (v6) ALLOW Anywhere (v6)
Apache Full (v6) ALLOW Anywhere (v6)
Comprueba desde el propio servidor que Apache responde:
curl -I http://localhost
HTTP/1.1 200 OK
Server: Apache/2.4.58 (Ubuntu)
Content-Type: text/html
Si abres http://your_server_ip en el navegador verás la página "Apache2 Default Page" de Ubuntu.
Paso 3: Conocer los archivos de configuración
Antes de tocar nada conviene saber dónde está cada cosa en Ubuntu:
| Ruta | Contenido |
|---|---|
/etc/apache2/apache2.conf | Configuración global del servidor |
/etc/apache2/ports.conf | Puertos en los que escucha (Listen 80, Listen 443) |
/etc/apache2/sites-available/ | Un archivo por virtual host |
/etc/apache2/sites-enabled/ | Enlaces a los sitios activos (se gestionan con a2ensite y a2dissite) |
/etc/apache2/mods-available/ y mods-enabled/ | Módulos disponibles y activos (a2enmod, a2dismod) |
/etc/apache2/conf-available/ y conf-enabled/ | Fragmentos de configuración global (a2enconf, a2disconf) |
/var/www/html/ | Raíz web del sitio por defecto |
/var/log/apache2/ | access.log y error.log |
La regla práctica es no editar los archivos de *-enabled/: crea o modifica el archivo en *-available/ y actívalo con la utilidad a2* correspondiente.
Paso 4: Definir el ServerName global
Si compruebas la sintaxis ahora, Apache mostrará un aviso porque no sabe el nombre del servidor:
sudo apache2ctl configtest
AH00558: apache2: Could not reliably determine the server's fully qualified domain name, using 127.0.1.1. Set the 'ServerName' directive globally to suppress this message
Syntax OK
Crea un fragmento de configuración con el nombre del servidor:
sudo nano /etc/apache2/conf-available/servername.conf
ServerName your_domain
Actívalo y vuelve a comprobar la sintaxis:
sudo a2enconf servername
sudo apache2ctl configtest
Syntax OK
Paso 5: Crear un virtual host para tu dominio
Un virtual host permite servir varios sitios desde el mismo servidor, cada uno con su directorio y sus logs. Crea el directorio del sitio y asígnalo a tu usuario para poder editar los archivos sin sudo:
sudo mkdir -p /var/www/your_domain/public_html
sudo chown -R $USER:$USER /var/www/your_domain
Crea una página de prueba:
nano /var/www/your_domain/public_html/index.html
<!DOCTYPE html>
<html lang="es">
<head><meta charset="utf-8"><title>your_domain</title></head>
<body><h1>El virtual host de your_domain funciona</h1></body>
</html>
Crea el archivo del virtual host:
sudo nano /etc/apache2/sites-available/your_domain.conf
<VirtualHost *:80>
ServerName your_domain
ServerAlias www.your_domain
ServerAdmin webmaster@your_domain
DocumentRoot /var/www/your_domain/public_html
<Directory /var/www/your_domain/public_html>
Options -Indexes +FollowSymLinks
AllowOverride All
Require all granted
</Directory>
ErrorLog ${APACHE_LOG_DIR}/your_domain_error.log
CustomLog ${APACHE_LOG_DIR}/your_domain_access.log combined
</VirtualHost>
Options -Indexes evita que Apache liste el contenido de un directorio sin index.html, y AllowOverride All permite usar .htaccess (si tu aplicación no lo necesita, usa AllowOverride None, que es algo más rápido).
Activa el sitio, desactiva el sitio por defecto, comprueba la sintaxis y recarga Apache:
sudo a2ensite your_domain.conf
sudo a2dissite 000-default.conf
sudo apache2ctl configtest
sudo systemctl reload apache2
Comprueba que responde con el contenido nuevo. Si el DNS aún no ha propagado, --resolve fuerza la resolución del nombre a la IP local:
curl --resolve your_domain:80:127.0.0.1 http://your_domain
<h1>El virtual host de your_domain funciona</h1>
Para configuraciones con varios dominios, subdominios o PHP-FPM, consulta la guía dedicada a virtual hosts en Apache.
Paso 6: Activar los módulos más habituales
Apache se amplía con módulos. Estos son los que casi cualquier sitio acaba necesitando:
rewrite: reescritura de URLs, imprescindible para WordPress, Laravel y la mayoría de frameworks.headers: añadir o modificar cabeceras HTTP.ssl: HTTPS (Certbot lo activa por ti en el paso 8).
deflate (compresión gzip) ya viene activado en Ubuntu. Activa los dos primeros y reinicia, ya que cargar módulos requiere un reinicio completo:
sudo a2enmod rewrite headers
sudo systemctl restart apache2
Lista los módulos cargados para comprobarlo:
sudo apache2ctl -M | grep -E 'rewrite|headers|deflate'
deflate_module (shared)
headers_module (shared)
rewrite_module (shared)
Puedes ver también qué MPM (modelo de procesos) usa Apache. En Ubuntu 24.04 es event, el más eficiente, salvo que instales libapache2-mod-php, que lo cambia a prefork:
sudo a2query -M
event
Paso 7: Reducir la información expuesta
Por defecto Apache anuncia su versión y el sistema operativo en la cabecera Server y en las páginas de error. Ubuntu centraliza estas opciones en security.conf:
sudo nano /etc/apache2/conf-available/security.conf
Localiza estas directivas y déjalas así:
ServerTokens Prod
ServerSignature Off
TraceEnable Off
Añade al final del mismo archivo algunas cabeceras de seguridad básicas (requieren el módulo headers del paso anterior):
<IfModule mod_headers.c>
Header always set X-Content-Type-Options "nosniff"
Header always set X-Frame-Options "SAMEORIGIN"
Header always set Referrer-Policy "strict-origin-when-cross-origin"
</IfModule>
Comprueba y recarga:
sudo apache2ctl configtest
sudo systemctl reload apache2
curl -I http://localhost
HTTP/1.1 200 OK
Server: Apache
X-Content-Type-Options: nosniff
X-Frame-Options: SAMEORIGIN
Referrer-Policy: strict-origin-when-cross-origin
La cabecera Server ya no muestra versión ni sistema.
Paso 8: Añadir HTTPS con Let's Encrypt
Certbot obtiene un certificado gratuito de Let's Encrypt, modifica el virtual host para usarlo y programa la renovación automática. Instálalo junto con su plugin para Apache:
sudo apt install certbot python3-certbot-apache
Solicita el certificado para los nombres definidos en ServerName y ServerAlias:
sudo certbot --apache -d your_domain -d www.your_domain
Certbot te pedirá un correo para avisos de caducidad y que aceptes los términos. Al terminar crea /etc/apache2/sites-available/your_domain-le-ssl.conf, activa mod_ssl y añade al virtual host del puerto 80 una redirección a HTTPS.
Comprueba la redirección y el certificado:
curl -I http://your_domain
HTTP/1.1 301 Moved Permanently
Location: https://your_domain/
La renovación la gestiona el temporizador certbot.timer. Verifica que está activo y simula una renovación:
systemctl list-timers certbot.timer
sudo certbot renew --dry-run
Congratulations, all simulated renewals succeeded:
/etc/letsencrypt/live/your_domain/fullchain.pem (success)
Paso 9: Consultar los logs
Cada virtual host escribe en sus propios archivos dentro de /var/log/apache2/. Para seguir las peticiones en tiempo real:
sudo tail -f /var/log/apache2/your_domain_access.log
Y para ver errores recientes:
sudo tail -n 50 /var/log/apache2/your_domain_error.log
Los logs se rotan cada día y se conservan 14 días según /etc/logrotate.d/apache2, así que no necesitas configurar nada más.
Solución de problemas
Apache no arranca: comprueba primero la sintaxis con sudo apache2ctl configtest, que indica el archivo y la línea del error. Si la sintaxis es correcta, consulta el motivo con sudo journalctl -u apache2 -n 50 --no-pager.
(98)Address already in use: AH00072: make_sock: could not bind to address [::]:80: otro proceso, a menudo Nginx, ocupa el puerto. Averigua cuál con sudo ss -tlnp | grep ':80 ' y detenlo o cambia su puerto.
403 Forbidden: suele deberse a que falta Require all granted en el bloque <Directory>, a que no existe un archivo índice y Indexes está desactivado, o a permisos. El usuario www-data necesita permiso de lectura sobre los archivos y de ejecución sobre todos los directorios de la ruta: namei -l /var/www/your_domain/public_html/index.html te muestra dónde falla.
500 Internal Server Error: casi siempre es un .htaccess con una directiva de un módulo no activado (por ejemplo RewriteEngine sin mod_rewrite). El motivo exacto aparece en el log de errores del sitio.
Se muestra el sitio por defecto en lugar del tuyo: el nombre que usas no coincide con ningún ServerName o ServerAlias. Ejecuta sudo apache2ctl -S para ver qué virtual hosts ha cargado Apache y cuál actúa como predeterminado.
Conclusión
Tienes Apache funcionando en Ubuntu 24.04 con el firewall abierto, un virtual host propio, los módulos rewrite y headers activos, la versión oculta y HTTPS con renovación automática. A partir de aquí puedes:
- Alojar varios dominios en el mismo servidor siguiendo la guía de virtual hosts en Apache.
- Instalar PHP-FPM (
php8.3-fpm) para ejecutar aplicaciones PHP manteniendo el MPMevent. - Comparar Apache con Nginx para decidir cuál encaja mejor con tu carga de trabajo.
