Hacking labs
How to Create an Isolated Docker Network for Your Lab
Build a Docker network with no internet access, run OWASP Juice Shop on it, and publish a browser copy only on 127.0.0.1. Verify each step.
Run OWASP Juice Shop in a Docker container bound to your own machine, confirm it responds, and stop it cleanly.
OWASP Juice Shop is an intentionally vulnerable web application. You can run it in a Docker container on your own computer, open it in a browser at http://127.0.0.1:3000, and practice web security on it without touching anyone else's systems. The project says it includes vulnerabilities from the entire OWASP Top Ten, plus others found in real applications. Below are the commands, what to check after each one, how to keep the port private, and how to stop the lab.
Juice Shop contains flaws on purpose. Keep it on a machine and network you control, and never expose it to the internet.
Run these two commands in a terminal:
docker --version
docker infoThe first command prints the Docker CLI version. The second contacts the Docker engine and prints its configuration. If docker info reports that it cannot connect to the daemon, start Docker Desktop or the Docker service, then run the command again. The exact error text depends on your platform, so follow Docker's install documentation if the fix is not obvious.
The project documentation names the image bkimminich/juice-shop. The project README runs it without a tag, which pulls latest. If you want a repeatable lab, pick a release tag on the Docker Hub page and append it to the image name (bkimminich/juice-shop:<tag>), so you know which version you are testing.
docker run --rm --name juice-shop-lab \
-p 127.0.0.1:3000:3000 \
bkimminich/juice-shopThe -p flag publishes a container port on the host. The value 127.0.0.1:3000:3000 has three parts: the host address, the host port and the container port. Docker's port publishing reference explains that a mapping without an address can listen on every host interface. Putting 127.0.0.1 first keeps the lab reachable only from your own machine.
The --rm flag removes the container when it stops. The command runs in the foreground, so the terminal keeps printing logs until you stop it. The first run downloads the image, which can take a while.
Open http://127.0.0.1:3000 in a browser on the same machine. You should see the Juice Shop home page. If it does not load, read the terminal for errors, then run docker ps in a second terminal to confirm that the container is running and the port mapping is correct. VPN clients, proxies and virtual machine networks can change how local traffic behaves, so check those as well before you change any flags.
Do not change 127.0.0.1 to 0.0.0.0 to make the page load. That setting exposes the lab to other devices on your network.
Before you try any challenge, look at how the browser and the server talk. Open the developer tools, switch to the Network tab and reload the page. Pick one request and note:
Content-Type;You can get the same information from a terminal:
curl -I http://127.0.0.1:3000In Windows PowerShell 5.1, curl is an alias for a different command, so type curl.exe instead.
The -I option sends a HEAD request and prints only the response headers. RFC 9110 defines the methods, status codes and header fields you are looking at. These are the first lines of what the untagged image returned on one run (2026-11-08); other releases may differ:
HTTP/1.1 200 OK
Access-Control-Allow-Origin: *
X-Content-Type-Options: nosniff
X-Frame-Options: SAMEORIGIN
Content-Type: text/html; charset=UTF-8Write down what your own server returns and compare.
The project documentation describes the training challenges and their hints. Read that material before you try an exploit, and keep every test pointed at 127.0.0.1. Knowing the request and response cycle first makes scanner results easier to judge later, because you can see the traffic those tools send and receive.
If the container runs in the foreground, press Ctrl+C in its terminal. Because you used --rm, Docker removes the container once it stops.
If you lost that terminal, stop the container from another one:
docker stop juice-shop-labDocker sends a stop signal and waits for the container to exit. Confirm that the lab is gone:
docker psIf the container name does not appear in the list, the lab is stopped. Closing the browser tab does not stop the container, so check docker ps every time.
If the port is already in use, docker run fails with Bind for 127.0.0.1:3000 failed: port is already allocated. Choose another host port, such as -p 127.0.0.1:3001:3000, and open http://127.0.0.1:3001 instead. Keep the 127.0.0.1 part.
If the container exits right away, read the logs in the terminal. Look for the first error line, not the last one.
If the first run takes a long time, Docker is downloading the image and its layers. Later runs start faster because Docker keeps the image locally.
A language model can explain a status code or help organize your notes, and NotHoly is one place to run that. It can also be wrong about what a response means, and it does not replace authorization or manual validation. Paste only output from your own lab, never session cookies, tokens or data from a real target.
Write your notes from what you observed, then compare them with the references below.
Hacking labs
Build a Docker network with no internet access, run OWASP Juice Shop on it, and publish a browser copy only on 127.0.0.1. Verify each step.
Hacking labs
Structure a pentest report and write one finding someone else can reproduce, with evidence, impact, a CVSS v4.0 vector and a fix.
Hacking labs
Build a home lab you are allowed to attack: a scope file, Docker ports bound to loopback, an isolated network, a notebook and a clean teardown.