Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
104 changes: 104 additions & 0 deletions command-signatures/json/pkill.json
Original file line number Diff line number Diff line change
@@ -0,0 +1,104 @@
{
"name": "pkill",
"description": "Find or signal processes by name",
"args": {
"name": "pattern",
"description": "Extended regular expression matched against process names, or full argument lists when -f is used",
"isVariadic": true,
"generatorName": "process_name"
},
"options": [
{
"name": "-F",
"description": "Restrict matches to a process whose PID is stored in the pidfile",
"args": {
"name": "pidfile",
"template": "filepaths"
}
},
{
"name": "-G",
"description": "Restrict matches to processes with a real group ID in the comma-separated list",
"args": {
"name": "gid"
}
},
{
"name": "-I",
"description": "Request confirmation before attempting to signal each process"
},
{
"name": "-L",
"description": "Require the pidfile given with -F to be locked"
},
{
"name": "-P",
"description": "Restrict matches to processes with a parent process ID in the comma-separated list",
"args": {
"name": "ppid"
}
},
{
"name": "-U",
"description": "Restrict matches to processes with a real user ID in the comma-separated list",
"args": {
"name": "uid",
"generatorName": "user_name"
}
},
{
"name": "-a",
"description": "Include process ancestors in the match list"
},
{
"name": "-f",
"description": "Match against full argument lists instead of process names"
},
{
"name": "-g",
"description": "Restrict matches to processes with a process group ID in the comma-separated list",
"args": {
"name": "pgrp"
}
},
{
"name": "-i",
"description": "Ignore case distinctions"
},
{
"name": "-l",
"description": "Display the kill command used for each process killed"
},
{
"name": "-n",
"description": "Select only the newest matching process"
},
{
"name": "-o",
"description": "Select only the oldest matching process"
},
{
"name": "-t",
"description": "Restrict matches to processes associated with terminals in the comma-separated list",
"args": {
"name": "tty"
}
},
{
"name": "-u",
"description": "Restrict matches to processes with an effective user ID in the comma-separated list",
"args": {
"name": "euid",
"generatorName": "user_name"
}
},
{
"name": "-v",
"description": "Reverse the sense of the matching"
},
{
"name": "-x",
"description": "Require an exact match"
}
]
}
2 changes: 2 additions & 0 deletions command-signatures/src/generators/mod.rs
Original file line number Diff line number Diff line change
Expand Up @@ -51,6 +51,7 @@ mod pacman;
mod pass;
mod phpunit_watcher;
mod pip;
mod pkill;
mod powershell;
mod pprof;
mod pyenv;
Expand Down Expand Up @@ -109,6 +110,7 @@ pub fn dynamic_command_signature_data() -> HashMap<String, DynamicCompletionData
phpunit_watcher::generator(),
pip::generator(),
pip::pip3_generator(),
pkill::generator(),
npm::pnpm_generators(),
pprof::generator(),
pyenv::generator(),
Expand Down
55 changes: 55 additions & 0 deletions command-signatures/src/generators/pkill.rs
Original file line number Diff line number Diff line change
@@ -0,0 +1,55 @@
use warp_completion_metadata::{
CommandBuilder, CommandSignatureGenerators, Generator, GeneratorResultsCollector, Suggestion,
};

use super::common;

pub fn generator() -> CommandSignatureGenerators {
CommandSignatureGenerators::new("pkill")
.add_generator("user_name", common::users_generator())
.add_generator(
"process_name",
Generator::script(
CommandBuilder::pipe(
CommandBuilder::single_command("ps -A -o comm"),
CommandBuilder::single_command("sort -u"),
),
process_names,
),
)
}

fn process_names(output: &str) -> warp_completion_metadata::GeneratorResults {
output
.trim()
.lines()
.filter_map(|path| {
let name = path.rsplit('/').next()?;
if !name.is_empty() && name != "COMMAND" {
Some(Suggestion::with_description(name, path))
} else {
None
}
})
.collect_unordered_results()
}

#[cfg(test)]
mod tests {
use super::process_names;

#[test]
fn test_process_names_handles_paths_and_plain_names() {
let suggestions = process_names("COMMAND\n/usr/bin/python3\nbash\n/System/Library/foo\n");
let names = suggestions
.suggestions
.into_iter()
.map(|suggestion| suggestion.exact_string)
.collect::<Vec<_>>();

assert!(names.contains(&"python3".into()));
assert!(names.contains(&"bash".into()));
assert!(names.contains(&"foo".into()));
assert!(!names.contains(&"COMMAND".into()));
}
}