Ubuntu Shell script issue: convert output of command into variable [closed] - linux

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 7 years ago.
Improve this question
I try to convert one command line output into a (or store into a ) variable.
The command is
ps -U root u | grep ruby | wc -l
The output is 1, but when I use
$(ps -U root u | grep ruby | wc -l)
the output is
1: command not found
What happens here?
Here is my snapshot

Here,
$(ps -U root u | grep ruby | wc -l)
You are not saving the output into a variable. So the shell attempts to execute the result (which happens to be 1 in your case). Since it couldn't find a command/function named 1, you get the error.
You probably want:
output=$(ps -U root u | grep ruby | wc -l)
Now, output will have 1 which you can print with:
echo "${output}"
Btw, grep can count itself using the -c option. So wc is unnecessary here:
output=$(ps -U root u | grep -c ruby)
echo "${output}"

In the latter case, the command inside the $(…) is evaluated and the result is then used to create a new command, which the shell then tries to execute. Since there is no command or program named 1, you get the message you are seeing. It easier to see what's happening if you writer echo Result: $(ps -U root u | grep ruby | wc -l). your output would be Result: 1.

To assign to a variable do it like this, using backtics
a=`ps -U root u | grep ruby | wc -l`

Related

How to reference the output of the previous command twice in Linux command?

For instance, if I'd like to reference the output of the previous command once, I can use the command below:
ls *.txt | xargs -I % ls -l %
But how to reference the output twice? Like how can I implement something like:
ls *.txt | xargs -I % 'some command' % > %
PS: I know how to do it in shell script, but I just want a simpler way to do it.
You can pass this argument to bash -c:
ls *.txt | xargs -I % bash -c 'ls -l "$1" > "out.$1"' - %
You can lookup up 'tpipe' on SO; it will also lead you to 'pee' (which is not a good search term elsewhere on the internet). Basically, they're variants of the tee command which write to multiple processes instead of writing to files like the tee command does.
However, with Bash, you can use Process Substitution:
ls *.txt | tee >(cmd1) >(cmd2)
This will write the input to tee to each of the commands cmd1 and cmd2.
You can arrange to lose standard output in at least two different ways:
ls *.txt | tee >(cmd1) >(cmd2) >/dev/null
ls *.txt | tee >(cmd1) | cmd2

bash execute command in variable

I have a command in a variable in Bash:
check_ifrunning=\`ps aux | grep "programmname" | grep -v "grep" | wc -l\`
The command checks if a specific program is running at the moment.
Later in my script, I want to query the value of the variable on a point.
If the specific program is running, the script should sleep for 15 minutes.
I solved it like this:
while [ $check_ifrunning -eq 1 ]; do
sleep 300
done
Will the script execute the command in the variable for each single loop-run or will the value in the variable stay after the first execution?
I have more variables in my script which can change their value. This was just one simple example of this.
Notice that check_ifrunning is set only once, in
check_ifrunning=`ps aux | grep "programmname" | grep -v "grep" | wc -l`
and that it is set before the loop:
while [ $check_ifrunning -eq 1 ]; do
sleep 300
done
You could add, for debugging purposes, an echo check_ifrunning is $check_ifrunning statement inside your while loop just before the sleep ...
You probably simply want (using pidof(8)) - without defining or using any check_ifrunning Bash variable:
while [ -n "$(pidof programname)" ]; do
sleep 300
done
Because you want to test if programname is running at every start of the loop!
You should use the more nestable and more readable $(...) instead of backquotes.
Consider reading the Advanced Bash Scripting Guide...
If you are writing a Bash script, consider to start it with
#!/bin/bash -vx
while debugging. When you are satisfied, remove the -vx...
If you want to encapsulate your commands, the proper way to do that is a function.
running () {
ps aux | grep "$1" | grep -q -v grep
}
With grep -q you get the result as the exit code, not as output; you use it simply like
if running "$programname"; then
:
Ideally, the second grep is unnecessary, but I did not want to complicate the code too much. It still won't work correctly if you are looking for grep. The proper solution is pidof.
See also http://mywiki.wooledge.org/BashFAQ/050

CPU % usage of all pid [duplicate]

This question already has answers here:
How to get overall CPU usage (e.g. 57%) on Linux [closed]
(6 answers)
Closed 9 years ago.
I can't obtain CPU% usage of all the pid, without know any program names.
I feel I am close to the solution, this is what I've done so far:
for line in $(pgrep -f chrome); \
do echo -n $line" - "; \
ps -p $line -o %cpu | sed -n 2p | sed 's/ //'; done
In this example I obtain only all chrome pid.. in next step I want all executing pid.
You can do this easily with the top command alone.
To order by CPU percentage (descending), you could use top -o -cpu
If you don't want to use top for some reason, couple of other ways I can think of doing this.
> ps -e -o "%p-%C"
Or if you wanted to do it in a script, something like (alternatively could just parse ps again or check /proc/pid/stat for cpu usage)
#!/bin/bash
shopt -s extglob
for line in /proc/+([0-9]); do
echo -n "${line##*/}- "
ps -p "${line##*/}" -o %cpu | sed -n 2p | sed 's/ //'
done
Where
shopt -s extglob Turns on extended file globing in bash
+([0-9]) Matches any files containing 1 or more digits
${line##*/} Strips everything before and including the last / character

Pass awk output as input to another script [closed]

Closed. This question needs details or clarity. It is not currently accepting answers.
Want to improve this question? Add details and clarify the problem by editing this post.
Closed 8 years ago.
Improve this question
Below I have tried to extract the pid of a running process to check its current ppid
ps -p 1111 -o ppid = $(ps -eo pid,args | awk '/PRD_/ && /startscen\.sh/ && $8 ~ /<string>/' | awk -F" " '{print $1}')
My script is wrong. Is there a better way?
does
ps -ef | awk '/PRD_/ && /startscen\.sh/ {print $3}'
give you what you want? That searchs for a process with "PRD_" and "startscen.sh" in the CMD string, and reports the PPID. If you want to run an additional ps to get info on the parent,
ps -p `ps -ef | awk '/PRD_/ && /startscen\.sh/ {print $3}'`
To check the ppid of a particular process, you use notation like this:
$ ps -p 1111 -o ppid=
This is close to what you've got, but note that the equals sign is immediately after ppid, with no space. This equals sign is not part of an expression, its function with the -o option is to specify custom headers. With this example I've included, you're telling ps to include no header at all, so the output will be just the ppid and nothing else. For example, try ps -p 1 -o ppid=Hello.
If I'm reading this correctly, the rest of your example code appears to be unrelated to your actual question, and is an attempt to collect the pid of perhaps a shell script that is running. So ... as an addendum to this answer, my advice on this point would be to modify the shell script so that it records its own somewhere, so you don't have to rely on parsing the process table to find it. For example, you could add something near the top of startscen.sh that looks like this:
pidfile="/var/run/`basename $0`.pid"
if [ -s "$pidfile" ]; then
if ps "$(cat $pidfile)" >/dev/null; then
echo "ERROR: already running, giving up." >&2
exit 1
fi
fi
trap "rm -f pidfile" 0 1 2 3 5 15
echo $$ > $pidfile
It's not perfect, but this will provide you with some protection against running the script twice at the same time, and will store the pid of the running script in a file where other pids live.

Finding process count in Linux via command line

I was looking for the best way to find the number of running processes with the same name via the command line in Linux. For example if I wanted to find the number of bash processes running and get "5". Currently I have a script that does a 'pidof ' and then does a count on the tokenized string. This works fine but I was wondering if there was a better way that can be done entirely via the command line. Thanks in advance for your help.
On systems that have pgrep available, the -c option returns a count of the number of processes that match the given name
pgrep -c command_name
Note that this is a grep-style match, not an exact match, so e.g. pgrep sh will also match bash processes. If you want an exact match, also use the -x option.
If pgrep is not available, you can use ps and wc.
ps -C command_name --no-headers | wc -l
The -C option to ps takes command_name as an argument, and the program prints a table of information about processes whose executable name matches the given command name. This is an exact match, not grep-style. The --no-headers option suppresses the headers of the table, which are normally printed as the first line. With --no-headers, you get one line per process matched. Then wc -l counts and prints the number of lines in its input.
result=`ps -Al | grep command-name | wc -l`
echo $result
ps -Al | grep -c bash
You can try :
ps -ef | grep -cw [p]rocess_name
OR
ps aux | grep -cw [p]rocess_name
For e.g.,:
ps -ef | grep -cw [i]nit
Some of the above didn't work for me, but they helped me on my way to this.
ps aux | grep [j]ava -c
For newbies to Linux:
ps aux prints all the currently running processes, grep searches for all processes that match the word java, the [] brackets remove the process you just ran so it wont include that as a running process and finally the -c option stands for count.
List all process names, sort and count
ps --no-headers -A -o comm | sort | uniq -c
You also can list process attached to a tty
ps --no-headers a -o comm | sort | uniq -c
You may filter with:
ps --no-headers -A -o comm | awk '{ list[$1] ++ } END { for (i in list) { if (list[i] > 10) printf ("%20s: %s\n", i, list[i]) } }'
Following bash script can be run as a cron job and you can possibly get email if any process forks itself too much.
for i in `ps -A -o comm= --sort=+comm | uniq`;
do
if (( `ps -C $i --no-headers | wc -l` > 10 )); then
echo `hostname` $i `ps -C $i --no-headers | wc -l` ;
fi
done
Replace 10 with your number of concern.
TODO: "10" could be passed as command line parameter as well. Also, few system processes can be put into exception list.
You can use ps(will show snapshot of processes) with wc(will count number of words, wc -l option will count lines i.e. newline characters).
Which is very easy and simple to remember.
ps -e | grep processName | wc -l
This simple command will print number of processes running on current server.
If you want to find the number of process running on current server for current user then use -U option of ps.
ps -U root | grep processName | wc -l
change root with username.
But as mentioned in lot of other answers you can also use ps -e | grep -c process_name which is more elegant way.
ps aux | wc -l
This command shows number of processes running on the system by all the users.
For a specific user you can use the following command:
ps -u <username> | wc -l
replace with the actual username before running :)
ps -awef | grep CAP | wc -l
Here "CAP" is the word which is in the my Process_Names.
This command output = Number of Processes + 1
This is why When we are running this command , our system read thats "ps -awef | grep CAP | wc -l " is also a process.
So yes our real answer is (Number of Processes) = Command Output - 1
Note : These processes are only those processes who include the name of "CAP"

Resources