Skip to content

fix: 自动处理海外用户 cookie 同意弹窗#580

Open
yunanwg wants to merge 2 commits intoxpzouying:mainfrom
yunanwg:fix/cookie-consent-popup
Open

fix: 自动处理海外用户 cookie 同意弹窗#580
yunanwg wants to merge 2 commits intoxpzouying:mainfrom
yunanwg:fix/cookie-consent-popup

Conversation

@yunanwg
Copy link

@yunanwg yunanwg commented Mar 14, 2026

Summary

实现方式

  • 使用 go-rod 原生 API(page.Has() + Click()),无 JS 注入
  • 点击失败时兜底移除弹窗 DOM 元素
  • 遵循已有的 removePopCover() 模式

验证日志(海外网络 + 无头模式)

time="2026-03-14T22:43:47+01:00" level=info msg="Registered 13 MCP tools"
time="2026-03-14T22:43:47+01:00" level=info msg="MCP Server initialized with official SDK"
time="2026-03-14T22:43:47+01:00" level=info msg="启动 HTTP 服务器: :18060"
time="2026-03-14T22:43:57+01:00" level=warning msg="failed to load cookies: failed to read cookies from tmp file: open cookies.json: no such file or directory"
time="2026-03-14T22:44:03+01:00" level=info msg="检测到 cookie 同意弹窗,自动点击接受"
time="2026-03-14T22:44:04+01:00" level=info msg="GET /api/v1/feeds/list ai-report 200"

Test plan

  • 海外网络 + 无头模式:list_feeds 正常返回,日志显示弹窗被自动处理
  • 海外网络 + 非无头模式:check_login_statuslist_feeds 正常返回
  • 国内网络(VPN):正常返回,无副作用
  • go build 编译通过
  • 单元测试通过(go test ./pkg/...

🤖 Generated with Claude Code

海外用户访问小红书时会出现 GDPR cookie consent 弹窗,在无头模式下
该弹窗不可见但会阻塞所有后续操作。新增 dismissCookieConsent 函数,
在每次页面导航后自动检测并点击 "Accept all cookies" 按钮。

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@yunanwg yunanwg requested a review from xpzouying as a code owner March 14, 2026 21:45
@kimi-agent-bot
Copy link
Contributor

🔍 Kimi Code Agent 正在自动审查此 PR...

@kimi-agent-bot
Copy link
Contributor

我来帮你审查这个 PR。首先获取 PR 信息和代码变更。
我已经获取了 PR 的信息和代码变更。让我进行详细审查。

代码审查报告

1. 总体评价

这是一个针对性很强的修复 PR,解决了海外用户因 GDPR cookie 弹窗导致无头模式阻塞的问题。实现方式简洁,沿用了项目中已有的 removePopCover() 模式,代码结构清晰。

2. 详细审查意见

✅ 优点

  1. 实现方式合理:使用 go-rod 原生 API(Has() + Click()),无 JS 注入,稳定性较好
  2. 兜底机制完善:点击失败时会尝试直接移除弹窗容器,避免阻塞
  3. 覆盖全面:在 10 个文件的 13 个导航点都添加了调用,确保弹窗在各入口都被处理
  4. 对国内用户无影响:采用非阻塞检测,无弹窗时立即返回,无副作用

⚠️ 需要改进的问题

问题 1:边界情况处理(建议修改)

// xiaohongshu/popup.go
func dismissCookieConsent(page *rod.Page) {
    has, btn, err := page.Has(".cookie-banner__btn--primary")
    if err != nil {
        return
    }
    if !has {
        return
    }
    // ❌ 缺少对 btn == nil 的防御性检查

page.Has() 返回 (*Element, bool, error),理论上当 has == truebtn 不应为 nil,但从防御性编程角度,建议增加 nil 检查:

func dismissCookieConsent(page *rod.Page) {
    has, btn, err := page.Has(".cookie-banner__btn--primary")
    if err != nil || !has {
        return
    }
    if btn == nil {  // 建议添加
        return
    }
    // ...
}

问题 2:selector 匹配准确性

.cookie-banner__btn--primary 这个 selector 是否足够准确?建议确认:

  • 小红书是否只有一个 cookie 弹窗样式?
  • 是否有其他语言版本(如英文按钮文字不同但 class 相同)?
  • 是否可能存在多个按钮(如 "Accept" / "Reject" / "Manage preferences")?

如果弹窗有多个按钮,当前 selector 是否可能误点?

问题 3:部分文件的调用时机

publish.gopublish_video.go 中:

dismissCookieConsent(pp)
time.Sleep(2 * time.Second)

而在其他文件(如 login.gofeeds.go 等)中是先 dismissCookieConsenttime.Sleep

建议:统一调用顺序,确保在 DOM 稳定后再处理弹窗可能更可靠。建议检查是否有潜在的竞态条件。

📝 代码风格

  • diff 中删除了一些多余的空行,代码整洁度有提升,这是好的
  • 新增的 popup.go 文件遵循了项目的命名和代码风格

3. 验证情况

根据 PR 描述,作者已验证:

  • ✅ 海外网络 + 无头模式
  • ✅ 海外网络 + 非无头模式
  • ✅ 国内网络(VPN)
  • ✅ 编译通过
  • ✅ 单元测试通过

4. 建议修改

优先级 问题 建议
P2 防御性编程 dismissCookieConsent 中增加 btn == nil 检查
P3 代码注释 建议在 popup.go 顶部增加文件功能说明注释

5. 总结

此 PR 解决了实际问题,实现思路正确,建议合并。但建议作者考虑增加上述防御性编程的修改以提高代码健壮性。


@yunanwg 感谢贡献!这个修复对海外用户非常有帮助。请考虑上述建议是否可行。

当检测到弹窗容器但按钮 selector 不匹配时,输出 debug 日志便于排查。

Co-Authored-By: Claude Opus 4.6 (1M context) <noreply@anthropic.com>
@yunanwg
Copy link
Author

yunanwg commented Mar 14, 2026

问题 1(btn == nil 防御性检查): 查看了 go-rod 源码 query.go:105-114,当 has == trueel 一定非 nil,所以 nil 检查是死代码,暂不添加。

问题 2(selector 准确性): 这个担忧有道理。selector 是 CSS class(BEM 命名),不依赖按钮文字,所以多语言不受影响。但确实存在未来 DOM 变更的风险。已补充改进:先检测弹窗容器 div.cookie-banner 是否存在,若存在但按钮 selector 不匹配,输出 debug 日志便于排查。失败模式是安全的(静默 no-op,回到修复前行为)。见最新 commit。

问题 3(调用时机): 每个文件的 dismissCookieConsent 都放在对应的 WaitLoad/WaitDOMStable/WaitStable 之后,DOM 稳定后才检测弹窗。publish 文件中的 time.Sleep 是原有代码,顺序一致。

P3(文件顶部注释): 文件只有一个函数且已有清晰的函数注释,额外的文件注释是冗余的,保持简洁。

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant