Showing preview only (484K chars total). Download the full file or copy to clipboard to get everything.
Repository: chadi0x/TheBigBrother
Branch: main
Commit: 3e9569acead3
Files: 45
Total size: 460.4 KB
Directory structure:
gitextract_16rro3kj/
├── .dockerignore
├── .gitignore
├── Dockerfile
├── LICENSE
├── README.md
├── VERSION
├── docker-compose.yml
├── pyproject.toml
├── requirements.txt
└── the_big_brother/
├── __init__.py
├── __main__.py
├── gui/
│ ├── __init__.py
│ ├── main.py
│ └── static/
│ ├── 3.css
│ └── index.html
├── image_grabber.py
├── modules/
│ ├── __init__.py
│ ├── ai_analyst.py
│ ├── breach_vault.py
│ ├── code_hunter.py
│ ├── crypto_analyzer.py
│ ├── dark_watch.py
│ ├── digital_footprint.py
│ ├── domain_oracle.py
│ ├── dork_studio.py
│ ├── exif_analyzer.py
│ ├── flight_radar.py
│ ├── geoint_spy.py
│ ├── mail_tracer.py
│ ├── network_mapper.py
│ ├── paste_dragnet.py
│ ├── phantom_id.py
│ ├── shadow_map.py
│ ├── sigint_sweep.py
│ ├── ssl_sentinel.py
│ └── wayback_spectre.py
├── notify.py
├── py.typed
├── resources/
│ ├── data.json
│ └── data.schema.json
├── result.py
├── reverse_search.py
├── scanner.py
├── sites.py
└── validators/
└── headless_validator.py
================================================
FILE CONTENTS
================================================
================================================
FILE: .dockerignore
================================================
__pycache__
*.pyc
*.pyo
*.pyd
.Python
env
venv
.venv
pip-log.txt
pip-delete-this-directory.txt
.tox
.coverage
.coverage.*
.cache
nosetests.xml
coverage.xml
*.cover
*.log
.git
.gitignore
.mypy_cache
.pytest_cache
.hydra
.DS_Store
================================================
FILE: .gitignore
================================================
__pycache__/
*.py[cod]
*$py.class
# C extensions
*.so
# Distribution / packaging
.Python
build/
develop-eggs/
dist/
downloads/
eggs/
.eggs/
lib/
lib64/
parts/
sdist/
var/
wheels/
share/python-wheels/
*.egg-info/
.installed.cfg
*.egg
MANIFEST
# PyInstaller
# Usually these files are written by a python script from a template
# before PyInstaller builds the exe, so as to inject date/other infos into it.
*.manifest
*.spec
# Installer logs
pip-log.txt
pip-delete-this-directory.txt
# Unit test / coverage reports
htmlcov/
.tox/
.nox/
.coverage
.coverage.*
.cache
nosetests.xml
coverage.xml
*.cover
*.py,cover
.hypothesis/
.pytest_cache/
cover/
# Translations
*.mo
*.pot
# Django stuff:
*.log
local_settings.py
db.sqlite3
db.sqlite3-journal
# Flask stuff:
instance/
.webassets-cache
# Scrapy stuff:
.scrapy
# Sphinx documentation
docs/_build/
# PyBuilder
.pybuilder/
# Jupyter Notebook
.ipynb_checkpoints
# IPython
profile_default/
ipython_config.py
# pyenv
# For a library or package, you might want to ignore these files since the code is
# intended to run in multiple environments; otherwise, check them in:
# .python-version
# pipenv
# According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
# However, in case of collaboration, if having platform-specific dependencies or dependencies
# with no cross-platform support, pipenv may install dependencies that don't work, or not
# install all needed dependencies.
#Pipfile.lock
# poetry
# Similar to Pipfile.lock, it is generally recommended to include poetry.lock in version control.
# This is especially recommended for binary packages to ensure reproducibility, and is more
# commonly ignored for libraries.
# https://python-poetry.org/docs/basic-usage/#commit-your-poetrylock-file-to-version-control
#poetry.lock
# pdm
# Similar to Pipfile.lock, it is generally recommended to include pdm.lock in version control.
#pdm.lock
# pdm stores project-wide configurations in .pdm.toml, but it is recommended to not include it
# in version control.
# https://pdm.fming.dev/#use-with-ide
.pdm.toml
# PEP 582; used by e.g. github.com/David-OConnor/pyflow and github.com/pdm-project/pdm
__pypackages__/
# Celery stuff
celerybeat-schedule
celerybeat.pid
# SageMath parsed files
*.sage.py
# Environments
.env
.venv
env/
venv/
ENV/
env.bak/
venv.bak/
# Spyder project settings
.spyderproject
.spyproject
# Rope project settings
.ropeproject
# mkdocs documentation
/site
# mypy
.mypy_cache/
.dmypy.json
dmypy.json
# Pyre type checker
.pyre/
# pytype static type analyzer
.pytype/
# Cython debug symbols
cython_debug/
# PyCharm
.idea/
# VS Code
.vscode/
# MacOS
.DS_Store
================================================
FILE: Dockerfile
================================================
FROM mcr.microsoft.com/playwright/python:v1.49.0-jammy
WORKDIR /app
# Install Python dependencies
COPY requirements.txt .
RUN pip install --no-cache-dir -r requirements.txt
# Force-install Chromium that matches the pip-installed Playwright version.
# This guarantees the chromium_headless_shell binary path matches whatever
# playwright pip resolves to, even if the base image's bundled browser is
# from a different release.
RUN playwright install chromium
# Copy application code
COPY . .
EXPOSE 8000
CMD ["python", "-m", "uvicorn", "the_big_brother.gui.main:app", "--host", "0.0.0.0", "--port", "8000", "--reload"]
================================================
FILE: LICENSE
================================================
MIT License
Copyright (c) 2025 The Big Brother
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
================================================
FILE: README.md
================================================
<div align="center">
<br/>
# ◆ 👁️THE BIG BROTHER · V5.0 👁️◆
<br/>
<img width="3910" height="1088" alt="x" src="https://github.com/user-attachments/assets/94879543-dac9-40c0-ab1c-f0a583513ba1" />
<br/>
```text
╔══════════════════════════════════════════════════════════════════════════╗
║ ║
║ ████████╗██╗ ██╗███████╗ ██████╗ ██╗ ██████╗ ║
║ ╚══██╔══╝██║ ██║██╔════╝ ██╔══██╗██║██╔════╝ ║
║ ██║ ███████║█████╗ ██████╔╝██║██║ ███╗ ║
║ ██║ ██╔══██║██╔══╝ ██╔══██╗██║██║ ██║ ║
║ ██║ ██║ ██║███████╗ ██████╔╝██║╚██████╔╝ ║
║ ╚═╝ ╚═╝ ╚═╝╚══════╝ ╚═════╝ ╚═╝ ╚═════╝ ║
║ ║
║ ██████╗ ██████╗ ██████╗ ████████╗██╗ ██╗███████╗██████╗ ║
║ ██╔══██╗██╔══██╗██╔═══██╗╚══██╔══╝██║ ██║██╔════╝██╔══██╗ ║
║ ██████╔╝██████╔╝██║ ██║ ██║ ███████║█████╗ ██████╔╝ ║
║ ██╔══██╗██╔══██╗██║ ██║ ██║ ██╔══██║██╔══╝ ██╔══██╗ ║
║ ██████╔╝██║ ██║╚██████╔╝ ██║ ██║ ██║███████╗██║ ██║ ║
║ ╚═════╝ ╚═╝ ╚═╝ ╚═════╝ ╚═╝ ╚═╝ ╚═╝╚══════╝╚═╝ ╚═╝ ║
║ ║
║ ◇ THE EYE THAT NEVER BLINKS — V5.0 ◇ ║
║ ULTRA-DEEP OSINT · 21 INTEL MODULES ║
║ ║
╚══════════════════════════════════════════════════════════════════════════╝
```
<br/>
**Advanced OSINT Framework · Premium Holographic Dashboard · 21 Intel Modules**
[](https://github.com/chadi0x/the-big-brother/releases)
[](LICENSE)
[](https://www.python.org/)
[](https://www.docker.com/)
[](https://github.com/chadi0x/)
[`★ WHAT'S NEW`](#-whats-new-in-v50) · [`★ MODULES`](#-the-21-modules) · [`★ INSTALL`](#-installation) · [`★ PREMIUM`](#-premium-projects) · [`★ TELEGRAM`](https://t.me/hisoka0morow)
</div>
---
## ⟦ OVERVIEW ⟧
**The Big Brother V5.0** is a weaponized OSINT framework. Built for Red Teams, Threat Hunters, and Cyber-Investigators — V5 introduces the **AI Analyst** orchestrator that runs every relevant module in parallel and synthesizes one unified threat profile per target.
```
┌─────────────────────────────────────────────────────────────┐
│ 21 MODULES · 1 UNIFIED ENGINE · FULL DOCKER STACK │
│ HOLOGRAPHIC HUD · PARTICLE GRID · ANIMATED INTEL TIMELINE │
└─────────────────────────────────────────────────────────────┘
```
---
## 🆕 WHAT'S NEW IN V5.0
### ◆ Six brand-new intel modules
| Tool | Capability |
|:--|:--|
| 🤖 **AI ANALYST** | Auto-detects target type (email · domain · IP · username), fans out to every relevant module in parallel, synthesizes a unified 0-100 risk score + narrative findings + raw payload dump |
| 🌐 **DOMAIN ORACLE** | WHOIS (RDAP) · 7 DNS record types · SPF/DMARC/DKIM grading (A-F) · HTTP security-headers grade · TLS metadata · crt.sh subdomain enum · reverse-IP neighbors · global hygiene score |
| 📨 **MAIL TRACER** | MX validity · SPF/DMARC posture · disposable/role/free-provider detection · Gravatar identity bind · 0-100 deliverability trust score with factor breakdown |
| 🐙 **CODE HUNTER** | GitHub OSINT via public API · top repos · language stats · **public commit-email harvesting** · 24h activity heatmap · org enumeration · influence score |
| 🕰️ **WAYBACK SPECTRE** | Wayback Machine CDX timeline · yearly distribution bars · auto-flags sensitive historical paths (admin · `.env` · `.git` · backups · `.bak` · `id_rsa` · 25+ patterns) |
| 📋 **PASTE DRAGNET** | Multi-site paste hunter across 12 services (Pastebin · Ghostbin · Rentry · Paste.ee · 0bin · JustPaste · Hastebin · Ideone · DPaste · etc) via DDG dorking · auto-flags critical hits |
---
## ⚡ THE 21 MODULES
<div align="center">
```text
┌─────────────────────────────────────────────────────────────────┐
│ ⟦ SYNTHESIS ⟧ │
├─────────────────────────────────────────────────────────────────┤
│ 🤖 AI ANALYST ── cross-module synthesis · NEW │
├─────────────────────────────────────────────────────────────────┤
│ ⟦ IDENTITY ⟧ │
├─────────────────────────────────────────────────────────────────┤
│ 🔍 TARGET PROFILER ── 200+ social enum + biometric capture │
│ 👻 PHANTOM ID ── cross-platform identity correlation │
│ 🔓 BREACH VAULT ── HaveIBeenPwned + paste-dump aggregator │
│ 👣 DIGITAL FOOTPRINT ─ phone + email enumeration │
│ 📨 MAIL TRACER ── email forensics · NEW │
│ 🐙 CODE HUNTER ── GitHub OSINT · NEW │
├─────────────────────────────────────────────────────────────────┤
│ ⟦ INTEL ⟧ │
├─────────────────────────────────────────────────────────────────┤
│ 📡 SIGINT SWEEP ── Reddit · HN · News · X aggregator │
│ 🗺️ SHADOW MAP ── AbuseIPDB · VT · URLhaus reputation │
│ 📋 PASTE DRAGNET ── 12-site paste hunter · NEW │
│ 🧅 DARK WEB ── Ahmia + ransomware leak feeds │
│ 🕰️ WAYBACK SPECTRE ── archive timeline + leak flags · NEW │
├─────────────────────────────────────────────────────────────────┤
│ ⟦ INFRASTRUCTURE ⟧ │
├─────────────────────────────────────────────────────────────────┤
│ 🌐 DOMAIN ORACLE ── deep domain intel + posture · NEW │
│ 🕸️ NETWORK MAPPER ── async ports + pyvis network graph │
│ 🔒 SSL SENTINEL ── certificate chain + SAN extraction │
│ 🪙 CRYPTO ── BTC/ETH blockchain wallet recon │
├─────────────────────────────────────────────────────────────────┤
│ ⟦ MEDIA · GEO ⟧ │
├─────────────────────────────────────────────────────────────────┤
│ 📸 EXIF X-RAY ── metadata + GPS extraction │
│ 🛠️ DORK STUDIO ── Google/Shodan/GitHub dork generator │
│ 🛰️ GEOINT SPY ── multi-engine coordinate intel │
│ ✈️ SKY RADAR ── live OpenSky aircraft tracking │
└─────────────────────────────────────────────────────────────────┘
```
</div>
---
## 🚀 INSTALLATION
### ⟦ PROTOCOL A · Docker (Recommended) ⟧
```bash
# 1. Clone the grid
git clone https://github.com/chadi0x/TheBigBrother.git
cd TheBigBrother
# 2. Boot the eye
docker-compose up --build -d
```
> ▸ **Access:** `http://localhost:8000`
> ▸ **Stop:** `docker-compose down`
> ▸ **Logs:** `docker-compose logs -f`
### ⟦ PROTOCOL B · Manual Bare-Metal ⟧
**Prerequisites:** Python `3.10+` · Playwright
```bash
# 1. Environment
python -m venv venv
source venv/bin/activate # Windows: venv\Scripts\activate
# 2. Dependencies
pip install -r requirements.txt
playwright install chromium
# 3. Launch
uvicorn the_big_brother.gui.main:app --host 0.0.0.0 --port 8000
```
---
## 📸 SCREENSHOTS
<div align="center">
<img width="1675" height="840" alt="V5 dashboard" src="https://github.com/user-attachments/assets/548d4613-d53c-4d89-85ea-fb538b5bedff" />
</div>
---
## ◆ THE STACK
| Layer | Tech |
|:--|:--|
| **Backend** | FastAPI · Python 3.10+ · async-first orchestration |
| **Frontend** | Vanilla JS · Leaflet · custom particle engine |
| **Recon** | Playwright (headless validation) · pyvis · dnspython · python-whois · DuckDuckGo |
| **Container** | Docker + docker-compose · single-command deploy |
```
┌──────────────┐
│ BROWSER │
│ (HUD · JS) │
└──────┬───────┘
│ /api/*
▼
┌──────────────┐
│ FASTAPI │ ← 22 endpoints
└──────┬───────┘
│
┌────────────────┼────────────────┐
▼ ▼ ▼
┌─────────┐ ┌─────────┐ ┌─────────┐
│ SCANNER │ │ MODULES │ │HEADLESS │
│ (200+ │ │ (21) │ │PLAYWRGHT│
│ sites) │ │ │ │ valid. │
└─────────┘ └─────────┘ └─────────┘
│ │ │
└────────────────▼────────────────┘
PUBLIC OSINT ENDPOINTS
(rdap · crt.sh · wayback · github · etc)
```
---
## 🔥 PREMIUM PROJECTS
For operators who need the full arsenal — exclusive offerings via Telegram.
- 👁️ **TheBigBrother God-EYE** · Proprietary servers · extended API access · zero-key deep intel
- 🐦 **X GodMode** · Twitter/X automation suite — engagement & sentiment engineering
- 🎵 **Amplifior** · Autonomous TikTok empire builder
- 🎣 **Psychopath** · Engineered campaign deployment with AI conversational bots
- 🛠️ **Custom Builds** · 200+ ready-to-deploy operational frameworks. If it doesn't exist, we build it.
<div align="center">
**[▸ INQUIRE · Telegram @hisoka0morow](https://t.me/hisoka0morow)**
</div>
---
## ⚠️ DISCLAIMER
This framework is for **educational research and authorized security testing only**. Users are solely responsible for compliance with all applicable laws. The author assumes zero liability for misuse.
> **CLASSIFIED · AUTHORIZED PERSONNEL ONLY**
---
## 📞 SUPPORT · COMMUNITY
- **Creator / Architect** — `CHADI0X`
- **Telegram (direct inquiries)** — [@hisoka0morow](https://t.me/hisoka0morow)
- **GitHub** — [@chadi0x](https://github.com/chadi0x)
---
## 📜 LICENSE
MIT License — see [LICENSE](LICENSE)
---
<div align="center">
```
◆ ─────────────────────────────────────────────────── ◆
"In the digital age, anonymity is a luxury.
Information is the currency of power."
── CHADI0X
◆ ─────────────────────────────────────────────────── ◆
```
**V5.0.0 · THE EYE THAT NEVER BLINKS · ◇**
*Built by CHADI0X · Quantum OSINT Surveillance Grid*
</div>
================================================
FILE: VERSION
================================================
2.1.0
================================================
FILE: docker-compose.yml
================================================
services:
the-big-brother:
build: .
ports:
- "8000:8000"
volumes:
- .:/app
environment:
- PYTHONUNBUFFERED=1
restart: unless-stopped
================================================
FILE: pyproject.toml
================================================
[build-system]
requires = ["setuptools>=61.0", "wheel"]
build-backend = "setuptools.build_meta"
[project]
name = "the-big-brother"
version = "2.1.0"
description = "Advanced OSINT Tool for Username Intelligence & Visual Reconnaissance"
readme = "README.md"
requires-python = ">=3.9"
license = {text = "MIT"}
authors = [
{name = "CHADI0X", email = "chadi0x@example.com"}
]
keywords = ["osint", "reconnaissance", "username", "reverse-image-search", "intelligence"]
classifiers = [
"Development Status :: 4 - Beta",
"Intended Audience :: Information Technology",
"License :: OSI Approved :: MIT License",
"Programming Language :: Python :: 3",
"Programming Language :: Python :: 3.9",
"Programming Language :: Python :: 3.10",
"Programming Language :: Python :: 3.11",
"Programming Language :: Python :: 3.12",
"Topic :: Security",
]
dependencies = [
"fastapi>=0.104.0",
"uvicorn>=0.24.0",
"requests>=2.31.0",
"beautifulsoup4>=4.12.0",
"playwright>=1.40.0",
"duckduckgo-search>=3.9.0",
"tomli>=2.0.0; python_version<'3.11'",
"pandas>=2.0.0",
"requests-futures>=1.0.0",
"colorama>=0.4.6",
"openpyxl>=3.1.0",
]
[project.optional-dependencies]
dev = [
"pytest>=7.0.0",
"black>=23.0.0",
"mypy>=1.0.0",
]
[project.urls]
Homepage = "https://github.com/chadi0x/the-big-brother"
Repository = "https://github.com/chadi0x/the-big-brother"
Issues = "https://github.com/chadi0x/the-big-brother/issues"
[project.scripts]
the-big-brother = "the_big_brother.__main__:main"
[tool.setuptools]
packages = ["the_big_brother"]
[tool.setuptools.package-data]
the_big_brother = ["py.typed", "gui/**/*", "resources/**/*"]
================================================
FILE: requirements.txt
================================================
fastapi>=0.104.0
uvicorn>=0.24.0
requests>=2.31.0
beautifulsoup4>=4.12.0
playwright==1.49.0
duckduckgo-search>=3.9.0
tomli>=2.0.0
pandas>=2.0.0
requests-futures>=1.0.0
colorama>=0.4.6
openpyxl>=3.1.0
holehe>=1.60
phonenumbers>=8.12.0
dnspython>=2.4.0
pyvis>=0.3.0
networkx>=3.0.0
Pillow>=9.0.0
python-whois>=0.9.0
python-multipart>=0.0.6
aiohttp>=3.9.0
================================================
FILE: the_big_brother/__init__.py
================================================
""" The Big Brother Module
This module contains the main logic to search for usernames at social
networks.
"""
from importlib.metadata import version as pkg_version, PackageNotFoundError
import pathlib
import tomli
def get_version() -> str:
"""Fetch the version number of the installed package."""
try:
return pkg_version("the_big_brother")
except PackageNotFoundError:
# Try reading from pyproject.toml (setuptools format)
pyproject_path: pathlib.Path = pathlib.Path(__file__).resolve().parent.parent / "pyproject.toml"
if pyproject_path.exists():
with pyproject_path.open("rb") as f:
pyproject_data = tomli.load(f)
# Use setuptools format: project.version instead of tool.poetry.version
if "project" in pyproject_data and "version" in pyproject_data["project"]:
return pyproject_data["project"]["version"]
# Fallback to VERSION file
version_path: pathlib.Path = pathlib.Path(__file__).resolve().parent.parent / "VERSION"
if version_path.exists():
return version_path.read_text().strip()
return "2.1.0" # Final fallback
# This variable is only used to check for ImportErrors induced by users running as script rather than as module or package
import_error_test_var = None
__shortname__ = "The Big Brother"
__longname__ = "The Big Brother: Find Usernames Across Social Networks"
__version__ = get_version()
# Update check disabled for now or point to new repo if exists
forge_api_latest_release = ""
================================================
FILE: the_big_brother/__main__.py
================================================
#! /usr/bin/env python3
"""
Sherlock: Find Usernames Across Social Networks Module
This module contains the main logic to search for usernames at social
networks.
"""
import sys
if __name__ == "__main__":
# Check if the user is using the correct version of Python
python_version = sys.version.split()[0]
if sys.version_info < (3, 9):
print(f"The Big Brother requires Python 3.9+\nYou are using Python {python_version}, which is not supported by The Big Brother.")
sys.exit(1)
from the_big_brother import scanner
scanner.main()
================================================
FILE: the_big_brother/gui/__init__.py
================================================
================================================
FILE: the_big_brother/gui/main.py
================================================
from fastapi import FastAPI, BackgroundTasks, Response, UploadFile, File, Form
from fastapi.staticfiles import StaticFiles
from fastapi.middleware.cors import CORSMiddleware
from pydantic import BaseModel
from uuid import uuid4
import os
import sys
import io
import csv
from typing import List, Optional
# Add parent directory to path to allow imports
sys.path.insert(0, os.path.abspath(os.path.join(os.path.dirname(__file__), "../..")))
from the_big_brother.scanner import scan, SitesInformation, QueryNotify, QueryStatus
from the_big_brother.image_grabber import fetch_images, fetch_images_with_diag
from the_big_brother.reverse_search import ReverseImageSearcher
from the_big_brother.validators.headless_validator import HeadlessValidator
from the_big_brother.modules.digital_footprint import get_phone_info, run_holehe
from the_big_brother.modules.network_mapper import scan_target, generate_network_map
from the_big_brother.modules.dark_watch import search_dark_web
from the_big_brother.modules.crypto_analyzer import analyze_crypto
from the_big_brother.modules.ssl_sentinel import get_ssl_info
from the_big_brother.modules.exif_analyzer import get_exif_data
from the_big_brother.modules.dork_studio import generate_dorks
from the_big_brother.modules.geoint_spy import get_geoint_data
from the_big_brother.modules.flight_radar import get_flight_radar
# New V4 modules
from the_big_brother.modules.phantom_id import phantom_id_search
from the_big_brother.modules.breach_vault import breach_vault_search
from the_big_brother.modules.sigint_sweep import sigint_sweep
from the_big_brother.modules.shadow_map import shadow_map_analyze
# New V5 modules
from the_big_brother.modules.domain_oracle import domain_oracle
from the_big_brother.modules.mail_tracer import mail_tracer
from the_big_brother.modules.code_hunter import code_hunter
from the_big_brother.modules.wayback_spectre import wayback_spectre
from the_big_brother.modules.paste_dragnet import paste_dragnet
from the_big_brother.modules.ai_analyst import ai_analyst
class FootprintRequest(BaseModel):
query: str
type: str # "email" or "phone"
class NetworkRequest(BaseModel):
domain: str
class DarkRequest(BaseModel):
query: str
class CryptoRequest(BaseModel):
address: str
coin: str
class SSLRequest(BaseModel):
domain: str
class ExifRequest(BaseModel):
url: str
class DorkRequest(BaseModel):
target: str
domain: str = ""
class DeepSearchRequest(BaseModel):
image_url: str
class GeointRequest(BaseModel):
lat: str
lon: str
class FlightRequest(BaseModel):
lat: float
lon: float
radius: float = 100
class PhantomRequest(BaseModel):
username: str
class BreachRequest(BaseModel):
query: str
type: str = "email"
class SigintRequest(BaseModel):
query: str
class ShadowMapRequest(BaseModel):
target: str
class DomainOracleRequest(BaseModel):
domain: str
class MailTracerRequest(BaseModel):
email: str
class CodeHunterRequest(BaseModel):
username: str
class WaybackRequest(BaseModel):
target: str
class PasteRequest(BaseModel):
query: str
class AIAnalystRequest(BaseModel):
target: str
mode: str = "auto"
app = FastAPI(title="The Big Brother V5 API")
app.add_middleware(
CORSMiddleware,
allow_origins=["*"],
allow_methods=["*"],
allow_headers=["*"],
)
# In-memory storage
class JobState:
def __init__(self):
self.status = "running"
self.results = []
self.images = []
self.image_diag = ""
self.stop_requested = False
jobs: dict[str, JobState] = {}
class ScanRequest(BaseModel):
username: str
class NotifyQueue(QueryNotify):
def __init__(self, job_id, jobs_dict):
self.job_id = job_id
self.jobs = jobs_dict
super().__init__()
def update(self, result):
if self.jobs[self.job_id].stop_requested:
raise InterruptedError("Stopped by user")
if result.status == QueryStatus.CLAIMED:
self.jobs[self.job_id].results.append({
"site": result.site_name,
"url": result.site_url_user,
"status": "Found",
"validation": "Pending",
"context": result.context
})
elif result.status == QueryStatus.WAF:
self.jobs[self.job_id].results.append({
"site": result.site_name,
"url": result.site_url_user,
"status": "WAF Blocked",
"validation": "Pending",
"context": result.context
})
def start(self, message=None):
pass
def finish(self, message=None):
pass
def run_scan_job(job_id: str, username: str):
try:
# Handle spaces: Check "John Doe" and "JohnDoe" (or replace space with nothing)
usernames_to_check = [username]
if " " in username:
usernames_to_check.append(username.replace(" ", ""))
# 1. Fetch Images (only for the primary username) — capture diagnostics
try:
images, diag = fetch_images_with_diag(username, limit=6)
jobs[job_id].images = images
jobs[job_id].image_diag = diag
except Exception as e:
print(f"Image fetch error: {e}")
jobs[job_id].image_diag = f"fatal: {e}"
# 2. Run Scan
# Use local data.json file to ensure all sites are loaded
# Get the path to the local data.json file
data_file_path = os.path.join(os.path.dirname(__file__), "..", "resources", "data.json")
sites_info = SitesInformation(data_file_path=data_file_path, honor_exclusions=False)
site_data = {site.name: site.information for site in sites_info}
notify = NotifyQueue(job_id, jobs)
try:
for u in usernames_to_check:
if jobs[job_id].stop_requested: break
scan(u, site_data, notify)
except InterruptedError:
jobs[job_id].status = "stopped"
return
if jobs[job_id].stop_requested:
jobs[job_id].status = "stopped"
return
# 3. Validate
jobs[job_id].status = "validating"
validate_results(job_id)
if jobs[job_id].stop_requested:
jobs[job_id].status = "stopped"
else:
jobs[job_id].status = "completed"
except Exception as e:
import traceback
traceback.print_exc()
print(f"Error in scan job: {e}")
jobs[job_id].status = "error"
def validate_results(job_id: str):
results = jobs[job_id].results
if not results:
return
to_validate = [r for r in results if r["status"] == "Found"]
if not to_validate:
return
try:
with HeadlessValidator(headless=True) as validator:
for res in to_validate:
if jobs[job_id].stop_requested:
break
res["validation"] = "Checking..."
val_res = validator.validate(res["url"])
if val_res.is_profile:
res["validation"] = "Verified"
res["page_title"] = val_res.title
res["snippet"] = val_res.visible_text[:200] if val_res.visible_text else ""
else:
res["validation"] = "False Positive"
res["reason"] = val_res.reason
except Exception as e:
print(f"Validation error: {e}")
@app.post("/api/scan")
async def start_scan(request: ScanRequest, background_tasks: BackgroundTasks):
job_id = str(uuid4())
jobs[job_id] = JobState()
background_tasks.add_task(run_scan_job, job_id, request.username)
return {"job_id": job_id}
@app.post("/api/stop/{job_id}")
async def stop_scan(job_id: str):
if job_id in jobs:
jobs[job_id].stop_requested = True
return {"status": "stopping"}
return {"error": "Job not found"}
@app.get("/api/results/{job_id}")
async def get_results(job_id: str):
if job_id not in jobs:
return {"error": "Job not found"}
return {
"status": jobs[job_id].status,
"results": jobs[job_id].results,
"images": jobs[job_id].images,
"image_diag": jobs[job_id].image_diag,
}
@app.get("/api/download/{job_id}")
async def download_report(job_id: str):
if job_id not in jobs:
return {"error": "Job not found"}
results = jobs[job_id].results
output = io.StringIO()
writer = csv.writer(output)
writer.writerow(["Site", "URL", "Status", "Validation", "Page Title"])
for r in results:
writer.writerow([
r.get("site"),
r.get("url"),
r.get("status"),
r.get("validation"),
r.get("page_title", "")
])
return Response(
content=output.getvalue(),
media_type="text/csv",
headers={"Content-Disposition": f"attachment; filename=report_{job_id}.csv"}
)
@app.post("/api/deep-search")
async def deep_search(request: DeepSearchRequest):
searcher = ReverseImageSearcher(headless=True)
results = await searcher.search(request.image_url)
return results
@app.post("/api/footprint")
async def footprint_scan(request: FootprintRequest):
if request.type == "phone":
return get_phone_info(request.query)
elif request.type == "email":
return await run_holehe(request.query)
elif request.type == "breach":
# Redirect to new breach vault
return await breach_vault_search(request.query, "email")
return {"error": "Invalid type"}
@app.post("/api/phantom")
async def phantom_scan(request: PhantomRequest):
return await phantom_id_search(request.username)
@app.post("/api/breach")
async def breach_scan(request: BreachRequest):
return await breach_vault_search(request.query, request.type)
@app.post("/api/sigint")
async def sigint_scan(request: SigintRequest):
return await sigint_sweep(request.query)
@app.post("/api/shadowmap")
async def shadowmap_scan(request: ShadowMapRequest):
return await shadow_map_analyze(request.target)
@app.post("/api/network/scan")
async def network_scan(request: NetworkRequest):
data = await scan_target(request.domain)
# Generate map HTML
if "error" not in data:
graph_html = generate_network_map(data)
data["map_html"] = graph_html
return data
@app.post("/api/dark/search")
async def dark_search(request: DarkRequest):
return await search_dark_web(request.query)
@app.post("/api/crypto/analyze")
async def crypto_analyze(request: CryptoRequest):
return analyze_crypto(request.address, request.coin)
@app.post("/api/ssl/scan")
async def ssl_scan(request: SSLRequest):
return get_ssl_info(request.domain)
@app.post("/api/tools/exif")
async def tool_exif(request: ExifRequest):
return get_exif_data(request.url)
# FILE UPLOAD for EXIF
@app.post("/api/tools/exif/upload")
async def tool_exif_upload(file: UploadFile = File(...)):
# Read bytes
content = await file.read()
# Modify get_exif_data to accept bytes.
# Since we can't easily modify the module function signature without breaking it elsewhere or refactoring,
# let's duplicate the logic here or update the module.
# Actually, let's update the module logic in-place via a helper if possible.
# But for now, let's pass a byte stream if the module supports it or just use PIL directly here.
from PIL import Image
from PIL.ExifTags import TAGS, GPSTAGS
from io import BytesIO
results = {"source": file.filename, "basic": {}, "gps": {}, "error": None}
try:
image = Image.open(BytesIO(content))
results["basic"]["format"] = image.format
results["basic"]["mode"] = image.mode
results["basic"]["size"] = f"{image.width}x{image.height}"
exif_data = image._getexif()
if exif_data:
for tag_id, value in exif_data.items():
tag = TAGS.get(tag_id, tag_id)
if isinstance(value, bytes):
try: value = value.decode()
except: value = str(value)
if tag == "GPSInfo":
gps_data = {}
for t in value:
sub_tag = GPSTAGS.get(t, t)
gps_data[sub_tag] = str(value[t])
results["gps"] = gps_data
else:
if len(str(value)) < 500:
results["basic"][tag] = value
except Exception as e:
results["error"] = str(e)
return results
@app.post("/api/tools/dork")
async def tool_dork(request: DorkRequest):
return generate_dorks(request.target, request.domain)
@app.post("/api/tools/geoint")
async def tool_geoint(request: GeointRequest):
return get_geoint_data(request.lat, request.lon)
@app.post("/api/tools/flight")
async def tool_flight(request: FlightRequest):
return get_flight_radar(request.lat, request.lon, request.radius)
# === V5 endpoints ===
@app.post("/api/oracle")
async def oracle_scan(request: DomainOracleRequest):
return await domain_oracle(request.domain)
@app.post("/api/mailtracer")
async def mail_scan(request: MailTracerRequest):
return await mail_tracer(request.email)
@app.post("/api/codehunter")
async def code_scan(request: CodeHunterRequest):
return await code_hunter(request.username)
@app.post("/api/wayback")
async def wayback_scan(request: WaybackRequest):
return await wayback_spectre(request.target)
@app.post("/api/paste")
async def paste_scan(request: PasteRequest):
return await paste_dragnet(request.query)
@app.post("/api/analyst")
async def analyst_scan(request: AIAnalystRequest):
return await ai_analyst(request.target, request.mode)
# Serve static files for frontend
static_dir = os.path.join(os.path.dirname(__file__), "static")
if os.path.exists(static_dir):
app.mount("/", StaticFiles(directory=static_dir, html=True), name="static")
================================================
FILE: the_big_brother/gui/static/3.css
================================================
/* ============================================================
THE BIG BROTHER V5 — EVOLVED CYBERPUNK
Premium HUD theme · holographic glass · max-FX motion layer
============================================================ */
@import url('https://fonts.googleapis.com/css2?family=Share+Tech+Mono&family=Orbitron:wght@400;500;700;800;900&family=JetBrains+Mono:wght@400;600&family=Inter:wght@300;400;500;600;700&display=swap');
/* ---------- design tokens ---------- */
:root {
--bg-0: #030308;
--bg-1: #07070f;
--bg-2: #0c0c18;
--bg-3: #131325;
--panel: rgba(10, 10, 22, 0.72);
--panel-2: rgba(14, 14, 30, 0.85);
--panel-edge: rgba(255, 0, 80, 0.28);
--panel-edge-cyan: rgba(0, 240, 255, 0.28);
--text: #e6e9f5;
--text-mute: #8a8fa8;
--text-dim: #5a5e75;
--red: #ff0050;
--red-bright: #ff3a73;
--red-deep: #b8002f;
--cyan: #00f0ff;
--cyan-bright: #6cfcff;
--magenta: #ff00d4;
--green: #00ff8c;
--amber: #ffb800;
--violet: #a259ff;
--grad-hot: linear-gradient(135deg, #ff0050 0%, #ff00d4 100%);
--grad-cool: linear-gradient(135deg, #00f0ff 0%, #a259ff 100%);
--grad-warn: linear-gradient(135deg, #ffb800 0%, #ff0050 100%);
--grad-ok: linear-gradient(135deg, #00ff8c 0%, #00f0ff 100%);
--grad-holo: linear-gradient(135deg, #ff0050, #a259ff 25%, #00f0ff 55%, #00ff8c 80%, #ffb800);
--grad-panel: linear-gradient(135deg, rgba(255,0,80,0.06), rgba(0,240,255,0.06));
--shadow-neon: 0 0 24px rgba(255, 0, 80, 0.35), 0 0 60px rgba(255, 0, 80, 0.12);
--shadow-cyan: 0 0 24px rgba(0, 240, 255, 0.35), 0 0 60px rgba(0, 240, 255, 0.12);
--shadow-panel: 0 14px 40px -16px rgba(0,0,0,0.7), inset 0 1px 0 rgba(255,255,255,0.04);
--radius: 14px;
--radius-sm: 8px;
--radius-pill: 999px;
--transition: 220ms cubic-bezier(0.2, 0.8, 0.2, 1);
--transition-slow: 480ms cubic-bezier(0.2, 0.8, 0.2, 1);
--font-display: 'Orbitron', sans-serif;
--font-mono: 'JetBrains Mono', 'Share Tech Mono', monospace;
--font-ui: 'Inter', system-ui, sans-serif;
}
* { box-sizing: border-box; }
*::selection { background: var(--red); color: #000; }
html, body {
margin: 0; padding: 0; height: 100%;
background: var(--bg-0);
color: var(--text);
font-family: var(--font-ui);
overflow: hidden;
-webkit-font-smoothing: antialiased;
text-rendering: optimizeLegibility;
}
body::before, body::after {
content: ''; position: fixed; inset: 0; pointer-events: none; z-index: 0;
}
body::before {
background:
radial-gradient(60% 50% at 10% 10%, rgba(255, 0, 80, 0.18), transparent 60%),
radial-gradient(50% 40% at 90% 20%, rgba(0, 240, 255, 0.15), transparent 60%),
radial-gradient(40% 40% at 50% 95%, rgba(162, 89, 255, 0.16), transparent 60%);
animation: auroraDrift 22s ease-in-out infinite alternate;
filter: blur(20px);
}
body::after {
background:
linear-gradient(rgba(255, 0, 80, 0.05) 1px, transparent 1px) 0 0 / 48px 48px,
linear-gradient(90deg, rgba(0, 240, 255, 0.05) 1px, transparent 1px) 0 0 / 48px 48px;
mask-image: radial-gradient(ellipse at center, black 30%, transparent 75%);
animation: gridPan 40s linear infinite;
}
@keyframes auroraDrift {
0% { transform: translate(0, 0) scale(1); }
100% { transform: translate(-3%, 2%) scale(1.06); }
}
@keyframes gridPan {
from { background-position: 0 0, 0 0; }
to { background-position: 480px 480px, 480px 480px; }
}
.scanlines {
position: fixed; inset: 0; pointer-events: none; z-index: 1;
background: repeating-linear-gradient(to bottom, rgba(255,255,255,0.012) 0 1px, transparent 1px 3px);
mix-blend-mode: overlay;
}
.vignette {
position: fixed; inset: 0; pointer-events: none; z-index: 2;
box-shadow: inset 0 0 220px rgba(0, 0, 0, 0.85);
}
#particle-canvas {
position: fixed; inset: 0; pointer-events: none; z-index: 1; opacity: 0.55;
}
.app-container {
position: relative; z-index: 5;
display: grid;
grid-template-columns: 280px 1fr;
width: 100%; height: 100vh;
}
.sidebar {
background: linear-gradient(180deg, rgba(8,8,18,0.92), rgba(8,8,18,0.78));
backdrop-filter: blur(18px) saturate(140%);
-webkit-backdrop-filter: blur(18px) saturate(140%);
border-right: 1px solid var(--panel-edge);
display: flex; flex-direction: column; overflow: hidden;
position: relative;
}
.sidebar::before {
content: ''; position: absolute; top: 0; right: -1px;
width: 1px; height: 100%;
background: linear-gradient(180deg, transparent, var(--red), var(--cyan), transparent);
opacity: 0.7; animation: edgePulse 6s ease-in-out infinite;
}
@keyframes edgePulse {
0%, 100% { opacity: 0.35; } 50% { opacity: 0.95; }
}
.sidebar-header {
padding: 26px 20px 22px;
border-bottom: 1px solid var(--panel-edge);
text-align: center; position: relative;
}
.brand-mark {
width: 64px; height: 64px; margin: 0 auto 12px;
border-radius: 50%;
background: var(--grad-holo);
background-size: 300% 300%;
animation: holoShift 8s linear infinite;
position: relative; display: grid; place-items: center;
box-shadow: 0 0 24px rgba(255, 0, 80, 0.45), inset 0 0 24px rgba(0, 240, 255, 0.25);
}
.brand-mark::after {
content: ''; position: absolute; inset: 4px;
border-radius: 50%;
background: radial-gradient(circle at 50% 35%, #1a1a2e, #050510);
}
.brand-mark span {
position: relative; font-size: 28px; z-index: 2;
filter: drop-shadow(0 0 8px var(--red));
}
.brand-mark svg {
position: relative;
z-index: 2;
width: 40px;
height: 40px;
filter: drop-shadow(0 0 10px rgba(255, 0, 80, 0.7))
drop-shadow(0 0 18px rgba(0, 240, 255, 0.35));
animation: markFloat 6s ease-in-out infinite;
}
@keyframes markFloat {
0%, 100% { transform: rotate(0deg) scale(1); }
50% { transform: rotate(2deg) scale(1.04); }
}
@keyframes holoShift {
0% { background-position: 0% 50%; }
50% { background-position: 100% 50%; }
100% { background-position: 0% 50%; }
}
.sidebar-header h1 {
margin: 0;
font-family: var(--font-display);
font-weight: 900; font-size: 1.35rem; letter-spacing: 4px;
background: var(--grad-hot);
-webkit-background-clip: text; background-clip: text;
color: transparent; position: relative;
text-shadow: 0 0 18px rgba(255, 0, 80, 0.3);
}
.sidebar-header h1.glitch::before,
.sidebar-header h1.glitch::after {
content: attr(data-text);
position: absolute; top: 0; left: 0; width: 100%; height: 100%;
background: var(--grad-hot);
-webkit-background-clip: text; background-clip: text;
color: transparent; overflow: hidden;
}
.sidebar-header h1.glitch::before { animation: glitchTop 2.4s infinite linear alternate-reverse; }
.sidebar-header h1.glitch::after { animation: glitchBot 3.2s infinite linear alternate-reverse; }
@keyframes glitchTop {
0% { transform: translate(0, 0); clip-path: inset(0 0 80% 0); }
20% { transform: translate(-2px, 1px); clip-path: inset(0 0 70% 0); }
40% { transform: translate(1px, -1px); clip-path: inset(10% 0 60% 0); }
60% { transform: translate(-1px, 1px); clip-path: inset(20% 0 50% 0); }
100% { transform: translate(0, 0); clip-path: inset(0 0 80% 0); }
}
@keyframes glitchBot {
0% { transform: translate(0, 0); clip-path: inset(80% 0 0 0); }
25% { transform: translate(2px, -1px); clip-path: inset(70% 0 0 0); }
50% { transform: translate(-1px, 1px); clip-path: inset(60% 0 10% 0); }
75% { transform: translate(1px, -1px); clip-path: inset(50% 0 20% 0); }
100% { transform: translate(0, 0); clip-path: inset(80% 0 0 0); }
}
.sidebar-header .subtitle {
font-family: var(--font-mono); font-size: 0.65rem;
color: var(--text-mute); margin-top: 10px;
letter-spacing: 3px; text-transform: uppercase;
}
.status-strip {
margin-top: 14px;
display: flex; gap: 8px; justify-content: center;
font-family: var(--font-mono); font-size: 0.55rem;
color: var(--text-mute); letter-spacing: 1.5px;
}
.status-dot { display: inline-flex; align-items: center; gap: 5px; }
.status-dot::before {
content: ''; width: 6px; height: 6px; border-radius: 50%;
background: var(--green); box-shadow: 0 0 10px var(--green);
animation: pulse 1.5s ease-in-out infinite;
}
.status-dot.warn::before { background: var(--amber); box-shadow: 0 0 10px var(--amber); }
@keyframes pulse {
0%, 100% { opacity: 1; transform: scale(1); }
50% { opacity: 0.4; transform: scale(0.85); }
}
.nav-section-title {
padding: 18px 16px 8px;
font-family: var(--font-mono); font-size: 0.6rem;
color: var(--text-dim);
letter-spacing: 2px; text-transform: uppercase;
display: flex; align-items: center; gap: 8px;
}
.nav-section-title::after {
content: ''; flex: 1; height: 1px;
background: linear-gradient(90deg, var(--panel-edge), transparent);
}
.sidebar-nav {
flex: 1; overflow-y: auto;
padding: 6px 10px 16px;
display: flex; flex-direction: column; gap: 3px;
scrollbar-width: thin; scrollbar-color: var(--red) transparent;
}
.sidebar-nav::-webkit-scrollbar { width: 4px; }
.sidebar-nav::-webkit-scrollbar-thumb {
background: linear-gradient(180deg, var(--red), var(--cyan));
border-radius: 4px;
}
.tab-btn {
display: flex; align-items: center; gap: 12px;
padding: 11px 14px;
background: transparent;
border: 1px solid transparent; border-left: 2px solid transparent;
border-radius: var(--radius-sm);
color: var(--text-mute);
font-family: var(--font-ui);
font-size: 0.78rem; font-weight: 500; letter-spacing: 1.2px;
text-align: left; cursor: pointer;
transition: var(--transition);
position: relative; overflow: hidden;
}
.tab-btn > span:first-child {
font-size: 1.05rem; width: 22px; text-align: center;
filter: grayscale(0.4); transition: var(--transition);
}
.tab-btn:hover {
color: var(--text);
border-color: var(--panel-edge);
background: rgba(255, 0, 80, 0.05);
transform: translateX(2px);
}
.tab-btn:hover > span:first-child { filter: grayscale(0) drop-shadow(0 0 4px var(--red)); }
.tab-btn.active {
color: #fff; border-left-color: var(--red);
background: linear-gradient(90deg, rgba(255, 0, 80, 0.18), rgba(255, 0, 80, 0.02) 80%);
box-shadow: inset 0 0 18px rgba(255, 0, 80, 0.08);
}
.tab-btn.active > span:first-child { filter: grayscale(0) drop-shadow(0 0 6px var(--red)); }
.tab-btn.active::after {
content: ''; position: absolute; right: 10px; top: 50%;
width: 4px; height: 4px;
background: var(--red); border-radius: 50%;
box-shadow: 0 0 8px var(--red);
transform: translateY(-50%); animation: pulse 1.4s ease-in-out infinite;
}
.tab-btn .new-badge {
margin-left: auto;
padding: 2px 6px;
font-family: var(--font-mono); font-size: 0.55rem; font-weight: 700; letter-spacing: 1px;
background: var(--grad-cool); color: #000;
border-radius: var(--radius-pill);
box-shadow: 0 0 12px rgba(0, 240, 255, 0.5);
}
.nav-premium-btn {
margin: 12px 10px;
padding: 13px 16px;
background: var(--grad-hot); background-size: 200% 200%;
border: 1px solid rgba(255, 255, 255, 0.15);
border-radius: var(--radius-sm);
color: #fff;
font-family: var(--font-display); font-weight: 700; font-size: 0.78rem; letter-spacing: 2px;
cursor: pointer;
box-shadow: 0 0 24px rgba(255, 0, 80, 0.45);
animation: holoShift 5s linear infinite;
transition: var(--transition);
text-align: center;
display: flex; align-items: center; justify-content: center; gap: 8px;
}
.nav-premium-btn:hover {
transform: translateY(-2px) scale(1.02);
box-shadow: 0 0 32px rgba(255, 0, 80, 0.7);
}
.main-content {
display: flex; flex-direction: column;
overflow: hidden; min-width: 0;
}
.topbar {
height: 72px;
background: var(--panel);
backdrop-filter: blur(16px) saturate(140%);
-webkit-backdrop-filter: blur(16px) saturate(140%);
border-bottom: 1px solid var(--panel-edge);
display: flex; align-items: center; padding: 0 28px;
justify-content: space-between;
position: relative;
}
.topbar::after {
content: ''; position: absolute; bottom: -1px; left: 0;
height: 1px; width: 100%;
background: linear-gradient(90deg, transparent, var(--red), var(--cyan), transparent);
opacity: 0.6;
}
.topbar-title {
display: flex; align-items: center; gap: 14px;
font-family: var(--font-display);
font-weight: 800; font-size: 1.05rem; letter-spacing: 3px;
color: #fff;
}
.topbar-title .crosshair {
width: 22px; height: 22px;
border: 1.5px solid var(--red); border-radius: 50%;
position: relative; animation: spin 8s linear infinite;
}
.topbar-title .crosshair::before,
.topbar-title .crosshair::after {
content: ''; position: absolute; background: var(--red);
}
.topbar-title .crosshair::before { top: 50%; left: -4px; right: -4px; height: 1px; transform: translateY(-50%); }
.topbar-title .crosshair::after { left: 50%; top: -4px; bottom: -4px; width: 1px; transform: translateX(-50%); }
@keyframes spin { to { transform: rotate(360deg); } }
.topbar-meta {
display: flex; gap: 22px;
font-family: var(--font-mono);
font-size: 0.7rem; color: var(--text-mute);
letter-spacing: 1.5px;
}
.topbar-meta strong { color: var(--cyan); font-weight: 500; }
.topbar-meta .live-dot {
display: inline-block; width: 6px; height: 6px;
border-radius: 50%;
background: var(--green); box-shadow: 0 0 8px var(--green);
margin-right: 6px; animation: pulse 1.2s ease-in-out infinite;
}
.content-area {
flex: 1; overflow-y: auto; padding: 28px;
scroll-behavior: smooth;
scrollbar-width: thin; scrollbar-color: var(--red) transparent;
}
.content-area::-webkit-scrollbar { width: 8px; }
.content-area::-webkit-scrollbar-track { background: transparent; }
.content-area::-webkit-scrollbar-thumb {
background: linear-gradient(180deg, var(--red), var(--cyan));
border-radius: 4px;
}
.tab-content { display: none; animation: tabEnter 480ms cubic-bezier(0.2, 0.8, 0.2, 1); }
.tab-content.active { display: block; }
@keyframes tabEnter {
0% { opacity: 0; transform: translateY(8px) scale(0.99); filter: blur(4px); }
100% { opacity: 1; transform: translateY(0) scale(1); filter: blur(0); }
}
.hud-panel {
background: var(--panel);
backdrop-filter: blur(18px) saturate(140%);
-webkit-backdrop-filter: blur(18px) saturate(140%);
border: 1px solid var(--panel-edge);
box-shadow: var(--shadow-panel);
padding: 22px; margin-bottom: 22px;
border-radius: var(--radius);
position: relative; overflow: hidden;
transition: var(--transition);
}
.hud-panel::before {
content: ''; position: absolute; inset: 0;
background: var(--grad-panel); opacity: 0.6; pointer-events: none;
}
.hud-panel:hover {
border-color: rgba(255, 255, 255, 0.15);
transform: translateY(-2px);
box-shadow: 0 22px 50px -20px rgba(255, 0, 80, 0.35), var(--shadow-panel);
}
.hud-panel .bracket {
position: absolute; width: 14px; height: 14px;
border: 1.5px solid var(--red);
pointer-events: none; opacity: 0.6;
}
.hud-panel .bracket.tl { top: 6px; left: 6px; border-right: 0; border-bottom: 0; }
.hud-panel .bracket.tr { top: 6px; right: 6px; border-left: 0; border-bottom: 0; }
.hud-panel .bracket.bl { bottom: 6px; left: 6px; border-right: 0; border-top: 0; }
.hud-panel .bracket.br { bottom: 6px; right: 6px; border-left: 0; border-top: 0; }
.panel-title {
font-family: var(--font-display);
font-weight: 700; font-size: 0.9rem; letter-spacing: 2px;
color: var(--text); margin: 0 0 16px;
display: flex; align-items: center; gap: 10px;
text-transform: uppercase;
}
.panel-title::before {
content: ''; width: 3px; height: 14px;
background: var(--grad-hot); border-radius: 2px;
box-shadow: 0 0 10px var(--red);
}
.search-area {
display: flex; gap: 10px; margin-bottom: 18px;
flex-wrap: wrap; align-items: stretch;
}
input, select, textarea {
flex: 1; min-width: 180px;
padding: 13px 18px;
background: rgba(5, 5, 14, 0.7);
border: 1px solid var(--panel-edge);
border-radius: var(--radius-sm);
color: var(--text);
font-family: var(--font-mono);
font-size: 0.88rem; letter-spacing: 0.5px;
outline: none; transition: var(--transition);
}
input::placeholder { color: var(--text-dim); font-family: var(--font-mono); letter-spacing: 1px; }
input:focus, select:focus, textarea:focus {
border-color: var(--red);
background: rgba(5, 5, 14, 0.95);
box-shadow: 0 0 0 2px rgba(255, 0, 80, 0.15), 0 0 24px rgba(255, 0, 80, 0.25);
}
.glitch-btn {
padding: 13px 26px;
background: transparent;
color: var(--cyan);
border: 1px solid var(--cyan);
border-radius: var(--radius-sm);
font-family: var(--font-display);
font-weight: 700; font-size: 0.85rem; letter-spacing: 2px;
cursor: pointer; position: relative; overflow: hidden;
transition: var(--transition); text-transform: uppercase;
box-shadow: inset 0 0 14px rgba(0, 240, 255, 0.1);
z-index: 1;
}
.glitch-btn::before {
content: ''; position: absolute; inset: 0;
background: var(--grad-cool);
transform: scaleX(0); transform-origin: left;
transition: var(--transition); z-index: -1;
}
.glitch-btn:hover::before { transform: scaleX(1); }
.glitch-btn:hover {
color: #000; border-color: transparent;
box-shadow: 0 0 28px rgba(0, 240, 255, 0.55), 0 0 8px rgba(0, 240, 255, 0.35);
transform: translateY(-1px);
}
.glitch-btn:active { transform: translateY(0); }
.glitch-btn.hot {
color: var(--red); border-color: var(--red);
box-shadow: inset 0 0 14px rgba(255, 0, 80, 0.1);
}
.glitch-btn.hot::before { background: var(--grad-hot); }
.glitch-btn.hot:hover { box-shadow: 0 0 28px rgba(255, 0, 80, 0.55); }
.glitch-btn.ok { color: var(--green); border-color: var(--green); }
.glitch-btn.ok::before { background: var(--grad-ok); }
.glitch-btn:disabled { opacity: 0.35; cursor: not-allowed; pointer-events: none; }
.ctrl-btn {
background: rgba(5, 5, 14, 0.6);
color: var(--text);
border: 1px solid var(--panel-edge);
padding: 10px 18px; border-radius: var(--radius-sm);
cursor: pointer;
font-family: var(--font-mono);
font-size: 0.78rem; letter-spacing: 1.5px;
transition: var(--transition);
height: 44px; text-transform: uppercase;
}
.ctrl-btn:hover { background: rgba(255, 0, 80, 0.08); border-color: var(--red); }
.ctrl-btn.stop {
color: var(--red);
border-color: rgba(255, 0, 80, 0.45);
background: rgba(255, 0, 80, 0.05);
}
.ctrl-btn.stop:hover { background: var(--red); color: #fff; box-shadow: 0 0 18px rgba(255, 0, 80, 0.5); }
.ctrl-btn.download {
color: var(--green);
border-color: rgba(0, 255, 140, 0.45);
background: rgba(0, 255, 140, 0.05);
}
.ctrl-btn.download:hover { background: var(--green); color: #000; box-shadow: 0 0 18px rgba(0, 255, 140, 0.5); }
.ctrl-btn:disabled { opacity: 0.35; cursor: not-allowed; }
.controls {
display: flex; gap: 12px; margin-bottom: 18px;
flex-wrap: wrap;
padding-top: 14px; border-top: 1px solid var(--panel-edge);
}
.results, .results-grid {
display: grid;
grid-template-columns: repeat(auto-fill, minmax(260px, 1fr));
gap: 14px;
}
.result-card {
background: linear-gradient(160deg, rgba(20, 20, 36, 0.85), rgba(8, 8, 18, 0.85));
border: 1px solid var(--panel-edge);
border-radius: var(--radius);
padding: 18px;
position: relative; overflow: hidden;
transform-style: preserve-3d;
transition: var(--transition);
will-change: transform;
}
.result-card::before {
content: ''; position: absolute;
top: -1px; left: -1px; right: -1px; height: 2px;
background: var(--grad-hot); opacity: 0.7;
}
.result-card::after {
content: ''; position: absolute; inset: 0;
background: radial-gradient(400px circle at var(--mx, 50%) var(--my, 50%), rgba(255, 0, 80, 0.12), transparent 40%);
pointer-events: none; opacity: 0; transition: var(--transition);
}
.result-card:hover {
transform: translateY(-4px);
border-color: rgba(255, 255, 255, 0.18);
box-shadow: 0 18px 40px -16px rgba(255, 0, 80, 0.35);
}
.result-card:hover::after { opacity: 1; }
.result-card .card-title {
font-family: var(--font-display);
font-weight: 700; font-size: 0.9rem; letter-spacing: 1px;
color: var(--text); margin: 0 0 6px;
}
.result-card .card-url {
font-family: var(--font-mono);
font-size: 0.72rem; color: var(--cyan);
text-decoration: none; word-break: break-all;
display: block; margin-bottom: 6px;
}
.result-card .card-url:hover { text-decoration: underline; }
.status-badge {
display: inline-flex; align-items: center; gap: 5px;
padding: 3px 10px;
border: 1px solid currentColor;
border-radius: var(--radius-pill);
font-family: var(--font-mono);
font-size: 0.62rem; letter-spacing: 1.5px;
text-transform: uppercase;
background: rgba(0, 0, 0, 0.4);
color: var(--text-mute);
}
.status-badge::before {
content: ''; width: 5px; height: 5px; border-radius: 50%;
background: currentColor; box-shadow: 0 0 6px currentColor;
}
.status-badge.verified { color: var(--green); }
.status-badge.check { color: var(--amber); animation: pulse 1.2s ease-in-out infinite; }
.status-badge.false { color: var(--red); }
.status-badge.critical { color: var(--red); }
.status-badge.high { color: #ff5e2b; }
.status-badge.medium { color: var(--amber); }
.status-badge.low { color: var(--green); }
.status-badge.clean { color: var(--text-dim); }
.status-badge.info { color: var(--cyan); }
[id$="-status"], .status {
font-family: var(--font-mono);
font-size: 0.78rem; letter-spacing: 1px;
color: var(--text-mute);
padding: 8px 0; min-height: 24px;
display: flex; align-items: center; gap: 8px;
}
[id$="-status"]:not(:empty)::before, .status:not(:empty)::before {
content: '>'; color: var(--red); font-weight: 700;
}
.score-shell {
display: flex; flex-direction: column; gap: 6px;
padding: 14px;
border: 1px solid var(--panel-edge);
border-radius: var(--radius);
background: rgba(5, 5, 14, 0.55);
position: relative; overflow: hidden;
}
.score-bar {
height: 14px;
background: rgba(255, 255, 255, 0.04);
border-radius: var(--radius-pill);
overflow: hidden; position: relative;
}
.score-fill {
height: 100%;
background: var(--grad-warn);
background-size: 200% 100%;
border-radius: var(--radius-pill);
transition: width 1.4s cubic-bezier(0.2, 0.8, 0.2, 1);
animation: gaugeShift 4s linear infinite;
box-shadow: 0 0 14px currentColor;
position: relative;
}
.score-fill::after {
content: ''; position: absolute; inset: 0;
background: linear-gradient(90deg, transparent, rgba(255,255,255,0.3), transparent);
animation: scoreShine 2.4s linear infinite;
}
@keyframes gaugeShift {
0%, 100% { background-position: 0% 0; }
50% { background-position: 100% 0; }
}
@keyframes scoreShine {
from { transform: translateX(-100%); }
to { transform: translateX(100%); }
}
.score-meta {
display: flex; justify-content: space-between;
font-family: var(--font-mono);
font-size: 0.72rem; letter-spacing: 1.5px;
color: var(--text-mute);
}
.score-meta strong { font-family: var(--font-display); font-size: 1.05rem; color: var(--text); }
.dork-wrapper {
display: flex; align-items: center;
background: rgba(5, 5, 14, 0.6);
border: 1px solid var(--panel-edge);
border-radius: var(--radius-sm);
overflow: hidden; height: 44px;
}
.dork-select {
background: transparent; color: var(--text);
border: none; padding: 0 14px;
font-family: var(--font-mono);
font-size: 0.78rem; letter-spacing: 1px;
outline: none; cursor: pointer;
min-width: auto;
}
.dork-select option { background: var(--bg-1); color: var(--text); }
.dork-btn {
background: rgba(0, 240, 255, 0.1);
color: var(--cyan); border: none;
border-left: 1px solid var(--panel-edge);
padding: 0 16px; height: 100%;
cursor: pointer;
font-family: var(--font-display);
font-weight: 700; font-size: 0.74rem; letter-spacing: 1.5px;
transition: var(--transition);
}
.dork-btn:hover { background: var(--cyan); color: #000; }
.images-container {
display: flex; justify-content: center; gap: 18px;
margin-bottom: 22px; min-height: 180px;
perspective: 1200px; flex-wrap: wrap;
}
.image-wrapper {
position: relative;
width: 190px; height: 190px;
border-radius: var(--radius);
overflow: hidden;
transform-style: preserve-3d;
transition: var(--transition-slow);
border: 1px solid var(--panel-edge);
box-shadow: 0 12px 30px -12px rgba(0, 0, 0, 0.7);
cursor: pointer;
}
.image-wrapper::after {
content: ''; position: absolute; inset: 0;
background: linear-gradient(160deg, transparent 40%, rgba(255, 0, 80, 0.18));
pointer-events: none;
}
.image-wrapper:hover {
transform: translateY(-6px) rotateY(8deg) rotateX(-4deg) scale(1.04);
border-color: var(--red);
box-shadow: 0 24px 48px -12px rgba(255, 0, 80, 0.5);
z-index: 10;
}
.captured-image {
width: 100%; height: 100%;
object-fit: cover; background: #000;
transition: var(--transition);
}
.image-wrapper:hover .captured-image { transform: scale(1.06); filter: contrast(1.1); }
.btn-deep, .dl-btn {
position: absolute;
background: rgba(0, 0, 0, 0.75);
color: var(--cyan);
border: 1px solid var(--cyan);
padding: 5px 10px;
font-family: var(--font-mono);
font-size: 0.65rem; letter-spacing: 1px;
cursor: pointer;
border-radius: var(--radius-sm);
opacity: 0; transition: var(--transition);
}
.image-wrapper:hover .btn-deep,
.image-wrapper:hover .dl-btn { opacity: 1; }
.btn-deep { bottom: 8px; left: 8px; }
.dl-btn { bottom: 8px; right: 8px; color: var(--green); border-color: var(--green); }
.deepModal {
position: fixed; inset: 0;
background: rgba(2, 2, 8, 0.92);
backdrop-filter: blur(14px);
-webkit-backdrop-filter: blur(14px);
z-index: 1000;
display: none;
flex-direction: column;
padding: 28px;
}
.deepModal.active { display: flex; animation: tabEnter 320ms ease-out; }
.deepModal h3 {
font-family: var(--font-display);
letter-spacing: 3px; color: var(--cyan); margin: 0 0 18px;
}
.deep-grid {
flex: 1; display: grid;
grid-template-columns: repeat(4, 1fr); gap: 16px;
overflow: hidden;
}
.deep-col {
background: var(--panel);
border: 1px solid var(--panel-edge);
border-radius: var(--radius);
padding: 14px; overflow-y: auto;
}
.deep-col h4 {
margin: 0 0 10px;
font-family: var(--font-display);
font-size: 0.78rem; letter-spacing: 2px;
color: var(--red);
}
.deep-col img {
width: 100%;
border-radius: var(--radius-sm);
margin-bottom: 8px;
border: 1px solid var(--panel-edge);
transition: var(--transition);
}
.deep-col img:hover { transform: scale(1.02); border-color: var(--cyan); }
.target-scan {
color: var(--green); font-family: var(--font-mono);
letter-spacing: 1.5px; animation: pulse 1s ease-in-out infinite;
}
.reveal {
opacity: 0; transform: translateY(14px);
transition: opacity 600ms ease, transform 600ms cubic-bezier(0.2, 0.8, 0.2, 1);
}
.reveal.visible { opacity: 1; transform: translateY(0); }
.typing::after {
content: '_'; color: var(--red);
animation: caretBlink 1s steps(2) infinite;
}
@keyframes caretBlink { 50% { opacity: 0; } }
#boot {
position: fixed; inset: 0;
background: #03030a;
z-index: 5000;
display: flex; flex-direction: column; align-items: center; justify-content: center;
gap: 22px;
font-family: var(--font-mono); color: var(--green);
transition: opacity 600ms ease, visibility 0s linear 600ms;
}
#boot.done { opacity: 0; visibility: hidden; }
#boot .boot-logo {
font-family: var(--font-display);
font-size: 2.4rem; letter-spacing: 8px;
background: var(--grad-hot);
-webkit-background-clip: text; background-clip: text; color: transparent;
filter: drop-shadow(0 0 18px rgba(255, 0, 80, 0.5));
animation: pulse 1.6s ease-in-out infinite;
}
#boot .boot-bar {
width: min(420px, 60vw); height: 4px;
border-radius: var(--radius-pill);
background: rgba(255, 255, 255, 0.06); overflow: hidden;
}
#boot .boot-bar > div {
height: 100%; width: 0;
background: var(--grad-cool);
animation: bootLoad 1.6s cubic-bezier(0.65, 0, 0.35, 1) forwards;
}
@keyframes bootLoad { to { width: 100%; } }
#boot .boot-lines {
font-size: 0.74rem; letter-spacing: 1.5px;
color: var(--text-mute); min-height: 110px;
text-align: left; width: min(420px, 60vw);
}
#boot .boot-lines span { display: block; opacity: 0; }
#boot .boot-lines span.show { opacity: 1; transition: opacity 200ms ease; }
#boot .boot-lines .ok { color: var(--green); }
#boot .boot-lines .err { color: var(--amber); }
.row { display: flex; gap: 12px; flex-wrap: wrap; align-items: center; }
.col { display: flex; flex-direction: column; gap: 10px; }
.spread { display: flex; justify-content: space-between; align-items: center; gap: 12px; flex-wrap: wrap; }
.mono { font-family: var(--font-mono); }
.dim { color: var(--text-mute); }
.bright { color: var(--text); }
.h-cyan { color: var(--cyan); }
.h-red { color: var(--red); }
.h-green { color: var(--green); }
.h-amber { color: var(--amber); }
.hide { display: none !important; }
.tag {
display: inline-block;
padding: 3px 9px;
background: rgba(0, 240, 255, 0.08);
border: 1px solid rgba(0, 240, 255, 0.3);
border-radius: var(--radius-sm);
color: var(--cyan);
font-family: var(--font-mono);
font-size: 0.66rem; letter-spacing: 1px;
margin: 2px;
}
.tag.hot { background: rgba(255, 0, 80, 0.08); border-color: rgba(255, 0, 80, 0.35); color: var(--red); }
.tag.ok { background: rgba(0, 255, 140, 0.08); border-color: rgba(0, 255, 140, 0.35); color: var(--green); }
.tag.warn{ background: rgba(255, 184, 0, 0.08); border-color: rgba(255, 184, 0, 0.35); color: var(--amber); }
.mini-bar { height: 6px; background: rgba(255,255,255,0.04); border-radius: var(--radius-pill); overflow: hidden; margin-top: 6px; }
.mini-bar > div { height: 100%; background: var(--grad-cool); border-radius: var(--radius-pill); transition: width 1s ease; }
@media (max-width: 980px) {
.app-container { grid-template-columns: 1fr; }
.sidebar { position: fixed; top: 0; left: -300px; bottom: 0; width: 280px; z-index: 200; transition: left var(--transition); }
.sidebar.open { left: 0; }
}
.leaflet-popup-content-wrapper {
background: var(--panel-2) !important;
color: var(--text) !important;
border: 1px solid var(--panel-edge) !important;
border-radius: var(--radius) !important;
font-family: var(--font-mono) !important;
}
.leaflet-popup-tip { background: var(--panel-2) !important; }
.leaflet-container { background: var(--bg-1) !important; }
================================================
FILE: the_big_brother/gui/static/index.html
================================================
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>THE BIG BROTHER · V5.0 // GOD'S EYE PROTOCOL</title>
<link rel="stylesheet" href="https://unpkg.com/leaflet@1.9.4/dist/leaflet.css">
<link rel="stylesheet" href="3.css?v=7.0.0">
</head>
<body>
<!-- ============================================================
BOOT OVERLAY
============================================================ -->
<div id="boot">
<div class="boot-logo">THE BIG BROTHER</div>
<div class="boot-bar"><div></div></div>
<div class="boot-lines" id="boot-lines"></div>
</div>
<!-- ============================================================
AMBIENT BACKDROP LAYERS
============================================================ -->
<canvas id="particle-canvas"></canvas>
<div class="scanlines"></div>
<div class="vignette"></div>
<!-- ============================================================
APP SHELL
============================================================ -->
<div class="app-container">
<!-- ===== SIDEBAR ===== -->
<aside class="sidebar">
<div class="sidebar-header">
<div class="brand-mark">
<svg viewBox="0 0 64 64" xmlns="http://www.w3.org/2000/svg" aria-hidden="true">
<defs>
<linearGradient id="bm-edge" x1="0" y1="0" x2="64" y2="64" gradientUnits="userSpaceOnUse">
<stop offset="0%" stop-color="#ff0050"/>
<stop offset="55%" stop-color="#a259ff"/>
<stop offset="100%" stop-color="#00f0ff"/>
</linearGradient>
<linearGradient id="bm-fill" x1="0" y1="0" x2="64" y2="64" gradientUnits="userSpaceOnUse">
<stop offset="0%" stop-color="#ff0050" stop-opacity="0.95"/>
<stop offset="100%" stop-color="#a259ff" stop-opacity="0.9"/>
</linearGradient>
<radialGradient id="bm-core" cx="0.5" cy="0.5" r="0.5">
<stop offset="0%" stop-color="#ffffff" stop-opacity="1"/>
<stop offset="60%" stop-color="#00f0ff" stop-opacity="0.9"/>
<stop offset="100%" stop-color="#00f0ff" stop-opacity="0"/>
</radialGradient>
</defs>
<!-- crosshair ticks -->
<g stroke="url(#bm-edge)" stroke-width="1.6" stroke-linecap="round">
<path d="M32 3 L32 9"/>
<path d="M32 55 L32 61"/>
<path d="M3 32 L9 32"/>
<path d="M55 32 L61 32"/>
</g>
<!-- outer diamond -->
<path d="M32 7 L57 32 L32 57 L7 32 Z"
fill="none" stroke="url(#bm-edge)" stroke-width="1.8" stroke-linejoin="miter"/>
<!-- inner diamond -->
<path d="M32 18 L46 32 L32 46 L18 32 Z"
fill="url(#bm-fill)" opacity="0.92"/>
<!-- core glow -->
<circle cx="32" cy="32" r="12" fill="url(#bm-core)" opacity="0.65"/>
<!-- inner accent line -->
<path d="M22 32 L42 32" stroke="#ffffff" stroke-width="0.8" opacity="0.55"/>
<!-- center diamond pip -->
<path d="M32 28 L36 32 L32 36 L28 32 Z" fill="#ffffff" opacity="0.95"/>
</svg>
</div>
<h1 class="glitch" data-text="BIG BROTHER">BIG BROTHER</h1>
<div class="subtitle">V5 · GOD'S EYE PROTOCOL</div>
<div class="status-strip">
<span class="status-dot">CORE</span>
<span class="status-dot">NEURAL</span>
<span class="status-dot">UPLINK</span>
</div>
</div>
<nav class="sidebar-nav" id="main-nav">
<div class="nav-section-title">Synthesis</div>
<button class="tab-btn" onclick="switchTab('tab-analyst', 'AI ANALYST')">
<span>🤖</span> AI ANALYST <span class="new-badge">NEW</span>
</button>
<div class="nav-section-title">Identity</div>
<button class="tab-btn active" onclick="switchTab('tab-profiler', 'TARGET PROFILER')">
<span>🔍</span> PROFILER
</button>
<button class="tab-btn" onclick="switchTab('tab-phantom', 'PHANTOM IDENTITY')">
<span>👻</span> PHANTOM ID
</button>
<button class="tab-btn" onclick="switchTab('tab-breach', 'BREACH VAULT')">
<span>🔓</span> BREACH VAULT
</button>
<button class="tab-btn" onclick="switchTab('tab-footprint', 'DIGITAL FOOTPRINT')">
<span>👣</span> FOOTPRINT
</button>
<button class="tab-btn" onclick="switchTab('tab-mailtracer', 'MAIL TRACER')">
<span>📨</span> MAIL TRACER <span class="new-badge">NEW</span>
</button>
<button class="tab-btn" onclick="switchTab('tab-codehunter', 'CODE HUNTER')">
<span>🐙</span> CODE HUNTER <span class="new-badge">NEW</span>
</button>
<div class="nav-section-title">Intel</div>
<button class="tab-btn" onclick="switchTab('tab-sigint', 'SIGINT SWEEP')">
<span>📡</span> SIGINT SWEEP
</button>
<button class="tab-btn" onclick="switchTab('tab-shadowmap', 'SHADOW MAP')">
<span>🗺️</span> SHADOW MAP
</button>
<button class="tab-btn" onclick="switchTab('tab-paste', 'PASTE DRAGNET')">
<span>📋</span> PASTE DRAGNET <span class="new-badge">NEW</span>
</button>
<button class="tab-btn" onclick="switchTab('tab-darkwatch', 'DARK WEB WATCH')">
<span>🧅</span> DARK WEB
</button>
<button class="tab-btn" onclick="switchTab('tab-wayback', 'WAYBACK SPECTRE')">
<span>🕰️</span> WAYBACK <span class="new-badge">NEW</span>
</button>
<div class="nav-section-title">Infrastructure</div>
<button class="tab-btn" onclick="switchTab('tab-oracle', 'DOMAIN ORACLE')">
<span>🌐</span> DOMAIN ORACLE <span class="new-badge">NEW</span>
</button>
<button class="tab-btn" onclick="switchTab('tab-network', 'NETWORK MAPPER')">
<span>🕸️</span> NET SCAN
</button>
<button class="tab-btn" onclick="switchTab('tab-ssl', 'SSL SENTINEL')">
<span>🔒</span> SSL
</button>
<button class="tab-btn" onclick="switchTab('tab-crypto', 'CRYPTO ANALYZER')">
<span>🪙</span> CRYPTO
</button>
<div class="nav-section-title">Media / Geo</div>
<button class="tab-btn" onclick="switchTab('tab-exif', 'EXIF X-RAY')">
<span>📸</span> EXIF
</button>
<button class="tab-btn" onclick="switchTab('tab-dorks', 'DORK STUDIO')">
<span>🛠️</span> DORKS
</button>
<button class="tab-btn" onclick="switchTab('tab-geoint', 'GEOINT SPY')">
<span>🛰️</span> GEOINT
</button>
<button class="tab-btn" onclick="switchTab('tab-flight', 'SKY RADAR')">
<span>✈️</span> SKY RADAR
</button>
</nav>
<button class="nav-premium-btn" onclick="switchTab('tab-premium', 'PREMIUM CATALOG')">
🔥 PREMIUM CATALOG
</button>
</aside>
<!-- ===== MAIN COLUMN ===== -->
<main class="main-content">
<header class="topbar">
<div class="topbar-title">
<div class="crosshair"></div>
<span id="active-module-title">TARGET PROFILER</span>
</div>
<div class="topbar-meta">
<span><span class="live-dot"></span><strong>LIVE</strong></span>
<span>SESSION <strong id="session-id">—</strong></span>
<span><strong id="clock">UTC 00:00:00</strong></span>
</div>
</header>
<div class="content-area" id="content-area">
<!-- ============================================================
TAB: AI ANALYST (NEW)
============================================================ -->
<div id="tab-analyst" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">AI Analyst · Cross-Module Synthesis</div>
<div class="dim mono" style="font-size:0.78rem; margin-bottom:14px;">
Auto-detects target type (email · domain · IP · username), fans out to every relevant module in parallel, and produces a unified risk profile with a single threat score.
</div>
<div class="search-area">
<input type="text" id="analyst-input" placeholder="ENTER TARGET (email, domain, ip, or @username)" onkeydown="if(event.key==='Enter') runAnalyst()">
<select id="analyst-mode" class="dork-select" style="min-width:120px;">
<option value="auto">AUTO</option>
<option value="email">EMAIL</option>
<option value="domain">DOMAIN</option>
<option value="ip">IP</option>
<option value="username">USERNAME</option>
</select>
<button onclick="runAnalyst()" class="glitch-btn hot">EXECUTE</button>
</div>
<div id="analyst-status"></div>
</div>
<div id="analyst-summary" class="hide"></div>
<div id="analyst-findings" class="hide"></div>
<div id="analyst-modules" class="hide"></div>
</div>
<!-- ============================================================
TAB: TARGET PROFILER
============================================================ -->
<div id="tab-profiler" class="tab-content active">
<div id="images-panel" class="hud-panel reveal hide">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="spread" style="margin-bottom:14px;">
<div class="panel-title" style="margin:0;">Biometric Capture · Visual Intel</div>
<span id="images-count" class="status-badge info">0 IMAGES</span>
</div>
<div class="dim mono" style="font-size:0.74rem; margin-bottom:14px;">Auto-pulled from DuckDuckGo · Bing · Google Images · click any thumb for reverse-image search across 4 engines</div>
<div id="images-container" class="images-container"></div>
</div>
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Target Profiler</div>
<div class="search-area">
<input type="text" id="username" placeholder="ENTER TARGET IDENTIFIER..."
onkeydown="if(event.key==='Enter') startScan()">
<button onclick="startScan()" id="btn-scan" class="glitch-btn hot">INITIATE</button>
</div>
<div class="controls">
<button id="btn-stop" class="ctrl-btn stop" onclick="stopScan()" disabled>[ X ] ABORT</button>
<button id="btn-download" class="ctrl-btn download" onclick="downloadReport()" disabled>[ ↓ ] EXPORT CSV</button>
<div class="dork-wrapper">
<select id="dork-select" class="dork-select">
<option value="linkedin">LINKEDIN</option>
<option value="instagram">INSTAGRAM</option>
<option value="twitter">TWITTER</option>
<option value="facebook">FACEBOOK</option>
<option value="tiktok">TIKTOK</option>
<option value="pinterest">PINTEREST</option>
<option value="github">GITHUB</option>
<option value="gitlab">GITLAB</option>
<option value="stackoverflow">STACKOVERFLOW</option>
<option value="pastebin">PASTEBIN</option>
<option value="reddit">REDDIT</option>
<option value="pdf">FILETYPE: PDF</option>
<option value="doc">FILETYPE: DOC</option>
<option value="txt">FILETYPE: TXT</option>
<option value="intext">INTEXT SCAN</option>
<option value="intitle">INTITLE SCAN</option>
<option value="inurl">INURL SCAN</option>
<option value="password">BREACH CHECK</option>
<option value="email">EMAIL CHECK</option>
<option value="phone">PHONE CHECK</option>
</select>
<button class="dork-btn" onclick="executeDork()">DEPLOY ›</button>
</div>
</div>
<div id="status">SYSTEM STANDBY.</div>
</div>
<div id="results" class="results"></div>
</div>
<!-- ============================================================
TAB: PHANTOM ID
============================================================ -->
<div id="tab-phantom" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Phantom Identity</div>
<div class="search-area">
<input type="text" id="phantom-input" placeholder="ENTER TARGET USERNAME" onkeydown="if(event.key==='Enter') scanPhantom()">
<button onclick="scanPhantom()" class="glitch-btn hot">HUNT</button>
</div>
<div class="score-shell" style="margin-top:14px;">
<div class="score-meta">
<span>EXPOSURE SCORE</span>
<strong id="phantom-score-text">STANDBY</strong>
</div>
<div class="score-bar"><div id="phantom-score-bar" class="score-fill" style="width:0%;"></div></div>
</div>
<div id="phantom-status">WAITING FOR TARGET.</div>
</div>
<div id="phantom-results" class="results-grid" style="display:block;">
<div id="phantom-meta" class="hide hud-panel" style="margin-bottom:18px;">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="row" style="align-items:center;">
<img id="phantom-avatar" src="" style="width:84px; height:84px; border-radius:50%; border:2px solid var(--cyan); box-shadow:0 0 22px rgba(0,240,255,0.5);">
<div id="phantom-cats" style="display:flex; gap:6px; flex-wrap:wrap;"></div>
</div>
</div>
<div id="phantom-grid" class="results"></div>
</div>
</div>
<!-- ============================================================
TAB: BREACH VAULT
============================================================ -->
<div id="tab-breach" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Breach Vault</div>
<div class="search-area">
<input type="text" id="breach-input" placeholder="ENTER EMAIL OR PASSWORD" onkeydown="if(event.key==='Enter') scanBreach()">
<select id="breach-type" class="dork-select" style="min-width:160px;">
<option value="email">EMAIL</option>
<option value="password">PASSWORD (HASHED)</option>
</select>
<button onclick="scanBreach()" class="glitch-btn hot">AUDIT</button>
</div>
<div id="breach-status">READY TO CHECK LEAKS.</div>
</div>
<div id="breach-summary" style="margin-bottom:18px;"></div>
<div id="breach-results" class="results"></div>
<div id="paste-dump-results" style="margin-top:18px; display:grid; gap:10px;"></div>
</div>
<!-- ============================================================
TAB: FOOTPRINT
============================================================ -->
<div id="tab-footprint" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Digital Footprint</div>
<div class="search-area">
<input type="text" id="footprint-input" placeholder="ENTER EMAIL OR PHONE (e.g. +1415...)">
<select id="footprint-type" class="dork-select" style="min-width:140px;">
<option value="email">EMAIL</option>
<option value="phone">PHONE</option>
</select>
<button onclick="scanFootprint()" class="glitch-btn">TRACK</button>
</div>
<div id="footprint-status">READY TO TRACK.</div>
</div>
<div id="footprint-results" class="results-grid" style="display:block;"></div>
</div>
<!-- ============================================================
TAB: MAIL TRACER (NEW)
============================================================ -->
<div id="tab-mailtracer" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Mail Tracer · Email Forensics</div>
<div class="dim mono" style="font-size:0.76rem; margin-bottom:12px;">MX validity · SPF/DMARC posture · disposable/role detection · gravatar lookup · trust score</div>
<div class="search-area">
<input type="text" id="mail-input" placeholder="ENTER EMAIL (e.g. someone@example.com)" onkeydown="if(event.key==='Enter') scanMail()">
<button onclick="scanMail()" class="glitch-btn">TRACE</button>
</div>
<div id="mail-status">AWAITING TARGET.</div>
</div>
<div id="mail-results"></div>
</div>
<!-- ============================================================
TAB: CODE HUNTER (NEW)
============================================================ -->
<div id="tab-codehunter" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Code Hunter · GitHub OSINT</div>
<div class="dim mono" style="font-size:0.76rem; margin-bottom:12px;">Profile · repos · commit-email harvesting · language stats · activity heatmap</div>
<div class="search-area">
<input type="text" id="code-input" placeholder="ENTER GITHUB USERNAME (without @)" onkeydown="if(event.key==='Enter') scanCode()">
<button onclick="scanCode()" class="glitch-btn">HUNT</button>
</div>
<div id="code-status">READY.</div>
</div>
<div id="code-results"></div>
</div>
<!-- ============================================================
TAB: SIGINT SWEEP
============================================================ -->
<div id="tab-sigint" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Sigint Sweep</div>
<div class="search-area">
<input type="text" id="sigint-input" placeholder="ENTER BRAND, PERSON, OR KEYWORD" onkeydown="if(event.key==='Enter') scanSigint()">
<button onclick="scanSigint()" class="glitch-btn">SWEEP</button>
</div>
<div class="row" id="sigint-sentiment" style="margin-top:12px; padding:12px; background:rgba(0,0,0,0.35); border-radius:8px; gap:24px; justify-content:center;">
<div class="h-green mono">▲ POSITIVE: <span id="sig-pos">0</span></div>
<div class="h-amber mono">● NEUTRAL: <span id="sig-neu">0</span></div>
<div class="h-red mono">▼ NEGATIVE: <span id="sig-neg">0</span></div>
</div>
<div id="sigint-status">AWAITING DIRECTIVES.</div>
</div>
<div id="sigint-results" style="display:flex; flex-direction:column; gap:12px;"></div>
</div>
<!-- ============================================================
TAB: SHADOW MAP
============================================================ -->
<div id="tab-shadowmap" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Shadow Map</div>
<div class="search-area">
<input type="text" id="shadow-input" placeholder="ENTER IP OR DOMAIN TO INVESTIGATE" onkeydown="if(event.key==='Enter') scanShadow()">
<button onclick="scanShadow()" class="glitch-btn hot">TRACE</button>
</div>
<div id="shadow-status">REPUTATION ENGINE NOMINAL.</div>
</div>
<div id="shadow-dashboard" class="hide" style="grid-template-columns: 1fr 2fr; gap:16px;">
<div class="result-card" style="text-align:center; display:flex; flex-direction:column; align-items:center; justify-content:center;">
<div class="dim mono" style="margin-bottom:14px;">THREAT SCORE</div>
<div id="shadow-score" style="font-size:4.5rem; font-weight:900; line-height:1; font-family:var(--font-display);">0</div>
<div id="shadow-level" class="status-badge" style="margin-top:12px; font-size:0.8rem; padding:6px 14px;">CLEAN</div>
<div id="shadow-factors" class="col" style="margin-top:18px; width:100%; text-align:left; font-size:0.78rem;"></div>
</div>
<div class="col">
<div class="result-card" id="shadow-abuse"></div>
<div class="result-card" id="shadow-vt"></div>
<div class="result-card" id="shadow-geo"></div>
</div>
</div>
</div>
<!-- ============================================================
TAB: PASTE DRAGNET (NEW)
============================================================ -->
<div id="tab-paste" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Paste Dragnet · Multi-Site Hunter</div>
<div class="dim mono" style="font-size:0.76rem; margin-bottom:12px;">Pastebin · Ghostbin · Rentry · Paste.ee · 0bin · JustPaste · Hastebin · Ideone · DPaste — via DuckDuckGo dorks</div>
<div class="search-area">
<input type="text" id="paste-input" placeholder="ENTER QUERY (email · domain · keyword)" onkeydown="if(event.key==='Enter') scanPaste()">
<button onclick="scanPaste()" class="glitch-btn hot">DRAGNET</button>
</div>
<div id="paste-status">READY TO HUNT.</div>
</div>
<div id="paste-summary"></div>
<div id="paste-results" class="results"></div>
</div>
<!-- ============================================================
TAB: DARK WEB
============================================================ -->
<div id="tab-darkwatch" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Dark Web Watch</div>
<div class="search-area">
<input type="text" id="dark-input" placeholder="ENTER KEYWORD (e.g. leak, database)">
<button onclick="scanDarkWeb()" class="glitch-btn hot">SEARCH ONION</button>
</div>
<div id="dark-status">CAUTION: ONION NETWORK GATEWAY.</div>
</div>
<div id="dark-results" class="results"></div>
</div>
<!-- ============================================================
TAB: WAYBACK SPECTRE (NEW)
============================================================ -->
<div id="tab-wayback" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Wayback Spectre · Time-Machine Recon</div>
<div class="dim mono" style="font-size:0.76rem; margin-bottom:12px;">Wayback Machine CDX timeline · year buckets · sensitive-path flagging (admin · .env · .git · backups)</div>
<div class="search-area">
<input type="text" id="wayback-input" placeholder="ENTER DOMAIN OR URL" onkeydown="if(event.key==='Enter') scanWayback()">
<button onclick="scanWayback()" class="glitch-btn">RECALL</button>
</div>
<div id="wayback-status">READY.</div>
</div>
<div id="wayback-results"></div>
</div>
<!-- ============================================================
TAB: DOMAIN ORACLE (NEW)
============================================================ -->
<div id="tab-oracle" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Domain Oracle · Deep Intel</div>
<div class="dim mono" style="font-size:0.76rem; margin-bottom:12px;">WHOIS (RDAP) · full DNS · SPF/DMARC/DKIM grade · HTTP security headers · TLS · crt.sh subs · reverse-IP</div>
<div class="search-area">
<input type="text" id="oracle-input" placeholder="ENTER DOMAIN (e.g. example.com)" onkeydown="if(event.key==='Enter') scanOracle()">
<button onclick="scanOracle()" class="glitch-btn hot">DIVINE</button>
</div>
<div id="oracle-status">READY.</div>
</div>
<div id="oracle-results"></div>
</div>
<!-- ============================================================
TAB: NETWORK MAPPER
============================================================ -->
<div id="tab-network" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Network Mapper</div>
<div class="search-area">
<input type="text" id="network-input" placeholder="ENTER DOMAIN (e.g. example.com)">
<button onclick="scanNetwork()" class="glitch-btn">MAP NETWORK</button>
</div>
<div id="network-status">READY TO SCAN.</div>
</div>
<div id="network-results" style="display:block; min-height:500px;">
<div id="network-graph" style="width:100%; height:500px; border:1px solid var(--panel-edge); border-radius:var(--radius); background:#000; overflow:hidden;"></div>
<div id="network-ports" style="margin-top:18px;"></div>
</div>
</div>
<!-- ============================================================
TAB: SSL SENTINEL
============================================================ -->
<div id="tab-ssl" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">SSL Sentinel</div>
<div class="search-area">
<input type="text" id="ssl-input" placeholder="ENTER DOMAIN (e.g. secure.com)">
<button onclick="scanSSL()" class="glitch-btn">INSPECT SSL</button>
</div>
<div id="ssl-status">TLS HANDSHAKE PROTOCOL READY.</div>
</div>
<div id="ssl-results"></div>
</div>
<!-- ============================================================
TAB: CRYPTO
============================================================ -->
<div id="tab-crypto" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Crypto Analyzer</div>
<div class="search-area">
<input type="text" id="crypto-input" placeholder="ENTER WALLET ADDRESS">
<select id="crypto-type" class="dork-select" style="min-width:140px;">
<option value="btc">BITCOIN</option>
<option value="eth">ETHEREUM</option>
</select>
<button onclick="scanCrypto()" class="glitch-btn">ANALYZE</button>
</div>
<div id="crypto-status">LEDGER CONNECTION ESTABLISHED.</div>
</div>
<div id="crypto-results"></div>
</div>
<!-- ============================================================
TAB: EXIF
============================================================ -->
<div id="tab-exif" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">EXIF X-Ray</div>
<div class="search-area">
<input type="text" id="exif-input" placeholder="ENTER IMAGE URL (http://...)">
<span class="mono dim" style="align-self:center;">OR</span>
<input type="file" id="exif-file" style="min-width:200px;">
</div>
<div class="row" style="margin-top:12px;">
<button onclick="analyzeExif()" class="glitch-btn">EXTRACT (URL)</button>
<button onclick="analyzeExifFile()" class="glitch-btn ok">EXTRACT (FILE)</button>
</div>
<div id="exif-status">WAITING FOR VISUAL DATA.</div>
</div>
<div id="exif-results"></div>
</div>
<!-- ============================================================
TAB: DORKS
============================================================ -->
<div id="tab-dorks" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Dork Studio</div>
<div class="search-area">
<input type="text" id="dork-target" placeholder="TARGET KEYWORD (e.g. Tesla)">
<input type="text" id="dork-domain" placeholder="DOMAIN (Optional)">
<button onclick="generateDorks()" class="glitch-btn">GENERATE</button>
</div>
<div id="dork-status">HACKING QUERIES READY.</div>
</div>
<div id="dork-results" class="results" style="grid-template-columns: 1fr;"></div>
</div>
<!-- ============================================================
TAB: GEOINT
============================================================ -->
<div id="tab-geoint" class="tab-content">
<div class="hud-panel reveal">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Geoint Spy</div>
<div class="search-area">
<input type="text" id="geo-lat" placeholder="LATITUDE (e.g. 40.7128)">
<input type="text" id="geo-lon" placeholder="LONGITUDE (e.g. -74.0060)">
<button onclick="runGeoint()" class="glitch-btn ok">SAT RECON</button>
</div>
<div id="geo-status">SATELLITE UPLINK STANDBY.</div>
</div>
<div id="geo-results"></div>
</div>
<!-- ============================================================
TAB: SKY RADAR
============================================================ -->
<div id="tab-flight" class="tab-content" style="height: calc(100vh - 160px); min-height:600px;">
<div style="display:flex; flex-direction:column; height:100%;">
<div class="hud-panel" style="margin-bottom:10px; flex-shrink:0;">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="panel-title">Sky Radar</div>
<div class="search-area" style="flex-wrap: wrap; gap:8px;">
<select id="sky-country" class="dork-select" onchange="updateSkyRegion()" style="min-width:160px;">
<option value="">SELECT REGION...</option>
<option value="uk">UNITED KINGDOM</option>
<option value="usa_east">USA (EAST)</option>
<option value="usa_west">USA (WEST)</option>
<option value="france">FRANCE</option>
<option value="germany">GERMANY</option>
<option value="russia">RUSSIA (MOSCOW)</option>
<option value="china">CHINA (EAST)</option>
<option value="japan">JAPAN</option>
<option value="dubai">UAE (DUBAI)</option>
</select>
<input type="text" id="sky-lat" placeholder="LAT" style="max-width:120px;">
<input type="text" id="sky-lon" placeholder="LON" style="max-width:120px;">
<input type="text" id="sky-rad" value="100" placeholder="RAD (KM)" style="max-width:120px;">
<button onclick="scanSky()" class="glitch-btn">RADAR SCAN</button>
<button onclick="if(navigator.geolocation) navigator.geolocation.getCurrentPosition(p=>{document.getElementById('sky-lat').value=p.coords.latitude; document.getElementById('sky-lon').value=p.coords.longitude;})" class="ctrl-btn">📍 MY LOC</button>
</div>
<div id="sky-status">OPENSKY NETWORK LINKED.</div>
</div>
<div style="display:flex; gap:14px; flex:1; min-height:0;">
<div id="sky-map" style="flex:3; height:100%; background:var(--bg-1); border:1px solid var(--panel-edge); border-radius:var(--radius); overflow:hidden;"></div>
<div style="flex:1; height:100%; overflow-y:auto; border:1px solid var(--panel-edge); border-radius:var(--radius); background:var(--panel); padding:14px;">
<div class="panel-title" style="margin-bottom:10px;">LIVE TRAFFIC</div>
<div id="sky-results">
<div class="dim mono" style="text-align:center;">NO DATA FEED</div>
</div>
</div>
</div>
</div>
</div>
<!-- ============================================================
TAB: PREMIUM
============================================================ -->
<div id="tab-premium" class="tab-content">
<div class="hud-panel reveal" style="text-align:center;">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<h2 class="panel-title" style="justify-content:center; font-size:1.1rem;">PREMIUM PROJECT CATALOG</h2>
<div class="dim mono" style="font-size:0.84rem;">UNLOCK ADVANCED CAPABILITIES WITH THESE EXCLUSIVE MODULES.</div>
</div>
<div class="results" style="grid-template-columns: repeat(auto-fill, minmax(320px, 1fr));">
<div class="result-card">
<div class="spread" style="margin-bottom:10px;">
<h3 class="card-title">TheBigBrother God-EYE</h3>
<span class="status-badge critical">PREMIUM</span>
</div>
<div class="dim" style="font-size:0.86rem; margin-bottom:18px;">The ultimate evolution of OSINT operations. Direct access to proprietary servers and global data APIs for unprecedented deep-level intelligence.</div>
<button class="glitch-btn hot" style="width:100%;" onclick="window.open('https://t.me/hisoka0morow', '_blank')">GET IT</button>
</div>
<div class="result-card">
<div class="spread" style="margin-bottom:10px;">
<h3 class="card-title">X GodMode</h3>
<span class="status-badge info">AUTOMATION</span>
</div>
<div class="dim" style="font-size:0.86rem; margin-bottom:18px;">Deploy fully automated farms across the X ecosystem — auto-publish, RT, like, comment, engineer sentiment.</div>
<button class="glitch-btn" style="width:100%;" onclick="window.open('https://t.me/hisoka0morow', '_blank')">GET IT</button>
</div>
<div class="result-card">
<div class="spread" style="margin-bottom:10px;">
<h3 class="card-title">Amplifior</h3>
<span class="status-badge medium">TIKTOK BOT</span>
</div>
<div class="dim" style="font-size:0.86rem; margin-bottom:18px;">Hands-free TikTok empire builder. Autonomous download → edit → publish loops for explosive organic growth.</div>
<button class="glitch-btn ok" style="width:100%;" onclick="window.open('https://t.me/hisoka0morow', '_blank')">GET IT</button>
</div>
<div class="result-card">
<div class="spread" style="margin-bottom:10px;">
<h3 class="card-title">Psychopath</h3>
<span class="status-badge low">PHISHING</span>
</div>
<div class="dim" style="font-size:0.86rem; margin-bottom:18px;">Definitive engineered phishing platform — 100+ targets, SMTP bridging, conversational AI bots.</div>
<button class="glitch-btn ok" style="width:100%;" onclick="window.open('https://t.me/hisoka0morow', '_blank')">GET IT</button>
</div>
<div class="result-card">
<div class="spread" style="margin-bottom:10px;">
<h3 class="card-title">Custom Project</h3>
<span class="status-badge critical">DEVELOPMENT</span>
</div>
<div class="dim" style="font-size:0.86rem; margin-bottom:18px;">Arsenal of 200+ operational tools. If a capability doesn't exist, we engineer it. Nothing is impossible.</div>
<button class="glitch-btn hot" style="width:100%;" onclick="window.open('https://t.me/hisoka0morow', '_blank')">GET IT</button>
</div>
</div>
</div>
</div><!-- /content-area -->
</main>
</div><!-- /app-container -->
<!-- ============================================================
DEEP SEARCH MODAL
============================================================ -->
<div id="deepModal" class="deepModal">
<div class="spread" style="margin-bottom:14px;">
<h3>DEEP VISUAL INTEL</h3>
<button class="ctrl-btn stop" onclick="closeDeepModal()">[ X ] CLOSE</button>
</div>
<div class="row" style="margin-bottom:14px; align-items:center;">
<img id="deep-target-img" src="" style="width:84px; height:84px; object-fit:cover; border-radius:var(--radius); border:1px solid var(--cyan); box-shadow:0 0 22px rgba(0,240,255,0.4);">
<div class="target-scan">⚲ SCANNING TARGET ACROSS VISUAL SEARCH ENGINES...</div>
</div>
<div id="deep-status" class="mono dim" style="margin-bottom:14px;">READY</div>
<div class="deep-grid">
<div class="deep-col"><h4>GOOGLE IMAGES</h4><div id="google-results"></div></div>
<div class="deep-col"><h4>BING VISUAL</h4><div id="bing-results"></div></div>
<div class="deep-col"><h4>YANDEX VISION</h4><div id="yandex-results"></div></div>
<div class="deep-col"><h4>TINEYE TRACKER</h4><div id="tineye-results"></div></div>
</div>
</div>
<!-- ============================================================
SCRIPTS
============================================================ -->
<script src="https://unpkg.com/leaflet@1.9.4/dist/leaflet.js"></script>
<script>
/* ---------- boot sequence ---------- */
(function() {
const lines = [
'[OK] core kernel · online',
'[OK] neural mesh · linked',
'[OK] crypt engines · primed',
'[OK] phantom net · ready',
'[OK] sigint relay · open',
'[!!] uplink · god\'s eye protocol engaged'
];
const host = document.getElementById('boot-lines');
lines.forEach((line, i) => {
const span = document.createElement('span');
span.textContent = line;
if (line.includes('[!!]')) span.classList.add('err');
else span.classList.add('ok');
host.appendChild(span);
setTimeout(() => span.classList.add('show'), 180 + i * 200);
});
setTimeout(() => document.getElementById('boot').classList.add('done'), 1700);
})();
/* ---------- clock + session ---------- */
function pad(n) { return String(n).padStart(2, '0'); }
function tickClock() {
const d = new Date();
document.getElementById('clock').textContent =
`UTC ${pad(d.getUTCHours())}:${pad(d.getUTCMinutes())}:${pad(d.getUTCSeconds())}`;
}
setInterval(tickClock, 1000); tickClock();
document.getElementById('session-id').textContent =
'#' + Math.random().toString(36).slice(2, 8).toUpperCase();
/* ---------- particle canvas ---------- */
(function() {
const c = document.getElementById('particle-canvas');
const ctx = c.getContext('2d');
let w, h, particles = [];
const COUNT = 80;
function resize() {
w = c.width = innerWidth;
h = c.height = innerHeight;
}
resize();
addEventListener('resize', resize);
for (let i = 0; i < COUNT; i++) {
particles.push({
x: Math.random() * w,
y: Math.random() * h,
vx: (Math.random() - 0.5) * 0.25,
vy: (Math.random() - 0.5) * 0.25,
r: Math.random() * 1.6 + 0.4,
hue: Math.random() < 0.5 ? '255, 0, 80' : '0, 240, 255'
});
}
function frame() {
ctx.clearRect(0, 0, w, h);
for (const p of particles) {
p.x += p.vx; p.y += p.vy;
if (p.x < 0 || p.x > w) p.vx *= -1;
if (p.y < 0 || p.y > h) p.vy *= -1;
ctx.beginPath();
ctx.arc(p.x, p.y, p.r, 0, Math.PI * 2);
ctx.fillStyle = `rgba(${p.hue}, 0.6)`;
ctx.fill();
}
// connect close particles
for (let i = 0; i < particles.length; i++) {
for (let j = i + 1; j < particles.length; j++) {
const a = particles[i], b = particles[j];
const dx = a.x - b.x, dy = a.y - b.y;
const d = Math.sqrt(dx * dx + dy * dy);
if (d < 120) {
ctx.beginPath();
ctx.moveTo(a.x, a.y);
ctx.lineTo(b.x, b.y);
ctx.strokeStyle = `rgba(255, 0, 80, ${0.08 * (1 - d / 120)})`;
ctx.lineWidth = 0.5;
ctx.stroke();
}
}
}
requestAnimationFrame(frame);
}
frame();
})();
/* ---------- tilt + cursor-glow on cards ---------- */
function bindTilt(scope) {
(scope || document).querySelectorAll('.result-card').forEach(card => {
if (card.dataset.tiltBound) return;
card.dataset.tiltBound = '1';
card.addEventListener('mousemove', e => {
const r = card.getBoundingClientRect();
const x = e.clientX - r.left, y = e.clientY - r.top;
const rx = ((y / r.height) - 0.5) * -6;
const ry = ((x / r.width) - 0.5) * 6;
card.style.transform = `translateY(-4px) perspective(900px) rotateX(${rx}deg) rotateY(${ry}deg)`;
card.style.setProperty('--mx', x + 'px');
card.style.setProperty('--my', y + 'px');
});
card.addEventListener('mouseleave', () => {
card.style.transform = '';
});
});
}
/* ---------- scroll reveal ---------- */
const revealObserver = new IntersectionObserver(entries => {
for (const e of entries) {
if (e.isIntersecting) {
e.target.classList.add('visible');
revealObserver.unobserve(e.target);
}
}
}, { threshold: 0.05 });
function bindReveal(scope) {
(scope || document).querySelectorAll('.reveal').forEach(el => revealObserver.observe(el));
}
bindReveal();
/* re-bind after each tab switch and after any innerHTML update on results */
function refreshFX(scope) { bindTilt(scope); bindReveal(scope); }
/* ---------- tab switching ---------- */
function switchTab(tabId, title) {
document.querySelectorAll('.tab-content').forEach(el => el.classList.remove('active'));
document.querySelectorAll('.tab-btn').forEach(btn => btn.classList.remove('active'));
const target = document.getElementById(tabId);
if (target) target.classList.add('active');
if (event && event.currentTarget) event.currentTarget.classList.add('active');
if (title) {
const tEl = document.getElementById('active-module-title');
tEl.textContent = '';
let i = 0;
const interval = setInterval(() => {
if (i >= title.length) { clearInterval(interval); return; }
tEl.textContent += title[i++];
}, 22);
}
refreshFX(target);
}
/* ============================================================
STATE + HELPERS
============================================================ */
let jobId = null, pollInterval = null, currentUsername = "";
function renderDict(obj, opts = {}) {
if (!obj || typeof obj !== 'object') return '';
return Object.entries(obj).map(([k, v]) => {
if (v === null || v === undefined || v === '') return '';
if (Array.isArray(v)) v = v.join(', ') || '—';
if (typeof v === 'object') v = JSON.stringify(v);
return `<div style="display:flex; gap:8px; padding:3px 0; font-size:0.82rem;"><span class="dim mono" style="min-width:120px;">${k}:</span><span>${v}</span></div>`;
}).join('');
}
function gradeBadgeClass(g) {
if (g === 'A') return 'verified';
if (g === 'B') return 'low';
if (g === 'C') return 'medium';
if (g === 'D') return 'high';
return 'critical';
}
function fillScore(barEl, scoreEl, value, invert = false) {
barEl.style.width = value + '%';
scoreEl.textContent = value + '%';
let c = 'var(--green)';
if (invert) {
if (value > 70) c = 'var(--red)';
else if (value > 40) c = 'var(--amber)';
} else {
if (value < 30) c = 'var(--red)';
else if (value < 60) c = 'var(--amber)';
}
barEl.style.background = c;
barEl.style.color = c;
}
/* ============================================================
PROFILER
============================================================ */
async function startScan() {
const username = document.getElementById('username').value.trim();
if (!username) return;
currentUsername = username;
document.getElementById('results').innerHTML = '';
document.getElementById('images-panel').classList.remove('hide');
document.getElementById('images-count').textContent = 'SEARCHING...';
document.getElementById('images-count').className = 'status-badge check';
document.getElementById('images-container').dataset.last = '';
document.getElementById('images-container').innerHTML = `
<div class="mono h-cyan" style="padding:30px; text-align:center; width:100%; letter-spacing:2px;">
<div style="font-size:0.9rem; margin-bottom:10px;">⚲ ACQUIRING BIOMETRIC DATA</div>
<div class="dim" style="font-size:0.74rem;">querying ddg · bing · google images for "${username}"</div>
</div>`;
document.getElementById('status').textContent = 'INITIALIZING NEURAL LINK...';
document.getElementById('btn-scan').disabled = true;
document.getElementById('btn-stop').disabled = false;
document.getElementById('btn-download').disabled = true;
document.getElementById('username').disabled = true;
try {
const res = await fetch('/api/scan', {
method: 'POST',
headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ username })
});
const data = await res.json();
jobId = data.job_id;
if (pollInterval) clearInterval(pollInterval);
pollInterval = setInterval(poll, 1500);
} catch (e) {
console.error(e);
alert('SYSTEM FAILURE: CONNECTION REFUSED');
resetState();
}
}
async function stopScan() {
if (!jobId) return;
try {
await fetch(`/api/stop/${jobId}`, { method: 'POST' });
document.getElementById('status').textContent = 'ABORTING SEQUENCE...';
} catch (e) { console.error(e); }
}
function downloadReport() {
if (!jobId) return;
window.location.href = `/api/download/${jobId}`;
}
function executeDork() {
const u = (document.getElementById('username').value.trim() || currentUsername).trim();
if (!u) return alert('ENTER TARGET IDENTIFIER FIRST');
const type = document.getElementById('dork-select').value;
const map = {
linkedin: `site:linkedin.com "${u}"`, instagram: `site:instagram.com "${u}"`,
twitter: `site:twitter.com "${u}"`, facebook: `site:facebook.com "${u}"`,
tiktok: `site:tiktok.com "${u}"`, pinterest: `site:pinterest.com "${u}"`,
github: `site:github.com "${u}"`, gitlab: `site:gitlab.com "${u}"`,
stackoverflow: `site:stackoverflow.com "${u}"`,
pastebin: `site:pastebin.com "${u}"`, reddit: `site:reddit.com "${u}"`,
pdf: `filetype:pdf "${u}"`, doc: `filetype:doc "${u}"`, txt: `filetype:txt "${u}"`,
intext: `intext:"${u}"`, intitle: `intitle:"${u}"`, inurl: `inurl:"${u}"`,
password: `"${u}" "password"`, email: `"${u}" email`, phone: `"${u}" phone`
};
const q = map[type];
if (q) window.open(`https://www.google.com/search?q=${encodeURIComponent(q)}`, '_blank');
}
function downloadImage(url) {
const a = document.createElement('a');
a.href = url; a.download = `target_${currentUsername}.jpg`; a.target = '_blank';
a.click();
}
async function poll() {
if (!jobId) return;
try {
const res = await fetch(`/api/results/${jobId}`);
const data = await res.json();
renderImages(data.images || []);
renderResults(data.results);
const statusMap = {
running: 'SCANNING GLOBAL NETWORKS...',
validating: 'VERIFYING TARGET VULNERABILITIES [HEADLESS]...',
stopped: 'SEQUENCE ABORTED BY USER.',
completed: 'TARGET ACQUISITION COMPLETE.',
error: 'CRITICAL SYSTEM FAILURE.'
};
document.getElementById('status').textContent = statusMap[data.status] || data.status;
if (['completed', 'error', 'stopped'].includes(data.status)) {
clearInterval(pollInterval);
if (!data.images || !data.images.length) setImagesEmpty(data.image_diag);
resetState(true);
}
} catch (e) { console.error(e); }
}
function renderImages(images) {
const container = document.getElementById('images-container');
const countEl = document.getElementById('images-count');
if (!images || !images.length) return;
// Only re-render when the set changes
if (container.dataset.last === String(images.length)) return;
container.dataset.last = String(images.length);
countEl.textContent = `${images.length} IMAGE${images.length === 1 ? '' : 'S'} FOUND`;
countEl.className = 'status-badge verified';
container.innerHTML = images.map((src, i) => `
<div class="image-wrapper" onclick="triggerDeepSearch('${src}', this)" style="animation: tabEnter 480ms ${i * 80}ms both;">
<img src="${src}" class="captured-image" onerror="this.parentElement.style.display='none'">
<div style="position:absolute; top:8px; left:8px; padding:3px 8px; background:rgba(0,0,0,0.7); border:1px solid var(--cyan); border-radius:var(--radius-pill); font-family:var(--font-mono); font-size:0.62rem; letter-spacing:1px; color:var(--cyan);">#${String(i + 1).padStart(2, '0')}</div>
<button class="btn-deep">⚲ DEEP SEARCH</button>
<button class="dl-btn" onclick="event.stopPropagation(); downloadImage('${src}')">↓</button>
</div>
`).join('');
}
function setImagesEmpty(diag) {
const container = document.getElementById('images-container');
const countEl = document.getElementById('images-count');
if (container.children.length > 0 && !container.querySelector('.h-cyan')) return;
countEl.textContent = 'NO IMAGES';
countEl.className = 'status-badge clean';
const d = (diag || '').toLowerCase();
let hint = '';
if (d.includes('chromium-missing') || d.includes('browser-missing')) {
hint = `<div class="h-red mono" style="font-size:0.74rem; margin-top:6px;">⚠ Playwright Chromium is missing inside the container.<br>Fix: rebuild with <span class="h-cyan">docker-compose build --no-cache</span> (the V5 Dockerfile re-runs <span class="h-cyan">playwright install chromium</span>).</div>`;
} else if (d.includes('rate-limited')) {
hint = `<div class="h-amber mono" style="font-size:0.74rem; margin-top:6px;">⚠ DuckDuckGo rate-limited this IP. Wait a minute and retry, or run from a different IP.</div>`;
} else if (d.includes('timeout')) {
hint = `<div class="h-amber mono" style="font-size:0.74rem; margin-top:6px;">⚠ Network timeout reaching image engines.</div>`;
} else if (d) {
hint = `<div class="dim mono" style="font-size:0.7rem; margin-top:6px;">diag: ${diag}</div>`;
}
container.innerHTML = `
<div style="padding:20px; text-align:center; width:100%;">
<div class="dim mono" style="font-size:0.82rem;">[ NO PUBLIC IMAGES FOUND FOR THIS TARGET ]</div>
${hint}
</div>`;
}
function renderResults(results) {
const container = document.getElementById('results');
const rank = s => s === 'Verified' ? 0 : s === 'Checking...' ? 1 : s === 'Pending' ? 2 : 3;
const sorted = [...results].sort((a, b) => rank(a.validation) - rank(b.validation));
container.innerHTML = sorted.map(r => `
<div class="result-card">
<div class="spread" style="margin-bottom:8px;">
<h3 class="card-title">${r.site}</h3>
${renderBadge(r)}
</div>
<a href="${r.url}" target="_blank" class="card-url">${r.url}</a>
${r.page_title ? `<div class="dim mono" style="font-size:0.74rem;">TITLE: ${r.page_title}</div>` : ''}
${r.reason ? `<div class="h-red mono" style="font-size:0.74rem;">ERR: ${r.reason}</div>` : ''}
</div>
`).join('');
refreshFX(container);
}
function renderBadge(res) {
if (res.validation === 'Pending') return '<span class="status-badge">PENDING</span>';
if (res.validation === 'Checking...') return '<span class="status-badge check">CHECKING</span>';
if (res.validation === 'Verified') return '<span class="status-badge verified">VERIFIED</span>';
if (res.validation === 'False Positive') return '<span class="status-badge false">FALSE+</span>';
return '';
}
function resetState(finished = false) {
document.getElementById('btn-scan').disabled = false;
document.getElementById('btn-stop').disabled = true;
document.getElementById('btn-download').disabled = !finished;
document.getElementById('username').disabled = false;
}
/* ============================================================
DEEP SEARCH MODAL
============================================================ */
async function triggerDeepSearch(url, wrapper) {
document.getElementById('deep-target-img').src = url;
const modal = document.getElementById('deepModal');
modal.classList.add('active');
document.getElementById('deep-status').textContent = 'DEPLOYING MULTI-VECTOR VISUAL SEARCH...';
['google-results', 'bing-results', 'yandex-results', 'tineye-results'].forEach(id => {
document.getElementById(id).innerHTML = '<div class="h-green mono" style="animation: pulse 1.2s ease-in-out infinite;">[ ESTABLISHING UPLINK... ]</div>';
});
try {
const res = await fetch('/api/deep-search', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ image_url: url })
});
const data = await res.json();
document.getElementById('deep-status').textContent = 'TARGET VISUAL MATCHES ACQUIRED.';
renderDeepResults('google-results', data.google);
renderDeepResults('bing-results', data.bing);
renderDeepResults('yandex-results', data.yandex);
renderDeepResults('tineye-results', data.tineye);
} catch (e) {
console.error(e);
document.getElementById('deep-status').textContent = 'VISUAL SEARCH FAILURE.';
}
}
function renderDeepResults(divId, images) {
const c = document.getElementById(divId);
if (!images || images.length === 0) {
c.innerHTML = '<div class="dim">NO MATCHES FOUND</div>';
return;
}
c.innerHTML = images.map(src => `<img src="${src}" onclick="window.open('${src}')">`).join('');
}
function closeDeepModal() {
document.getElementById('deepModal').classList.remove('active');
}
/* ============================================================
PHANTOM ID
============================================================ */
async function scanPhantom() {
const username = document.getElementById('phantom-input').value.trim();
if (!username) return;
document.getElementById('phantom-status').textContent = 'HUNTING USERNAME ACROSS 200+ PLATFORMS...';
document.getElementById('phantom-grid').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px; width:100%;">SCANNING NETWORKS...</div>';
document.getElementById('phantom-meta').classList.add('hide');
try {
const res = await fetch('/api/phantom', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ username })
});
const data = await res.json();
const bar = document.getElementById('phantom-score-bar');
const text = document.getElementById('phantom-score-text');
fillScore(bar, text, data.risk_score || 0, true);
document.getElementById('phantom-avatar').src = data.gravatar || '';
document.getElementById('phantom-meta').classList.remove('hide');
document.getElementById('phantom-cats').innerHTML =
Object.entries(data.categories || {}).map(([c, n]) => `<span class="tag">${c.toUpperCase()}: ${n}</span>`).join('');
const grid = document.getElementById('phantom-grid');
if (!data.profiles || !data.profiles.length) {
grid.innerHTML = '<div class="dim mono" style="text-align:center; padding:30px;">NO PROFILES FOUND.</div>';
} else {
grid.innerHTML = data.profiles.map(p => `
<div class="result-card" style="cursor:pointer;" onclick="window.open('${p.url}')">
<h3 class="card-title">${p.platform}</h3>
<div class="dim mono" style="font-size:0.74rem;">STATUS ${p.status} · ${p.cat || 'general'}</div>
</div>
`).join('');
}
document.getElementById('phantom-status').textContent =
`FOUND PRESENCE ON ${data.found} / ${data.total_checked} PLATFORMS.`;
refreshFX(grid);
} catch (e) {
console.error(e);
document.getElementById('phantom-status').textContent = 'PHANTOM IDENTIFICATION FAILED.';
}
}
/* ============================================================
BREACH VAULT
============================================================ */
async function scanBreach() {
const query = document.getElementById('breach-input').value.trim();
const type = document.getElementById('breach-type').value;
if (!query) return;
document.getElementById('breach-status').textContent = 'QUERYING DARK VAULTS...';
document.getElementById('breach-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">ANALYZING LEAKS...</div>';
document.getElementById('breach-summary').innerHTML = '';
document.getElementById('paste-dump-results').innerHTML = '';
try {
const res = await fetch('/api/breach', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ query, type })
});
const data = await res.json();
if (data.type === 'password') {
if (data.pwned) {
document.getElementById('breach-results').innerHTML = `
<div class="result-card" style="border-color:var(--red); text-align:center;">
<h3 class="card-title h-red">PASSWORD COMPROMISED</h3>
<div class="mono" style="font-size:1.2rem;">SEEN ${data.count} TIMES</div>
<div class="dim mono" style="font-size:0.78rem; margin-top:8px;">DO NOT USE THIS PASSWORD</div>
</div>`;
document.getElementById('breach-status').textContent = 'WARNING: HIGH SEVERITY.';
} else {
document.getElementById('breach-results').innerHTML = `
<div class="result-card" style="border-color:var(--green); text-align:center;">
<h3 class="card-title h-green">PASSWORD SAFE</h3>
<div class="mono">NO MATCHES IN KNOWN DATABASES.</div>
</div>`;
document.getElementById('breach-status').textContent = 'NO KNOWN EXPOSURE.';
}
refreshFX(document.getElementById('breach-results'));
return;
}
document.getElementById('breach-summary').innerHTML = `
<div class="result-card" style="display:flex; gap:24px; justify-content:center; text-align:center;">
<div><div style="font-size:2rem; font-family:var(--font-display);" class="h-red">${data.breach_count}</div><div class="dim mono" style="font-size:0.7rem;">DATABASES</div></div>
<div><div style="font-size:2rem; font-family:var(--font-display);" class="h-amber">${data.paste_count}</div><div class="dim mono" style="font-size:0.7rem;">PASTES</div></div>
<div><div style="font-size:2rem; font-family:var(--font-display);" class="h-cyan">${(data.total_records_exposed||0).toLocaleString()}</div><div class="dim mono" style="font-size:0.7rem;">RECORDS</div></div>
</div>`;
let html = "";
(data.breaches || []).forEach(b => {
if (b._note) { html += `<div class="dim mono" style="text-align:center;">${b._note}</div>`; return; }
const sev = (b.severity || 'LOW').toLowerCase();
html += `
<div class="result-card">
<div class="spread" style="margin-bottom:8px;">
<h3 class="card-title">${b.name}</h3>
<span class="status-badge ${sev}">${b.severity}</span>
</div>
<div class="row" style="gap:14px;">
${b.logo ? `<img src="${b.logo}" style="width:48px; height:48px; object-fit:contain; border-radius:6px;" onerror="this.style.display='none'">` : ''}
<div style="flex:1;">
<div class="dim mono" style="font-size:0.74rem; margin-bottom:6px;">${b.date} · ${b.domain || 'unknown'}</div>
<div style="font-size:0.85rem; margin-bottom:8px;">${b.description}</div>
<div class="row" style="gap:4px;">${(b.data_classes || []).map(d => `<span class="tag hot">${d}</span>`).join('')}</div>
</div>
</div>
</div>`;
});
if (!data.breaches || !data.breaches.length) {
html = '<div class="result-card" style="border-color:var(--green); text-align:center;"><h3 class="card-title h-green">CLEAN REPUTATION</h3><div>NO BREACHES DETECTED.</div></div>';
}
document.getElementById('breach-results').innerHTML = html;
if (data.paste_dumps && data.paste_dumps.length) {
const pd = data.paste_dumps.map(p => `
<div class="result-card" style="display:flex; justify-content:space-between; align-items:center;">
<div>
<strong class="h-amber">Pastebin ID: ${p.id}</strong>
<div class="dim mono" style="font-size:0.74rem;">Indexed: ${new Date(p.date * 1000).toISOString().split('T')[0]}</div>
</div>
<button class="dork-btn" onclick="window.open('${p.url}')">VIEW CACHE ›</button>
</div>
`).join('');
document.getElementById('paste-dump-results').innerHTML = pd;
}
document.getElementById('breach-status').textContent = 'AUDIT COMPLETE.';
refreshFX(document.getElementById('breach-results'));
} catch (e) {
console.error(e);
document.getElementById('breach-status').textContent = 'VAULT CONNECTION TERMINATED.';
}
}
/* ============================================================
FOOTPRINT
============================================================ */
async function scanFootprint() {
const query = document.getElementById('footprint-input').value.trim();
const type = document.getElementById('footprint-type').value;
if (!query) return;
document.getElementById('footprint-status').textContent = 'SCANNING DIGITAL TRACE...';
document.getElementById('footprint-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:30px;">ACCESSING DATABASES...</div>';
try {
const res = await fetch('/api/footprint', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ query, type })
});
const data = await res.json();
if (data.error) {
document.getElementById('footprint-results').innerHTML = `<div class="result-card" style="border-color:var(--red);">${data.error}</div>`;
document.getElementById('footprint-status').textContent = 'ERROR.';
return;
}
if (type === 'phone') {
const p = data;
document.getElementById('footprint-results').innerHTML = `
<div class="result-card">
<h3 class="card-title h-green">PHONE INTELLIGENCE</h3>
${renderDict({
'VALID NUMBER': p.valid,
'FORMAT': p.number,
'COUNTRY': p.country,
'CARRIER': p.carrier,
'LINE TYPE': p.line_type,
'TIMEZONES': (p.timezones || []).join(', ')
})}
</div>`;
document.getElementById('footprint-status').textContent = 'PHONE TRACE COMPLETE.';
} else {
let html = '';
if (data.found_on && data.found_on.length) {
html += `<div class="result-card"><h3 class="card-title h-green">DIGITAL FOOTPRINT DETECTED</h3>
<div class="results" style="grid-template-columns: repeat(auto-fill, minmax(140px, 1fr)); gap:8px; margin-top:10px;">
${data.found_on.map(s => `<div class="tag ok" style="text-align:center; padding:8px;">${s}</div>`).join('')}
</div></div>`;
} else {
html += `<div class="result-card" style="text-align:center;"><h3 class="card-title dim">NO PUBLIC TRACE</h3><div class="dim">TARGET EMAIL APPEARS CLEAN.</div></div>`;
}
html += `<div class="result-card" style="margin-top:12px; border-color:${data.valid_mx ? 'var(--green)' : 'var(--red)'};">
<h3 class="card-title">MX RECORDS</h3>
<div class="mono" style="font-size:1.05rem;">${data.valid_mx ? 'VALID MAIL SERVER' : 'INVALID / UNREACHABLE'}</div>
<div class="dim mono" style="font-size:0.78rem;">${(data.mx_records || []).length} SERVERS</div>
</div>`;
document.getElementById('footprint-results').innerHTML = html;
document.getElementById('footprint-status').textContent =
(data.found_on || []).length ? `EMAIL FOUND ON ${data.found_on.length} PLATFORMS.` : 'NO PUBLIC TRACE.';
}
refreshFX(document.getElementById('footprint-results'));
} catch (e) {
document.getElementById('footprint-status').textContent = 'ERROR EXECUTING TRACE.';
}
}
/* ============================================================
NETWORK MAPPER
============================================================ */
async function scanNetwork() {
const domain = document.getElementById('network-input').value.trim();
if (!domain) return;
document.getElementById('network-status').textContent = 'MAPPING TOPOLOGY...';
document.getElementById('network-graph').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:100px;">ESTABLISHING CONNECTIONS...</div>';
document.getElementById('network-ports').innerHTML = '';
try {
const res = await fetch('/api/network/scan', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ domain })
});
const data = await res.json();
if (data.error) { document.getElementById('network-status').textContent = 'ERROR: ' + data.error; return; }
if (data.map_html) {
const blob = new Blob([data.map_html], { type: 'text/html' });
const url = URL.createObjectURL(blob);
document.getElementById('network-graph').innerHTML = `<iframe src="${url}" style="width:100%; height:100%; border:none;"></iframe>`;
}
let intel = '<div class="results" style="grid-template-columns: 1fr 1fr 1fr; gap:14px;">';
intel += `<div class="result-card"><h3 class="card-title">OPEN PORTS</h3>${
(data.ports || []).length
? data.ports.map(p => `<div class="row" style="font-family:var(--font-mono); font-size:0.84rem;"><span class="h-red mono">${p.port}</span><span>${p.service}</span></div>`).join('')
: '<div class="dim">NO OPEN PORTS DETECTED</div>'
}</div>`;
intel += `<div class="result-card"><h3 class="card-title">GEO / WHOIS</h3>${
renderDict({
LOC: data.geoip && data.geoip.country ? `${data.geoip.country} (${data.geoip.countryCode})` : null,
ISP: data.geoip && data.geoip.isp,
ORG: data.geoip && data.geoip.org,
REG: data.whois && data.whois.registrar,
DATE: data.whois && data.whois.creation_date
})
}</div>`;
intel += `<div class="result-card"><h3 class="card-title">DNS RECORDS</h3>${
renderDict({
MX: (data.dns && data.dns.MX || []).join(', ') || null,
NS: (data.dns && data.dns.NS || []).join(', ') || null,
A: (data.dns && data.dns.A || []).join(', ') || null,
TXT: (data.dns && data.dns.TXT && data.dns.TXT.length) ? `${data.dns.TXT.length} records` : null
})
}</div></div>`;
document.getElementById('network-ports').innerHTML = intel;
document.getElementById('network-status').textContent = 'SCAN COMPLETE.';
refreshFX(document.getElementById('network-ports'));
} catch (e) {
document.getElementById('network-status').textContent = 'NETWORK ERROR.';
}
}
/* ============================================================
DARK WEB
============================================================ */
async function scanDarkWeb() {
const query = document.getElementById('dark-input').value.trim();
if (!query) return;
document.getElementById('dark-status').textContent = 'ROUTING THROUGH TOR GATEWAYS...';
document.getElementById('dark-results').innerHTML = '<div class="mono h-amber" style="text-align:center;">DECYPHERING...</div>';
try {
const res = await fetch('/api/dark/search', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ query })
});
const data = await res.json();
if (data.error) { document.getElementById('dark-results').innerHTML = `<div class="h-red">ERROR: ${data.error}</div>`; return; }
if (!data.results.length) { document.getElementById('dark-results').innerHTML = '<div class="dim mono" style="text-align:center;">NO HIDDEN SERVICES FOUND.</div>'; return; }
document.getElementById('dark-results').innerHTML = data.results.map(item => {
const isRansom = (item.title || '').includes('Ransomware');
return `
<div class="result-card">
<div class="spread" style="margin-bottom:8px;">
<h3 class="card-title h-red">${item.title}</h3>
<span class="status-badge ${isRansom ? 'critical' : 'high'}">${isRansom ? 'LEAK' : 'ONION'}</span>
</div>
<div class="dim mono" style="font-size:0.74rem;">${item.date || ''}</div>
<div style="font-size:0.86rem; margin:8px 0;">${item.snippet || ''}</div>
<a href="${item.link}" target="_blank" class="card-url">${item.link}</a>
</div>`;
}).join('');
document.getElementById('dark-status').textContent = `FOUND ${data.count} ONION SERVICES.`;
refreshFX(document.getElementById('dark-results'));
} catch (e) { document.getElementById('dark-status').textContent = 'CONNECTION FAILURE.'; }
}
/* ============================================================
CRYPTO
============================================================ */
async function scanCrypto() {
const address = document.getElementById('crypto-input').value.trim();
const coin = document.getElementById('crypto-type').value;
if (!address) return;
document.getElementById('crypto-status').textContent = 'SYNCING WITH DISTRIBUTED LEDGER...';
document.getElementById('crypto-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">FETCHING BLOCKS...</div>';
try {
const res = await fetch('/api/crypto/analyze', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ address, coin })
});
const data = await res.json();
if (data.error) { document.getElementById('crypto-status').textContent = 'ERROR: ' + data.error; document.getElementById('crypto-results').innerHTML = ''; return; }
document.getElementById('crypto-results').innerHTML = `
<div class="result-card" style="max-width:760px; margin:0 auto;">
<div class="spread" style="margin-bottom:14px;">
<h3 class="card-title h-amber">${data.coin.toUpperCase()} WALLET</h3>
<span class="status-badge verified">ACTIVE</span>
</div>
<div class="results" style="grid-template-columns: 1fr 1fr; gap:14px;">
<div><div class="dim mono" style="font-size:0.74rem;">BALANCE</div><div style="font-size:2rem; font-family:var(--font-display);">${data.balance}</div></div>
<div><div class="dim mono" style="font-size:0.74rem;">TOTAL RECEIVED</div><div style="font-size:2rem; font-family:var(--font-display);">${data.total_received}</div></div>
<div><div class="dim mono" style="font-size:0.74rem;">TRANSACTIONS</div><div style="font-size:1.4rem; font-family:var(--font-display);">${data.tx_count}</div></div>
<div><div class="dim mono" style="font-size:0.74rem;">LAST ACTIVITY</div><div style="font-size:1.4rem; font-family:var(--font-display);">${data.last_seen}</div></div>
</div>
<div class="dim mono" style="margin-top:14px; word-break:break-all; font-size:0.78rem;">ADDR: ${data.address}</div>
</div>`;
document.getElementById('crypto-status').textContent = `ANALYSIS COMPLETE: ${data.coin.toUpperCase()}`;
refreshFX(document.getElementById('crypto-results'));
} catch (e) { document.getElementById('crypto-status').textContent = 'LEDGER SYNC FAILED.'; }
}
/* ============================================================
SSL SENTINEL
============================================================ */
async function scanSSL() {
const domain = document.getElementById('ssl-input').value.trim();
if (!domain) return;
document.getElementById('ssl-status').textContent = 'INITIATING SSL HANDSHAKE...';
document.getElementById('ssl-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">DECODING CERTIFICATE CHAIN...</div>';
try {
const res = await fetch('/api/ssl/scan', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ domain })
});
const data = await res.json();
if (data.error) { document.getElementById('ssl-status').textContent = 'SSL FAIL: ' + data.error; document.getElementById('ssl-results').innerHTML = ''; return; }
document.getElementById('ssl-results').innerHTML = `
<div class="result-card">
<div class="spread" style="margin-bottom:12px;">
<h3 class="card-title h-cyan">${data.domain}</h3>
<span class="status-badge ${data.expired ? 'critical' : 'verified'}">${data.expired ? 'EXPIRED' : 'VALID'}</span>
</div>
<div class="results" style="grid-template-columns: 1fr 1fr; gap:14px;">
<div>
<h4 class="h-cyan mono" style="margin:0 0 8px;">ISSUED BY</h4>
${renderDict(data.issuer)}
<div class="dim mono" style="font-size:0.74rem; margin-top:10px;">VALIDITY</div>
<div class="mono" style="font-size:0.84rem;">${data.not_before} → ${data.not_after}</div>
</div>
<div>
<h4 class="h-cyan mono" style="margin:0 0 8px;">ISSUED TO</h4>
${renderDict(data.subject)}
</div>
</div>
<div style="margin-top:14px;">
<h4 class="h-cyan mono" style="margin:0 0 8px;">SUBDOMAINS (SANs) [${(data.sans || []).length}]</h4>
<div>${(data.sans || []).map(s => `<span class="tag">${s}</span>`).join('')}</div>
</div>
</div>`;
document.getElementById('ssl-status').textContent = 'CERTIFICATE VERIFIED.';
refreshFX(document.getElementById('ssl-results'));
} catch (e) { document.getElementById('ssl-status').textContent = 'HANDSHAKE FAILED.'; }
}
/* ============================================================
EXIF
============================================================ */
async function analyzeExif() {
const url = document.getElementById('exif-input').value.trim();
if (!url) return;
document.getElementById('exif-status').textContent = 'DOWNLOADING RAW BYTES...';
document.getElementById('exif-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">EXTRACTING METADATA LAYERS...</div>';
try {
const res = await fetch('/api/tools/exif', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ url })
});
renderExif(await res.json());
} catch (e) { document.getElementById('exif-status').textContent = 'ANALYSIS ERROR.'; }
}
async function analyzeExifFile() {
const fileInput = document.getElementById('exif-file');
if (!fileInput.files.length) return;
document.getElementById('exif-status').textContent = 'UPLOADING BITSTREAM...';
document.getElementById('exif-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">EXTRACTING...</div>';
const fd = new FormData(); fd.append('file', fileInput.files[0]);
try {
const res = await fetch('/api/tools/exif/upload', { method: 'POST', body: fd });
renderExif(await res.json());
} catch (e) { document.getElementById('exif-status').textContent = 'UPLOAD FAILED.'; }
}
function renderExif(data) {
if (data.error) { document.getElementById('exif-status').textContent = 'EXTRACT FAIL: ' + data.error; document.getElementById('exif-results').innerHTML = ''; return; }
document.getElementById('exif-status').textContent = 'METADATA REVEALED.';
const gpsBlock = data.gps && Object.keys(data.gps).length
? `<h4 class="h-red mono" style="margin-top:14px;">GEOLOCATION DATA</h4>${renderDict(data.gps)}`
: `<div class="dim mono" style="margin-top:14px;">[NO GPS DATA EMBEDDED]</div>`;
document.getElementById('exif-results').innerHTML = `
<div class="result-card">
<div class="spread" style="margin-bottom:10px;">
<h3 class="card-title">IMAGE METADATA</h3>
<span class="status-badge info">EXIF</span>
</div>
<h4 class="h-cyan mono" style="margin:0 0 8px;">BASIC INFO</h4>
${renderDict(data.basic)}
${gpsBlock}
</div>`;
refreshFX(document.getElementById('exif-results'));
}
/* ============================================================
DORKS
============================================================ */
async function generateDorks() {
const target = document.getElementById('dork-target').value.trim();
const domain = document.getElementById('dork-domain').value.trim();
if (!target) return;
try {
const res = await fetch('/api/tools/dork', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ target, domain })
});
const data = await res.json();
const sections = [
{ key: 'google', title: 'GOOGLE (EXTREME)', color: 'var(--cyan)', baseUrl: 'https://www.google.com/search?q=' },
{ key: 'shodan', title: 'SHODAN (INFRA)', color: 'var(--amber)', baseUrl: 'https://www.shodan.io/search?query=' },
{ key: 'github', title: 'GITHUB (LEAKS)', color: 'var(--violet)', baseUrl: 'https://github.com/search?type=Code&q=' }
];
let html = '';
for (const s of sections) {
if (!data[s.key] || !data[s.key].length) continue;
html += `<h3 class="panel-title" style="margin-top:14px; color:${s.color};">${s.title}</h3>`;
html += data[s.key].map(d => `
<div class="result-card">
<h3 class="card-title">${d.title}</h3>
<div class="mono" style="background:rgba(0,0,0,0.5); padding:10px; border-radius:6px; margin:8px 0; word-break:break-all; font-size:0.78rem; color:var(--cyan);">${d.query}</div>
<button class="dork-btn" onclick="window.open('${s.baseUrl}${encodeURIComponent(d.query)}')">OPEN ${s.title.split(' ')[0]} ›</button>
</div>`).join('');
}
document.getElementById('dork-results').innerHTML = html;
document.getElementById('dork-status').textContent = 'ATTACK VECTORS GENERATED.';
refreshFX(document.getElementById('dork-results'));
} catch (e) { console.error(e); }
}
/* ============================================================
GEOINT
============================================================ */
async function runGeoint() {
const lat = document.getElementById('geo-lat').value.trim();
const lon = document.getElementById('geo-lon').value.trim();
if (!lat || !lon) return;
document.getElementById('geo-status').textContent = 'TRIANGULATING POSITION...';
document.getElementById('geo-results').innerHTML = '<div class="mono h-green" style="text-align:center; padding:40px;">ACQUIRING SATELLITE LOCK...</div>';
try {
const res = await fetch('/api/tools/geoint', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ lat, lon })
});
const data = await res.json();
if (data.error) { document.getElementById('geo-status').textContent = data.error; document.getElementById('geo-results').innerHTML = ''; return; }
const links = Object.entries(data.links || {}).map(([k, url]) => `
<div class="result-card">
<h3 class="card-title h-green">${k}</h3>
<button class="dork-btn" style="background:rgba(0,255,140,0.15); color:var(--green); border-color:var(--green);" onclick="window.open('${url}')">LAUNCH VIEW ›</button>
</div>`).join('');
document.getElementById('geo-results').innerHTML = `<div class="results" style="grid-template-columns:1fr 1fr; gap:12px;">${links}</div>`;
document.getElementById('geo-status').textContent = `TARGET ACQUIRED: ${data.coords}`;
refreshFX(document.getElementById('geo-results'));
} catch (e) { document.getElementById('geo-status').textContent = 'SATELLITE LINK FAILED.'; }
}
/* ============================================================
SKY RADAR
============================================================ */
let flightMap = null;
async function scanSky() {
const lat = document.getElementById('sky-lat').value.trim();
const lon = document.getElementById('sky-lon').value.trim();
const rad = document.getElementById('sky-rad').value.trim();
if (!lat || !lon) return;
document.getElementById('sky-status').textContent = 'SCANNING AIRSPACE...';
document.getElementById('sky-results').innerHTML = '<div class="mono h-cyan" style="text-align:center;">READING TRANSPONDERS...</div>';
if (!flightMap) {
flightMap = L.map('sky-map').setView([lat, lon], 7);
L.tileLayer('https://cartodb-basemaps-{s}.global.ssl.fastly.net/dark_all/{z}/{x}/{y}.png', {
attribution: '© OSM © CartoDB', subdomains: 'abcd', maxZoom: 19
}).addTo(flightMap);
} else {
flightMap.setView([lat, lon], 7);
flightMap.eachLayer(layer => { if (layer instanceof L.Marker) flightMap.removeLayer(layer); });
}
L.marker([lat, lon]).addTo(flightMap).bindPopup('TARGET LOCATION').openPopup();
try {
const res = await fetch('/api/tools/flight', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ lat: parseFloat(lat), lon: parseFloat(lon), radius: parseFloat(rad) })
});
const data = await res.json();
if (data.error || data.message) {
document.getElementById('sky-status').textContent = 'SECTOR CLEAR or ERROR.';
document.getElementById('sky-results').innerHTML = `<div class="dim mono" style="text-align:center;">${data.error || data.message}</div>`;
return;
}
let listHtml = '';
data.flights.forEach(f => {
if (f.lat && f.lon) {
const ico = `<div style="color:var(--cyan); font-size:20px; transform: rotate(${f.true_track || 0}deg); text-shadow:0 0 5px var(--cyan);">✈</div>`;
const divIcon = L.divIcon({ html: ico, className: 'plane-icon', iconSize: [24, 24], popupAnchor: [0, -10] });
L.marker([f.lat, f.lon], { icon: divIcon }).addTo(flightMap)
.bindPopup(`<strong style="color:var(--cyan)">${f.callsign || 'UNKNOWN'}</strong><br>${f.country}<br>Alt: ${f.alt}m | Vel: ${f.velocity}m/s`);
}
listHtml += `
<div class="result-card" style="cursor:pointer; margin-bottom:8px;" onclick="focusMap(${f.lat}, ${f.lon}, '${f.callsign || ''}')">
<div class="spread" style="margin-bottom:6px;">
<h3 class="card-title h-cyan">${f.callsign || 'UNK'}</h3>
<span class="tag">${(f.country || '').substring(0, 3).toUpperCase()}</span>
</div>
<div class="row mono" style="font-size:0.78rem; justify-content:space-between;">
<span class="dim">ALT: ${f.alt}m</span>
<span class="dim">VEL: ${f.velocity}m/s</span>
</div>
</div>`;
});
document.getElementById('sky-results').innerHTML = listHtml || '<div class="dim mono" style="text-align:center;">NO TARGETS IN RANGE</div>';
document.getElementById('sky-status').textContent = `TRACKING ${data.count} AIRCRAFT.`;
} catch (e) { document.getElementById('sky-status').textContent = 'RADAR MALFUNCTION.'; }
}
function focusMap(lat, lon, callsign) {
if (flightMap) flightMap.setView([lat, lon], 11);
}
function updateSkyRegion() {
const r = {
uk: { lat: 51.5074, lon: -0.1278, rad: 300 },
usa_east: { lat: 40.7128, lon: -74.0060, rad: 500 },
usa_west: { lat: 34.0522, lon: -118.2437, rad: 500 },
france: { lat: 48.8566, lon: 2.3522, rad: 300 },
germany: { lat: 52.5200, lon: 13.4050, rad: 300 },
russia: { lat: 55.7558, lon: 37.6173, rad: 400 },
china: { lat: 31.2304, lon: 121.4737, rad: 500 },
japan: { lat: 35.6762, lon: 139.6503, rad: 300 },
dubai: { lat: 25.2048, lon: 55.2708, rad: 200 }
};
const sel = document.getElementById('sky-country').value;
if (r[sel]) {
document.getElementById('sky-lat').value = r[sel].lat;
document.getElementById('sky-lon').value = r[sel].lon;
document.getElementById('sky-rad').value = r[sel].rad;
}
}
/* ============================================================
SIGINT SWEEP
============================================================ */
async function scanSigint() {
const query = document.getElementById('sigint-input').value.trim();
if (!query) return;
document.getElementById('sigint-status').textContent = 'INTERCEPTING TRANSMISSIONS...';
document.getElementById('sigint-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">ANALYZING CHATTER...</div>';
try {
const res = await fetch('/api/sigint', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ query })
});
const data = await res.json();
document.getElementById('sig-pos').textContent = data.sentiment_summary.POSITIVE;
document.getElementById('sig-neu').textContent = data.sentiment_summary.NEUTRAL;
document.getElementById('sig-neg').textContent = data.sentiment_summary.NEGATIVE;
let html = '';
data.feed.forEach(item => {
const sentClass = item.sentiment === 'POSITIVE' ? 'verified' : item.sentiment === 'NEGATIVE' ? 'critical' : 'medium';
html += `
<div class="result-card" style="cursor:pointer;" onclick="window.open('${item.url}')">
<div class="spread" style="margin-bottom:8px;">
<span class="tag">[${item.source.toUpperCase()}] ${item.outlet || item.subreddit || ''}</span>
<span class="dim mono" style="font-size:0.74rem;">${item.date || ''}</span>
</div>
<h3 class="card-title" style="font-family:var(--font-ui); font-weight:600;">${item.title}</h3>
<div class="dim" style="font-size:0.86rem; margin:8px 0;">${item.snippet || ''}</div>
<div class="row" style="gap:10px; margin-top:6px;">
<span class="status-badge ${sentClass}">${item.sentiment}</span>
${item.score ? `<span class="dim mono" style="font-size:0.74rem;">SCORE: ${item.score}</span>` : ''}
</div>
</div>`;
});
document.getElementById('sigint-results').innerHTML = html || '<div class="dim mono" style="text-align:center;">NO RECENT INTEL CAPTURED.</div>';
document.getElementById('sigint-status').textContent = `GATHERED ${data.total} INTELLIGENCE PACKETS.`;
refreshFX(document.getElementById('sigint-results'));
} catch (e) { document.getElementById('sigint-status').textContent = 'INTERCEPTION FAILURE.'; }
}
/* ============================================================
SHADOW MAP
============================================================ */
async function scanShadow() {
const target = document.getElementById('shadow-input').value.trim();
if (!target) return;
document.getElementById('shadow-status').textContent = 'TRACING SHADOW INFRASTRUCTURE...';
document.getElementById('shadow-dashboard').classList.add('hide');
try {
const res = await fetch('/api/shadowmap', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ target })
});
const data = await res.json();
const d = document.getElementById('shadow-dashboard');
d.classList.remove('hide');
d.style.display = 'grid';
document.getElementById('shadow-score').textContent = data.threat_score;
document.getElementById('shadow-level').textContent = data.threat_level;
document.getElementById('shadow-level').className = 'status-badge ' + (
data.threat_level === 'CRITICAL' ? 'critical' :
data.threat_level === 'HIGH' ? 'high' :
data.threat_level === 'MEDIUM' ? 'medium' :
data.threat_level === 'LOW' ? 'low' : 'clean'
);
document.getElementById('shadow-factors').innerHTML = (data.threat_factors || [])
.map(f => `<div class="result-card" style="padding:8px 12px; border-color:var(--red);">⚠ ${f}</div>`)
.join('') || '<div class="dim mono">NO ACTIVE THREATS REPORTED.</div>';
const abuse = data.abuseipdb;
document.getElementById('shadow-abuse').innerHTML = `<h3 class="card-title h-amber">ABUSE IPDB</h3>${
abuse && abuse.available ? renderDict({
'CONFIDENCE': abuse.abuse_score + '%',
'TOTAL REPORTS': abuse.total_reports,
'ISP': abuse.isp || 'N/A',
'USAGE': abuse.usage_type || 'N/A'
}) : '<div class="dim">[NO DATA OR API KEY MISSING]</div>'
}`;
const vt = data.virustotal;
document.getElementById('shadow-vt').innerHTML = `<h3 class="card-title h-green">VIRUSTOTAL</h3>${
vt && vt.available ? renderDict({
MALICIOUS: vt.malicious, SUSPICIOUS: vt.suspicious,
REPUTATION: vt.reputation, 'TOTAL ENGINES': vt.total_engines
}) : '<div class="dim">[NO DATA OR API KEY MISSING]</div>'
}`;
const geo = data.geo || data.ipinfo;
document.getElementById('shadow-geo').innerHTML = `<h3 class="card-title h-cyan">TELEMETRY</h3>${
geo && Object.keys(geo).length ? renderDict({
IP: geo.ip, HOSTNAME: geo.hostname || 'None', CITY: geo.city,
COUNTRY: geo.country, ORGANIZATION: geo.org
}) : '<div class="dim">[UNABLE TO RESOLVE LOCATION]</div>'
}`;
document.getElementById('shadow-status').textContent = 'TRACE COMPLETE.';
refreshFX(d);
} catch (e) { document.getElementById('shadow-status').textContent = 'TRACE ABORTED.'; }
}
/* ============================================================
──── NEW V5 MODULES ─────────────────────────────────────────
============================================================ */
/* ---------- DOMAIN ORACLE ---------- */
async function scanOracle() {
const domain = document.getElementById('oracle-input').value.trim();
if (!domain) return;
document.getElementById('oracle-status').textContent = 'INVOKING THE ORACLE...';
document.getElementById('oracle-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">EXTRACTING DOMAIN INTELLIGENCE...</div>';
try {
const res = await fetch('/api/oracle', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ domain })
});
const data = await res.json();
if (data.error) { document.getElementById('oracle-status').textContent = data.error; document.getElementById('oracle-results').innerHTML = ''; return; }
const es = data.email_security || {};
const http = data.http_security || {};
const tls = data.tls || {};
const rdap = data.rdap || {};
const score = data.score || 0;
const scoreLevel = score >= 80 ? 'verified' : score >= 60 ? 'low' : score >= 40 ? 'medium' : score >= 20 ? 'high' : 'critical';
let html = `
<div class="result-card">
<div class="spread" style="margin-bottom:12px;">
<h3 class="card-title h-cyan">${data.domain} · ${data.ip}</h3>
<span class="status-badge ${scoreLevel}">HYGIENE ${score}/100</span>
</div>
<div class="score-shell" style="margin-bottom:12px;">
<div class="score-meta"><span>SECURITY POSTURE</span><strong>${score}/100</strong></div>
<div class="score-bar"><div class="score-fill" style="width:${score}%; background:var(--grad-ok);"></div></div>
</div>
</div>
<div class="results" style="grid-template-columns: 1fr 1fr; gap:14px;">
<div class="result-card">
<h3 class="card-title">EMAIL SECURITY</h3>
<div class="row" style="gap:6px; margin-bottom:8px;">
<span class="status-badge ${gradeBadgeClass(es.spf && es.spf.grade)}">SPF · ${es.spf && es.spf.grade || 'F'}</span>
<span class="status-badge ${gradeBadgeClass(es.dmarc && es.dmarc.grade)}">DMARC · ${es.dmarc && es.dmarc.grade || 'F'}</span>
<span class="status-badge ${gradeBadgeClass(es.dkim && es.dkim.grade)}">DKIM · ${es.dkim && es.dkim.grade || 'F'}</span>
</div>
${es.spf && es.spf.present ? `<div class="dim mono" style="font-size:0.74rem;">SPF policy: ${es.spf.policy}</div>` : '<div class="h-red mono" style="font-size:0.74rem;">No SPF — domain is spoofable</div>'}
${es.dmarc && es.dmarc.present ? `<div class="dim mono" style="font-size:0.74rem;">DMARC policy: ${es.dmarc.policy}</div>` : '<div class="h-red mono" style="font-size:0.74rem;">No DMARC — no enforcement</div>'}
${es.dkim && es.dkim.present ? `<div class="dim mono" style="font-size:0.74rem;">DKIM selectors: ${es.dkim.selectors_found.join(', ')}</div>` : '<div class="dim mono" style="font-size:0.74rem;">No DKIM selectors auto-discovered</div>'}
</div>
<div class="result-card">
<h3 class="card-title">HTTP SECURITY HEADERS</h3>
<div class="row" style="gap:6px; margin-bottom:8px;">
<span class="status-badge ${gradeBadgeClass(http.grade)}">GRADE · ${http.grade || 'F'}</span>
<span class="tag">${http.https_reachable ? 'HTTPS OK' : 'NO HTTPS'}</span>
</div>
<div class="dim mono" style="font-size:0.74rem; margin-bottom:6px;">Server: ${http.server || '—'} · Powered: ${http.powered_by || '—'}</div>
<div>${(http.missing || []).map(h => `<span class="tag hot">missing: ${h}</span>`).join('') || '<span class="tag ok">all headers present</span>'}</div>
</div>
<div class="result-card">
<h3 class="card-title">REGISTRATION</h3>
${renderDict({
REGISTRAR: rdap.registrar,
CREATED: rdap.created,
EXPIRES: rdap.expires,
UPDATED: rdap.updated,
STATUS: (rdap.status || []).join(', ') || '—'
})}
</div>
<div class="result-card">
<h3 class="card-title">TLS</h3>
${tls.error ? `<div class="h-red mono">${tls.error}</div>` : renderDict({
VERSION: tls.tls_version, CIPHER: tls.cipher,
NOT_BEFORE: tls.not_before, NOT_AFTER: tls.not_after,
ISSUER_CN: tls.issuer && tls.issuer.commonName,
SUBJECT_CN: tls.subject && tls.subject.commonName
})}
</div>
</div>
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title">DNS RECORDS</h3>
${Object.entries(data.dns || {}).map(([k, v]) =>
v && v.length ? `<div style="margin-bottom:6px;"><span class="tag">${k}</span> <span class="mono" style="font-size:0.78rem;">${v.join(', ').slice(0, 600)}</span></div>` : ''
).join('')}
</div>
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title">SUBDOMAINS (crt.sh) · ${(data.subdomains || []).length}</h3>
<div style="max-height:200px; overflow-y:auto;">
${(data.subdomains || []).slice(0, 200).map(s => `<span class="tag">${s}</span>`).join('') || '<div class="dim">none discovered</div>'}
</div>
</div>
${data.neighbors && data.neighbors.length ? `
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title">REVERSE-IP NEIGHBORS · ${data.neighbors.length}</h3>
<div style="max-height:200px; overflow-y:auto;">
${data.neighbors.slice(0, 50).map(n => `<span class="tag">${n}</span>`).join('')}
</div>
</div>` : ''}
`;
document.getElementById('oracle-results').innerHTML = html;
document.getElementById('oracle-status').textContent = 'ORACLE COMPLETE.';
refreshFX(document.getElementById('oracle-results'));
} catch (e) {
console.error(e);
document.getElementById('oracle-status').textContent = 'ORACLE CHANNEL CLOSED.';
}
}
/* ---------- MAIL TRACER ---------- */
async function scanMail() {
const email = document.getElementById('mail-input').value.trim();
if (!email) return;
document.getElementById('mail-status').textContent = 'TRACING MAIL INFRASTRUCTURE...';
document.getElementById('mail-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">QUERYING DNS · GRAVATAR · DMARC...</div>';
try {
const res = await fetch('/api/mailtracer', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ email })
});
const data = await res.json();
if (data.error) { document.getElementById('mail-status').textContent = data.error; document.getElementById('mail-results').innerHTML = ''; return; }
const level = data.trust_score >= 80 ? 'verified' : data.trust_score >= 60 ? 'low' : data.trust_score >= 40 ? 'medium' : 'critical';
const es = data.email_security || {};
document.getElementById('mail-results').innerHTML = `
<div class="result-card">
<div class="spread" style="margin-bottom:12px;">
<h3 class="card-title h-cyan">${data.email}</h3>
<span class="status-badge ${level}">${data.trust_level} · ${data.trust_score}/100</span>
</div>
<div class="score-shell" style="margin-bottom:14px;">
<div class="score-meta"><span>TRUST SCORE</span><strong>${data.trust_score}/100</strong></div>
<div class="score-bar"><div class="score-fill" style="width:${data.trust_score}%; background:var(--grad-ok);"></div></div>
</div>
<div class="row" style="gap:6px; margin-bottom:12px;">
<span class="tag ${data.flags.deliverable ? 'ok' : 'hot'}">${data.flags.deliverable ? 'DELIVERABLE' : 'NO MX'}</span>
${data.flags.disposable ? '<span class="tag hot">DISPOSABLE</span>' : ''}
${data.flags.role_based ? '<span class="tag warn">ROLE-BASED</span>' : ''}
${data.flags.free_provider ? '<span class="tag">FREE PROVIDER</span>' : ''}
</div>
<div class="row" style="gap:6px; margin-bottom:14px;">
<span class="status-badge ${gradeBadgeClass(es.spf && es.spf.grade)}">SPF · ${es.spf && es.spf.grade || 'F'}</span>
<span class="status-badge ${gradeBadgeClass(es.dmarc && es.dmarc.grade)}">DMARC · ${es.dmarc && es.dmarc.grade || 'F'}</span>
</div>
${data.gravatar && data.gravatar.exists ? `<div class="row" style="margin-bottom:12px; align-items:center;">
<img src="${data.gravatar.url}" style="width:64px; height:64px; border-radius:50%; border:1px solid var(--cyan);">
<span class="dim mono">Gravatar identity bound</span>
</div>` : ''}
<div>
<h4 class="mono dim" style="margin:0 0 6px;">MX RECORDS</h4>
${(data.mx || []).map(m => `<span class="tag">${m}</span>`).join('') || '<span class="tag hot">none</span>'}
</div>
<div style="margin-top:14px;">
<h4 class="mono dim" style="margin:0 0 6px;">SIGNAL FACTORS</h4>
${data.factors.map(f => `<div class="dim mono" style="font-size:0.78rem;">• ${f}</div>`).join('')}
</div>
</div>`;
document.getElementById('mail-status').textContent = 'TRACE COMPLETE.';
refreshFX(document.getElementById('mail-results'));
} catch (e) {
document.getElementById('mail-status').textContent = 'MAIL TRACER FAILED.';
}
}
/* ---------- CODE HUNTER ---------- */
async function scanCode() {
const username = document.getElementById('code-input').value.trim();
if (!username) return;
document.getElementById('code-status').textContent = 'PROBING GITHUB...';
document.getElementById('code-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">QUERYING GITHUB API...</div>';
try {
const res = await fetch('/api/codehunter', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ username })
});
const data = await res.json();
if (data.error) { document.getElementById('code-status').textContent = data.error; document.getElementById('code-results').innerHTML = ''; return; }
const maxLang = Math.max(1, ...(data.languages || []).map(l => l.count));
const maxHour = Math.max(1, ...(data.activity?.hourly_utc || [1]));
document.getElementById('code-results').innerHTML = `
<div class="result-card">
<div class="row" style="align-items:flex-start; gap:16px;">
<img src="${data.avatar}" style="width:96px; height:96px; border-radius:50%; border:2px solid var(--cyan); box-shadow:0 0 20px rgba(0,240,255,0.5);">
<div style="flex:1;">
<div class="spread" style="margin-bottom:6px;">
<h3 class="card-title h-cyan">${data.name || data.login} · <span class="dim">@${data.login}</span></h3>
<span class="status-badge verified">INFLUENCE ${data.influence_score}</span>
</div>
<div class="dim" style="font-size:0.86rem; margin-bottom:8px;">${data.bio || ''}</div>
<div class="row" style="gap:6px; flex-wrap:wrap;">
${data.company ? `<span class="tag">🏢 ${data.company}</span>` : ''}
${data.location ? `<span class="tag">📍 ${data.location}</span>` : ''}
${data.blog ? `<span class="tag">🔗 <a href="${data.blog}" target="_blank" style="color:inherit; text-decoration:none;">${data.blog}</a></span>` : ''}
${data.twitter ? `<span class="tag">🐦 ${data.twitter}</span>` : ''}
${data.email_public ? `<span class="tag hot">📧 ${data.email_public}</span>` : ''}
</div>
</div>
</div>
<div class="row" style="margin-top:14px; gap:18px; flex-wrap:wrap;">
<div><div class="dim mono" style="font-size:0.7rem;">FOLLOWERS</div><div style="font-size:1.4rem; font-family:var(--font-display);">${data.followers}</div></div>
<div><div class="dim mono" style="font-size:0.7rem;">FOLLOWING</div><div style="font-size:1.4rem; font-family:var(--font-display);">${data.following}</div></div>
<div><div class="dim mono" style="font-size:0.7rem;">REPOS</div><div style="font-size:1.4rem; font-family:var(--font-display);">${data.public_repos}</div></div>
<div><div class="dim mono" style="font-size:0.7rem;">⭐ STARS</div><div style="font-size:1.4rem; font-family:var(--font-display);">${data.total_stars}</div></div>
<div><div class="dim mono" style="font-size:0.7rem;">GISTS</div><div style="font-size:1.4rem; font-family:var(--font-display);">${data.gist_count}</div></div>
<div><div class="dim mono" style="font-size:0.7rem;">CREATED</div><div class="mono" style="font-size:0.86rem;">${(data.created_at || '').split('T')[0]}</div></div>
</div>
</div>
${(data.commit_emails && data.commit_emails.length) ? `
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title h-red">COMMIT EMAILS HARVESTED · ${data.commit_emails.length}</h3>
${data.commit_emails.map(e => `<div class="row" style="justify-content:space-between; padding:4px 0;"><span class="mono">${e.email}</span><span class="tag hot">${e.count}×</span></div>`).join('')}
</div>` : ''}
<div class="results" style="grid-template-columns: 1fr 1fr; gap:14px; margin-top:14px;">
<div class="result-card">
<h3 class="card-title">LANGUAGES</h3>
${(data.languages || []).map(l => `
<div style="margin-bottom:6px;">
<div class="row" style="justify-content:space-between; font-size:0.78rem;"><span>${l.name}</span><span class="dim mono">${l.count}</span></div>
<div class="mini-bar"><div style="width:${(l.count / maxLang) * 100}%;"></div></div>
</div>`).join('') || '<div class="dim">No languages</div>'}
</div>
<div class="result-card">
<h3 class="card-title">ACTIVITY · HOURLY (UTC)</h3>
<div class="row" style="gap:2px; align-items:flex-end; height:80px; margin-bottom:6px;">
${(data.activity?.hourly_utc || []).map(h => `<div style="flex:1; background:var(--grad-cool); height:${(h / maxHour) * 100}%; min-height:2px; border-radius:2px;" title="${h} events"></div>`).join('')}
</div>
<div class="row dim mono" style="font-size:0.66rem; justify-content:space-between;"><span>00h</span><span>12h</span><span>23h</span></div>
</div>
</div>
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title">TOP REPOSITORIES</h3>
<div class="results" style="grid-template-columns: repeat(auto-fill, minmax(260px, 1fr)); gap:10px;">
${(data.top_repos || []).map(r => `
<div class="result-card" style="border-color:rgba(0,240,255,0.25);">
<div class="spread" style="margin-bottom:6px;">
<a href="${r.url}" target="_blank" class="card-url" style="margin:0;">${r.name}</a>
<span class="tag">⭐ ${r.stars}</span>
</div>
<div class="dim" style="font-size:0.78rem; margin-bottom:6px;">${r.description || ''}</div>
<div class="row" style="gap:6px;">${r.language ? `<span class="tag">${r.language}</span>` : ''}${r.fork ? '<span class="tag warn">FORK</span>' : ''}</div>
</div>`).join('')}
</div>
</div>
${(data.orgs && data.orgs.length) ? `
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title">ORGANIZATIONS</h3>
<div>${data.orgs.map(o => `<span class="tag">${o.login}</span>`).join('')}</div>
</div>` : ''}
`;
document.getElementById('code-status').textContent = 'HUNT COMPLETE.';
refreshFX(document.getElementById('code-results'));
} catch (e) {
document.getElementById('code-status').textContent = 'GITHUB QUERY FAILED.';
}
}
/* ---------- WAYBACK SPECTRE ---------- */
async function scanWayback() {
const target = document.getElementById('wayback-input').value.trim();
if (!target) return;
document.getElementById('wayback-status').textContent = 'SUMMONING WAYBACK MACHINE...';
document.getElementById('wayback-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">TRAVERSING ARCHIVED TIMELINE...</div>';
try {
const res = await fetch('/api/wayback', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ target })
});
const data = await res.json();
if (data.error) { document.getElementById('wayback-status').textContent = data.error; document.getElementById('wayback-results').innerHTML = ''; return; }
if (!data.total_snapshots) {
document.getElementById('wayback-results').innerHTML = `<div class="result-card" style="text-align:center;"><h3 class="card-title dim">NO SNAPSHOTS</h3><div class="dim">${data.message || 'Wayback Machine has no records.'}</div></div>`;
document.getElementById('wayback-status').textContent = 'TIMELINE EMPTY.';
return;
}
const maxY = Math.max(...data.yearly.map(y => y.count), 1);
document.getElementById('wayback-results').innerHTML = `
<div class="result-card">
<div class="spread" style="margin-bottom:12px;">
<h3 class="card-title h-cyan">${data.target}</h3>
<span class="status-badge info">${data.total_snapshots.toLocaleString()} SNAPSHOTS</span>
</div>
<div class="row" style="gap:18px; flex-wrap:wrap;">
<div><div class="dim mono" style="font-size:0.7rem;">FIRST SEEN</div><div class="mono">${data.first_seen}</div></div>
<div><div class="dim mono" style="font-size:0.7rem;">LAST SEEN</div><div class="mono">${data.last_seen}</div></div>
<div><div class="dim mono" style="font-size:0.7rem;">SENSITIVE PATHS</div><div class="mono h-red" style="font-size:1.2rem;">${data.sensitive_count}</div></div>
</div>
</div>
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title">YEARLY DISTRIBUTION</h3>
<div class="row" style="gap:4px; align-items:flex-end; height:120px; margin-bottom:6px;">
${data.yearly.map(y => `<div style="flex:1; background:var(--grad-cool); height:${(y.count / maxY) * 100}%; min-height:3px; border-radius:3px;" title="${y.year}: ${y.count}"></div>`).join('')}
</div>
<div class="row dim mono" style="font-size:0.66rem; justify-content:space-between;">
<span>${data.yearly[0].year}</span><span>${data.yearly[data.yearly.length - 1].year}</span>
</div>
</div>
${data.sensitive.length ? `
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title h-red">⚠ SENSITIVE PATHS DISCOVERED · ${data.sensitive.length}</h3>
${data.sensitive.map(s => `
<div class="row" style="justify-content:space-between; padding:6px 0; border-bottom:1px solid rgba(255,255,255,0.04);">
<div style="flex:1;">
<span class="tag hot">${s.pattern}</span>
<a href="${s.snapshot}" target="_blank" class="card-url" style="margin:4px 0;">${s.url}</a>
</div>
<span class="dim mono" style="font-size:0.74rem;">${s.timestamp}</span>
</div>`).join('')}
</div>` : ''}
<div class="result-card" style="margin-top:14px;">
<h3 class="card-title">SAMPLE SNAPSHOTS · ${data.sample.length}</h3>
${data.sample.slice(0, 25).map(s => `
<div class="row" style="justify-content:space-between; padding:4px 0; font-size:0.78rem;">
<a href="${s.snapshot}" target="_blank" class="card-url" style="margin:0; flex:1;">${s.url}</a>
<span class="dim mono" style="font-size:0.72rem;">${s.timestamp}</span>
</div>`).join('')}
</div>`;
document.getElementById('wayback-status').textContent = `TIMELINE TRAVERSED · ${data.total_snapshots} CAPTURES.`;
refreshFX(document.getElementById('wayback-results'));
} catch (e) {
document.getElementById('wayback-status').textContent = 'TIME-MACHINE OFFLINE.';
}
}
/* ---------- PASTE DRAGNET ---------- */
async function scanPaste() {
const query = document.getElementById('paste-input').value.trim();
if (!query) return;
document.getElementById('paste-status').textContent = 'DEPLOYING DRAGNET ACROSS PASTE NETWORKS...';
document.getElementById('paste-results').innerHTML = '<div class="mono h-cyan" style="text-align:center; padding:40px;">SCRAPING DUMP SITES...</div>';
document.getElementById('paste-summary').innerHTML = '';
try {
const res = await fetch('/api/paste', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ query })
});
const data = await res.json();
if (data.error) { document.getElementById('paste-status').textContent = data.error; document.getElementById('paste-results').innerHTML = ''; return; }
const sites = Object.entries(data.per_site || {});
document.getElementById('paste-summary').innerHTML = `
<div class="result-card" style="margin-bottom:14px;">
<h3 class="card-title">DRAGNET REPORT · ${data.total_hits} TOTAL HITS</h3>
<div class="row" style="gap:6px; flex-wrap:wrap; margin-top:8px;">
${sites.map(([site, count]) => `<span class="tag ${count > 0 ? 'hot' : ''}">${site}: ${count}</span>`).join('')}
</div>
</div>`;
if (!data.results.length) {
document.getElementById('paste-results').innerHTML = '<div class="result-card" style="text-align:center;"><h3 class="card-title dim">CLEAN</h3><div class="dim">No paste-site references found.</div></div>';
} else {
document.getElementById('paste-results').innerHTML = data.results.map(r => `
<div class="result-card">
<div class="spread" style="margin-bottom:8px;">
<h3 class="card-title">${r.title || '(no title)'}</h3>
<span class="status-badge ${r.severity === 'CRITICAL' ? 'critical' : 'low'}">${r.severity}</span>
</div>
<div class="row" style="gap:6px; margin-bottom:6px;"><span class="tag">${r.site}</span></div>
<div class="dim" style="font-size:0.84rem; margin-bottom:8px;">${r.snippet || ''}</div>
<a href="${r.url}" target="_blank" class="card-url">${r.url}</a>
</div>`).join('');
}
document.getElementById('paste-status').textContent = `DRAGNET COMPLETE · ${data.total_hits} HITS.`;
refreshFX(document.getElementById('paste-results'));
} catch (e) {
document.getElementById('paste-status').textContent = 'DRAGNET FAILED.';
}
}
/* ---------- AI ANALYST ---------- */
async function runAnalyst() {
const target = document.getElementById('analyst-input').value.trim();
const mode = document.getElementById('analyst-mode').value;
if (!target) return;
document.getElementById('analyst-status').textContent = 'ORCHESTRATING MODULES — THIS MAY TAKE 30-60s...';
document.getElementById('analyst-summary').classList.add('hide');
document.getElementById('analyst-findings').classList.add('hide');
document.getElementById('analyst-modules').classList.add('hide');
try {
const res = await fetch('/api/analyst', {
method: 'POST', headers: { 'Content-Type': 'application/json' },
body: JSON.stringify({ target, mode })
});
const data = await res.json();
if (data.error) { document.getElementById('analyst-status').textContent = data.error; return; }
const verdictClass = data.verdict === 'CRITICAL' ? 'critical' : data.verdict === 'HIGH' ? 'high' : data.verdict === 'MODERATE' ? 'medium' : 'low';
const summary = document.getElementById('analyst-summary');
summary.classList.remove('hide');
summary.innerHTML = `
<div class="hud-panel reveal" style="margin-top:14px;">
<span class="bracket tl"></span><span class="bracket tr"></span>
<span class="bracket bl"></span><span class="bracket br"></span>
<div class="spread" style="margin-bottom:12px;">
<div>
<div class="panel-title" style="margin:0;">UNIFIED THREAT PROFILE</div>
<div class="dim mono" style="font-size:0.74rem; margin-top:6px;">${data.target} · detected as <span class="h-cyan">${data.detected_type}</span></div>
</div>
<span class="status-badge ${verdictClass}" style="font-size:0.78rem; padding:6px 14px;">${data.verdict} · ${data.risk_score}/100</span>
</div>
<div class="score-shell">
<div class="score-meta"><span>AGGREGATE RISK</span><strong>${data.risk_score}/100</strong></div>
<div class="score-bar"><div class="score-fill" style="width:${data.risk_score}%;"></div></div>
</div>
<div class="row" style="gap:6px; margin-top:12px; flex-wrap:wrap;">
${(data.modules_run || []).map(m => `<span class="tag ok">✓ ${m}</span>`).join('')}
</div>
</div>`;
const findings = document.getElementById('analyst-findings');
findings.classList.remove('hide');
findings.innerHTML = `
<div class="hud-panel reveal" style="margin-top:14px;">
<div class="panel-title">SIGNAL FINDINGS</div>
${(data.findings || []).map((f, i) => `<div class="result-card" style="margin-bottom:8px;"><div class="row" style="gap:10px;"><span class="tag">${String(i + 1).padStart(2, '0')}</span><span>${f}</span></div></div>`).join('')}
</div>`;
const modules = document.getElementById('analyst-modules');
modules.classList.remove('hide');
modules.innerHTML = `
<div class="hud-panel reveal" style="margin-top:14px;">
<div class="panel-title">MODULE PAYLOADS (RAW)</div>
${Object.entries(data.raw || {}).map(([name, payload]) => `
<details class="result-card" style="margin-bottom:8px;">
<summary class="card-title" style="cursor:pointer;">${name} ${payload && payload.error ? '<span class="status-badge critical" style="margin-left:8px;">ERROR</span>' : '<span class="status-badge verified" style="margin-left:8px;">OK</span>'}</summary>
<pre class="mono dim" style="margin-top:10px; max-height:300px; overflow:auto; font-size:0.72rem; padding:10px; background:rgba(0,0,0,0.4); border-radius:6px;">${JSON.stringify(payload, null, 2)}</pre>
</details>`).join('')}
</div>`;
document.getElementById('analyst-status').textContent = `SYNTHESIS COMPLETE · ${data.verdict}`;
refreshFX(summary); refreshFX(findings); refreshFX(modules);
} catch (e) {
console.error(e);
document.getElementById('analyst-status').textContent = 'ANALYST OFFLINE.';
}
}
</script>
</body>
</html>
================================================
FILE: the_big_brother/image_grabber.py
================================================
from duckduckgo_search import DDGS
from playwright.sync_api import sync_playwright
import time
import random
def fetch_images_google_playwright(query: str, limit: int = 3, headless: bool = True) -> list[str]:
"""Fallback: Fetch images using Playwright (Google Images)"""
print(f" [+] Attempting Google Images for {query}...")
try:
with sync_playwright() as p:
browser = p.chromium.launch(headless=headless)
context = browser.new_context(
user_agent="Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/120.0.0.0 Safari/537.36",
viewport={"width": 1920, "height": 1080},
locale="en-US"
)
page = context.new_page()
# Google Images Search with SafeSearch OFF
page.goto(f"https://www.google.com/search?tbm=isch&q={query}&safe=off", timeout=15000)
# Human-like delay
time.sleep(random.uniform(1.5, 3.0))
# Accept cookies if needed
try:
page.click("button:has-text('Reject all')", timeout=2000)
except: pass
images = page.evaluate("""() => {
const imgs = Array.from(document.querySelectorAll('img'));
return imgs
.map(img => img.src || img.getAttribute('data-src'))
.filter(src => src && src.startsWith('http') && src.length > 50 && !src.includes('googleg') && !src.includes('.svg'))
.slice(0, 5);
}""")
browser.close()
return images[:limit]
except Exception as e:
print(f" [-] Google Playwright error: {e}")
return []
def fetch_images_bing_playwright(query: str, limit: int = 3, headless: bool = True) -> list[str]:
"""Fallback: Fetch images using Playwright (Bing Images)"""
print(f" [+] Attempting Bing Images for {query}...")
try:
with sync_playwright() as p:
br
gitextract_16rro3kj/
├── .dockerignore
├── .gitignore
├── Dockerfile
├── LICENSE
├── README.md
├── VERSION
├── docker-compose.yml
├── pyproject.toml
├── requirements.txt
└── the_big_brother/
├── __init__.py
├── __main__.py
├── gui/
│ ├── __init__.py
│ ├── main.py
│ └── static/
│ ├── 3.css
│ └── index.html
├── image_grabber.py
├── modules/
│ ├── __init__.py
│ ├── ai_analyst.py
│ ├── breach_vault.py
│ ├── code_hunter.py
│ ├── crypto_analyzer.py
│ ├── dark_watch.py
│ ├── digital_footprint.py
│ ├── domain_oracle.py
│ ├── dork_studio.py
│ ├── exif_analyzer.py
│ ├── flight_radar.py
│ ├── geoint_spy.py
│ ├── mail_tracer.py
│ ├── network_mapper.py
│ ├── paste_dragnet.py
│ ├── phantom_id.py
│ ├── shadow_map.py
│ ├── sigint_sweep.py
│ ├── ssl_sentinel.py
│ └── wayback_spectre.py
├── notify.py
├── py.typed
├── resources/
│ ├── data.json
│ └── data.schema.json
├── result.py
├── reverse_search.py
├── scanner.py
├── sites.py
└── validators/
└── headless_validator.py
SYMBOL INDEX (180 symbols across 28 files)
FILE: the_big_brother/__init__.py
function get_version (line 13) | def get_version() -> str:
FILE: the_big_brother/gui/main.py
class FootprintRequest (line 43) | class FootprintRequest(BaseModel):
class NetworkRequest (line 47) | class NetworkRequest(BaseModel):
class DarkRequest (line 50) | class DarkRequest(BaseModel):
class CryptoRequest (line 53) | class CryptoRequest(BaseModel):
class SSLRequest (line 57) | class SSLRequest(BaseModel):
class ExifRequest (line 60) | class ExifRequest(BaseModel):
class DorkRequest (line 63) | class DorkRequest(BaseModel):
class DeepSearchRequest (line 67) | class DeepSearchRequest(BaseModel):
class GeointRequest (line 70) | class GeointRequest(BaseModel):
class FlightRequest (line 74) | class FlightRequest(BaseModel):
class PhantomRequest (line 79) | class PhantomRequest(BaseModel):
class BreachRequest (line 82) | class BreachRequest(BaseModel):
class SigintRequest (line 86) | class SigintRequest(BaseModel):
class ShadowMapRequest (line 89) | class ShadowMapRequest(BaseModel):
class DomainOracleRequest (line 92) | class DomainOracleRequest(BaseModel):
class MailTracerRequest (line 95) | class MailTracerRequest(BaseModel):
class CodeHunterRequest (line 98) | class CodeHunterRequest(BaseModel):
class WaybackRequest (line 101) | class WaybackRequest(BaseModel):
class PasteRequest (line 104) | class PasteRequest(BaseModel):
class AIAnalystRequest (line 107) | class AIAnalystRequest(BaseModel):
class JobState (line 121) | class JobState:
method __init__ (line 122) | def __init__(self):
class ScanRequest (line 131) | class ScanRequest(BaseModel):
class NotifyQueue (line 134) | class NotifyQueue(QueryNotify):
method __init__ (line 135) | def __init__(self, job_id, jobs_dict):
method update (line 140) | def update(self, result):
method start (line 161) | def start(self, message=None):
method finish (line 164) | def finish(self, message=None):
function run_scan_job (line 167) | def run_scan_job(job_id: str, username: str):
function validate_results (line 219) | def validate_results(job_id: str):
function start_scan (line 249) | async def start_scan(request: ScanRequest, background_tasks: BackgroundT...
function stop_scan (line 256) | async def stop_scan(job_id: str):
function get_results (line 263) | async def get_results(job_id: str):
function download_report (line 274) | async def download_report(job_id: str):
function deep_search (line 299) | async def deep_search(request: DeepSearchRequest):
function footprint_scan (line 305) | async def footprint_scan(request: FootprintRequest):
function phantom_scan (line 316) | async def phantom_scan(request: PhantomRequest):
function breach_scan (line 320) | async def breach_scan(request: BreachRequest):
function sigint_scan (line 324) | async def sigint_scan(request: SigintRequest):
function shadowmap_scan (line 328) | async def shadowmap_scan(request: ShadowMapRequest):
function network_scan (line 332) | async def network_scan(request: NetworkRequest):
function dark_search (line 341) | async def dark_search(request: DarkRequest):
function crypto_analyze (line 345) | async def crypto_analyze(request: CryptoRequest):
function ssl_scan (line 349) | async def ssl_scan(request: SSLRequest):
function tool_exif (line 353) | async def tool_exif(request: ExifRequest):
function tool_exif_upload (line 358) | async def tool_exif_upload(file: UploadFile = File(...)):
function tool_dork (line 400) | async def tool_dork(request: DorkRequest):
function tool_geoint (line 404) | async def tool_geoint(request: GeointRequest):
function tool_flight (line 408) | async def tool_flight(request: FlightRequest):
function oracle_scan (line 415) | async def oracle_scan(request: DomainOracleRequest):
function mail_scan (line 419) | async def mail_scan(request: MailTracerRequest):
function code_scan (line 423) | async def code_scan(request: CodeHunterRequest):
function wayback_scan (line 427) | async def wayback_scan(request: WaybackRequest):
function paste_scan (line 431) | async def paste_scan(request: PasteRequest):
function analyst_scan (line 435) | async def analyst_scan(request: AIAnalystRequest):
FILE: the_big_brother/image_grabber.py
function fetch_images_google_playwright (line 6) | def fetch_images_google_playwright(query: str, limit: int = 3, headless:...
function fetch_images_bing_playwright (line 43) | def fetch_images_bing_playwright(query: str, limit: int = 3, headless: b...
function fetch_images (line 72) | def fetch_images(query: str, limit: int = 3) -> list[str]:
function fetch_images_with_diag (line 81) | def fetch_images_with_diag(query: str, limit: int = 3):
function _short_err (line 128) | def _short_err(msg: str) -> str:
FILE: the_big_brother/modules/ai_analyst.py
function detect_type (line 28) | def detect_type(target: str) -> str:
function _safe (line 41) | async def _safe(coro, label):
function ai_analyst (line 48) | async def ai_analyst(target: str, mode: str = "auto") -> dict:
FILE: the_big_brother/modules/breach_vault.py
function get_severity (line 46) | def get_severity(data_classes: list) -> str:
function check_breaches_hibp (line 57) | async def check_breaches_hibp(email: str) -> list:
function check_pastes_hibp (line 98) | async def check_pastes_hibp(email: str) -> list:
function check_password_pwned (line 122) | async def check_password_pwned(password: str) -> dict:
function check_paste_aggregator (line 146) | async def check_paste_aggregator(query: str) -> list:
function breach_vault_search (line 169) | async def breach_vault_search(query: str, query_type: str = "email"):
FILE: the_big_brother/modules/code_hunter.py
function _get (line 18) | def _get(path: str, params: Optional[dict] = None):
function _commit_emails (line 32) | def _commit_emails(login: str, repos: list) -> list:
function _activity_buckets (line 46) | def _activity_buckets(events: list) -> dict:
function code_hunter (line 65) | async def code_hunter(login: str) -> dict:
FILE: the_big_brother/modules/crypto_analyzer.py
function analyze_crypto (line 4) | def analyze_crypto(address: str, coin: str):
FILE: the_big_brother/modules/dark_watch.py
function search_ransomware_leaks (line 5) | async def search_ransomware_leaks(query: str):
function search_dark_web (line 34) | async def search_dark_web(query: str):
function check_tor_status (line 83) | async def check_tor_status(onion_url: str):
FILE: the_big_brother/modules/digital_footprint.py
function check_email_osint (line 9) | async def check_email_osint(email: str):
function get_phone_info (line 54) | def get_phone_info(number_str: str):
function run_holehe (line 84) | async def run_holehe(email: str):
FILE: the_big_brother/modules/domain_oracle.py
function _resolver (line 26) | def _resolver():
function _query (line 33) | def _query(domain: str, rtype: str):
function _rdap (line 43) | def _rdap(domain: str) -> dict:
function _spf (line 76) | def _spf(txt_records: list) -> dict:
function _dmarc (line 98) | def _dmarc(domain: str) -> dict:
function _dkim (line 113) | def _dkim(domain: str) -> dict:
function _http_security_headers (line 129) | def _http_security_headers(domain: str) -> dict:
function _tls_meta (line 157) | def _tls_meta(domain: str) -> dict:
function _subdomains (line 175) | def _subdomains(domain: str) -> list:
function _reverse_ip (line 191) | def _reverse_ip(ip: str) -> list:
function domain_oracle (line 201) | async def domain_oracle(domain: str) -> dict:
FILE: the_big_brother/modules/dork_studio.py
function generate_dorks (line 1) | def generate_dorks(target: str, domain: str = ""):
FILE: the_big_brother/modules/exif_analyzer.py
function get_exif_data (line 6) | def get_exif_data(image_source: str, is_url: bool = True):
FILE: the_big_brother/modules/flight_radar.py
function get_flight_radar (line 4) | def get_flight_radar(lat: float, lon: float, radius_km: float = 100):
FILE: the_big_brother/modules/geoint_spy.py
function get_geoint_data (line 3) | def get_geoint_data(lat: str, lon: str):
FILE: the_big_brother/modules/mail_tracer.py
function _gravatar (line 36) | def _gravatar(email: str) -> str:
function _gravatar_exists (line 41) | def _gravatar_exists(url: str) -> bool:
function mail_tracer (line 49) | async def mail_tracer(email: str) -> dict:
FILE: the_big_brother/modules/network_mapper.py
function check_port (line 18) | async def check_port(ip, port):
function get_geoip (line 28) | def get_geoip(ip):
function get_rdap_whois (line 37) | def get_rdap_whois(domain):
function get_dns_records (line 53) | def get_dns_records(domain):
function scan_target (line 84) | async def scan_target(domain: str):
function generate_network_map (line 142) | def generate_network_map(data):
FILE: the_big_brother/modules/paste_dragnet.py
function _ddg_search (line 27) | def _ddg_search(query: str, max_results: int = 15):
function _hunt_site (line 36) | def _hunt_site(query: str, site: str):
function paste_dragnet (line 50) | async def paste_dragnet(query: str) -> dict:
FILE: the_big_brother/modules/phantom_id.py
function check_platform (line 74) | async def check_platform(session: aiohttp.ClientSession, platform: dict,...
function phantom_id_search (line 103) | async def phantom_id_search(username: str):
FILE: the_big_brother/modules/shadow_map.py
function resolve_to_ip (line 30) | def resolve_to_ip(target: str) -> str:
function check_abuseipdb (line 42) | async def check_abuseipdb(session: aiohttp.ClientSession, ip: str) -> dict:
function check_virustotal (line 76) | async def check_virustotal(session: aiohttp.ClientSession, target: str, ...
function check_urlhaus (line 113) | async def check_urlhaus(session: aiohttp.ClientSession, target: str) -> ...
function check_ipinfo (line 136) | async def check_ipinfo(session: aiohttp.ClientSession, ip: str) -> dict:
function shadow_map_analyze (line 157) | async def shadow_map_analyze(target: str):
FILE: the_big_brother/modules/sigint_sweep.py
function detect_sentiment (line 18) | def detect_sentiment(text: str) -> str:
function clean_html (line 29) | def clean_html(raw: str) -> str:
function fetch_reddit (line 39) | async def fetch_reddit(session: aiohttp.ClientSession, query: str) -> list:
function fetch_google_news (line 69) | async def fetch_google_news(session: aiohttp.ClientSession, query: str) ...
function fetch_hackernews (line 101) | async def fetch_hackernews(session: aiohttp.ClientSession, query: str) -...
function fetch_twitter_nitter (line 128) | async def fetch_twitter_nitter(session: aiohttp.ClientSession, query: st...
function sigint_sweep (line 168) | async def sigint_sweep(query: str):
FILE: the_big_brother/modules/ssl_sentinel.py
function get_ssl_info (line 5) | def get_ssl_info(domain: str):
FILE: the_big_brother/modules/wayback_spectre.py
function _cdx (line 23) | def _cdx(domain: str, limit: int = 5000):
function _flag_sensitive (line 46) | def _flag_sensitive(rows: list) -> list:
function _yearly_buckets (line 70) | def _yearly_buckets(rows: list) -> list:
function _mime_buckets (line 79) | def _mime_buckets(rows: list) -> list:
function wayback_spectre (line 84) | async def wayback_spectre(target: str) -> dict:
FILE: the_big_brother/notify.py
class QueryNotify (line 14) | class QueryNotify:
method __init__ (line 23) | def __init__(self, result=None):
method start (line 42) | def start(self, message=None):
method update (line 61) | def update(self, result):
method finish (line 80) | def finish(self, message=None):
method __str__ (line 99) | def __str__(self):
class QueryNotifyPrint (line 111) | class QueryNotifyPrint(QueryNotify):
method __init__ (line 117) | def __init__(self, result=None, verbose=False, print_all=False, browse...
method start (line 142) | def start(self, message):
method countResults (line 168) | def countResults(self):
method update (line 182) | def update(self, result):
method finish (line 259) | def finish(self, message="The processing has been finished."):
method __str__ (line 277) | def __str__(self):
FILE: the_big_brother/result.py
class QueryStatus (line 8) | class QueryStatus(Enum):
method __str__ (line 19) | def __str__(self):
class QueryResult (line 30) | class QueryResult():
method __init__ (line 35) | def __init__(self, username, site_name, site_url_user, status,
method __str__ (line 74) | def __str__(self):
FILE: the_big_brother/reverse_search.py
class ReverseImageSearcher (line 6) | class ReverseImageSearcher:
method __init__ (line 7) | def __init__(self, headless=True):
method _search_google (line 10) | async def _search_google(self, context, encoded_url):
method _search_bing (line 43) | async def _search_bing(self, context, encoded_url):
method _search_yandex (line 72) | async def _search_yandex(self, context, encoded_url):
method _search_tineye (line 99) | async def _search_tineye(self, context, encoded_url):
method search (line 123) | async def search(self, image_url: str) -> dict:
FILE: the_big_brother/scanner.py
class BigBrotherFuturesSession (line 48) | class BigBrotherFuturesSession(FuturesSession):
method request (line 49) | def request(self, method, url, hooks=None, *args, **kwargs):
function get_response (line 113) | def get_response(request_future, error_type, social_network):
function interpolate_string (line 143) | def interpolate_string(input_object, username):
function check_for_parameter (line 153) | def check_for_parameter(username):
function multiple_usernames (line 162) | def multiple_usernames(username):
function scan (line 170) | def scan(
function timeout_check (line 508) | def timeout_check(value):
function handler (line 533) | def handler(signal_received, frame):
function main (line 541) | def main():
FILE: the_big_brother/sites.py
class SiteInformation (line 14) | class SiteInformation:
method __init__ (line 15) | def __init__(self, name, url_home, url_username_format, username_claimed,
method __str__ (line 65) | def __str__(self):
class SitesInformation (line 80) | class SitesInformation:
method __init__ (line 81) | def __init__(
method remove_nsfw_sites (line 215) | def remove_nsfw_sites(self, do_not_remove: list = []):
method site_name_list (line 233) | def site_name_list(self):
method __iter__ (line 245) | def __iter__(self):
method __len__ (line 258) | def __len__(self):
FILE: the_big_brother/validators/headless_validator.py
class LinkValidationResult (line 10) | class LinkValidationResult:
class HeadlessValidator (line 18) | class HeadlessValidator:
method __init__ (line 19) | def __init__(self, headless: bool = True):
method __enter__ (line 26) | def __enter__(self):
method __exit__ (line 32) | def __exit__(self, exc_type, exc_val, exc_tb):
method validate (line 38) | def validate(self, url: str) -> LinkValidationResult:
method _validate_with_browser (line 49) | def _validate_with_browser(self, browser, url: str) -> LinkValidationR...
Condensed preview — 45 files, each showing path, character count, and a content snippet. Download the .json file or copy for the full structured content (511K chars).
[
{
"path": ".dockerignore",
"chars": 229,
"preview": "__pycache__\n*.pyc\n*.pyo\n*.pyd\n.Python\nenv\nvenv\n.venv\npip-log.txt\npip-delete-this-directory.txt\n.tox\n.coverage\n.coverage."
},
{
"path": ".gitignore",
"chars": 2706,
"preview": "__pycache__/\n*.py[cod]\n*$py.class\n\n# C extensions\n*.so\n\n# Distribution / packaging\n.Python\nbuild/\ndevelop-eggs/\ndist/\ndo"
},
{
"path": "Dockerfile",
"chars": 624,
"preview": "FROM mcr.microsoft.com/playwright/python:v1.49.0-jammy\n\nWORKDIR /app\n\n# Install Python dependencies\nCOPY requirements.tx"
},
{
"path": "LICENSE",
"chars": 1072,
"preview": "MIT License\n\nCopyright (c) 2025 The Big Brother\n\nPermission is hereby granted, free of charge, to any person obtaining a"
},
{
"path": "README.md",
"chars": 11068,
"preview": "<div align=\"center\">\n\n<br/>\n\n# ◆ 👁️THE BIG BROTHER · V5.0 👁️◆\n<br/>\n\n<img width=\"3910\" height=\"1088\" alt=\"x\" src=\"https:"
},
{
"path": "VERSION",
"chars": 6,
"preview": "2.1.0\n"
},
{
"path": "docker-compose.yml",
"chars": 173,
"preview": "services:\n the-big-brother:\n build: .\n ports:\n - \"8000:8000\"\n volumes:\n - .:/app\n environment:\n "
},
{
"path": "pyproject.toml",
"chars": 1698,
"preview": "[build-system]\nrequires = [\"setuptools>=61.0\", \"wheel\"]\nbuild-backend = \"setuptools.build_meta\"\n\n[project]\nname = \"the-b"
},
{
"path": "requirements.txt",
"chars": 353,
"preview": "fastapi>=0.104.0\nuvicorn>=0.24.0\nrequests>=2.31.0\nbeautifulsoup4>=4.12.0\nplaywright==1.49.0\nduckduckgo-search>=3.9.0\ntom"
},
{
"path": "the_big_brother/__init__.py",
"chars": 1592,
"preview": "\"\"\" The Big Brother Module\n\nThis module contains the main logic to search for usernames at social\nnetworks.\n\n\"\"\"\n\nfrom i"
},
{
"path": "the_big_brother/__main__.py",
"chars": 570,
"preview": "#! /usr/bin/env python3\n\n\"\"\"\nSherlock: Find Usernames Across Social Networks Module\n\nThis module contains the main logic"
},
{
"path": "the_big_brother/gui/__init__.py",
"chars": 0,
"preview": ""
},
{
"path": "the_big_brother/gui/main.py",
"chars": 14116,
"preview": "from fastapi import FastAPI, BackgroundTasks, Response, UploadFile, File, Form\nfrom fastapi.staticfiles import StaticFil"
},
{
"path": "the_big_brother/gui/static/3.css",
"chars": 31130,
"preview": "/* ============================================================\n THE BIG BROTHER V5 — EVOLVED CYBERPUNK\n Premium HUD"
},
{
"path": "the_big_brother/gui/static/index.html",
"chars": 130595,
"preview": "<!DOCTYPE html>\n<html lang=\"en\">\n<head>\n <meta charset=\"UTF-8\">\n <meta name=\"viewport\" content=\"width=device-width"
},
{
"path": "the_big_brother/image_grabber.py",
"chars": 5834,
"preview": "from duckduckgo_search import DDGS\nfrom playwright.sync_api import sync_playwright\nimport time\nimport random\n\ndef fetch_"
},
{
"path": "the_big_brother/modules/__init__.py",
"chars": 0,
"preview": ""
},
{
"path": "the_big_brother/modules/ai_analyst.py",
"chars": 6376,
"preview": "\"\"\"\nAI ANALYST — Cross-module orchestrator.\nTakes a single target + auto-detected type, fans out to the relevant modules"
},
{
"path": "the_big_brother/modules/breach_vault.py",
"chars": 7458,
"preview": "\"\"\"\nBREACH VAULT — Data breach checker.\nUses HaveIBeenPwned v3 k-anonymity API (no API key needed for passwords,\nbreache"
},
{
"path": "the_big_brother/modules/code_hunter.py",
"chars": 4927,
"preview": "\"\"\"\nCODE HUNTER — GitHub OSINT via public API (no auth required, rate-limited to 60/hr/IP).\nPulls user profile, repos, t"
},
{
"path": "the_big_brother/modules/crypto_analyzer.py",
"chars": 4866,
"preview": "import requests\nimport datetime\n\ndef analyze_crypto(address: str, coin: str):\n \"\"\"\n Analyzes a crypto address for "
},
{
"path": "the_big_brother/modules/dark_watch.py",
"chars": 3790,
"preview": "import requests\nfrom bs4 import BeautifulSoup\nimport asyncio\n\nasync def search_ransomware_leaks(query: str):\n \"\"\"\n "
},
{
"path": "the_big_brother/modules/digital_footprint.py",
"chars": 4586,
"preview": "import phonenumbers\nfrom phonenumbers import geocoder, carrier, timezone\n\nimport asyncio\nimport subprocess\nimport json\ni"
},
{
"path": "the_big_brother/modules/domain_oracle.py",
"chars": 8037,
"preview": "\"\"\"\nDOMAIN ORACLE — Passive deep domain intelligence.\nPulls WHOIS (RDAP), full DNS set, SPF/DMARC/DKIM posture, HTTP sec"
},
{
"path": "the_big_brother/modules/dork_studio.py",
"chars": 3385,
"preview": "def generate_dorks(target: str, domain: str = \"\"):\n \"\"\"\n Generates a list of advanced dorks for various platforms."
},
{
"path": "the_big_brother/modules/exif_analyzer.py",
"chars": 2041,
"preview": "from PIL import Image\nfrom PIL.ExifTags import TAGS, GPSTAGS\nimport requests\nfrom io import BytesIO\n\ndef get_exif_data(i"
},
{
"path": "the_big_brother/modules/flight_radar.py",
"chars": 1719,
"preview": "import requests\nimport datetime\n\ndef get_flight_radar(lat: float, lon: float, radius_km: float = 100):\n \"\"\"\n Fetch"
},
{
"path": "the_big_brother/modules/geoint_spy.py",
"chars": 1837,
"preview": "import requests\n\ndef get_geoint_data(lat: str, lon: str):\n \"\"\"\n Generates a GEOINT package for the given coordinat"
},
{
"path": "the_big_brother/modules/mail_tracer.py",
"chars": 3982,
"preview": "\"\"\"\nMAIL TRACER — Email infrastructure forensics.\nInspects an email address: MX validity, SPF/DMARC presence, disposable"
},
{
"path": "the_big_brother/modules/network_mapper.py",
"chars": 6602,
"preview": "import socket\nimport asyncio\nimport requests\nfrom pyvis.network import Network\nimport tempfile\nimport os\nimport dns.reso"
},
{
"path": "the_big_brother/modules/paste_dragnet.py",
"chars": 2201,
"preview": "\"\"\"\nPASTE DRAGNET — Hunts paste sites for a query using DuckDuckGo dorks.\nFalls back gracefully if duckduckgo-search is "
},
{
"path": "the_big_brother/modules/phantom_id.py",
"chars": 8428,
"preview": "\"\"\"\nPHANTOM ID — Username enumeration across 200+ platforms.\nUses async HTTP with HEAD/GET requests against a curated si"
},
{
"path": "the_big_brother/modules/shadow_map.py",
"chars": 9412,
"preview": "\"\"\"\nSHADOW MAP — IP/Domain threat intelligence and reputation analysis.\nQueries AbuseIPDB, VirusTotal (public API), Shod"
},
{
"path": "the_big_brother/modules/sigint_sweep.py",
"chars": 8631,
"preview": "\"\"\"\nSIGINT SWEEP — Social Intelligence gathering.\nFetches Reddit posts, Google News RSS, and Hacker News mentions\nfor a "
},
{
"path": "the_big_brother/modules/ssl_sentinel.py",
"chars": 2062,
"preview": "import ssl\nimport socket\nimport datetime\n\ndef get_ssl_info(domain: str):\n \"\"\"\n Connects to a domain and retrieves "
},
{
"path": "the_big_brother/modules/wayback_spectre.py",
"chars": 4107,
"preview": "\"\"\"\nWAYBACK SPECTRE — Wayback Machine CDX timeline + sensitive-path flagging.\nUses the free CDX server to enumerate ever"
},
{
"path": "the_big_brother/notify.py",
"chars": 9057,
"preview": "\"\"\"The Big Brother Notify Module\n\nThis module defines the objects for notifying the caller about the\nresults of queries."
},
{
"path": "the_big_brother/py.typed",
"chars": 0,
"preview": ""
},
{
"path": "the_big_brother/resources/data.json",
"chars": 102044,
"preview": "{\n \"$schema\": \"data.schema.json\",\n \"1337x\": {\n \"errorMsg\": [\n \"<title>Error something went wrong.</title>\",\n "
},
{
"path": "the_big_brother/resources/data.schema.json",
"chars": 4388,
"preview": "{\n \"$schema\": \"https://json-schema.org/draft/2020-12/schema\",\n \"title\": \"Sherlock Target Manifest\",\n \"description\": \""
},
{
"path": "the_big_brother/result.py",
"chars": 3191,
"preview": "\"\"\"The Big Brother Result Module\n\nThis module defines various objects for recording the results of queries.\n\"\"\"\nfrom enu"
},
{
"path": "the_big_brother/reverse_search.py",
"chars": 7158,
"preview": "from playwright.async_api import async_playwright\nimport urllib.parse\nimport asyncio\nimport random\n\nclass ReverseImageSe"
},
{
"path": "the_big_brother/scanner.py",
"chars": 35036,
"preview": "#! /usr/bin/env python3\n\n\"\"\"\nFind Usernames Across Social Networks Module\n\nThis module contains the main logic to search"
},
{
"path": "the_big_brother/sites.py",
"chars": 10619,
"preview": "\"\"\"The Big Brother Sites Information Module\n\nThis module supports storing information about websites.\nThis is the raw da"
},
{
"path": "the_big_brother/validators/headless_validator.py",
"chars": 3699,
"preview": "from dataclasses import dataclass\nfrom typing import Optional\n\ntry:\n from playwright.sync_api import sync_playwright\n"
}
]
About this extraction
This page contains the full source code of the chadi0x/TheBigBrother GitHub repository, extracted and formatted as plain text for AI agents and large language models (LLMs). The extraction includes 45 files (460.4 KB), approximately 124.8k tokens, and a symbol index with 180 extracted functions, classes, methods, constants, and types. Use this with OpenClaw, Claude, ChatGPT, Cursor, Windsurf, or any other AI tool that accepts text input. You can copy the full output to your clipboard or download it as a .txt file.
Extracted by GitExtract — free GitHub repo to text converter for AI. Built by Nikandr Surkov.