年轻只知学习营利,乃生命中最黯淡之时刻。—— 格里尔

Holehe:从邮箱线索出发,查找已注册账号的 OSINT 工具

项目地址:https://github.com/megadose/holehe

在开放信息收集的工作里,邮箱往往像一把轻巧却重要的钥匙。它可能只是一个简短的字符串,却可能连接着用户在不同网站留下的注册痕迹。Holehe 便围绕这一线索展开:输入一个邮箱地址,检查它是否关联了多个网站上的账号,并在部分支持找回密码流程的网站中获取相关信息。

Holehe 是一个使用 Python 3 的 OSINT 工具,目标明确而直接:高效地从邮箱地址寻找已注册账号。它支持检查 Twitter、Instagram、Imgur 等网站,并覆盖超过 120 个站点。

它并不试图替用户登录账号,也不要求输入目标邮箱的密码。它通过网站已有的注册、登录、密码找回或其他相关流程,判断某个邮箱是否可能已被某项服务使用。

README 对它的定位十分简洁:根据邮箱查找已注册账号。

一个邮箱,一组站点检查结果

Holehe 的核心能力,是检查邮箱地址是否关联了不同网站上的账号。

当一个邮箱被提交给 Holehe 后,各个模块会面向不同服务进行检查。不同服务采用的方式并不完全相同,有些模块使用注册流程,有些使用登录流程,有些借助密码找回功能,也有少数模块采用其他方式。

这种设计让 Holehe 不只是返回单一的存在或不存在结果。每个模块都以统一的字典结构返回数据,让调用方能够从标准化字段中读取检查结果。

1
2
3
4
5
6
7
8
{
"name": "example",
"rateLimit": false,
"exists": true,
"emailrecovery": "ex****e@gmail.com",
"phoneNumber": "0*******78",
"others": null
}

这个输出结构中包含多个关键字段:

  • name 表示模块名称
  • rateLimit 表示当前请求是否受到了速率限制
  • exists 表示对应服务上是否存在使用该邮箱的账号
  • emailrecovery 表示有时返回的部分遮蔽恢复邮箱
  • phoneNumber 表示有时返回的部分遮蔽恢复手机号
  • others 用于承载其他附加信息

这种统一格式让不同站点的检查结果拥有相同的外壳。无论模块背后采用注册、登录、密码找回还是其他方式,最终都可以被整理为便于程序处理的结构化结果。

支持命令行,也能嵌入 Python

Holehe 可以直接在命令行中运行,也可以快速嵌入已有的 Python 应用。

最简单的安装方式是通过 PyPI:

1
pip3 install holehe

安装完成后,可以直接在命令行中传入邮箱地址:

1
holehe test@gmail.com

这一条命令开启的,是一组面向不同网站模块的检查流程。对于希望快速执行检查的人来说,命令行入口足够直接,不需要先编写额外脚本。

Holehe 也提供 Docker 使用方式:

1
2
docker build . -t my-holehe-image
docker run my-holehe-image holehe test@gmail.com

通过镜像构建与运行,工具可以在容器中执行对应的邮箱检查命令。

用异步方式嵌入程序

除了命令行,Holehe 也可以作为 Python 代码的一部分参与现有流程。

README 中给出了 Snapchat 模块的示例。代码使用 trio 运行异步主函数,创建 httpx.AsyncClient,准备邮箱与输出列表,然后调用模块并打印结果。

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
import trio
import httpx

from holehe.modules.social_media.snapchat import snapchat


async def main():
email = "test@gmail.com"
out = []
client = httpx.AsyncClient()

await snapchat(email, client, out)

print(out)
await client.aclose()

trio.run(main)

这段代码呈现了 Holehe 模块化的一面。

邮箱地址被作为输入传入模块,HTTP 客户端承担请求工作,输出列表接收模块生成的结果。模块调用完成后,结果可以被打印出来,也可以被进一步送往其他程序逻辑。

对于 Python 应用而言,这种异步调用方式意味着 Holehe 不只是一个独立命令,而是可以嵌入应用流程中的一个组件。

超过 120 个站点模块

Holehe 的模块列表覆盖了大量不同类型的网站与服务。

其中包括社交媒体、开发者服务、内容社区、论坛、办公服务、音乐平台、购物服务、地图与运动服务、图像服务以及其他在线平台。Twitter、Instagram、GitHub、Google、Discord、Spotify、Snapchat、Yahoo、Zoho、Docker、Imgur、Patreon、Pinterest、SoundCloud、Tumblr、WordPress 等服务均在模块列表中出现。

模块的检查方式并不相同。

一些服务使用注册流程进行检查,例如 GitHub、Instagram、Twitter、Discord、Docker、Pinterest、SoundCloud 与 Tumblr。

一些服务使用登录流程,例如 Amazon、Bitmoji、eBay、Eventbrite、Evernote、Flickr、HubSpot、Snapchat、Yahoo 与 Zoho。

另一些服务会使用密码找回流程,例如 Adobe、Mail.ru 与 Odnoklassniki。

README 还为模块列出了是否经常受到速率限制。这个字段与统一输出中的 rateLimit 相互呼应,让使用者能够注意到请求在服务侧可能遇到的限制状态。

从找回密码流程中读取信息

Holehe 的一个重要特点,是能够在部分网站中利用忘记密码功能获取信息。

当某些服务的流程返回部分遮蔽的恢复邮箱或恢复手机号时,Holehe 会将这些内容放入标准输出结构中的 emailrecoveryphoneNumber 字段。

例如,恢复邮箱可能以类似下面的形式出现:

1
ex****e@gmail.com

恢复手机号则可能以部分遮蔽的形式出现:

1
0*******78

Holehe 不把这些字段当作必然存在的数据。README 使用了有时这个表达,说明这些信息只会在部分场景、部分模块中被返回。对于调用方而言,这些字段是可能出现的补充信息,而不是每次检查都会得到的固定结果。

标准化输出让模块更容易组合

在拥有大量站点模块的工具中,输出的一致性十分重要。

Holehe 为每个模块规定了相同的数据结构。这样一来,调用方不需要因为目标站点不同而为每个模块分别适配完全不同的返回格式。是否存在账号、是否被限流、是否有部分遮蔽的恢复邮箱、是否有部分遮蔽的手机号,以及其他信息,都能够通过固定字段读取。

这种结构让命令行展示与 Python 集成拥有共同的数据基础。

在命令行中,用户可以看到模块检查的结果。在 Python 中,开发者则可以将结果列表继续用于打印、过滤、保存或传递给后续流程。模块背后的服务不同,数据的基本形状却保持一致。

速率限制也是结果的一部分

网络服务通常会对频繁请求施加限制。Holehe 没有把这一情况隐藏在执行过程里,而是将其作为模块输出的一部分。

rateLimit 字段用于标识是否受到了速率限制。README 还在模块列表中标出哪些服务经常出现速率限制。

这让检查结果不只有账号是否存在这一层含义。一次检查也会告诉调用方,当前服务是否已经对请求频率作出反应。对于依赖多个模块执行的流程而言,速率限制状态本身就是需要被读取和处理的信息。

面向教育用途的工具定位

Holehe 在 README 中明确写明,它面向教育用途构建。

这一定位与它的工作方式紧密相关。工具以邮箱为起点,检查不同在线服务中是否存在关联账号,并从部分密码找回流程中读取可能返回的信息。它关注的是公开可访问的服务流程与账号存在性线索,将结果整理成能够被命令行或 Python 程序使用的数据。

从一个邮箱地址出发,到多个站点模块逐一检查,再到标准化的结构化输出,Holehe 将原本分散的在线服务流程收拢为一个可调用的 Python 工具。

它像一张由模块织成的网:每个模块面向一个服务,每个服务返回自己的检查结果,而统一的数据格式则让这些结果能够被放在同一张表面上阅读。邮箱仍然只是一个入口,但在 Holehe 的流程中,它能够被转化为一组关于不同网站账号关联状态的结构化信号。