|
17 | 17 | [![PyPI][pypi-shield]](https://pypi.org/project/MetaDetective/) |
18 | 18 | [![Docker][docker-shield]](https://hub.docker.com/r/franckferman/metadetective) |
19 | 19 | [![License][license-shield]](https://github.com/franckferman/MetaDetective/blob/stable/LICENSE) |
| 20 | + |
| 21 | + |
20 | 22 |
|
21 | 23 | <a href="https://github.com/franckferman/MetaDetective"> |
22 | 24 | <img src="https://raw.githubusercontent.com/franckferman/MetaDetective/stable/docs/github/graphical_resources/Logo-Without_background-MetaDetective.png" alt="MetaDetective" width="340"> |
@@ -190,37 +192,157 @@ jq '.unique.Author' MetaDetective_Export-*.json |
190 | 192 |
|
191 | 193 | ### Web scraping |
192 | 194 |
|
| 195 | +MetaDetective can crawl a target website, discover downloadable files (PDF, DOCX, XLSX, images, etc.), and download them for local metadata analysis. |
| 196 | + |
| 197 | +**Two scraping modes:** |
| 198 | + |
| 199 | +- **`--download-dir`** - Download files to a local directory for analysis. This is the primary mode. |
| 200 | +- **`--scan`** - Preview only: list discovered files and stats without downloading. Useful for scoping before a full download. |
| 201 | + |
| 202 | +> `--scan` and `--download-dir` are mutually exclusive. |
| 203 | +
|
| 204 | +**The `--depth` flag is critical.** By default, depth is **0**: MetaDetective only looks at the URL you provide. Most interesting files (reports, presentations, internal documents) are linked from subpages, not the homepage. **Always set `--depth 1` or higher for real engagements.** |
| 205 | + |
| 206 | +| Depth | Behavior | |
| 207 | +|-------|----------| |
| 208 | +| `0` (default) | Only the target URL. Finds files directly linked on that single page. | |
| 209 | +| `1` | Target URL + all pages linked from it. Covers most site structures. | |
| 210 | +| `2+` | Follows links N levels deep. Broader coverage, more requests, slower. | |
| 211 | + |
| 212 | +**Download (primary workflow):** |
| 213 | + |
193 | 214 | ```bash |
194 | | -# Scan target site, list files found |
195 | | -python3 MetaDetective.py --scraping --scan --url https://target.com/ |
| 215 | +# Standard download with depth 1 (recommended starting point) |
| 216 | +python3 MetaDetective.py --scraping --url https://target.com/ \ |
| 217 | + --download-dir ~/loot/ --depth 1 |
196 | 218 |
|
197 | | -# Filter by extension |
198 | | -python3 MetaDetective.py --scraping --scan --url https://target.com/ --extensions pdf docx xlsx |
| 219 | +# Target specific file types |
| 220 | +python3 MetaDetective.py --scraping --url https://target.com/ \ |
| 221 | + --download-dir ~/loot/ --depth 2 --extensions pdf docx xlsx pptx |
199 | 222 |
|
200 | | -# Download files (depth 2, 8 threads) |
| 223 | +# Parallel download (8 threads, 10 req/s) |
201 | 224 | python3 MetaDetective.py --scraping --url https://target.com/ \ |
202 | | - --download-dir ~/loot/ --extensions pdf docx --depth 2 --threads 8 |
| 225 | + --download-dir ~/loot/ --depth 2 --threads 8 --rate 10 |
203 | 226 |
|
204 | | -# Control request rate (requests/sec) |
| 227 | +# Follow external links (CDN, subdomain, partner sites) |
205 | 228 | python3 MetaDetective.py --scraping --url https://target.com/ \ |
206 | | - --download-dir ~/loot/ --rate 5 |
| 229 | + --download-dir ~/loot/ --depth 1 --follow-extern |
207 | 230 |
|
208 | | -# Follow external links |
| 231 | +# Stealth: realistic User-Agent + low rate |
209 | 232 | python3 MetaDetective.py --scraping --url https://target.com/ \ |
210 | | - --download-dir ~/loot/ --follow-extern |
| 233 | + --download-dir ~/loot/ --depth 2 --user-agent stealth --rate 2 |
| 234 | +``` |
| 235 | + |
| 236 | +**Scan (preview):** |
| 237 | + |
| 238 | +```bash |
| 239 | +# Quick preview: how many files are reachable? |
| 240 | +python3 MetaDetective.py --scraping --scan --url https://target.com/ --depth 1 |
| 241 | + |
| 242 | +# Filter preview by extension |
| 243 | +python3 MetaDetective.py --scraping --scan --url https://target.com/ \ |
| 244 | + --depth 2 --extensions pdf docx |
| 245 | +``` |
| 246 | + |
| 247 | +**Full pipeline (scrape + analyze + export):** |
| 248 | + |
| 249 | +```bash |
| 250 | +# Step 1: download files |
| 251 | +python3 MetaDetective.py --scraping --url https://target.com/ \ |
| 252 | + --download-dir ~/loot/ --depth 2 --extensions pdf docx xlsx |
| 253 | + |
| 254 | +# Step 2: analyze and export |
| 255 | +python3 MetaDetective.py -d ~/loot/ -e html -o ~/results/ |
| 256 | +``` |
| 257 | + |
| 258 | +| Flag | Default | Description | |
| 259 | +|------|---------|-------------| |
| 260 | +| `--url` | required | Target URL | |
| 261 | +| `--download-dir` | - | Download destination (created if needed) | |
| 262 | +| `--scan` | - | Preview mode (no download) | |
| 263 | +| `--depth` | `0` | Link depth to follow. **Set to 1+ for real use.** | |
| 264 | +| `--extensions` | all supported | Filter by file type | |
| 265 | +| `--threads` | `4` | Concurrent download threads (1-100) | |
| 266 | +| `--rate` | `5` | Max requests per second (1-1000) | |
| 267 | +| `--follow-extern` | off | Follow links to external domains | |
| 268 | +| `--user-agent` | `MetaDetective/<ver>` | Custom or preset UA string | |
| 269 | + |
| 270 | +### Display modes |
| 271 | + |
| 272 | +MetaDetective offers two display modes that control how results are structured: |
| 273 | + |
| 274 | +**`--display singular`** (default) - Aggregates all unique values per field across every file. Best for OSINT: "who touched these documents?" at a glance. |
| 275 | + |
| 276 | +```bash |
| 277 | +# Default: deduplicated singular view |
| 278 | +python3 MetaDetective.py -d ./loot/ |
| 279 | + |
| 280 | +# With formatted style (vertical list with markers) |
| 281 | +python3 MetaDetective.py -d ./loot/ --format formatted |
| 282 | + |
| 283 | +# With concise style (comma-separated on one line) |
| 284 | +python3 MetaDetective.py -d ./loot/ --format concise |
| 285 | +``` |
| 286 | + |
| 287 | +**`--display all`** - One block per file with its individual metadata. Best for forensic analysis: examine each document's properties independently. |
| 288 | + |
| 289 | +```bash |
| 290 | +python3 MetaDetective.py -d ./loot/ --display all |
| 291 | +``` |
| 292 | + |
| 293 | +> `--format` only works with `--display singular`. Using `--format` with `--display all` produces an error. |
| 294 | +
|
| 295 | +### Export formats |
| 296 | + |
| 297 | +Three export formats are available. All respect the current `--display` mode. |
| 298 | + |
| 299 | +```bash |
| 300 | +# HTML report with dark theme, stats bar, and responsive layout |
| 301 | +python3 MetaDetective.py -d ./loot/ -e html |
| 302 | + |
| 303 | +# HTML per-file view |
| 304 | +python3 MetaDetective.py -d ./loot/ --display all -e html |
| 305 | + |
| 306 | +# Plain text |
| 307 | +python3 MetaDetective.py -d ./loot/ -e txt |
| 308 | + |
| 309 | +# JSON (structured, pipe into jq) |
| 310 | +python3 MetaDetective.py -d ./loot/ -e json |
| 311 | + |
| 312 | +# Custom output directory (created automatically if it does not exist) |
| 313 | +python3 MetaDetective.py -d ./loot/ -e html -o ~/results/ |
| 314 | + |
| 315 | +# Custom filename suffix |
| 316 | +python3 MetaDetective.py -d ./loot/ -e json -c pentest-corp -o ~/results/ |
| 317 | +``` |
| 318 | + |
| 319 | +The HTML export includes a summary header showing total files analyzed, total metadata fields extracted, and unique identities found (from Author, Creator, and Last Modified By fields). |
| 320 | + |
| 321 | +### User-Agent (scraping) |
| 322 | + |
| 323 | +When scraping, MetaDetective identifies itself as `MetaDetective/<version>` by default. Use `--user-agent` to change this: |
| 324 | + |
| 325 | +```bash |
| 326 | +# Use a preset |
| 327 | +python3 MetaDetective.py --scraping --scan --url https://target.com/ --user-agent stealth |
| 328 | + |
| 329 | +# Available presets |
| 330 | +# stealth, chrome-win, chrome-mac, chrome-linux, |
| 331 | +# firefox-win, firefox-mac, firefox-linux, |
| 332 | +# safari-mac, edge-win, android, iphone, googlebot |
| 333 | + |
| 334 | +# Custom string |
| 335 | +python3 MetaDetective.py --scraping --scan --url https://target.com/ \ |
| 336 | + --user-agent 'Mozilla/5.0 (compatible; MyScanner/1.0)' |
211 | 337 | ``` |
212 | 338 |
|
213 | | -### Filtering and display options |
| 339 | +### Filtering |
214 | 340 |
|
215 | 341 | | Flag | Description | |
216 | 342 | |------|-------------| |
217 | 343 | | `-t pdf docx` | Restrict to file types | |
218 | 344 | | `-i admin anonymous` | Ignore values matching pattern (regex supported) | |
219 | 345 | | `--parse-only Author Creator` | Extract only specified fields | |
220 | | -| `--display all` | Show metadata per file | |
221 | | -| `--display singular` | Deduplicated view across all files (default) | |
222 | | -| `--format formatted` | Decorated output | |
223 | | -| `--format concise` | Compact output | |
224 | 346 |
|
225 | 347 | ### Supported formats |
226 | 348 |
|
|
0 commit comments