学习如何使用 Flask 构建一个可用于生产环境的 Webhook 服务器,该服务器可以异步抓取 LinkedIn 个人资料。 Crawlbase API 并将数据存储在 MySQL 数据库中。本教程涵盖环境搭建、数据库设计、回调服务器实现和实时监控等方面的内容。
您将构建什么
一个可扩展的 LinkedIn 数据抓取系统,具备以下功能:
- Flask webhook 服务器 接收抓取的数据
- MySQL数据库 用于结构化数据存储
- 异步处理 用于大批量刮削
- 实时监测 XNUMX月XNUMX日
使用案例
- 人才招聘自动化候选人搜寻和个人资料分析
- 市场情报追踪行业趋势和竞争对手动态
- 领先一代构建目标明确的B2B潜在客户数据库
- HR Analytics分析劳动力模式和职业发展轨迹
- 人工智能训练数据为机器学习模型生成数据集
本指南仅演示如何抓取公开的 LinkedIn 数据。请务必遵守 LinkedIn 的服务条款和数据保护法律。 Crawlbase 禁止提取私人数据。
第一部分:准备环境
A. 创建 Crawlbase 帐户和激活 LinkedIn 抓取
- 首先访问 Crawlbase 网站和 注册新账号.
- 去 LinkedIn 协议页面 阅读并接受条款。
- 添加您的账单详细信息,方法是转至 帐单信息设置.
B. 设置 MySQL 数据库
我们将使用 MySQL,因为它是一种流行的关系数据库管理系统,广泛用于各种应用程序。 在此示例中,我将使用 MySQL 版本 8。如果您的计算机上尚未安装此版本,请转到 MySQL官方安装手册.
安装完成后,打开MySQL命令行客户端。 系统将提示您输入 MySQL root 用户的密码。 输入密码后,您将进入MySQL命令行界面。 然后,您可以执行以下命令行。
- 创建一个新用户
1 | CREATE USER '链接爬虫'@'本地主机' 已识别 BY 'linked1nS3cret'; |
该代码创建一个名为的新 MySQL 用户 linkedincrawler 用密码 linked1nS3cret,仅限于从同一台计算机 (localhost) 连接。
- 建立资料库
1 | CREATE 数据库linkedin_crawler_db; |
该数据库将是一个空容器,可以存储表、数据和其他对象。
- 授予权限
1 | 授 全部 特权 ON linkedin_crawler_db。* TO '链接爬虫'@'本地主机'; |
这将授予我们的用户对新创建的数据库的完全特权和权限。
- 设置当前数据库
1 | 使用linkedin_crawler_db; |
这将选择我们的数据库并将所有指令定向到该数据库。
- 现在,让我们在当前选定的数据库中创建三个表:
crawl_requests,linkedin_profiles和linkedin_profile_experiences.
此 crawl_requests 将成为主表,充当跟踪整个异步抓取过程的机制。
在此表中,我们将有 3 列: url, status, crawlbase_rid.
此 status 列可以具有以下三个值之一 - waiting, receiving和 processed。 这些状态的目的将在稍后详细说明。
1 | 创建表 IF 不是 EXISTS `爬行请求` ( |
然后我们创建数据库索引以提高查询性能。
1 | CREATE 索引 `idx_crawl_requests_status` ON `crawl_requests` (`status`); |
对于最后 2 个表,它将允许您存储已爬网的 LinkedIn 个人资料及其相关详细信息的结构化信息。
1 | 创建表 IF 不是 EXISTS `linkedin_profiles` ( |
要查看您在 MySQL 数据库中创建的表,请在 MySQL 命令行界面或 MySQL 客户端工具中使用 SQL 查询。

C. 文件和目录结构
在 Python 中设置环境时组织文件非常重要。 确保它们都保存在同一项目目录下,如下所示:

D. 用Python构建虚拟环境
虚拟环境是一个隔离的空间,您可以在其中安装 Python 包,而不会影响系统范围内的 Python 安装。 管理不同项目的依赖关系很有用。
在这个项目中我们将使用 Python的3。 确保下载并安装适当的版本。
可选 吉特·巴什(Git Bash) 或终端执行以下命令。
1 | PROJECT_FOLDER$ python3 -m venv .venv |
创建虚拟环境后,您需要激活它。
1 | PROJECT_FOLDER$ 。 .venv/bin/激活 |
在项目文件夹中创建一个文本文件并将其另存为 PROJECT_FOLDER/requirements.txt。 该文件应包含我们的项目所依赖的以下 Python 包。
1 | 长颈瓶 |
使用以下命令安装依赖项 pip 命令。
1 | PROJECT_FOLDER$ pip install -r requests.txt |
在同一目录下,创建一个名为 PROJECT_FOLDER/settings.yml 这将作为您的 Crawlbase (TCP)令牌和 Crawler 名称。
1 | 令牌: < > |
E. 如何获取 LinkedIn 个人资料列表
要获取 LinkedIn 个人资料 URL 列表,您通常需要从不同来源(例如搜索结果、连接或公共个人资料)收集这些 URL。 您可以通过以下几种方式获取 LinkedIn 个人资料 URL:
- 手动采集:
- 您可以手动访问 LinkedIn 个人资料并从网络浏览器的地址栏中复制 URL。 此方法适用于配置文件数量较少的情况。
- 领英搜索结果:
- 使用 LinkedIn 的搜索功能根据特定条件(例如职位、地点、行业)查找个人资料。
- 复制搜索结果中列出的配置文件的 URL。
- 连接的个人资料:
- 如果您在 LinkedIn 上与某人建立了联系,您可以访问他们的联系列表并从那里提取个人资料 URL。
- 第三方API:
- 您可以利用以下工具构建一个单独的抓取工具 Crawlbase 自动收集 LinkedIn URL。我们可能会在以后的文章中介绍这一点,敬请关注。
为了本文的目的,我们提供了要抓取的 LinkedIn URL 列表。 默认情况下,我们已经配置了文本文件 LinkedIn 上最受关注的 5 名人物.
该文件位于 PROJECT_FOLDER/urls.txt.
注意: 每一行对应一个有效的 URL。 如果您有现成的 URL,您可以编辑此文本文件并将它们添加到列表中。
第二部分:为项目编写脚本
A. 使用 SQLAlchemy 创建 ORM 定义以与数据库交互
现在,我们必须构建一个脚本来处理 MySQL 数据库中的 LinkedIn 相关数据。 该脚本将首先从 SQLAlchemy 导入必要的模块以及类型提示的键入模块。
出于演示目的,我们将此脚本保存在 PROJECT_FOLDER/lib/database.py
1 | , 键入 进口 列表 |
此代码提供了创建数据库交互会话的功能。 请注意,我们将提供的脚本假设您已经安装了必要的库,并且 MySQL 服务器正在使用指定的连接详细信息运行。
B. 发送请求到 Crawlbase Crawler
此 Crawlbase Crawler 在使用回调 URL 的推送系统中异步运行。当您向 Crawler,它分配一个 唯一的RID 到每个请求。 Crawler 内部执行抓取,直到 成功响应 获得。 随后,此响应将传输回您指定的 Webhook,使您能够处理数据并将其存储在数据库中。
欲了解更多详情,您可以查看 完整的文档 的 Crawlbase Crawler.
该脚本首先导入必要的模块,包括用于发出 HTTP 请求的 requests、用于 URL 编码的 urllib.parse、用于处理 JSON 数据的 json 以及用于处理 JSON 解码错误的 JSONDecodeError。
出于演示目的,我们将此脚本保存在 PROJECT_FOLDER/crawl.py.
1 | 进口 要求 |
该代码将从以下位置读取 URL PROJECT_FOLDER/urls.txt 并将每个 URL 发送到 Crawlbase 用于抓取的 API,然后会使用请求 ID 进行响应,例如 {”rid”: 12341234}。 该代码将创建一个新的行条目来将 RID 存储在我们的 crawl_requests 表的状态为 waiting.
请注意,我们必须插入相应的 crawlbase_token 与 crawlbase_crawler 在此脚本中的名称,我们将在稍后的指南中解决。
C. 创建 Flask 回调服务器
长颈瓶 是一个用 Python 编写的微型 Web 框架,我们将用它来创建回调服务器。
确保您的回调能够执行 base64 解码和 gzip 解压缩。这很重要,因为 Crawler 引擎将使用带有 gzip 压缩和 base64 编码的 POST 方法将数据传输到您的回调端点。
出于演示目的,我们将此脚本保存在 PROJECT_FOLDER/callback_server.py.
1 | 进口 GZIP |
此代码设置了一个 Flask 应用,其中包含一个路由来处理来自 Crawlbase Crawler。 请注意 Crawlbase Crawler 将 RID 信息放入名为 rid.
此外,此代码将检查我们的 crawl_requests 具有相同 RID 的表 waiting 状态,否则请求将被忽略。
它还确保请求标头 Original-Status 与 PC-Status 是 HTTP 200 OK 成功状态响应代码。
一旦它从 Crawler,它将被处理(解码和解压缩)并保存在数据文件夹中,然后将 RID 的状态更新为 received.
D. 检索爬取数据并存储在数据库中的脚本
这段代码承担了定期监控crawl_requests表中RID状态的任务。 当它检测到已收到状态时,它会启动数据处理以填充 linkedin_profiles 和 linkedin_profiles_experiences 表。 完成后,它将 RID 状态更新为已处理。
出于演示目的,我们将此脚本保存在 PROJECT_FOLDER/process.py.
1 | 进口 JSON |
第三部分:执行脚本
A. 使用 Ngrok 启动本地隧道服务
恩格罗克 是一个创建到本地主机的安全隧道的工具,允许您暂时将本地托管的 Web 应用程序公开到互联网。
使用 Ngrok 创建一个临时的公共 URL,指向你本地托管的应用。这将允许我们使用 Flask Callback 服务器作为 webhook 连接到 Crawlbase Crawler.
1 | $ ngrok http 5000 |
一旦执行,获取公共 URL,我们稍后将使用它来创建我们的 Crawler.

注意:我们需要将 ngrok 指向端口 5000 作为我们的 Flask 应用程序 callback_server.py 将默认为同一端口。
B. 运行回调服务器
现在 Ngrok 已经初始化,我们可以运行回调服务器,它将捕获 RID 和爬取的内容 Crawlbase.
1 | PROJECT_FOLDER$ pythoncallback_server.py |
根据我们的代码,这是处理回调的完整路由:
https://400d-120-29-87-188.ngrok.io/crawlbase_crawler_callback
C. 测试回调服务器
我们必须确保回调服务器按预期工作并且可以传递 Crawlbase 。 为此,您可以执行以下代码片段并观察结果:
1 | $ 卷曲 -i -X POST 'http://localhost:5000/crawlbase_crawler_callback' -H 'RID:虚拟请求' -H '接受:应用/ JSON' -H '内容类型:gzip/json' -H '用户代理: Crawlbase 监控机器人 1.0' -H '内容编码:gzip' --数据二进制 '"\x1F\x8B\b\x00+\xBA\x05d\x00\x03\xABV*\xCALQ\xB2RJ)\xCD\xCD\xAD,J-,M-.Q\xD2QJ\xCAO\xA9\x04\x8A*\xD5\x02\x00L\x06\xB1\xA7 \x00\x00\x00' --压缩 |
本篇 curl 命令将使用自定义 HTTP 标头向您的回调 URL 发出 POST 请求 'HTTP_RID' 设置 'test'.
成功执行后,您应该收到如下所示的相同响应:
[app][2023-08-10 17:42:16] Callback server is working
D. 配置 Crawlbase Crawler 使用您的回调 URL
现在我们已经建立了一个工作的回调服务器并成功设计了一个数据库,现在是时候创建一个 Crawler 并将我们的回调 URL 集成到 Crawlbase.
登录到您的 Crawlbase 帐户并导航到 创建 Crawler 页面。输入您想要 Crawler 命名并粘贴我们之前创建的回调 URL。

注意: Crawlbase 已分配正常请求 (TCP) Crawler 对于 LinkedIn,所以我们必须选择该选项。即使选择了“正常”请求,也值得注意的是 Crawlbase 采用先进的人工智能机器人,其算法旨在模仿人类行为。此外,我们还使用高级住宅代理,进一步提高每次抓取的成功率。
E. 运行处理器
在同一目录中打开新的控制台或终端并激活。
1 | PROJECT_FOLDER$ 。 .venv/bin/激活 |
启动脚本 process.py
1 | PROJECT_FOLDER$ python process.py |
该脚本应在后台持续运行,因为它会频繁检查来自 Crawlbase Crawler.
F. 开始爬行
在触发您的请求之前,请确保您已为脚本设置了所有正确的变量。 从以下位置获取您的正常请求/ TCP 令牌 Crawlbase 帐户页面.
转到项目的主目录,打开 PROJECT_FOLDER/settings.yml 文件并添加您的 TCP 令牌值和 Crawler 名称。
1 | 令牌: < > |
在同一目录中打开新的控制台或终端并激活。
1 | PROJECT_FOLDER$ 。 .venv/bin/激活 |
启动脚本 crawl.py
1 | PROJECT_FOLDER$ pythoncrawl.py |
发送请求后,您应该注意到您的 crawl_requests 数据库将填充被爬取的 URL、来自 Crawlbase,以及如下图所示的相应状态。

第四部分: Crawler 监控
此 Crawlbase Crawler 是一个多功能系统,提供有用的功能,包括实时监控,可以方便地实时跟踪我们自定义爬虫的请求状态。要访问该页面,只需从您的 Crawler 仪表板并点击 实时监控 标签。

第五部分:结论
这是一个简单的组件流程图,总结了我们的项目范围:

总而言之,本指南带您构建高效且高度可扩展的 LinkedIn 个人资料 Crawler 运用 Crawlbase。面对从 LinkedIn 抓取数据的挑战,本指南提供了获取有价值的专业资料信息的战略解决方案。
Crawlbase作为网络爬虫领域的先驱,它配备了专为 LinkedIn 数据设计的算法,确保了流畅的抓取体验。该项目旨在创建一个 Flask 回调服务器,以高效的方式异步捕获 LinkedIn 个人资料,并将其存储在 MySQL 数据库中。需要注意的是,根据 LinkedIn 的条款,我们仅使用公开可用的数据。
从环境设置、脚本编写到代码执行,本指南涵盖了每个关键步骤。您将通过测试服务器、配置 Crawlbase Crawler,并启动数据请求。
Crawler 监控功能可在您推进过程中提供实时洞察,从而增强对流程的控制。掌握本指南后,您就可以充分利用 Crawlbase,打造动态 LinkedIn 个人资料 Crawler 它为您的项目提供宝贵的 LinkedIn 见解。
最后,前往 GitHub上 如果您想获取该项目的完整代码库。
第六部分:常见问题
问:如何向异步请求发送附加数据并在回调服务器中检索它?
你可以通过 callback_headers 您的请求的参数。 例如,假设我们想要附加附加数据,例如 BATCH-ID 与 CUSTOMER-ID 对于每个请求:
1 | 批次 ID = '批次 ID' |
然后添加 encoded_callback_headers 到请求中的 url 参数。
计费示例:
1 | 爬行库_api_url = f'https://api.crawlbase.com?token=mynormaltoken&callback=true&crawler=LinkedIn-Crawler&url=https%3A%2F%2Fwww.linkedin.com%2Fin%2Fwilliamhgates%2F&autoparse=true&callback_headers={encoded_callback_headers}' |
您可以通过 HTTP 请求标头在我们的回调服务器中检索这些值。 所以在我们的例子中, BATCH-ID 与 CUSTOMER-ID 将被检索为:
1 | batch_id = request.headers.get('批次 ID') |
欲了解更多信息,请访问本部分 Crawlbase 文件.
问:如何保护我的 Webhook?
您还可以 保护 webhook 端点 使用以下方法的任意组合:
- 将自定义标头附加到您的请求,其中包含一个令牌,您将验证该标头是否存在于 Webhook 中。
- 在 URL 中使用 URL 参数,在 Webhook 请求期间检查其是否存在。 例如:yourdomain.com/2340JOiow43djoqe21rjosi?token=1234。
- 限制仅接受 POST 请求。
- 验证特定的预期标头是否存在,例如
Pc-Status,Original-Status,rid等等。
顺便说一句,我们建议不要将 IP 白名单列入,因为我们的爬虫可能来自各种 IP,并且这些 IP 可能会发生变化,恕不另行通知。
问:抓取 LinkedIn 数据合法吗?
与抓取 LinkedIn 数据一样,网络抓取的合法性很复杂。 在里面 hiQ Labs 诉 LinkedIn Corp. 案,第九巡回法院裁定抓取公开数据可能不会违反《计算机欺诈和滥用法》(CFAA)。 然而,这是特定于 CFAA 的管辖权和解释的。 网络抓取的合法性取决于数据性质、使用的方法、协议和管辖法律等因素。
抓取受版权保护的内容或无视使用条款可能会引发法律问题。这就是为什么 Crawlbase 仅允许抓取公开可用的数据——无需登录会话即可访问的数据。
如果您需要更多地了解这如何适用于您的情况,建议您向法律专业人士寻求建议以获得准确的指导。
问:我还可以从 Crawlbase LinkedIn 抓取工具?
从 LinkedIn 个人资料中抓取的最有价值和最常见的数据如下:
- 姓名:用户的全名。
- 标题/专业:用户专业角色或专业知识的简短描述。
- 连接数:用户在 LinkedIn 上拥有的连接数。
- 位置:用户的地理位置。
- 封面图像:显示在用户个人资料顶部的可选横幅图像。
- 个人资料图片:用户的个人资料图片。
- 个人资料 URL:用户 LinkedIn 个人资料的唯一网址。
- 职位信息:有关用户当前和过去工作职位的详细信息。
- 教育信息:有关用户教育背景的信息。
- 经验:用户工作经验和职业经历的全面概述。
- 活动:LinkedIn 上用户生成的帖子、文章和其他活动。
- 资格:用户已获得的其他认证或资格。
- 组织:有关与用户关联的组织的详细信息。
问:为什么使用 Flask 进行 webhook?
- 定制: Flask 是一个 Python Web 框架,允许您创建高度可定制的 Webhook 端点。 您可以根据您的具体需求定义行为、身份验证和处理逻辑。
- 灵活性: Flask 为您提供了处理各种类型传入数据的灵活性,例如 JSON、表单数据或文件。 这在处理不同类型的 Webhook 负载时非常重要。
- 集成化: Flask 回调服务器可以轻松地与您现有的基于 Python 的应用程序或服务集成。 这使得将 Webhook 数据合并到您的工作流程中变得很方便。
- 身份验证和安全: 您可以在 Flask webhook 服务器中实施身份验证机制和安全措施,以确保只有授权源才能触发服务器。
- 调试和日志记录: Flask 提供了用于调试和日志记录的工具,这在监视 Webhook 服务器的行为和诊断任何问题时非常有用。
- 扩展和部署: Flask 应用程序可以部署到各种托管环境,允许您根据需要扩展 Webhook 服务器。
- 社区和资源: Flask 拥有一个庞大且活跃的社区,这意味着您可以轻松找到教程、文档和第三方包来帮助您构建和维护 Webhook 服务器。
问:为什么要进行更复杂的异步抓取而不是同步抓取?
同步抓取以顺序方式处理任务,这可能更简单但速度更慢,尤其是在涉及等待时。 异步爬网同时处理任务,从而提高性能和资源利用率。 它也非常适合同时处理大量任务。
实现起来更加复杂,调试起来也更具挑战性,但在这种情况下,利大于弊。这就是为什么 Crawlbase 推动 LinkedIn 的异步抓取。











