Async command-line downloader for Instagram. Profiles, posts, reels, stories, highlights, hashtags, and comments — saved to disk with the original timestamps preserved.
pip install instagram-dl # pip
pipx install instagram-dl # or as an isolated CLI app
export HIKERAPI_TOKEN=your_token
insta-dl instagramOr run it without installing Python at all:
docker run --rm -v "$PWD/out:/data" -e HIKERAPI_TOKEN \
ghcr.io/subzeroid/insta-dl:latest instagramGrab a free HikerAPI token at hikerapi.com — first 100 requests are free, no credit card. One request ≈ one post or one page of a feed.
insta-dl
- downloads profiles, hashtags, single posts, reels, stories, highlights, and comments,
- preserves the original
taken_attimestamp as file mtime so Photos/Finder sort correctly, - writes a JSON metadata sidecar next to every post (caption, like count, location, owner),
- supports incremental updates with
--fast-updateand--latest-stamps, - accepts profile names,
#hashtag, post shortcodes, and fullinstagram.comURLs, - ships two pluggable backends: a paid commercial API (HikerAPI, no Instagram session, no ban risk) out of the box, and an opt-in private-API library via
pip install 'instagram-dl[aiograpi]'(your own login).
insta-dl [--backend hiker|aiograpi]
[--dest DIR] [--fast-update] [--latest-stamps FILE]
[--stories] [--highlights] [--comments]
profile | "#hashtag" | post:SHORTCODE | https://instagram.com/...
📖 Full documentation — installation, CLI reference, backends comparison, Python API, troubleshooting.
| insta-dl | instaloader | gallery-dl | |
|---|---|---|---|
| Backend | HikerAPI cloud (default), aiograpi optional | Logged-in Instagram session | Logged-in Instagram session |
| Account ban risk | None with HikerAPI backend | High — your account scrapes | High — your account scrapes |
| Login required | No (HikerAPI token only) | Yes | Yes |
| Stories / highlights | ✅ | ✅ (login required) | ✅ (login required) |
| Hashtags | ✅ | ✅ (rate-limited) | ✅ (rate-limited) |
| Comments | ✅ | ✅ | ✅ |
| Async / concurrent | ✅ native asyncio | Sync | Sync |
taken_at mtime |
✅ | ✅ | |
| JSON sidecar | ✅ | ✅ | ✅ |
| Multi-site (TikTok, Twitter, …) | Instagram-only | Instagram-only | ✅ 300+ sites |
When to pick insta-dl — you want an Instagram archive without losing your account. The default HikerAPI backend uses no Instagram session, so there's nothing for Instagram to flag, ban, or 2FA-challenge. instaloader and gallery-dl both drive scraping through your own logged-in cookies, which works until Instagram raises the rate-limit floor again.
When to pick instaloader — you don't want any external service in the loop and you have a throwaway Instagram account you don't mind burning. Battle-tested, huge user base, more granular --filter expression language.
When to pick gallery-dl — you want one tool for many platforms (Twitter, TikTok, DeviantArt, etc.) and Instagram is just one of them. Less Instagram-specialised but covers a much wider catalogue.
Related projects: instaloot (Python, less maintained), instagram-php-scraper (PHP, login-based), aiograpi (the async Instagram private API library that powers the optional [aiograpi] backend here).
export HIKERAPI_TOKEN=$(cat ~/.config/hikerapi-token)
insta-dl --dest ./out instagramThis grabs every post, names files 2026-04-21_16-04-15_DXZlTiKEpxw.mp4, and writes a metadata sidecar next to each.
insta-dl --fast-update --latest-stamps ./stamps.ini --dest ./out instagram--fast-update stops at the first post that's already on disk; --latest-stamps records the newest taken_at per profile so even a deleted local copy can be resumed.
insta-dl post:DXZlTiKEpxw
insta-dl https://www.instagram.com/p/DXZlTiKEpxw/
insta-dl https://www.instagram.com/reel/DXZlTiKEpxw/insta-dl '#sunset' --dest ./outPulls the recent feed for the tag into ./out/#sunset/.
insta-dl --stories --highlights --dest ./out instagramStories and highlights land under <dest>/<username>/stories/ and <dest>/<username>/highlights/<id>_<title>/.
insta-dl --comments --dest ./out instagramEach post gets a ..._comments.json sidecar streamed to disk.
Pick the one that matches how you want to authenticate.
| hiker (default) | aiograpi | |
|---|---|---|
| Auth | API token | Instagram login + 2FA |
| Cost | Paid per request, 100 free requests to start | Free |
| Account ban risk | None — no Instagram session involved | Real, mitigated by session reuse |
| Stability vs. Instagram changes | High (managed proxy) | Brittle |
| Private profiles | What HikerAPI exposes | Anything your account can see |
Switch with --backend:
insta-dl --backend hiker --hiker-token TOKEN instagram
pip install 'instagram-dl[aiograpi]' # aiograpi's deps are opt-in
insta-dl --backend aiograpi --login USER --password PASS --session ./session.json instagramDetailed comparison and auth setup: see the backends documentation. For how insta-dl stacks up against instaloader, yt-dlp, and gallery-dl, see compared to alternatives.
<dest>/<username>/
2026-04-21_16-04-15_DXZlTiKEpxw.mp4
2026-04-21_16-04-15_DXZlTiKEpxw.json # metadata sidecar
2026-04-21_16-04-15_DXZlTiKEpxw_comments.json # with --comments
stories/
2026-04-21_18-30-00_178290.jpg # with --stories
highlights/
17991_Travel/ # with --highlights
2025-10-12_19-20-30_4011.jpg
Hashtag downloads land under <dest>/#<tag>/; single-post downloads use the post owner's username (or owner_pk fallback).
This is alpha. Both backends (hiker, aiograpi) are functional end-to-end (278 tests, 96% coverage). aiograpi ships behind the [aiograpi] extra so its Rust deps don't bloat default installs. CLI flags and output layout are stable; Python API may still shift.
What's not yet implemented:
:feedand:savedtargets (account-bound, would need session reuse from aiograpi backend)
See the changelog for what landed when, and contributing for how to help.
Bug reports, fixes, and backend implementations welcome. Start with CONTRIBUTING.md. Tests: pip install -e .[dev] && pytest.
insta-dl is not affiliated with, authorized, maintained, or endorsed by Instagram or Meta. Use at your own risk and respect the rights of content creators. Licensed under MIT.
