A modern, interactive process killer for macOS & Linux with "Why Is This Running" analysis.
This project is a complete rewrite and modernization of the original gkill, rebuilt from the ground up with modern Go, Bubble Tea, and fuzzy search capabilities.
For a Chinese version of this document, see: README_zh.md.
gokill integrates process ancestry analysis inspired by witr (why-is-this-running), helping you understand not just what is running, but why it exists.
| Feature | Description |
|---|---|
| Process Ancestry Chain | Traces the full parent chain from init/systemd to target process |
| Source Detection | Identifies the supervisor/launcher (systemd, launchd, Docker, PM2, supervisor, cron, shell) |
| Container Awareness | Detects if a process runs inside Docker, containerd, Kubernetes, or LXC |
| Git Context | Shows the Git repository and branch when a process runs from a Git directory |
| Health Warnings | Alerts for zombie processes, root execution, high memory usage, long-running processes |
When you press i on a selected process, gokill shows:
PID : 14233
User : pm2
Command : node index.js
Started : 2 days ago
Why It Exists:
systemd (pid 1) → pm2 (pid 5034) → node (pid 14233)
Source : pm2
Git Repo : expense-manager (main)
Warnings : Process is running as root
This is especially powerful during incident response when you need to quickly understand the chain of responsibility for a running process.
brew install w31r4/tap/gokillnpm install -g @zenfun510/gokillEnsure you have a working Go environment. You can install gokill with go install:
go install github.com/w31r4/gokill@latestAlternatively, you can clone the repository and build it from source:
git clone https://github.com/w31r4/gokill.git
cd gokill
go buildRun gokill in your terminal to start the interactive interface. You can immediately start typing to fuzzy search for processes by name, PID, username, or ports.
| Key | Action |
|---|---|
up/k |
Move cursor up |
down/j |
Move cursor down |
/ |
Enter search/filter mode |
enter |
Kill selected process (in navigation mode) / Exit search mode |
esc |
Exit search mode / Close overlays (details, error, ports-only, dependency tree, help) |
p |
Pause selected process (SIGSTOP) |
r |
Resume selected process (SIGCONT) |
i |
Show process details |
P |
Toggle ports-only view |
T |
Open dependency tree (T-mode) for the selected process |
? |
Open contextual help overlay for the current mode |
ctrl+r |
Refresh process list |
q/ctrl+c |
Quit |
Press i on a selected process to open a details view showing PID, user, CPU/MEM, start time, and command. Press esc to return to the list once you are done.
Additional fields you may see in the details view:
Target: Unified summary of the name, PID, and first listening port (if any).Service: Service name when detected via systemd/launchd.Container: Container identifier when detected from cgroup metadata.Restart Count: Best-effort count of consecutive restarts inferred from the ancestry chain.Context: Extra runtime context lines such asSocket State(listener count/public interface),Resource(RSS + threads), andFiles(open FD count).
Press P (uppercase) to show only processes that are listening on ports. In this view, the list is sorted by the smallest port number in ascending order.
By default, gokill scans listening ports for processes displayed in the list and in the details view. This can be slow or require elevated privileges on some systems. To disable port scanning, set:
export GOKILL_SCAN_PORTS=0When disabled, the list won’t highlight listeners and the details view won’t include the Ports line.
You can tune the port scan timeout (per process) via GOKILL_PORT_TIMEOUT_MS (default 300):
export GOKILL_PORT_TIMEOUT_MS=200Press T on a selected process to enter a full-screen dependency tree view rooted at that process. In T-mode:
- Use
up/down(j/k) to move the cursor. - Use
left/right(h/l) orspaceto fold/unfold branches.
When the cursor is on a… (deeper)line, pressingright/lorspacedrills into a deeper level of the subtree;
when it is on a… (N more)line, pressingright/lorspacepages through additional siblings at the same level. - Press
enter/oto make the selected node the new root;umoves the root up to its parent. - Press
/to filter the tree by text or PID;Stoggles “alive-only” andLtoggles “listening-only”. - Press
ito open details for the selected node, orx/p/rto kill, pause, or resume that node (with a confirmation prompt). - Press
escto leave T-mode and return to the main list.
Press ? at any time to open a help overlay summarizing the available keybindings for the current view (main list or T-mode). Press ? or esc again to close it.
| Error message | When it appears | Suggested fix |
|---|---|---|
operation not permitted |
You tried to send a signal to a root/protected process without enough privileges. | Run gokill with sudo or target processes owned by your user. |
process with pid XXX not found |
The process exited (or the PID was reassigned) before the signal landed. | Press ctrl+r to refresh the list and pick another process. |
failed to get user/create time/... (shown in warnings) |
gopsutil could not read that attribute. |
Usually safe to ignore; running with higher privileges can reduce these warnings. |
connection scan timeout (with GOKILL_SCAN_PORTS enabled) |
The port scan took too long or was blocked by a firewall. | Increase GOKILL_PORT_TIMEOUT_MS or disable port scanning. |
The error screen appears as a red pane with the prompt esc: dismiss • q: quit, so you can return to the main view without quitting the program.
- gkill - The original project that this is a modernization of.
- fkill-cli - A great Node.js alternative that inspired the project.
- witr - "Why Is This Running" - the project that inspired our process ancestry analysis.
Special thanks to witr (why-is-this-running) by @pranshuparmar. The internal/why package in gokill is heavily inspired by witr's core concept of building causal chains to explain why a process exists. witr's philosophy of making process causality explicit—answering not just what is running but why—directly shaped our process details and ancestry analysis features.
"When something is running on a system, there is always a cause. witr makes that causality explicit."
MIT