☰
freehire 安全策略与信任边界解析:漏洞报告范围、认证防线与 SSRF/Prompt 注入的防护设计
2026/10/23 1:47:12 网站建设 项目流程

【免费下载链接】freehire

freehire — the open-source search engine for job seekers

项目地址:https://gitcode.com/GitHub_Trending/fr/freehire
点击查看免费下载

freehire 是一套服务端应用,由公开 HTTP API、独立的抓取/富化 worker、PostgreSQL 数据库与 Meilisearch 索引共同组成。本篇文章以仓库根目录的 SECURITY.md 为骨架,逐条解读其信任边界、漏洞报告流程与 In/Out of Scope 划分,并结合仓库内真实源码(JWT 签发、账户链接、moderator 门禁、linksource 解析、LLM 富化清洗等)剖析每一条安全承诺背后的实现依据。读完你将清楚:什么算 freehire 的安全漏洞、应当如何私密上报、哪些情况(如自托管配置不当)不在项目责任范围内,以及"LLM 富化输出被污染"为何被设计为可过滤而非漏洞。

freehire 的系统构成与信任边界

按 SECURITY.md 的界定,freehire 由四类组件构成:

  • 公开 HTTP API:面向浏览器与扩展提供职位检索、账户、订阅等接口;
  • 独立的抓取/富化 worker:从各类招聘源抓取职位、解析正文并做 LLM 富化,典型入口见cmd/下的 ingest、tg-ingest 等命令;
  • PostgreSQL 数据库:存储用户、职位、订阅等全部业务数据(migrations 目录展示了完整的库表演进);
  • Meilisearch 索引:承担职位全文/语义检索。

信任边界的含义是:worker 抓取的网页正文、用户提交的表单内容、LLM 的富化输出,都属于"不可信输入",只有经过认证、授权、校验和清洗的数据才能进入数据库与索引。整份安全策略其实就是围绕"如何守住这条边界"展开的。

漏洞报告流程:必须私密上报

安全策略明确要求:疑似漏洞必须私密报告,而不是开公开 issue。两条上报通道:

  • 通过本仓库的GitHub Security Advisories(Security → Report a vulnerability)提交私有报告;
  • 邮件联系strelov1@gmail.com。

报告需要包含四类信息:

  1. 问题描述及其影响(impact);
  2. 复现步骤、概念证明(proof of concept)或相关日志;
  3. 受影响的 endpoint、worker、依赖包、commit SHA或配置;
  4. 已知的缓解措施(如果有)。

这条要求对应仓库内"修复闭环"的工程实践:报告中给出 commit SHA 与精确 endpoint,能帮助维护者快速定位到internal/api/handler/下具体 handler、cmd/下具体 worker 或某份配置,缩短从确认到修复的链路。

In Scope:项目明确负责的攻击面

认证与会话:JWT cookie、API key 与 OAuth 授权码流

策略点名的三类认证机制——JWT 会话 cookie、API-key 认证、授权码 OAuth 流(Google / GitHub / LinkedIn)——在源码中均有对应实现:

  • JWT 会话由 internal/identity/auth/token.go 的Issuer负责。它是无状态 HS256 签名,subject承载用户 id,并带一个私有声明tv(TokenVersion):版本号让无状态 token 仍然"可撤销"——只要更新账号的版本列,旧版本签发的一切 token 全部失效。同时每个 token 携带随机 16 字节的jti(session id)。
  • 会话 cookie 的Domain属性由 internal/identity/auth/domain.go 的CookieDomainForHost决定:按请求 host 归属于配置的 registrable 域名列表(如freehire.me),cookieDomains为空列表时仅限当前 host(开发环境)。
  • OAuth 侧,internal/api/handler/auth.go 中的oauthRegistry按请求 origin 构建 provider 回调,使登录流能在任意被服务的域名上完成;servedHosts限定可被当作 OAuth redirect origin 的精确 hostname——策略注释明确指出:后缀匹配适合 cookie 作用域,却错误地用于 redirect 目标,因此两者刻意分离。浏览器扩展连接流还被extensionRedirectAllowlist收紧到 chromiumapp.org / extensions.allizom.org。
  • API key 只保存哈希,明文 token 仅在创建响应中出现一次,internal/api/handler/api_keys.go 的apiKeyResponse只回传显示前缀(token_prefix)与 scope,永不回传明文。

账户接管:未验证邮箱是硬性禁区

策略把"用未验证的外部邮箱链接/创建账户,或将已有账户 re-key 到另一个身份"列为账户接管向量。源码将这条规则固化为硬约束:internal/identity/accounts/accounts.go 中,ErrNoVerifiedEmail被注释为"链接或创建账户前的硬性要求(unverified email is an account-takeover vector)"。对应的LinkOrCreateByEmail(accounts.go)只在外部身份携带provider 已验证的邮箱时才允许创建无密码账户;密码注册的CreateUser则显式传入emailVerified=false(accounts.go),后续必须通过MarkEmailVerified证明控制权。

授权:moderator 角色门禁

职位创建/编辑是 moderator 专属能力,任何绕过的尝试都属漏洞。internal/api/handler/jobs_moderation.go 的CreateJob/UpdateJob入口通过requireUserID取得当前用户并交给h.moderation服务,而路由注册处(见 auth.go 注释)明确指出RequireRole是真正的权限执行点,"moderator-only UI" 只是表面层。同样,社区帖子关闭等操作也显式挂载mw.moderator中间件(community.go)。策略同时强调"任何跨用户的数据泄漏"都在范围内——即水平越权同样属于漏洞。

SSRF:worker 抓取链路的红线

抓取/link-following worker(cmd/ingest、cmd/tg-ingest、internal/ingest/linksource)会跟随用户可控或第三方可控的 URL,因此是 SSRF 的高发点——被诱导请求内部地址或用于外传元数据。仓库用测试固化了这一防线:

  • internal/ingest/linksource/habrcareer_test.go 构造了一个恶意场景:短链u.habr.com/EVIL重定向到https://169.254.169.254/vacancies/123(云厂商元数据服务地址)。测试断言:重定向到 career.habr.com 之外的主机必须报错而不是解析出职位,防止元数据被外传或内部地址被探测;
  • internal/ingest/linksource/remoteyeah_test.go 同样以http://169.254.169.254/latest/meta-data/作为恶意重定向目标验证拒绝行为;
  • 各来源适配器(如 ashby.go)通过Match(u *url.URL)严格限定 host 与路径形状,非匹配 URL 直接跳过,重定向跨 host 即拒绝。

注入:API 与 ingest 管线可达的注入点

策略要求"通过 API 或 ingest 管线可达的注入"必须上报。仓库在存储侧做了纵深防御:internal/ingest/moderation/moderation.go 在写入前调用htmltext.Sanitize对描述做允许列表清洗(存储型 XSS 防护),创建/编辑共享同一条Validate契约(moderation.go)——URL 必须是绝对 http(s) 链接,缺失必需字段直接 400,任何脏数据在落库前被拦截。

密钥暴露

属于项目的、可访问freehire.me基础设施的凭据泄露(如数据库口令、Meilisearch master key、第三方服务 token)属于最高优先级漏洞,应直接私密上报。

Out of Scope:哪些情况不算 freehire 的漏洞

自托管部署的配置不当

策略明确把以下"自托管配置不当"划出范围,并指出安全运行自己的实例是使用者责任:

  • 弱JWT_SECRET;
  • 公网 HTTP 下COOKIE_SECURE=false(会话 cookie 不以 Secure 标记发送);
  • 数据库或 Meilisearch master key 暴露。

这正好呼应源码中的设计:cookieSecure由部署配置注入(auth.go),JWT 的强度完全取决于NewIssuer(secret, ttl)传入的 secret(token.go)。也就是说,代码层防线健全,但运行层安全由部署者负责。

无放大/不对称的纯流量淹没(DoS)

简单的流量灌水若没有放大或不对称效应,不属于漏洞;但利用 freehire 自身不对称性的 DoS(例如让 worker 持续抓取攻击者指定的昂贵目标)理论上仍在考察范围内。

LLM 富化的 Prompt 注入:被设计为"可过滤"而非漏洞

这是本策略最有技术特色的一条。worker 的输入是不可信的职位正文,LLM 只负责分类,其输出在存储前经过固定受控词表的清洗:

  • internal/ai/enrich/enrichment.go 的servedScalarEnums定义了对外提供的枚举字段集合(relocation、salary_period、company_type、company_size),这是"服务端可标量集合"的唯一定义处;
  • Validate(enrichment.go)逐一检查这些字段是否落在受控词表中,越界即报错;
  • Sanitize(enrichment.go)则把越界标量直接置空、多值字段只保留已知成员,并对Summary、TimezoneNote、SalaryCurrency等自由文本做长度裁剪(TrimTruncateRunes),同时过滤掉非正数等不合理的薪资值。

因此"让模型吐出垃圾"是预期行为,会被过滤,不构成漏洞——除非能证明它穿越了真实边界(执行代码、泄露密钥、持久化一个越界词表的值)。这一设计把"模型不可靠"转化为"输出不可信但无害",边界非常清晰。

不可达的第三方依赖漏洞

第三方依赖中无法通过 freehire 触达的漏洞不在范围内;提交依赖漏洞报告时必须附上"该问题确实可达"的证据。

聚合职位内容本身

职位数据来自第三方、非本项目创作,因此关于聚合职位内容(如某条职位描述不准确)的报告不属于安全范畴。

Notes for Reporters:最有价值的报告长什么样

策略对报告质量给出明确指引:最有用的报告应针对最新 release 或最新main,演示当前可复现的边界突破并具有真实影响,同时给出:

  • 精确受影响的 endpoint 或 worker;
  • commit SHA;
  • 相关配置;
  • 概念证明(PoC)。

从仓库结构看,一条高质量的 SSRF 报告可以精确到internal/ingest/linksource/下某个 source 的 host 校验缺陷,一条认证缺陷可以精确到internal/identity/auth/token.go的 claim 校验逻辑——这正是 SECURITY.md 要求提供 commit SHA 与 endpoint 的用意:让维护者能以最小代价定位并修复。

小结:freehire 的安全姿态

透过 SECURITY.md 与源码的对照,可以总结出 freehire 的三层安全姿态:

  1. 输入永远不可信:职位正文、用户提交、LLM 输出一律经过校验与清洗后才入库(moderation 的Validate/Sanitize、enrich 的受控词表);
  2. 边界由代码固话:JWT 版本化撤销、未验证邮箱禁止建户、moderator 门禁、linksource 跨 host 拒绝、API key 只存哈希,全部落在 internal/api 与 internal/identity、internal/ingest 的实现里,并有对应测试(如 habrcareer_test.go)守护;
  3. 运行责任交给部署者:自托管方必须自行保证JWT_SECRET强度、COOKIE_SECURE与数据库/索引凭据安全。

对安全研究者和自托管用户而言,这份策略既是漏洞报告的入口,也是一份浓缩的"攻击面地图"——沿着 In Scope 列出的六类问题(认证、账户接管、授权、SSRF、注入、密钥),再对照文中给出的源码路径逐条核实,即可快速形成对 freehire 安全模型的完整判断。

【免费下载链接】freehire

freehire — the open-source search engine for job seekers

项目地址:https://gitcode.com/GitHub_Trending/fr/freehire
点击查看免费下载

相关推荐

上一篇:开发者必看:text2vec-base-chinese-openmind的Transformer+Pooling实现细节
下一篇:Raspberry Pi 4内存映射I/O完全指南:GPIO与UART配置详解

创作声明:本文部分内容由AI辅助生成(AIGC),仅供参考

需要专业的网站建设服务?

联系我们获取免费的网站建设咨询和方案报价,让我们帮助您实现业务目标

立即咨询