Running your first file download: saving files with the name from the URL, renaming with -O, streaming output to stdout with -O -, and controlling the progress bar and logs with -q, -nv, and -a.

After dissecting wget's architecture in episode 2 — from the non-interactive model to the six transfer stages — it's time for the most practical episode: downloading an actual file. This episode is a milestone, because from here on every command you learn can be applied to real things: fetching files from servers, downloading assets, and reading data from APIs.
The key difference we'll feel from the very start: wget writes files to disk, rather than showing the body on screen like curl. This isn't a small detail — it's the philosophical difference between the two we touched on in episode 1, and now we'll see it in practice.
Open a terminal, go to a clean working directory, and run:
wget https://example.comNotice the output:
--2026-08-03 09:15:00-- https://example.com/
Resolving example.com (example.com)... 93.184.215.14
Connecting to example.com (example.com)|93.184.215.14|:443... connected.
HTTP request sent, awaiting response... 200 OK
Length: 1256 (1.2K) [text/html]
Saving to: ‘index.html’
index.html 100%[===========================>] 1.23K --.-KB/s in 0s
2026-08-03 09:15:00 (5.84 MB/s) - ‘index.html’ saved [1256/1256]Look at those lines — they're exactly the six stages from episode 2:
Resolving example.com... — the DNS resolution stage.Connecting to example.com ... 443... connected. — the TCP connection stage.HTTP request sent, awaiting response... 200 OK — the request is sent, the server answers with status 200.Length: 1256 (1.2K) [text/html] — the file size and content type from the response headers.Saving to: ‘index.html’ — the local file name. Why index.html? Because the URL https://example.com/ ends with / and carries no file name — following the naming rule from episode 2.saved [1256/1256] — the file was written completely to disk.Why example.com? Because this domain is deliberately reserved by IANA for documentation — stable, light, and always available, so it's safe for practice. Check the result with ls — you'll see an index.html file in the working directory.
Important
Wget's golden rule: it writes files to disk by default. Unlike curl, which dumps the body to stdout, wget saves the result as a file. If you run wget URL and don't see any file, the likely explanation is that you ran it in the wrong directory — check with ls and pwd before blaming wget.
-OOften you want to save the download under a name of your choosing — for example, something more descriptive. The -O option (or --output-document) sets the local file name:
wget -O landing.html https://example.comNow the file is saved as landing.html, not index.html. The -O option overrides the default naming rule from the URL — you're in control of the file name.
Warning
Note: wget will overwrite an existing file without asking. If landing.html already exists, its contents are replaced. For downloads that are safe against overwriting, you can combine with -c (resume), which we'll cover in episode 4 — or make sure the file name you use is unique.
-O -There's a special variant of -O: with the file name -, wget writes output to stdout instead of disk. This is a very useful pattern for fetching data and piping it straight into another command — for example into jq to read JSON:
wget -qO- https://httpbin.org/ip | jqThe -qO- combination means: quiet (-q), output to stdout (-O -). As a result, you don't need to save an intermediate file — the data flows directly from the server to jq. You'll use this wget -qO- URL | jq pattern over and over throughout the series.
Tip
When -O - is used, wget automatically turns off the progress bar — because the output is streaming, not being saved. So don't be surprised if there's no progress; that's actually a sign wget is working correctly. For large files, wget -O - URL > file.bin also works, but -O name is simpler for that case.
By default, wget shows a progress bar complete with percentages in the terminal. There are three output modes you should master:
| Option | Behavior |
|---|---|
-q | Completely silent — no progress, no log (only fatal errors) |
-nv | Concise — important info only, no progress bar |
-a FILE | Appends the log to FILE — doesn't overwrite history |
-q is best for scripts that want clean output. -nv is a middle ground that still shows important summaries like file name and size. -a is for recording download history:
wget -nv -a download.log https://example.comAfter running it twice, download.log will contain two history lines — useful for auditing or debugging problematic downloads. Combine -q in your main scripts and -a for permanent recording.
There's also -S (introduced in episode 2), which shows the server's response headers before the body is saved — try wget -S https://example.com when you want to confirm the server is sending the right headers:
wget -S https://example.comIn its output you'll see lines like HTTP/1.1 200 OK, Content-Type: text/html, and Content-Length — exactly the headers discussed in episode 0.
Thinking wget shows the body on screen. Wget writes files; for screen output use -O -. This habit from curl often confuses beginners.
Running in the wrong directory. Download files go to the current working directory. Always check pwd before downloading if the file location matters.
Overwriting existing files. Wget overwrites without confirmation. To be safe, give a unique name with -O or use -c (episode 4).
Forgetting that a URL ending with / produces index.html. This isn't an error — it's wget's default naming rule.
In episode 3, you've run your first file download: seen the six transfer stages in practice, understood why the file is named index.html, saved with a custom name via -O, streamed output to stdout with -O - and piped it to jq, and mastered the -q, -nv, and -a output modes along with -S.
Key takeaways:
wget URL writes a file to disk — the file name comes from the URL path, or index.html for URLs ending in /.-O FILE renames the file; -O - streams output to stdout.wget -qO- URL | jq is a quick pattern for reading JSON data.-q is silent, -nv is concise, -a FILE records history without removing the old entries.-S reveals the server's response headers.In episode 4, we'll cover resume, retry & download control — resuming interrupted downloads with -c, configuring retries with --tries, controlling timeouts and speed with --timeout and --limit-rate, and running downloads in the background with -b. See you in episode 4!