github.com/endocode/docker@v1.4.2-0.20160113120958-46eb4700391e/docs/userguide/usingdocker.md (about) 1 <!--[metadata]> 2 +++ 3 title = "Run a simple application" 4 description = "Learn how to manage and operate Docker containers." 5 keywords = ["docker, the docker guide, documentation, docker.io, monitoring containers, docker top, docker inspect, docker port, ports, docker logs, log, Logs"] 6 [menu.main] 7 parent="smn_containers" 8 weight=-5 9 +++ 10 <![end-metadata]--> 11 12 # Run a simple application 13 14 In the ["*Hello world in a container*"](dockerizing.md) you launched your 15 first containers using the `docker run` command. You ran an *interactive container* that ran in the foreground. You also ran a *detached container* that ran in the background. In the process you learned about several Docker commands: 16 17 * `docker ps` - Lists containers. 18 * `docker logs` - Shows us the standard output of a container. 19 * `docker stop` - Stops running containers. 20 21 ## Learn about the Docker client 22 23 If you didn't realize it yet, you've been using the Docker client each time you 24 typed `docker` in your Bash terminal. The client is a simple command line client 25 also known as a command-line interface (CLI). Each action you can take with 26 the client is a command and each command can take a series of flags and arguments. 27 28 # Usage: [sudo] docker [subcommand] [flags] [arguments] .. 29 # Example: 30 $ docker run -i -t ubuntu /bin/bash 31 32 You can see this in action by using the `docker version` command to return 33 version information on the currently installed Docker client and daemon. 34 35 $ docker version 36 37 This command will not only provide you the version of Docker client and 38 daemon you are using, but also the version of Go (the programming 39 language powering Docker). 40 41 Client: 42 Version: 1.8.1 43 API version: 1.20 44 Go version: go1.4.2 45 Git commit: d12ea79 46 Built: Thu Aug 13 02:35:49 UTC 2015 47 OS/Arch: linux/amd64 48 49 Server: 50 Version: 1.8.1 51 API version: 1.20 52 Go version: go1.4.2 53 Git commit: d12ea79 54 Built: Thu Aug 13 02:35:49 UTC 2015 55 OS/Arch: linux/amd64 56 57 ## Get Docker command help 58 59 You can display the help for specific Docker commands. The help details the 60 options and their usage. To see a list of all the possible commands, use the 61 following: 62 63 $ docker --help 64 65 To see usage for a specific command, specify the command with the `--help` flag: 66 67 $ docker attach --help 68 69 Usage: docker attach [OPTIONS] CONTAINER 70 71 Attach to a running container 72 73 --help Print usage 74 --no-stdin Do not attach stdin 75 --sig-proxy=true Proxy all received signals to the process 76 77 > **Note:** 78 > For further details and examples of each command, see the 79 > [command reference](../reference/commandline/cli.md) in this guide. 80 81 ## Running a web application in Docker 82 83 So now you've learned a bit more about the `docker` client you can move onto 84 the important stuff: running more containers. So far none of the 85 containers you've run did anything particularly useful, so you can 86 change that by running an example web application in Docker. 87 88 For our web application we're going to run a Python Flask application. 89 Start with a `docker run` command. 90 91 $ docker run -d -P training/webapp python app.py 92 93 Review what the command did. You've specified two flags: `-d` and 94 `-P`. You've already seen the `-d` flag which tells Docker to run the 95 container in the background. The `-P` flag is new and tells Docker to 96 map any required network ports inside our container to our host. This 97 lets us view our web application. 98 99 You've specified an image: `training/webapp`. This image is a 100 pre-built image you've created that contains a simple Python Flask web 101 application. 102 103 Lastly, you've specified a command for our container to run: `python app.py`. This launches our web application. 104 105 > **Note:** 106 > You can see more detail on the `docker run` command in the [command 107 > reference](../reference/commandline/run.md) and the [Docker Run 108 > Reference](../reference/run.md). 109 110 ## Viewing our web application container 111 112 Now you can see your running container using the `docker ps` command. 113 114 $ docker ps -l 115 CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES 116 bc533791f3f5 training/webapp:latest python app.py 5 seconds ago Up 2 seconds 0.0.0.0:49155->5000/tcp nostalgic_morse 117 118 You can see you've specified a new flag, `-l`, for the `docker ps` 119 command. This tells the `docker ps` command to return the details of the 120 *last* container started. 121 122 > **Note:** 123 > By default, the `docker ps` command only shows information about running 124 > containers. If you want to see stopped containers too use the `-a` flag. 125 126 We can see the same details we saw [when we first Dockerized a 127 container](dockerizing.md) with one important addition in the `PORTS` 128 column. 129 130 PORTS 131 0.0.0.0:49155->5000/tcp 132 133 When we passed the `-P` flag to the `docker run` command Docker mapped any 134 ports exposed in our image to our host. 135 136 > **Note:** 137 > We'll learn more about how to expose ports in Docker images when 138 > [we learn how to build images](dockerimages.md). 139 140 In this case Docker has exposed port 5000 (the default Python Flask 141 port) on port 49155. 142 143 Network port bindings are very configurable in Docker. In our last example the 144 `-P` flag is a shortcut for `-p 5000` that maps port 5000 inside the container 145 to a high port (from *ephemeral port range* which typically ranges from 32768 146 to 61000) on the local Docker host. We can also bind Docker containers to 147 specific ports using the `-p` flag, for example: 148 149 $ docker run -d -p 80:5000 training/webapp python app.py 150 151 This would map port 5000 inside our container to port 80 on our local 152 host. You might be asking about now: why wouldn't we just want to always 153 use 1:1 port mappings in Docker containers rather than mapping to high 154 ports? Well 1:1 mappings have the constraint of only being able to map 155 one of each port on your local host. 156 157 Suppose you want to test two Python applications: both bound to port 5000 inside 158 their own containers. Without Docker's port mapping you could only access one at 159 a time on the Docker host. 160 161 So you can now browse to port 49155 in a web browser to 162 see the application. 163 164 ![Viewing the web application](webapp1.png). 165 166 Our Python application is live! 167 168 > **Note:** 169 > If you have been using a virtual machine on OS X, Windows or Linux, 170 > you'll need to get the IP of the virtual host instead of using localhost. 171 > You can do this by running the `docker-machine ip your_vm_name` from your command line or terminal application, for example: 172 > 173 > $ docker-machine ip my-docker-vm 174 > 192.168.99.100 175 > 176 > In this case you'd browse to `http://192.168.99.100:49155` for the above example. 177 178 ## A network port shortcut 179 180 Using the `docker ps` command to return the mapped port is a bit clumsy so 181 Docker has a useful shortcut we can use: `docker port`. To use `docker port` we 182 specify the ID or name of our container and then the port for which we need the 183 corresponding public-facing port. 184 185 $ docker port nostalgic_morse 5000 186 0.0.0.0:49155 187 188 In this case you've looked up what port is mapped externally to port 5000 inside 189 the container. 190 191 ## Viewing the web application's logs 192 193 You can also find out a bit more about what's happening with our application and 194 use another of the commands you've learned, `docker logs`. 195 196 $ docker logs -f nostalgic_morse 197 * Running on http://0.0.0.0:5000/ 198 10.0.2.2 - - [23/May/2014 20:16:31] "GET / HTTP/1.1" 200 - 199 10.0.2.2 - - [23/May/2014 20:16:31] "GET /favicon.ico HTTP/1.1" 404 - 200 201 This time though you've added a new flag, `-f`. This causes the `docker 202 logs` command to act like the `tail -f` command and watch the 203 container's standard out. We can see here the logs from Flask showing 204 the application running on port 5000 and the access log entries for it. 205 206 ## Looking at our web application container's processes 207 208 In addition to the container's logs we can also examine the processes 209 running inside it using the `docker top` command. 210 211 $ docker top nostalgic_morse 212 PID USER COMMAND 213 854 root python app.py 214 215 Here we can see our `python app.py` command is the only process running inside 216 the container. 217 218 ## Inspecting our web application container 219 220 Lastly, we can take a low-level dive into our Docker container using the 221 `docker inspect` command. It returns a JSON document containing useful 222 configuration and status information for the specified container. 223 224 $ docker inspect nostalgic_morse 225 226 You can see a sample of that JSON output. 227 228 [{ 229 "ID": "bc533791f3f500b280a9626688bc79e342e3ea0d528efe3a86a51ecb28ea20", 230 "Created": "2014-05-26T05:52:40.808952951Z", 231 "Path": "python", 232 "Args": [ 233 "app.py" 234 ], 235 "Config": { 236 "Hostname": "bc533791f3f5", 237 "Domainname": "", 238 "User": "", 239 . . . 240 241 We can also narrow down the information we want to return by requesting a 242 specific element, for example to return the container's IP address we would: 243 244 $ docker inspect -f '{{range .NetworkSettings.Networks}}{{.IPAddress}}{{end}}' nostalgic_morse 245 172.17.0.5 246 247 ## Stopping our web application container 248 249 Okay you've seen web application working. Now you can stop it using the 250 `docker stop` command and the name of our container: `nostalgic_morse`. 251 252 $ docker stop nostalgic_morse 253 nostalgic_morse 254 255 We can now use the `docker ps` command to check if the container has 256 been stopped. 257 258 $ docker ps -l 259 260 ## Restarting our web application container 261 262 Oops! Just after you stopped the container you get a call to say another 263 developer needs the container back. From here you have two choices: you 264 can create a new container or restart the old one. Look at 265 starting your previous container back up. 266 267 $ docker start nostalgic_morse 268 nostalgic_morse 269 270 Now quickly run `docker ps -l` again to see the running container is 271 back up or browse to the container's URL to see if the application 272 responds. 273 274 > **Note:** 275 > Also available is the `docker restart` command that runs a stop and 276 > then start on the container. 277 278 ## Removing our web application container 279 280 Your colleague has let you know that they've now finished with the container 281 and won't need it again. Now, you can remove it using the `docker rm` command. 282 283 $ docker rm nostalgic_morse 284 Error: Impossible to remove a running container, please stop it first or use -f 285 2014/05/24 08:12:56 Error: failed to remove one or more containers 286 287 What happened? We can't actually remove a running container. This protects 288 you from accidentally removing a running container you might need. You can try 289 this again by stopping the container first. 290 291 $ docker stop nostalgic_morse 292 nostalgic_morse 293 $ docker rm nostalgic_morse 294 nostalgic_morse 295 296 And now our container is stopped and deleted. 297 298 > **Note:** 299 > Always remember that removing a container is final! 300 301 # Next steps 302 303 Until now you've only used images that you've downloaded from Docker Hub. Next, 304 you can get introduced to building and sharing our own images. 305 306 Go to [Working with Docker Images](dockerimages.md).