qn
Run a command and send its completion result to an HTTP endpoint.
qn reports the command, exit code, elapsed time, working directory, and—when requested—its standard output and standard error. It sends a notification for every wrapped command, including commands that finish immediately; it does not apply a duration threshold. Notification failures are written to standard error and do not change the command's exit status.
Installation
Quick start
Configure an endpoint, token, and device name in an interactive terminal:
Then run a command through qn:
Without configuration, qn still runs the command but prints a reminder and skips the notification.
Usage
qn [-a|--attach-output] [--no-notify] <command> [args...]
qn [-a|--attach-output] [--no-notify] --shell <command-string>
qn init
qn init-shell <fish|bash|zsh>
| Option | Behavior |
|---|---|
-a, --attach-output |
Capture standard output and standard error, replay them after the command exits, and add them to the notification. Output is therefore not streamed live while the command runs. |
--no-notify |
Run the command without checking configuration or sending a notification. |
--shell <command-string> |
Run the string with sh -c on non-Windows systems (cmd /C on Windows) when using the executable directly. With shell integration loaded, the string is evaluated by the current shell instead. |
-- |
Stop parsing qn options; the remaining arguments are the command to run. |
For ordinary command arguments, the executable starts the requested program directly. qn exits with that command's exit code; a failed notification does not replace it.
Configuration
qn init requires an interactive terminal and writes this file:
~/.config/qn/config
It obtains values in this order:
QN_ENDPOINT— the endpoint URL. If this environment variable is unset,qn initprompts for it; press Enter to use the default,https://krust.iepose.cn/task-completed.QN_TOKEN— the required Bearer token, always prompted byqn init.- Device name — defaults to the machine hostname.
The resulting file contains endpoint=..., token=..., and name=.... On Unix, files created by qn are written with permission 0600. Running qn init replaces the file with the newly entered values.
At notification time, only these environment variables override the corresponding file values:
| Environment variable | Config key | Purpose |
|---|---|---|
QN_ENDPOINT |
endpoint |
HTTP endpoint URL |
QN_TOKEN |
token |
Bearer token |
name has no environment-variable override. If it is missing from an existing config file, qn uses the hostname and appends it to the file.
Shell integration
Shell integration is optional. It makes qn <command> a shell function, so shell builtins and shell-specific command strings can be run in the current shell before qn sends the completion report.
Install it explicitly for one of the supported shells:
init-shell does not auto-detect the shell. It writes a qn-managed function block to the selected startup file; rerunning it updates that block in place instead of appending a duplicate. Restart the selected shell after installation:
| Shell | Startup file |
|---|---|
| Fish | ~/.config/fish/config.fish |
| Bash | ~/.bashrc |
| Zsh | ~/.zshrc |
After upgrading from an older release, run qn init-shell <shell> once for the current shell to migrate its legacy loader into the function block.
Notification request
qn sends one HTTP POST request to the configured endpoint after the command completes. The endpoint path is part of QN_ENDPOINT; /task-completed is only the path in the default URL.
Authorization: Bearer <token>
Content-Type: application/json
{"summary":"device-name\n任务完成\n命令:make -j12\n退出码:0\n耗时:2m 15s\n工作目录:/home/me/project"}
The JSON body always has one summary string. A nonzero command exit code changes 任务完成 to 任务失败. With --attach-output, the summary also includes an 输出: section containing the captured standard output and/or standard error.
Any HTTP service that accepts this request format can be used. QQ Task Notifier is an optional companion service for forwarding these notifications to QQ.
How it works
qnruns the requested command and records its exit code and elapsed time.- It builds a Chinese-language summary with the current working directory and configured device name.
- If notifications are enabled and both endpoint and token are available, it POSTs
{"summary": ...}with Bearer authentication. - A transport error or non-success HTTP status is reported as a warning; the wrapped command's exit code is retained.
License
Licensed under either of Apache License, Version 2.0 or MIT license at your option.