Docker Logs, Monitoring, and Debugging
# CHAPTER 13
Docker Logs, Monitoring, and Debugging
1. Introduction
When an application runs natively on your laptop, debugging is straightforward: you open the log files on your hard drive, or watch the terminal output. However, a Docker container is a black box. If an isolated container crashes and destroys itself, how do you know what went wrong? In this chapter, we will master the art of observing the black box. We will explore how to extract application logs, monitor real-time CPU/RAM usage, and interactively debug crashed environments.2. Learning Objectives
By the end of this chapter, you will be able to:-
Retrieve historical and real-time logs using
docker logs.
-
Monitor container resource consumption using
docker stats.
-
Investigate container metadata and network IP addresses using
docker inspect.
-
Debug running applications using
docker exec.
- Interpret container exit codes to diagnose crash causes.
3. Beginner-Friendly Explanation
Imagine a submarine operating deep underwater (The Container).-
docker logs(The Sonar): You cannot see the submarine, but you can listen to the sonar pings. The sonar tells you everything the submarine crew is saying (the application output).
-
docker stats(The Dashboard): A gauge that tells you how much fuel and oxygen the submarine is currently using (CPU and RAM).
-
docker exec(The Radio): You open a direct radio channel to the captain and ask them to run specific diagnostic commands while the sub is still underwater.
-
docker inspect(The Blueprint): You look at the original engineering schematics of the submarine to see exactly how it was built.
4. Extracting Logs (docker logs)
By default, Docker captures everything an application prints to the Standard Output (stdout) and Standard Error (stderr) channels.
-
View all logs:
docker logs <containername>
-
View the last 50 lines:
docker logs --tail 50 <containername>
-
Watch logs live (Streaming):
docker logs -f <container_name>(PressCtrl+Cto stop watching).
If your container crashes immediately upon starting, docker logs is always the very first command you run to find the stack trace.
5. Monitoring Resources (docker stats)
A common issue in production is a memory leak. A poorly written PHP script might slowly consume RAM until the server crashes.
To watch real-time resource consumption, run:
This opens a live dashboard in your terminal showing every running container, its CPU percentage, memory usage, and network I/O. If you see a container sitting at 99% CPU or maxing out its memory limit, you have found your bottleneck.
6. The Ultimate Debugger (docker exec)
If the logs do not provide enough information, you must break into the container.
Suppose a web server is returning a 500 Internal Server Error, and you suspect a configuration file is wrong.
Once inside, you can use standard Linux commands like cat, ls, or top to investigate the file system and running processes exactly as if you were SSH'd into a physical server.
7. Mini Project: Debug a Broken Container
Let's intentionally break a container and use our tools to solve the mystery.Step-by-Step Tutorial:
- 1. Open your terminal. We will launch a container that is programmed to fail.
- 2. Check if the container is running:
*(You won't see it! It crashed and stopped).*
- 3. Find the stopped container:
*(You will see broken-app with a status of Exited (1). An exit code of 1 indicates an application error).*
- 4. Investigate the cause:
*(The logs clearly show: CRITICAL ERROR: Database IP missing!).*
- 5. Now you know exactly why the container crashed, and you can fix your code! Clean up the evidence:
8. Real-World Scenarios
A microservice architecture consists of 10 containers. Suddenly, the website goes incredibly slow. The DevOps engineer runsdocker stats and notices the redis-cache container is utilizing 100% of its allocated CPU. The engineer then runs docker logs -f redis-cache and sees thousands of connection errors flooding the screen, pinpointing the exact root cause of the slowdown within seconds.
9. Best Practices
- Log Rotation: By default, Docker saves logs to a JSON file on your host machine's hard drive. If your container runs for 6 months and generates massive logs, it can fill up your laptop's entire hard drive, crashing the host OS! In production, you must configure Docker "Log Rotation" settings to automatically delete logs older than X days, or ship the logs off the server to a service like AWS CloudWatch.
10. Common Mistakes
-
Logging to Files inside the Container: A common beginner mistake is writing an application that saves its error logs to a file like
/var/log/app.loginside the container.docker logscannot read files!docker logsonly reads output printed directly to the terminal. You must configure your application to output tostdoutfor Docker to capture the logs.
11. Exercises
-
1.
What does the
Exited (0)status code mean compared to anExited (1)orExited (137)status code? *(Hint: 0 means normal shutdown, non-zero means error).*
-
2.
Explain why writing application logs to a static
.logfile inside a container's isolated file system is considered an anti-pattern in Docker.
12. FAQs
Q: How do I look inside a container that crashed instantly? I can't usedocker exec if it's dead!
A: Correct, docker exec only works on running containers. To inspect a dead container's file system, you can use docker commit <container_id> temp-image to save the dead container as an image, and then run docker run -it --entrypoint sh temp-image to boot into a fresh shell and explore the crime scene.
13. Interview Questions
- Q: A production Docker container is consuming an abnormal amount of host resources, threatening to crash the underlying EC2 instance. Detail the CLI commands you would utilize to identify the offending container and analyze its resource consumption.
-
Q: Describe the behavior of Docker's default
json-filelogging driver. What are the long-term storage risks associated with this default configuration, and how is it mitigated in enterprise deployments?
14. Summary
In Chapter 13, we demystified the black box. We established a rigorous troubleshooting methodology, relying ondocker ps -a to identify crashed processes and decoding Exit Codes. We utilized docker logs to retrieve critical application output and deployed docker stats to monitor real-time resource exhaustion. Finally, we demonstrated how to breach an active container's perimeter using docker exec to perform surgical, interactive debugging.