A long-running task terminal operations manual for POSIX shells, macOS, and Linux. It does not falsely claim native Windows compatibility; Windows users should use it in WSL or another POSIX environment.
Customer-readable description
What this skill can do
| Customer wants | Skill will do | Customer can see |
|---|---|---|
| Start or observe a long-running task | Start a tmux/background task with parameterized session, log directory, and command | command, workdir, session/PID, log path, and current status |
| Determine whether a task is stalled | Cross-check logs, CPU, and network/subprocess progress within the user-specified observation window | Evidence for each signal and a conclusion of "running/suspected stalled/unable to determine" |
| Recover or terminate a task | First confirm the target and data risk, then proceed in the order TERM→recheck→KILL | Each signal, confirmation point, exit status, and follow-up recovery recommendations |
How customers use it
Provide the following inputs; when inputs that would change the termination target or log destination are missing, ask first and do not guess:
- The command to run or diagnose, and the working directory;
- An existing PID or tmux session (if applicable);
session_name、log_dir、stall_window_seconds、term_grace_seconds;- Optional
fallback_command, and whether termination of the target process is pre-authorized.
No need to invoke this skill when only viewing short command output or file contents.
Dependencies and installation
Install this skill:
claude plugin marketplace add soia-team/soia-open-skills
claude plugin install soia-dev@soia
When you only want this one skill, you can use the npx route. Note that the skill will land in the shared source of truth ~/.agents/skills; if a plugin is also installed, the same skill will appear in two indexes and each will drift, so it is recommended to choose one of the two:
npx skills add soia-team/soia-open-dev-skills -g -a '*' -s soia-dev-terminal-ops -y
Hard dependencies: POSIX shell,ps、kill. The tmux workflow requires tmux. Network connectivity checks optionally use lsof; when missing, mark it as "network signal not checked" and do not use it to conclude a deadlock.
Optional configuration:
~/.config/soia-skills/soia-dev-terminal-ops/config.yml
SOIA_DEV_TERMINAL_OPS_CONFIG_FILE=<custom-config-path>
Recommended configuration structure:
schema_version: 2
env:
TERMINAL_OPS_LOG_DIR: "<user-log-dir>"
TERMINAL_OPS_SESSION_NAME: "<session-name>"
TERMINAL_OPS_STALL_WINDOW_SECONDS: "<seconds>"
TERMINAL_OPS_TERM_GRACE_SECONDS: "<seconds>"
TERMINAL_OPS_FALLBACK_COMMAND: "<optional-command>"
Priority: this user input/CLI parameters → process environment → configuration file. Only use this when no log directory is provided ${TMPDIR}; if TMPDIR is also not set, first ask the user to specify a directory. Ordinary configuration can only store non-secret parameters; when a command contains a token or other secret, it must instead be passed via the Provider's official login state, the system credential store, or a secure process environment, and must not be written to configuration or logs.
WorkBuddy 's loading unit is role-based experts rather than plugins,npx skills add -a '*' cannot cover it, and it needs to be installed separately, see docs/install/workbuddy.md。
Private information and intermediate data
- Commands, environments, process lists, and logs may expose source code, paths, accounts, or secrets; identify sensitive parameters before execution, and receipts should only show the redacted command and a minimal log summary.
- Class A runtime logs are written to the customer-specified directory; when unspecified, use
${TMPDIR}/soia-dev-terminal-ops/<session>/. After the task ends, by default clean up temporary logs created by this skill, unless the customer explicitly requests that they be retained. - When high-impact actions truly require a persistent audit, write to the customer-specified state root directory, or
${XDG_STATE_HOME:-~/.local/state}/soia-skills/soia-dev-terminal-ops/; record only the time, target identifier, authorization, and result; do not record environment variables, full command secrets, or log bodies. - The diagnostic package requested by the customer is a deliverable; write only its specified path; the target project's own logs follow the project rules. This skill does not create undeclared caches or prompt/response archives.
- Class B audit records are not automatically deleted before the customer confirms the retention policy; Class A temporary data only cleans up directories created by this skill whose targets have been reviewed.
Logs and completion receipts
Each report:
完成:<启动、诊断、恢复或终止结果>。
日志摘要:
- command/workdir: <命令与目录>
- session/pid: <会话名或 PID>
- log: <日志路径或“纯 stdout”>
- signals: <日志/CPU/网络/子进程证据>
- status: running / suspected-stall / inconclusive / completed / terminated / killed
验证:<退出码、复查命令和最后输出摘要>
问题与下一步:<fallback 或待确认项;没有则写“无”>
Trigger conditions
- Start or monitor commands expected to run for more than 30 seconds;
- Manage tmux sessions, background builds/tests, or continuous logs;
- Diagnose a process with no output, a hanging tool call, or an unrecoverable terminal;
- Terminate or downgrade long tasks under an explicit confirmation gate.
Parameter parsing
Parse and echo non-secret parameters before execution:
SESSION_NAME="${TERMINAL_OPS_SESSION_NAME:?set session name}"
LOG_DIR="${TERMINAL_OPS_LOG_DIR:-${TMPDIR:?set TERMINAL_OPS_LOG_DIR or TMPDIR}}"
STALL_WINDOW_SECONDS="${TERMINAL_OPS_STALL_WINDOW_SECONDS:?set observation window}"
TERM_GRACE_SECONDS="${TERMINAL_OPS_TERM_GRACE_SECONDS:?set TERM grace period}"
FALLBACK_COMMAND="${TERMINAL_OPS_FALLBACK_COMMAND:-}"
Verify that the session name contains only letters, digits, dots, underscores, or hyphens; show the resolved absolute path before creating directories. Do not hard-code agent names, executor states, timeout values, or log file names in the skill.
Command risk classification
Default to read-only/idempotent:
tmux list-sessions
ps -o pid,ppid,stat,etime,time,command -p <PID>
tail -n <LINES> <LOG_FILE>
lsof -nP -p <PID> -i # 可选
High-impact actions must first explain the target, basis, and data risk, and obtain user confirmation (or cite explicit pre-authorization in this request):
kill -TERM <PID>;kill -KILL <PID>;tmux kill-session -t <SESSION_NAME>;- Execute
FALLBACK_COMMAND, because it may incur costs, remote state, or duplicate work.
After confirming the PID, read the full command and parent PID again to avoid PID reuse or selecting the wrong process. Do not use a broad pkill/killall in place of a precise PID.
Background session management
The log name is specified by the caller and is not derived from the product name or agent name:
mkdir -p "$LOG_DIR"
LOG_FILE="$LOG_DIR/<log-name>.log"
tmux new-session -d -s "$SESSION_NAME" \
"cd '<workdir>' && <command> 2>&1 | tee '$LOG_FILE'"
tmux list-sessions
tmux capture-pane -p -t "$SESSION_NAME" -S -50
tail -n 50 "$LOG_FILE"
When commands, directories, or paths contain user input, use host tools to pass parameters safely; do not directly concatenate unchecked shell fragments. If a compound command must be run, first show the final command to the user exactly as it is.
Multi-signal stall diagnosis
S only indicates interruptible sleep; being in S for a long time may also be normal waiting. Elapsed time or a single timeout is never a kill condition.
At STALL_WINDOW_SECONDS check at least two sampling points covered by:
- Log progress: whether the log mtime, size, or last business progress entry has changed; when there is no log, explicitly record the gap.
- CPU progress: whether cumulative CPU time has increased; a single low CPU reading only indicates idleness at that moment.
- Network/IPC progress: if the task depends on the network, check whether the connection exists and whether its state has changed;
lsofwhen unavailable, do not fabricate conclusions. - Child process progress: check whether child processes are still working, have exited, or are producing new output.
- Task-specific heartbeat: whether test counts, build targets, downloaded bytes, or queue counts, etc., have changed.
Only when "the observation window has exceeded the threshold" and at least two independent progress signals remain unchanged, and there is no reasonable explanation of normal waiting, mark it as suspected-stall. When signals are insufficient, mark it as inconclusive, continue observing, or ask the user to judge.
Example sampling (column names for commands on macOS/Linux may differ slightly; interpret according to the actual output):
ps -o pid,ppid,stat,etime,time,command -p <PID>
wc -c < "$LOG_FILE"
tail -n 20 "$LOG_FILE"
lsof -nP -p <PID> -i 2>/dev/null || true
TARGET_PID=<PID>
ps -o pid,ppid,stat,etime,time,command -ax | awk -v p="$TARGET_PID" '$2 == p'
Wait for the user-configured observation window, then resample and take a diff. Do not misreport "the command has not exited" as "no progress."
Safe termination and recovery
- Show the PID, full command, parent PID, working directory (when obtainable), and multi-signal evidence.
- Explain that TERM may interrupt writes and KILL gives no chance to clean up; obtain confirmation.
- Send TERM.
- Within
TERM_GRACE_SECONDS, repeatedly recheck whether the process has exited, and inspect the logs/disk-write status. - If it is still alive, show the recheck evidence and potential data loss, and obtain KILL confirmation again.
- Send KILL only to the same rechecked PID; then confirm the process has disappeared, the session state, and output integrity.
- If a fallback is configured, first explain how context is passed and whether side effects and costs may be duplicated, then obtain confirmation before executing.
kill -TERM <PID>
# 按 TERM_GRACE_SECONDS 轮询:
ps -p <PID> >/dev/null 2>&1 || echo "terminated"
# 仍存活且再次确认后:
kill -KILL <PID>
ps -p <PID> >/dev/null 2>&1 && echo "still alive" || echo "killed"
Five output file categories
| Category | Examples in this skill | Location |
|---|---|---|
| A Temporary | Build/test logs and sampling snapshots for this run | User-specified log directory; otherwise ${TMPDIR}/soia-dev-terminal-ops/<session>/ |
| B Audit | Records of high-impact actions such as kill, session cleanup, and fallback | User-specified state directory or ${XDG_STATE_HOME:-~/.local/state}/soia-skills/soia-dev-terminal-ops/; if not configured, ask first |
| C Deliverables | Complete diagnostic packages the user asks to keep | User-specified path |
| D Product functionality is the log | Task logs defined by the target project | Comply only with conventions already documented by the target project; do not invent them in this skill |
| E Pure stdout | Short status checks and summaries that need not be retained | Do not write to disk |
Do not treat a relative cwd as the default log directory. Category A may be rotated; Category B must not be deleted before the retention policy is confirmed.