Diagnose a Linux website without changing its configuration
A website that does not load can fail at several different boundaries. A browser error alone cannot tell you whether the application stopped, a proxy returned a bad response, or the request never reached the machine. This walkthrough builds a small evidence trail before restarting anything.
Use a Linux server you administer. The examples assume Ubuntu with systemd, curl, and ss. Docker commands apply only when the site uses Docker. Replace example.com and the service or container names with your own values; the sample outputs below are illustrative.
1. Describe the symptom precisely
Record the URL, the time, and the actual error. “The site is down” is less useful than “the HTTPS request timed out from my laptop at 14:05.” Test from a second network if possible. A problem visible from one client can have a different explanation from one visible everywhere.
curl -sS -o /dev/null --max-time 10 -w '%{http_code}\n' https://example.com/
An HTTP 200 means an HTTP response succeeded, not that the page contents are correct. A 301 or 308 is a redirect that needs its destination checked. A 502 suggests a gateway received an unsuitable upstream response; a timeout does not identify the failing layer by itself. Curl’s manual explains its output and timeout options. Do not bypass certificate verification to make a failed TLS check look successful.
2. Check whether the expected port is listening
ss -ltn 'sport = :443'
This shows listening TCP sockets on port 443. A loopback address such as 127.0.0.1 has different reachability from 0.0.0.0 or an IPv6 wildcard address. A listener proves that something has bound the port; it does not prove that a cloud firewall permits traffic or that the application is healthy. The ss manual describes the socket filters.
3. Find the actual process boundary
systemctl is-active nginx
systemctl is-active docker
docker ps --format "table {{.Names}}\t{{.Status}}\t{{.Ports}}"
Do not assume the web server is a host service. A machine can show nginx as inactive and still serve a site through a Caddy container. Inspect the deployment you actually have. Docker’s container-list reference explains that the default listing contains running containers; add -a if you need to identify stopped ones.
Docker access is security-sensitive. Use your existing authorized access rather than adding an account to a privileged group just to run this exercise. Record the proxy-to-application relationship without dumping environment variables or secrets.
4. Read a narrow log window
journalctl -u nginx --since "10 minutes ago" --no-pager -n 50
docker logs --since 10m --tail 50 YOUR_CONTAINER
Choose the service that actually exists. Correlate error timestamps with the failed request. A historical warning from yesterday may not explain today’s outage. The journalctl documentation covers unit and time filters. Journal permissions affect which entries you can see; no visible entries is not proof that nothing happened.
Logs may contain private request information. Keep them local while investigating and redact any credentials or personal data before sharing an excerpt.
5. Check one basic resource constraint
df -h /
A full filesystem can prevent writes even while a process remains running. Free space alone does not rule out exhausted inodes, memory limits, permission errors, or a read-only mount. Choose the next measurement based on the evidence rather than collecting every possible command output.
Build a short incident note
Write four lines: observed symptom; affected boundary; evidence; next hypothesis. For example: “Public HTTPS returns 502; proxy is listening; application container exited; inspect the application exit log.” This note is more useful than a history of random restarts because another operator can follow the reasoning.
Validation and limits
The socket query, public HTTP status check, Docker service status, zero-entry journal query, disk check, and container listing were exercised on an Ubuntu 24.04 host. The guide does not claim to reproduce every failure case. It does not change firewall rules, service configuration, or running containers.
Next, create a local development service you can safely stop and start. Predict the difference between a missing listener and an application-level error, then compare your observations. Keep experiments away from your production readers.