别再傻等了,给 Claude Code 装个通知铃铛:Hook + SKILL 实战
1. 长任务跑起来之后我为什么总在切窗口Claude Code 这类 AI Agent 工具最舒服的用法是让它接一个稍微大一点的任务重构一个模块、补一整套单元测试、把某个接口从同步改成异步。这种活儿通常要跑几分钟到十几分钟中间还会穿插读文件、跑命令、改代码。问题就出在这段时间里——你根本不知道它到底跑完没有。我自己的习惯特别典型让 Claude Code 开始干活然后切到浏览器查个文档过两分钟忍不住切回来看看进度发现还在跑再切走再过两分钟又切回来。一个十分钟的任务我可能来回切了七八次。更难受的是权限确认Claude Code 执行到某一步需要你授权一条 shell 命令它会在那里静静等你点确认而你正在另一个窗口里以为它还在忙。等你十分钟后切回来发现它从第八分钟就卡住了前面全白等。这个问题的本质不是 Claude Code 慢而是任务完成状态没有主动推送到你面前。它是个本地 CLI 工具跑在终端里默认不会弹系统通知也不会给你发消息。你只能靠主动去看来感知状态而人一旦进入别的工作流就会忘记回来看。我一开始也偷懒想让 AI 自己解决。最常见的AI 方案是在~/.claude/CLAUDE.md里加一段提示词告诉模型任务完成后播放一个提示音比如## Task Completion Sound When you complete a task, play a sound: afplay /System/Library/Sounds/Glass.aiff实测下来这东西极不稳定。有时候响有时候不响完全看模型当时心情。原因也不难理解提示词是软约束模型对生成文本以外的操作类指令本来就不太可靠它可能觉得当前场景不需要播放声音就跳过了长对话里上下文还会被压缩这段指令的优先级会被降低甚至直接丢掉再加上什么算任务完成每次理解都不一样触发时机飘忽不定。所以正确的思路是确定性的动作交给确定性的机制。Claude Code 提供了 Hook 系统它是在特定事件发生时由工具本身去执行一段命令不经过模型判断触发是 100% 的。这篇就带你从零把 Hook 通知配起来再封装成一个可复用的 SKILL让任务跑完、需要授权时主动提醒你。适合谁看本地用 Claude Code 做开发的、跑 AI Agent 工作流的、经常被它到底跑完没有折磨的人。下面所有配置都可以直接复制我会把每一步的验证方法也写清楚。2. 前置准备TaoToken 接入与 Claude Code 环境确认在配 Hook 之前得先保证 Claude Code 本身能正常跑起来。如果你已经在用官方账号可以跳过接入部分直接看环境确认。如果你希望用统一的 API 入口来管理模型调用可以走 TaoToken 这套方案它的 Base URL 和 Key 管理比较集中后面配 Hook 时也不影响。先说清楚 TaoToken 是什么它是一个大模型 API 聚合入口提供统一的 Base URL 和 API KeyClaude Code、Cline、Codex 这类工具都可以通过它来调用模型。官网地址是 https://taotoken.net/?utm_sourcetaotoken_aicg_blog_endutm_mediumcsdnutm_campaignrewriteutm_content API 入口是 https://taotoken.net/api 这个不加 UTM。你需要先去控制台创建一个 API Key路径在 https://taotoken.net/console?utm_sourcetaotoken_aicg_blog_endutm_contentconsoleutm_campaignrewrite Key 列表在 https://taotoken.net/api-keys?utm_sourcetaotoken_aicg_blog_endutm_contentapi-keysutm_campaignrewrite 。拿到 Key 之后Claude Code 的接入方式是通过环境变量指定 Base URL 和 Key。在~/.zshrc或~/.bashrc里加上export ANTHROPIC_BASE_URLhttps://taotoken.net/api export ANTHROPIC_API_KEYsk-你的Key然后source ~/.zshrc让配置生效。这里有个坑要注意Claude Code 读的是ANTHROPIC_BASE_URL和ANTHROPIC_API_KEY这两个变量名别写成OPENAI_开头的否则它不认。改完之后用claude启动随便问一句你好能正常回复就说明接入通了。接下来确认 Hook 的运行环境。Hook 本质上是 Claude Code 在特定事件触发时去执行一条 shell 命令所以你需要第一确认 Claude Code 版本支持 Hook。Hook 是较新版本才有的能力用claude --version看一下版本太老就升级。第二确认本机有 Python 3因为后面通知脚本用 Python 写python3 --version能打印出来就行。第三确认配置文件位置。Claude Code 的用户级配置在~/.claude/settings.json如果这个文件不存在就手动创建注意它是标准 JSON不能有注释和尾逗号。关于模型选择如果你后面要跑长任务测试通知建议用一个稳定的模型 ID。在 TaoToken 的模型对话页面可以先验证模型是否可用 https://taotoken.net/chat?utm_sourcetaotoken_aicg_blog_endutm_contentmodel-chatutm_campaignrewrite 。如果你打算长期用 Claude Code 做编码和 Agent 工作流可以考虑 Coding Plan入口在 https://taotoken.net/coding-plan?utm_sourcetaotoken_aicg_blog_endutm_contentcoding-planutm_campaignrewrite 它更适合高频编码场景。环境确认清单检查项命令期望结果Claude Code 版本claude --version能打印版本号且支持 HookPython 版本python3 --versionPython 3.x配置目录ls ~/.claude/存在 settings.json 或可创建API 接入claude后提问能正常回复这四步都过了再往下配 Hook 就不会因为环境问题卡住。很多人配 Hook 失败最后发现是 Claude Code 根本没接上模型Hook 触发了但任务本身没跑起来自然看不到通知。3. 可复制配置settings.json Hook 与 notify.py 脚本这一节是核心给你两份可以直接复制的配置一份是 Claude Code 的 Hook 配置一份是通知脚本。先讲 Hook 配置。Claude Code 的 Hook 写在~/.claude/settings.json里。它的结构是按事件名分组每个事件下有一个 matcher 和一组 hooks。我们要监听的是Notification事件它会在 Claude Code 需要你注意时触发包括任务完成等待输入idle_prompt和需要权限确认permission_prompt。配置片段如下{ hooks: { Notification: [ { matcher: , hooks: [ { type: command, command: python3 ~/.claude/skills/agent-notifier/notify.py } ] } ] } }这里matcher留空表示匹配所有 Notification 子类型。type固定是commandcommand就是事件触发时执行的命令。注意路径要写绝对路径或者用~展开Claude Code 执行时的工作目录不一定是你以为的那个写相对路径很容易找不到脚本。如果你已经有 settings.json不要整个覆盖把hooks这一段合并进去就行。合并后可以用python3 -m json.tool ~/.claude/settings.json校验一下 JSON 是否合法格式错了 Claude Code 会直接忽略整个配置而且不一定报错这是最容易踩的坑。接下来是通知脚本notify.py。它的职责是从 stdin 读取 Claude Code 传过来的 JSON解析出事件类型和消息然后分发到各个通知渠道。下面是一个精简但可用的版本只依赖 Python 标准库#!/usr/bin/env python3 import sys import json import subprocess import platform from concurrent.futures import ThreadPoolExecutor def parse_event(raw): try: data json.loads(raw) except Exception: return {platform: claude-code, event: unknown, message: raw.strip()} ntype data.get(notification_type, unknown) msg data.get(message, ) if ntype idle_prompt: msg Task completed - waiting for your input elif ntype permission_prompt: msg Permission required return {platform: claude-code, event: ntype, message: msg} def send_sound(event): system platform.system() if system Darwin: subprocess.run([afplay, /System/Library/Sounds/Glass.aiff], checkFalse) elif system Linux: subprocess.run([paplay, /usr/share/sounds/freedesktop/stereo/complete.oga], checkFalse) def send_macos_notification(event): if platform.system() ! Darwin: return script display notification {} with title Claude Code.format(event[message]) subprocess.run([osascript, -e, script], checkFalse) def dispatch(event): channels [send_sound, send_macos_notification] with ThreadPoolExecutor(max_workerslen(channels)) as pool: futures [pool.submit(ch, event) for ch in channels] for f in futures: try: f.result() except Exception as e: print(channel error: {}.format(e), filesys.stderr) def main(): raw sys.stdin.read() event parse_event(raw) dispatch(event) if __name__ __main__: main()把这段保存到~/.claude/skills/agent-notifier/notify.py然后chmod x给它执行权限。脚本里几个关键点解释一下parse_event把 Claude Code 的notification_type映射成人类可读的消息idle_prompt我特意改成了 Task completed因为原始消息 Claude is waiting for your input 不够直观dispatch用线程池并发调用多个渠道单个渠道失败只打到 stderr不影响其他渠道。如果你还想加 Telegram 通知在dispatch的 channels 里加一个函数用urllib.request发 POST 到 Telegram Bot API 即可同样不需要装任何第三方库。这样设计的好处是只要机器上有 Python脚本拿来就能用不用pip install任何东西。配置和脚本都就位后目录结构应该是这样~/.claude/ ├── settings.json └── skills/ └── agent-notifier/ └── notify.py4. 验证请求手动触发与真实任务测试配完不验证等于没配。这一节给你两种验证方式先手动模拟事件确认脚本本身没问题再跑真实任务确认 Hook 真的被触发。先做手动测试。Claude Code 的 Hook 是通过 stdin 把 JSON 传给脚本的所以我们可以直接模拟这个输入echo {notification_type:idle_prompt,message:test} | python3 ~/.claude/skills/agent-notifier/notify.py如果配置正确你应该能听到提示音macOS 上还会弹出系统通知。再测权限请求echo {notification_type:permission_prompt,message:needs permission} | python3 ~/.claude/skills/agent-notifier/notify.py这一步能过说明脚本解析和渠道分发都正常。如果没声音先检查afplay路径是否存在Linux 上检查paplay或aplay是否装了。手动测试通过后做真实任务测试。启动 Claude Code给它一个会跑一会儿的任务比如请帮我给当前目录下的 utils.py 里所有函数补上 docstring并逐个说明参数含义。任务开始后你故意切到别的窗口不要盯着终端。等它跑完Claude Code 会进入等待输入状态触发idle_prompt这时你应该收到通知。如果任务中途需要你授权某条命令会触发permission_prompt同样会通知你。验证成功的标志有三个一是提示音响了二是 macOS 通知中心出现了 Claude Code 标题的通知三是通知文案是 Task completed - waiting for your input 而不是原始的英文长句。三个都满足说明整条链路通了。如果你接了 Telegram还可以做一次远程验证让 Claude Code 跑一个稍长的任务然后人离开电脑用手机看 Telegram 有没有收到消息。这一步能验证任务完成即提醒的闭环在跨设备场景下也成立。这里补充一个调试技巧如果真实任务没触发通知但手动测试正常问题多半在 Hook 配置没被加载。可以在notify.py开头加一行日志把每次收到的 stdin 写到文件里with open(/tmp/claude-hook.log, a) as f: f.write(raw \n)然后跑一次任务看/tmp/claude-hook.log有没有内容。有内容说明 Hook 触发了问题在脚本内部没内容说明 Hook 根本没触发回去检查 settings.json 的 JSON 格式和路径。5. 常见报错排查401、local proxy failed 与 reading choices配 Hook 和接入 API 的过程中报错基本集中在几类。这一节按真实报错来对照排查你遇到哪个查哪个。第一类401 Unauthorized。这个几乎都是 Key 的问题。检查ANTHROPIC_API_KEY是不是复制时带了空格或者 Key 已经失效。如果你用的是 TaoToken去 API Keys 页面重新生成一个路径在 https://taotoken.net/api-keys?utm_sourcetaotoken_aicg_blog_endutm_contentapi-keysutm_campaignrewrite 。注意环境变量改完要重新开一个终端或者source一下旧终端里还是老值。第二类local proxy failed或连接被拒绝。这类报错通常是 Base URL 写错了。确认ANTHROPIC_BASE_URL是https://taotoken.net/api不要多加斜杠或者写成别的路径。另外检查本机网络是否能正常访问该地址可以用curl -I https://taotoken.net/api看返回。如果公司网络有额外限制需要按公司规范处理不要用任何非正规的网络工具。第三类reading choices相关报错或者返回体解析失败。这通常出现在用 OpenAI 兼容格式去请求 Anthropic 接口或者反过来。Claude Code 走的是 Anthropic 协议Base URL 和请求格式要匹配。如果你在 Cline 或 Codex 里配注意它们的配置字段不一样Cline 用 MCP 配置时要写全 Base URL、Key、Model ID 三件套Codex 的auth.json里字段名也不同。三件套缺一个都会导致reading choices之类的解析错误。第四类Hook 触发了但没通知。分两种脚本报错和渠道失败。脚本报错看 stderrClaude Code 一般会把 Hook 的输出打出来渠道失败看是不是afplay路径不对或者 Telegram Token 填错。记住单个渠道失败不影响其他渠道所以如果声音响了但 Telegram 没收到问题只在 Telegram 那一路。第五类OAuth相关报错。如果你之前用官方账号登录过环境变量和 OAuth 登录可能冲突。Claude Code 优先用环境变量里的 Key如果 Key 无效又残留了 OAuth 状态就会报 OAuth 错误。解决办法是清理掉冲突的登录状态确保只用一种接入方式。排查顺序建议先确认 Claude Code 本身能正常对话排除 API 问题再手动测 notify.py排除脚本问题最后跑真实任务看 Hook 日志排除配置加载问题。这个顺序能帮你快速定位问题在哪一层而不是盲目改配置。6. 把通知封装成 SKILL长期用起来手动配一次 Hook 能用但如果你换机器、换项目或者同时用 Claude Code、Copilot CLI、Cursor 多个工具每次都重配一遍很烦。更好的做法是把它封装成一个 SKILL一次配置多平台复用。SKILL 的核心思路是统一事件模型。不同平台传过来的 JSON 格式不一样Claude Code 是{notification_type: idle_prompt, ...}Copilot CLI 是{hook_event_name: sessionEnd, ...}Cursor 是stop或afterFileEdit。notify.py 里加一层平台识别把这些格式统一解析成{platform, event, message}三元组再分发到通知渠道。这样新增一个平台只需要加一个解析分支通知渠道完全不用动。配置层面用一个notify-config.json管理渠道开关和凭据{ channels: { sound: { enabled: true }, macos_notification: { enabled: true }, telegram: { enabled: false, bot_token: , chat_id: } } }默认只开声音和系统通知Telegram、Email、Slack 这些需要凭据的默认关闭要用的时候再填。这样既安全又不会一上来就要求你配一堆东西。安装层面写一个setup.py做交互式引导自动检测你装了哪些 Agent 平台引导你填通知渠道然后自动往对应平台的配置文件里写 Hook。比如 Claude Code 写~/.claude/settings.jsonCursor 写它的hooks.json。写完发一条测试通知验证。这套封装下来你得到的不是一个一次性配置而是一个可迁移的通知能力。换电脑时把 skills 目录拷过去跑一次 setup 就行。对于长期跑 AI Agent 工作流的人来说这个投入很值——它把我是不是该去看一眼这个反复出现的念头变成了它跑完会主动叫我。最后说一个实测经验通知文案很重要。原始消息 Claude is waiting for your input 让人以为是它在等我改成 Task completed - waiting for your input 之后一眼就知道是任务跑完了。这种细节不影响功能但直接影响你用起来顺不顺手。配好之后你可以放心地把长任务丢给 Claude Code然后去干别的事等通知响了再回来。

相关新闻

企业人力资源管理系统课程设计:VB.NET+SQL Server三层架构与核心模块实现

企业人力资源管理系统课程设计:VB.NET+SQL Server三层架构与核心模块实现

简介:这份企业人力资源管理系统设计说明书面向计算机相关专业的课程设计、毕业设计学生及需要撰写开题报告与概要设计文档的开发者。内容围绕需求分析、数据库设计、各功能模块设计与实现、考核评价点四大部分展开,涵盖部门信息管理、员工信息管理、工资…

2026/10/12 22:18:21 阅读更多 →
pstack诊断Claude本地工具链卡顿的底层原理与实战

pstack诊断Claude本地工具链卡顿的底层原理与实战

1. “pstack-claude”不是工具名,而是开发者现场诊断的隐喻切口你搜“pstack-claude”,大概率是在终端里敲下pstack命令后,突然发现某个叫claude的进程卡死、响应迟滞,或者在调试 VS Code 插件、本地 Codex 服务、Claude Desktop …

2026/10/12 20:48:58 阅读更多 →
MVR蒸发器工艺全解析:二次蒸汽回收、设备选型与经济性测算

MVR蒸发器工艺全解析:二次蒸汽回收、设备选型与经济性测算

简介:MVR蒸发器工艺的设计介绍.doc是一份面向环保、化工、制药、食品等行业工艺与设备工程师的技术文档,重点讲解高盐废水处理中蒸汽机械再压缩(MVR)蒸发技术的原理、流程及设备选型。全文从基本工作原理切入,系统介绍…

2026/10/12 12:13:45 阅读更多 →

最新新闻

A*算法在路径规划中的原理与实践优化

A*算法在路径规划中的原理与实践优化

1. 路径规划中的A*算法初探第一次接触A算法是在开发仓库机器人导航系统时。当时我们尝试了Dijkstra、深度优先搜索等各种路径规划方法,要么计算时间太长,要么找到的路径不够优化。直到一位同事推荐了A算法,测试效果令人惊艳——在100x100的网…

2026/10/14 2:22:24 阅读更多 →
ViTPose 仓库 DeepFashion 服装关键点检测实战:DeepPose + ResNet 回归模型配置与评估指南

ViTPose 仓库 DeepFashion 服装关键点检测实战:DeepPose + ResNet 回归模型配置与评估指南

人工智能计算机视觉深度学习 【免费下载链接】ViTPose The official repo for [NeurIPS22] "ViTPose: Simple Vision Transformer Baselines for Human Pose Estimation" and [TPAMI23] "ViTPose: Vision Transformer for Generic Body Pose Estimation" 项…

2026/10/14 2:22:24 阅读更多 →
SimpMusic 的 Android 构建逻辑:用 Convention Plugins 与 Version Catalog 打造可扩展的 Gradle 构建体系

SimpMusic 的 Android 构建逻辑:用 Convention Plugins 与 Version Catalog 打造可扩展的 Gradle 构建体系

音视频 【免费下载链接】SimpMusic A cross-platform music app using YouTube Music for backend 项目地址: https://gitcode.com/gh_mirrors/si/SimpMusic 点击查看 免费下载 导读 本文围绕 SimpMusic 仓库中的构建配置实践,系统讲解如何用 Gradle C…

2026/10/14 2:22:24 阅读更多 →
从慢查询到Elasticsearch:倒排索引与分布式搜索入门避坑

从慢查询到Elasticsearch:倒排索引与分布式搜索入门避坑

第一次认真接触 Elasticsearch,不是赶新技术,而是被一条慢查询逼的。当时我在维护一个订单检索模块,数据量涨到六百多万条以后,按商品名称做模糊搜索的接口开始频繁超时。改 SQL、加索引、换缓存,折腾了一圈&#xff0…

2026/10/14 2:22:24 阅读更多 →
LVS+Keepalived+Nginx Docker负载均衡集群实战

LVS+Keepalived+Nginx Docker负载均衡集群实战

1. 项目概述:为什么一个负载均衡集群要绕这么大一圈?“基于Docker搭建lvskeepalivednginx实现高性能负载均衡集群”——这个标题里藏着三层技术栈的叠加,不是炫技,而是现实业务中反复踩坑后沉淀下来的务实选择。我最早在某高校实验…

2026/10/14 2:22:24 阅读更多 →
风电水电联合调度优化算法与工程实践

风电水电联合调度优化算法与工程实践

1. 项目背景与核心价值去年参与某省级电网清洁能源消纳项目时,我第一次接触到风-水联合调度这个课题。当时面对风电出力的强随机性和水电调节的滞后性,团队在制定优化运行方案时遇到了不少挑战。这个经历让我深刻认识到:在双碳目标下&#xf…

2026/10/14 2:21:24 阅读更多 →

日新闻

AnyPS5通用适配层设计:兼容性与性能的工程取舍

AnyPS5通用适配层设计:兼容性与性能的工程取舍

1. 从"AnyPS5"这个名字说起:它到底想解决什么问题第一次看到"AnyPS5"这个标题,我脑子里冒出来的第一个念头是:这大概率是一个围绕"跨平台运行"或者"通用适配"做文章的项目。名字里的"Any"…

2026/10/14 0:00:41 阅读更多 →
Flutter跨平台开发实战:二手交易应用与HarmonyOS适配

Flutter跨平台开发实战:二手交易应用与HarmonyOS适配

1. 项目概述:Flutter跨平台二手交易应用开发作为一名长期从事移动应用开发的工程师,我最近完成了一个基于Flutter框架的二手物品交易平台项目。这个项目最吸引我的地方在于它完美结合了Flutter的跨平台优势与HarmonyOS的生态特性,实现了"…

2026/10/14 0:00:41 阅读更多 →
DFS算法解决飞机降落调度问题实战

DFS算法解决飞机降落调度问题实战

1. 项目背景与核心思路飞机降落问题是一个经典的调度优化场景,也是算法竞赛和面试中的高频题目。这个题目要求我们合理安排多架飞机的降落顺序和时间,确保所有飞机都能安全着陆而不发生冲突。在实际航空管制中,这类问题直接关系到飞行安全和机…

2026/10/14 0:00:41 阅读更多 →

周新闻

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

流感时间序列预测实战:ARIMA/LSTM全流程拆解与避坑指南

简介:基于 ARIMA、LSTM、Transformer 等模型的流感时间序列预测 Python 源码,面向计算机相关专业课程设计与期末大作业学生,以及项目实战学习者。内容覆盖预处理、平稳性检验、定阶、残差分析、多模型对比预测的完整时序建模流程,…

2026/10/13 2:54:56 阅读更多 →
影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别

影刀RPA新手教程:键盘模拟输入实战——输入文本与模拟按键的区别 做影刀RPA自动化,十个新手有八个栽在"往输入框里填东西"这件事上:要么填不进去,要么填了一半,要么直接把原来内容追加在后面。这背后的根因&…

2026/10/13 16:22:04 阅读更多 →
影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容

影刀RPA新手教程:阅文起点小说数据采集实战——书籍信息与章节内容 1. 认识影刀:什么场景该用RPA采小说数据 起点中文网的页面结构相对稳定——分类榜单、书籍详情、章节内容三块独立页面,跳转链路清晰。这种场景非常适合影刀自动化&#x…

2026/10/13 1:58:08 阅读更多 →

月新闻

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

我发现了一个新思路:用 Remotion + Claude Code 像写代码一样自动化生成短视频

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/13 22:01:27 阅读更多 →
Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

Windows下 Codex 中 Chrome 和 Computer Use 插件不可用问题排查及解决参考方式:TaoToken 统一 Key 配置与验证

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/13 14:57:39 阅读更多 →
黑夜航拍船只数据集训练YOLOV5模型全流程解析

黑夜航拍船只数据集训练YOLOV5模型全流程解析

/* MD / 富文本中的 .toc(含博客园搬家等嵌套结构);.toc-box 在侧栏,不受影响 */#content_views .toc,/* 编辑器常在目录前后插入空 p(:empty 仍占 20px),一并去掉避免顶空隙 */#content_views.markdown_views > p:empty:has(+ .toc),#content_views.markdown_views …

2026/10/12 18:11:17 阅读更多 →