| 99 | |
| 100 | |
| 101 | def _format_profile(user: dict, repos: list[dict], emails: set[str]) -> str: |
| 102 | lines = [ |
| 103 | f"[GitHub] Login: {user.get('login', '')}", |
| 104 | f"[GitHub] Name: {user.get('name') or 'N/A'}", |
| 105 | f"[GitHub] Bio: {user.get('bio') or 'N/A'}", |
| 106 | f"[GitHub] Location: {user.get('location') or 'N/A'}", |
| 107 | f"[GitHub] Company: {user.get('company') or 'N/A'}", |
| 108 | f"[GitHub] Email (profile): {user.get('email') or 'N/A'}", |
| 109 | f"[GitHub] Followers: {user.get('followers', 0)} | Following: {user.get('following', 0)}", |
| 110 | f"[GitHub] Public repos: {user.get('public_repos', 0)} | Gists: {user.get('public_gists', 0)}", |
| 111 | f"[GitHub] Account type: {user.get('type', 'N/A')}", |
| 112 | f"[GitHub] Created: {user.get('created_at', 'N/A')}", |
| 113 | f"[GitHub] Profile URL: {user.get('html_url', '')}", |
| 114 | ] |
| 115 | if emails: |
| 116 | lines.append(f"[GitHub] Emails found in commits: {', '.join(sorted(emails))}") |
| 117 | if repos: |
| 118 | lines.append(f"\n[GitHub] Recent repositories (up to {_MAX_REPOS}):") |
| 119 | for repo in repos: |
| 120 | stars = repo.get("stargazers_count", 0) |
| 121 | lang = repo.get("language") or "unknown" |
| 122 | desc = (repo.get("description") or "").strip() |
| 123 | suffix = f" — {desc[:80]}" if desc else "" |
| 124 | lines.append(f" • {repo['name']} [{lang}] ★{stars}{suffix}") |
| 125 | return "\n".join(lines) |
| 126 | |
| 127 | |
| 128 | async def run_github_osint(query: str, timeout_seconds: int = _DEFAULT_TIMEOUT) -> str: |