On a linux box, I have at most 3 java jars files running. How do I quickly kill all 3 with one command?
Usually I would:
ps ex - get the processes running
then find the process ids then do:
kill -9 #### #### ####
Any way to shorten this process? My eyes hurts from squinting to find the process ids.
My script does the following:
nohup ./start-gossip &
nohup ./start &
nohup ./start-admin &
Is there a way to get the process ids of each without looking it up?
Short answer:
pkill java
This looks up a process (or processes) to kill by name. This will find any other java processes too, so be careful. It also accepts -9, but you should avoid using -9 unless something is really broken.
EDIT:
Based on updates, you may be able to specify the script names to pkill as well (I'm not positive). But, the more traditional way to handle this issue is to leave pid files around. After you start a new process and background it, its pid is available in $!. If you write that pid to a file, then it's easy to check if the process is still running and kill just the processes you mean to. There is some chance that the pid will be reused, however.
You can save the PIDs when you start the processes so you can use them later:
nohup ./start-gossip &
START_GOSSIP_PID=$!
nohup ./start &
START_PID=$!
nohup ./start-admin &
START_ADMIN_PID=$!
...
kill -9 $START_GOSSIP_PID
kill -9 $START_PID
kill -9 $START_ADMIN_PID
This has the advantage (over pkill) of not killing off any other processes that coincidentally have similar names. If you don't want to perform the kill operation from the script itself, but just want to have the PIDs handy, write them to a file (from the script):
echo $START_GOSSIP_PID > /some/path/start_gossip.pid
Or even just do this when you launch the process, rather than saving the PID to a variable:
nohup ./start-gossip &
echo $! > /some/path/start_gossip.pid
To get the process id of that java process run
netstat -tuplen
Process ID (PID) of that process whom you want to kill and run
kill -9 PID
Related
I have written a bash script to carry out some tests on my system. The tests run in the background and in parallel. The tests can take a long time and sometimes I may wish to abort the tests part way through.
If I Control+C then it aborts the parent script, but leaves the various children running. I wish to make it so that I can hit Control+C or otherwise to quit and then kill all child processes running in the background. I have a bit of code that does the job if I'm running running the background jobs directly from the terminal, but it doesn't work in my script.
I have a minimal working example.
I have tried using trap in combination with pgrep -P $$.
#!/bin/bash
trap 'kill -n 2 $(pgrep -P $$)' 2
sleep 10 &
wait
I was hoping that on hitting control+c (SIGINT) would kill everything that the script started but it actually says:
./breakTest.sh: line 1: kill: (3220) - No such process
This number changes, but doesn't seem to apply to any running processes, so I don't know where it is coming from.
I guess if the contents of the trap command get evaluated where the trap command occurs then it might explain the outcome. The 3220 pid might be for pgrep itself.
I'd appreciate some insight here
Thanks
I have found a solution using pkill. This example also deals with many child processes.
#!/bin/bash
trap 'pkill -P $$' SIGINT SIGTERM
for i in {1..10}; do
sleep 10 &
done
wait
This appears to kill all the child processes elegantly. Though I don't properly understand what the issue was with my original code, apart from sending the correct signal.
in bash whenever you you use & after a command it places that command as a background job ( this background jobs are called job_spec ) which is incremented by one until you exit that terminal session. You can use the jobs command to get the list of the background jobs running. To work with this jobs you have to use the % with the job id. The jobs command also accept other options such as jobs -p to see the proces sids of all jobs , jobs -p %JOB_SPEC to see the process of id of that particular job.
#!/usr/bin/env bash
trap 'kill -9 %1' 2
sleep 10 &
wait
or
#!/usr/bin/env bash
trap 'kill -9 $(jobs -p %1)' 2
sleep 10 &
wait
I implemented something like this few years back, you can take a look at it async bash
You can try something like the following:
pkill -TERM -P <your_parent_id_here>
I've turned a program I wrote into a service, and I have a bash script that runs to start up the actual program, since there are things that have to be started in a particular order. The contents of the startup script (called with start-stop-daemon from the init.d script look like :
./rfid_reader &
sleep 2
java ReaderClass &
This works fine, but how do I go about killing them when it comes time to stop the process?
I've seen pidfiles used, do I just get the PIDs of the two programs, write them to a file, and then kill them when it comes time to shut them down, or do I have to ps -ef | grep program to get their PIDs?
I don't think killall is a good idea to do this. You'd better to record the PID of the program started in background in some file(e.g. PID_FILE) and then kill $(<$PID_FILE) to stop it.
Please refer to this thread for how to get the PID the previous started background program.
Assuming you know the name of your program, you can kill them as below :
killall -KILL program_name
I have a program I want to start. Let' say this program will run a while(true)-loop (so it does not terminate. I want to write a bash script which:
Starts the program (./endlessloop &)
Waits 1 second (sleep 1)
Kills the program --> How?
I cannot use $! to get pid from child because server is running a lot of instances concurrently.
Store the PID:
./endlessloop & endlessloop_pid=$!
sleep 1
kill "$endlessloop_pid"
You can also check whether the process is still running with kill -0:
if kill -0 "$endlessloop_pid"; then
echo "Endlessloop is still running"
fi
...and storing the content in a variable means it scales to multiple processes:
endlessloop_pids=( ) # initialize an empty array to store PIDs
./endlessloop & endlessloop_pids+=( "$!" ) # start one in background and store its PID
./endlessloop & endlessloop_pids+=( "$!" ) # start another and store its PID also
kill "${endlessloop_pids[#]}" # kill both endlessloop instances started above
See also BashFAQ #68, "How do I run a command, and have it abort (timeout) after N seconds?"
The ProcessManagement page on the Wooledge wiki also discusses relevant best practices.
You can use the pgrep command for the same:
kill $(pgrep endlessloop)
I am working with a Raspberry Pi running linux, and have modified the .bash_profile file in order to a run a program I've made automatically upon login. This works great, but I was wondering how to turn the program off, since for ctrl+c I would need to be running the program in the terminal.
You can use Kill to terminate program by its process Id, Top command will list all the processes, You can also use Pkill, which will Terminate the process by its name.
-9 option forces process to shut down, so its very commonly used.
Example:
kill -9 "Process ID without Quotation marks"
pkill -9 "Name with Quotation marks (Case Sensitive)"
Check this.
I always use
pkill - f processname
I know I can start the process with cron, but how would I go about stopping it? I thought about starting a new process1 everyday at 00:00, then at 23:59 I'd start a process2 doing ps -aux | grep process1, getting the pid from the line and then killing it, but I was wondering if there's be a better way to do it.
I could use Python or Java too if it's easier with either language.
Record its PID:
nohup my_service &
echo $! > /var/run/my_service.pid
and then kill by that PID.
You might want to check both PID and process name to make sure that during the day the process did not crash and some other process did not get that PID. (And even better idea would be to set up supervisor.) But if you are sure that there are no other process with that name you can simply use pkill or killall.