内容
# SciTeX Notification (<code>scitex-notification</code>)
<!-- scitex-badges:start -->
[](https://pypi.org/project/scitex-notification/)
[](https://pypi.org/project/scitex-notification/)
[](https://github.com/ywatanabe1989/scitex-notification/actions/workflows/test.yml)
[](https://github.com/ywatanabe1989/scitex-notification/actions/workflows/install-test.yml)
[](https://codecov.io/gh/ywatanabe1989/scitex-notification)
[](https://scitex-notification.readthedocs.io/en/latest/)
[](https://www.gnu.org/licenses/agpl-3.0)
<!-- scitex-badges:end -->
<p align="center">
<a href="https://scitex.ai">
<img src="docs/scitex-logo-blue-cropped.png" alt="SciTeX" width="400">
</a>
</p>
<p align="center"><b>一次性调用通知,支持9种后端 — 音频,桌面,Emacs,Matplotlib,Playwright,电子邮件,Webhook,Telegram,Twilio。</b></p>
<p align="center">
<a href="https://scitex-notification.readthedocs.io/">完整文档</a> · <code>pip install scitex-notification</code>
</p>
---
## 问题与解决方案
| # | 问题 | 解决方案 |
|---|---------|----------|
| 1 | **临时通知混乱** — `smtplib.sendmail`, `requests.post(slack_webhook, …)`, `plyer.notify`, `twilio.rest.Client`, `print + beep` 均需要不同的API,环境变量和错误处理 | **一次调用,九种后端** — `stxn.alert("done")` 路由到音频TTS,桌面,Emacs,Matplotlib,Playwright,电子邮件,Webhook,Telegram和Twilio,具有统一的签名 |
| 2 | **静默故障浪费时间** — Webhook 500错误或SMTP宕机,代理未通知,导致用户盯着终端 "以防万一" | **自动故障转移链** — 默认顺序 音频 → Emacs → Matplotlib → Playwright → 电子邮件;第一个可用的后端获胜,基于级别的路由将 `critical` 提升到电话/短信 |
| 3 | **AI代理无声音** — 长时间作业和夜间训练结束时无人通知;用户无法离开桌面或睡觉 | **升级到电话/短信** — `stxn.call()` / `stxn.sms()` 通过Twilio唤醒用户以获取关键事件;音频TTS覆盖整个房间,Telegram/Webhook覆盖其他人 |
## 支持的后端
<details>
<summary>9种后端,统一API</summary>
| 后端 | API | 传输 | 成本 | 互联网 | 备注 |
|---------|-----|-----------|------|----------|-------|
| 音频 | `alert()` | TTS到本地扬声器 | 免费 | 无 | 通过 [scitex-audio](https://github.com/ywatanabe1989/scitex-audio);支持SSH中继 |
| 桌面 | `alert()` | `notify-send` / PowerShell | 免费 | 无 | Linux / WSL |
| Emacs | `alert()` | `emacsclient` 消息 | 免费 | 无 | 弹出窗口,迷你缓冲区或警报 |
| Matplotlib | `alert()` | 视觉弹出窗口 | 免费 | 无 | |
| Playwright | `alert()` | 浏览器弹出窗口 | 免费 | 无 | |
| 电子邮件 | `alert()` | SMTP | 免费 | 需要 | Gmail,SMTP中继 |
| Webhook | `alert()` | HTTP POST | 免费 | 需要 | Slack,Discord,自定义端点 |
| Twilio | `call()` `sms()` | 电话呼叫 / 短信 | 付费 | 需要 | [Twilio](https://www.twilio.com/) 设置需 |
`alert()` 按故障转移顺序尝试后端,直到一个成功。 `call()` 和 `sms()` 直接针对Twilio。
</details>
## 听觉反馈 -> 电话呼叫升级
当AI代理需要用户关注时 — 即使在用户睡觉时 — 它可以从音频升级到电话呼叫。
<p align="center">
<img src="docs/called-take-your-time.png" alt="终端中的代理升级工作流" width="420">
<img src="docs/scitex-alert.png" alt="SciTeX Alert — 电话呼叫历史记录" height="280">
</p>
<p align="center"><em>图1:左 — Claude Code终端显示音频 → 电话呼叫升级,在7次连续听觉反馈但用户无响应后。右 — iPhone接收到AI代理重复的“SciTeX Alert”呼叫。</em></p>
> **穿透iPhone静音模式**:
> 1. **紧急绕过(最可靠)**:将Twilio号码保存为联系人 → 铃声 → 启用 **紧急绕过**。所有呼叫都会响铃,无论聚焦/静音模式如何。
> 2. **重复呼叫(备用)**:iOS允许在3分钟内来自同一号码的第二次呼叫响铃。 `repeat=2` 自动触发,间隔30秒。
<details>
<summary><strong>Claude Code命令示例(/speak-and-continue)</strong></summary>
[`/speak-and-continue` 命令](./docs/speak-and-continue.md) 是scitex-notification实际应用的示例。它配置了一个AI编码代理(Claude Code):
1. **提供TTS反馈** 通过 `audio_speak` MCP工具,在自主工作时
2. **重复** 相同的音频消息,当用户再次发送 `/speak-and-continue` (他们可能不在)
3. **计数** 连续讲话次数,无用户响应(讲话计数器)
4. **升级到电话呼叫** 在7次无回答的讲话后 — 如果用户正在睡觉,则唤醒用户
这使得24/7开发工作流成为可能:代理自主工作,大声汇报进度,并在需要用户关注或所有任务完成时呼叫用户的电话。
</details>
## 安装
需要Python >= 3.10。
```bash
pip install scitex-notification
```
安装可选后端:
```bash
pip install "scitex-notification[audio]" # 音频通知通过 scitex-audio
pip install "scitex-notification[twilio]" # 通过Twilio发送短信
pip install "scitex-notification[mcp]" # AI代理的MCP服务器
pip install "scitex-notification[all]" # 所有功能
```
## 快速入门
```python
import scitex_notification as stxn
stxn.alert("训练完成!") # 故障转移链
stxn.alert("关键错误", level="critical") # 可能升级到电话/短信
stxn.call("服务器宕机 — 唤醒!") # Twilio电话
stxn.sms("构建完成") # Twilio短信
```
## 4种接口
<details>
<summary><strong>Python API</strong></summary>
<br>
```python
import scitex_notification as notification
notification.alert("任务完成") # 默认后端(带故障转移)
notification.alert("错误", backend="email") # 指定后端
notification.alert("关键", backend=["sms", "email"]) # 多个后端
notification.call("紧急!") # 通过Twilio拨打电话
notification.sms("构建完成!") # 通过Twilio发送短信
notification.available_backends() # 列出已安装的后端
```
> **[完整API参考](https://scitex-notification.readthedocs.io/)**
</details>
<details>
<summary><strong>CLI命令</strong></summary>
<br>
```bash
scitex-notification --help # 显示所有命令
scitex-notification send "任务完成" # 通过默认后端发送
scitex-notification send "完成" --backend email # 通过指定后端发送
scitex-notification config # 显示配置
scitex-notification backends # 列出可用后端
scitex-notification mcp list-tools # 列出MCP工具
```
> **[完整CLI参考](https://scitex-notification.readthedocs.io/)**
</details>
<details>
<summary><strong>MCP服务器 — 用于AI代理</strong></summary>
<br>
AI代理可以自主发送通知和检查系统状态。
| 工具 | 描述 |
|------|-------------|
| `notify_handler` | 通过指定或故障转移后端发送警报 |
| `notify_by_level_handler` | 使用基于级别的后端配置发送警报 |
| `list_backends_handler` | 列出所有后端及其可用状态 |
| `get_config_handler` | 显示当前通知配置 |
```bash
scitex-notification mcp start
```
> **[完整MCP规范](https://scitex-notification.readthedocs.io/)**
</details>
## 设置
环境变量列表 [`.env.example`](.env.example)。
### MCP服务器
适用于Claude Code等AI代理。
<details>
<summary><strong>示例</strong></summary>
在项目根目录添加 `.mcp.json`。使用 `SCITEX_NOTIFICATION_ENV_SRC` 从 `.src` 文件加载所有配置 — 这使 `.mcp.json` 在不同环境中保持静态:
```json
{
"mcpServers": {
"scitex-notification": {
"command": "scitex-notification",
"args": ["mcp", "start"],
"env": {
"SCITEX_NOTIFICATION_DEFAULT_BACKEND": "audio",
"SCITEX_NOTIFICATION_TWILIO_SID": "ACxxxxxxx",
"SCITEX_NOTIFICATION_TWILIO_TOKEN": "...",
"SCITEX_NOTIFICATION_TWILIO_TO": "+XX-XXX-XXX-XXXX",
"SCITEX_AUDIO_RELAY_PORT": "${SCITEX_AUDIO_RELAY_PORT}"
}
}
}
}
```
</details>
### 扬声器集中化
远程机器可以从本地扬声器讲话。
设置示例参见 [`./docs/audio-relay-setup.src`](./docs/audio-relay-setup.src)
<details>
<summary><strong>示例</strong></summary>
<br>
**1. 本地机器** (有扬声器) — 启动中继服务器:
```bash
scitex-audio relay start --port 31293
```
**2. SSH配置** (`~/.ssh/config`) — 转发中继端口:
```
Host my-server
HostName 192.168.x.x
RemoteForward 31293 127.0.0.1:31293
```
**3. 远程服务器** — 音频在本地扬声器上播放:
```python
import scitex_notification as notify
notify.alert("训练完成。Val loss: 0.042")
```
**4. Shell配置文件** (可选) — 自动按主机配置:
```bash
# ~/.bashrc.d/audio.src (通过SCITEX_AUDIO_ENV_SRC加载)
export SCITEX_AUDIO_RELAY_PORT=31293
# 本地机器:运行中继服务器
if [[ "$(hostname)" == "my-laptop" ]]; then
export SCITEX_AUDIO_MODE=local
scitex-audio relay start --port $SCITEX_AUDIO_RELAY_PORT &>/dev/null &
fi
# 远程服务器:通过SSH隧道使用中继
if [[ "$(hostname)" == "my-server" ]]; then
export SCITEX_AUDIO_MODE=remote
fi
```
</details>
### Twilio用于电话呼叫和短信
<details>
<summary><strong>示例</strong></summary>
```bash
export SCITEX_NOTIFICATION_DEFAULT_BACKEND=audio
export SCITEX_NOTIFICATION_TWILIO_SID=ACxxxxxxx
export SCITEX_NOTIFICATION_TWILIO_TOKEN=...
export SCITEX_NOTIFICATION_TWILIO_TO=+XX-XXX-XXX-XXXX
```
</details>
## SciTeX的一部分
`scitex-notification` 是 [**SciTeX**](https://scitex.ai) 的一部分。通过 `pip install scitex[notification]` 安装为 `scitex.notification` (Python)或 `scitex notification ...` (CLI)。
SciTeX系统遵循以下四项研究自由,灵感来自 [自由软件定义](https://www.gnu.org/philosophy/free-sw.en.html):
> 四项研究自由
>
> 0. 在任何地方**运行**您的研究 — 您的机器,您的条款。
> 1. **研究** 如何每一步工作 — 从原始数据到最终手稿。
> 2. **重新分发** 您的工作流,而不仅仅是您的论文。
> 3. **修改** 任何模块并与社区分享改进。
> AGPL-3.0 — 因为我们相信研究基础设施应该享有与软件相同的自由。
<p align="center">
<a href="https://scitex.ai" target="_blank"><img src="docs/scitex-icon-navy-inverted.png" alt="SciTeX" width="40"/></a>
</p>
<!-- EOF -->