session-nudge

Compare original and translation side by side

🇺🇸

Original

English
🇨🇳

Translation

Chinese

Session nudge

Session nudge

One helper does everything; run it with the Python 3.9+ on PATH:
sh
python3 <this skill's directory>/scripts/nudge.py <action> [options]
一个辅助脚本即可完成全部操作;使用 PATH 中的 Python 3.9+ 运行:
sh
python3 <this skill's directory>/scripts/nudge.py <action> [options]

Map the request to an action

将请求映射到操作

User saysRun
on
,
enable
, "turn nudges on here"
on
off
,
disable
, "stop nudging this session"
off
nothing,
status
, "is the nudge on?"
status
a pace: "nudge every 20 minutes", "每半小时", "hourly", "every 1.5h"
on --every N
"nudge once at 2:01 AM local time"
once --at 02:01
a different terminal (e.g. a Codex or Grok Build window)add
--pid N
"test the nudge", or first use on a machine
test
change the default pace for new opt-ins
install --interval N
remove the background job
uninstall
A pace turns the nudge on (or changes the pace of an already-enabled session). Convert it to whole minutes yourself: "half an hour" -> 30, "every 2 hours" -> 120, "1.5h" -> 90; anything under one minute becomes 1. With no pace,
on
keeps the session's existing pace, else the default (61). The pace is per session: other sessions keep theirs.
once --at HH:MM
schedules the next local occurrence, or tomorrow if today's time has passed. The scheduler delivers it once and removes the entry.
off
also cancels a scheduled one-time nudge.
Report the helper's one-line result. Do not edit the scheduler job, the state files or the templates by hand; the helper is the interface.
用户说运行
on
、
enable
、“在这里开启 nudge”
on
off
、
disable
、“停止 nudge 此会话”
off
没有指定操作、
status
、“nudge 是否已开启?”
status
指定间隔:“每 20 分钟 nudge 一次”、“每半小时”、“每小时”、“每 1.5 小时”
on --every N
“在本地时间凌晨 2:01 nudge 一次”
once --at 02:01
指定其他终端(例如 Codex 或 Grok Build 窗口)附加
--pid N
“测试 nudge”,或首次在机器上使用
test
更改新启用会话的默认间隔
install --interval N
移除后台任务
uninstall
设置间隔会开启 nudge;如果会话已经启用,则修改其间隔。 你需要自行换算为整数分钟:“半小时” -> 30,“每 2 小时” -> 120, “1.5h” -> 90;小于一分钟的间隔按 1 分钟处理。未指定间隔时,
on
会保持会话现有的间隔;如果不存在,则使用默认间隔(61 分钟)。间隔按 会话设置:其他会话仍保留各自的间隔。
once --at HH:MM
会安排本地时间中的下一次触发;如果今天的该时间已经过去, 则安排到明天。调度器投递一次后会删除该条目。
off
也会取消已安排的 一次性 nudge。
报告辅助脚本输出的一行结果。不要手动编辑调度器任务、状态文件或模板; 辅助脚本是唯一的操作入口。

First run on a machine: ask, then test

首次在机器上运行:先询问,再测试

status
,
on
,
once
,
install
and
test
first make sure the background job exists and matches this skill's location, creating it from
templates/
for the current OS if not (
off
never installs anything). Until an end-to-end
test
has passed on this machine, their output also contains setup questions:
ASK-USER [Header]: question
    - Option label: what to do if chosen
For each one, ask the user with your question tool (AskUserQuestion in Claude Code: the bracketed word as header, the listed options as options; in agents without one, ask in plain text). Do what the chosen option says. Then run
test
, and if it fails, handle the
ASK-USER
lines it prints the same way and run
test
again until it passes or the user stops. The
on
that printed the questions has already taken effect, so there is no need to repeat it after the test; tell the user the session's state plus one sentence on the test result. No
ASK-USER
lines means this machine is already set up: skip
test
. Typical questions:
  • macOS: allow python3 to control iTerm2 (Automation permission; the first test triggers the system prompt).
  • Linux: enable systemd lingering so the timer runs while logged out; start a cron daemon if only the cron fallback is available.
  • Windows: register the task with highest privileges when agents run in an elevated terminal.
  • Any OS: this terminal cannot be typed into -> run agent sessions in tmux, WezTerm (or iTerm2 on macOS).
test
opens a throwaway terminal (tmux, WezTerm, iTerm2 window or Windows console), has the real scheduler job fire at it, and checks the message arrived and was submitted.
test --pid N
targets an existing agent terminal instead (the nudge text really lands in that session).
status
、
on
、
once
、
install
和
test
会先确认后台任务存在且与本 skill 的位置匹配;如果不存在,则根据当前 OS 从
templates/
创建(
off
绝不会安装任何内容)。在这台机器上完成端到端
test
之前,它们的输出还会 包含设置问题:
ASK-USER [Header]: question
    - Option label: what to do if chosen
对于每个问题,使用你的提问工具询问用户(在 Claude Code 中使用 AskUserQuestion:将方括号中的词用作 header,将列出的选项用作 options; 在没有该工具的 Agent 中,直接用纯文本提问)。按照用户所选选项执行。 然后运行
test
;如果失败,以同样方式处理它输出的
ASK-USER
行,并再次 运行
test
,直到测试通过或用户停止。已输出问题并执行过的
on
已经生效, 因此测试后无需再次运行;告知用户会话的状态,并用一句话说明测试结果。 没有
ASK-USER
行表示这台机器已完成设置:跳过
test
。典型问题包括:
  • macOS:允许 python3 控制 iTerm2(Automation 权限;第一次 test 会触发 系统提示)。
  • Linux:启用 systemd lingering,使用户退出登录后 timer 仍可运行;如果只能 使用 cron 回退方案,则启动 cron daemon。
  • Windows:当 Agent 在提权终端中运行时,使用最高权限注册任务。
  • 任意 OS:如果无法向此终端输入内容 -> 在 tmux、WezTerm(或 macOS 上的 iTerm2)中运行 Agent 会话。
test
会打开一个临时终端(tmux、WezTerm、iTerm2 窗口或 Windows 控制台),让真实的调度器任务向其触发,并检查消息是否到达且已提交。
test --pid N
则改为指定现有的 Agent 终端(nudge 文本会实际进入该 会话)。

How it works

工作原理

  • Scheduler: launchd agent
    local.session-nudge
    (macOS), systemd user timer
    session-nudge.timer
    or a crontab line when there is no systemd user session (Linux), Task Scheduler task
    session-nudge
    (Windows). It runs
    nudge.py fire
    every minute; each tick nudges only sessions whose own interval has elapsed.
  • Opt-ins live in the state directory (
    ~/.local/state/session-nudge/
    , or
    %LOCALAPPDATA%\session-nudge\
    on Windows;
    $SESSION_NUDGE_HOME
    overrides), file
    include
    : one line per agent TUI PID with its pace and last nudge time. Keyed by PID, so an opt-in ends with its process and never sticks to a terminal a later session reuses.
    nudge.log
    there records every delivery and skip;
    config.json
    holds the default pace and the message (
    {now}
    and
    {next}
    are filled in).
  • Delivery: tmux
    send-keys
    , WezTerm
    cli send-text
    , iTerm2 AppleScript (macOS), console input injection (Windows). Text first, then CR after 0.5s and again after 1s: Claude Code treats a CR in the same burst as pasted text, and the second CR is a no-op on an empty composer. Other terminals (Terminal.app, GNOME Terminal, VS Code's terminal without tmux) cannot be typed into and are logged as skipped. A session sitting at a permission prompt consumes the text there.
  • 调度器:macOS 上的 launchd agent
    local.session-nudge
    、Linux 上的 systemd user timer
    session-nudge.timer
    (没有 systemd user session 时使用 crontab 条目),或 Windows 上的 Task Scheduler 任务
    session-nudge
    。 它每分钟运行一次
    nudge.py fire
    ;每次 tick 只会 nudge 已达到各自 间隔的会话。
  • 选择启用的会话记录在状态目录(
    ~/.local/state/session-nudge/
    ,Windows 上为
    %LOCALAPPDATA%\\session-nudge\\
    ;
    $SESSION_NUDGE_HOME
    可覆盖此 路径)中。文件
    include
    每行记录一个 Agent TUI PID 及其间隔和上次 nudge 时间。它以 PID 为键,因此启用状态会随进程结束而终止,绝不会 残留并应用到之后复用同一终端的新会话。该目录中的
    nudge.log
    记录每次 投递和跳过;
    config.json
    保存默认间隔和消息(
    {now}
    与
    {next}
    会被 填入)。
  • 投递:tmux
    send-keys
    、WezTerm
    cli send-text
    、iTerm2 AppleScript (macOS)、console input injection(Windows)。先输入文本,然后在 0.5 秒后输入 CR,并在 1 秒后再次输入:Claude Code 会将同一批次中的 CR 视为粘贴文本,而第二次 CR 对空输入框无作用。其他终端(Terminal.app、 GNOME Terminal、未使用 tmux 的 VS Code 终端)无法输入,因此会记录为已 跳过。会话若正停留在权限提示界面,文本会被输入到该提示中。

Finding this session's terminal

查找此会话的终端

  • Claude Code:
    CLAUDE_PID
    is the TUI. Codex or anything else: the nearest ancestor process named
    claude
    ,
    codex
    or
    grok
    that has a terminal.
  • A Claude Code background session (
    kind: bg
    in
    ~/.claude/sessions/<pid>.json
    ) is shown through an attached TUI that the session files do not name; the helper takes the single interactive TUI in the same working directory. With several it lists them and changes nothing -- ask the user which window shows this session and rerun with
    --pid N
    .
  • Find a PID by hand with
    ps axww -o pid=,tty=,command= | grep -E 'claude|codex|grok'
    (Windows:
    Get-Process claude,codex,grok,node
    ). Headless processes (
    claude -p
    ,
    codex exec
    , the codex app-server) have no terminal and are never nudged.
  • The opt-in follows the TUI process, not the conversation: if that window is switched to another session, that session is nudged too.
  • Claude Code:
    CLAUDE_PID
    是 TUI。对于 Codex 或其他工具:向上查找最近的、 名称为
    claude
    、
    codex
    或
    grok
    且拥有终端的祖先进程。
  • Claude Code 后台会话(
    ~/.claude/sessions/<pid>.json
    中为
    kind: bg
    ) 通过一个已附加的 TUI 显示,而会话文件并未命名该 TUI;辅助脚本会选择 同一工作目录中的唯一交互式 TUI。如果存在多个,它会列出这些 TUI 且 不做任何更改——询问用户哪个窗口显示此会话,然后使用
    --pid N
    重新运行。
  • 可通过以下命令手动查找 PID:
    ps axww -o pid=,tty=,command= | grep -E 'claude|codex|grok'
    (Windows:
    Get-Process claude,codex,grok,node
    )。无头进程(
    claude -p
    、
    codex exec
    、codex app-server)没有终端,因此永远不会被 nudge。
  • 启用状态跟随 TUI 进程,而不是对话:如果该窗口切换到另一个会话, 该会话也会收到 nudge。