English 中文(简体)
if-statement always evaluates to TRUE
原标题:

Is there any reason why this script always returns "running", regardless of whether my process is started or stopped?

if ps ax | grep -v grep | grep "processName" > /dev/null
then
   echo $"running"
else
   echo $"not running"
fi

Thank you very much

UPDATE : I add a full example of my script, maybe there is something wrong elsewhere.

case "$1" in
  start)
    # Start daemons.

    echo -n $"Starting daemon: "
    ;;

  stop)
    # Stop daemons.
    echo -n $"Shutting down: "
    echo
    ;;
  status)
    pgrep -f "ProcessName" > /dev/null
    if [ $? -eq 0 ]; then
        echo $"ProcessName is running"
    else
        echo $"ProcessName is not running"
    fi
    ;;
  restart)
    $0 stop
    $0 start
    ;;

  *)
    echo $"Usage: $0 {start|stop|status|restart}"
    exit 1
esac

UPDATE 2 :

[user@dev init.d]# pgrep -f "MyProcess" > /dev/null
[user@dev init.d]# echo $?
0
[user@dev init.d]# service MyProcess stop
Shutting down MyProcess: Terminated
[user@dev init.d]# pgrep -f "MyProcess" > /dev/null
[user@dev init.d]# echo $?
1

But if [ $? -eq 0 ]; then seems to be TRUE all the time

最佳回答

Try this instead:

ps aux | grep -q "[p]rocessName"
if [ $? -eq 0 ]; then
    echo "running"
else
    echo "not running"
fi

The brackets around the first letter of processName means do don t need the "grep -v grep", while the -q means we don t need the pipe to /dev/null

$? gives you the return code of the previous command executed. Hence, testing if it were 0 would indicate if "grep" found what it was looking for.

Update

If your process name is really short (say "cup"), you might get a false positive as it may match other processes too (say "cupsd"). You can overcome this by having grep match whole words - add the "-w" flag.

Not that this technique is not perfect. You may end up matching entries in the username/date fields. If that happens, look up "man ps" and be more selective of what you print out before doing a grep. Alternatively, prefilter the output with awk to extract only the column showing process/cmd name . E.g:

ps aux | awk  {print $11}  | grep -q -w "[p]rocessName"
if [ $? -eq 0 ]; then
    echo "running"
else
    echo "not running"
fi

Update 2

you can also use pgrep as suggested in answer below.

For really short process names, you might want to specify word boundaries () before and after your process name to prevent overmatching (as described above)

pgrep "procname" > /dev/null
if [ $? -eq 0 ]; then
    echo "running"
else
    echo "not running"
fi

Update 3

From the updated question, I see that you re running it from an init script. There s always a danger of pgrep matching the script itself. Try:

pgrep Processname | grep -q -v $$
if [ $? -eq 0 ]; then
    echo "running"
else
    echo "not running"
fi

That excludes the PID of the script from pgrep matches.

Update 4

(final update? fingers crossed)

If the init script is run via the "service" command, then we need to filter out the parent PID as well. How about:

pgrep Processname | grep -v $$ | grep -q -v $PPID
if [ $? -eq 0 ]; then
    echo "running"
else
    echo "not running"
fi
问题回答

Probably becasue grep "processName" finds itself. I found this self same problem yesterday, except I was xarging the results to kill...

As an alternative you might like to try the pgrep command instead of your string of ps and various greps:

sd@camel:~$ pgrep bash
415
3477
sd@camel:~$ echo $?
0
sd@camel:~$ pgrep arf
sd@camel:~$ echo $?
1

G day,

As an aside, instead of

ps ax | grep -v grep | grep "processName"

Try doing

ps ax | grep "[p]rocessName"

The ps is listing the grep function because it is seeing the string "grep processName" in the process list which is being passed by your grep for the string "processName".

Grepping for "[p]rocessName" will match just "processName" on its own, but not the string "grep [p]rocessName".

your not doing a test. put brackets around the test condition like so:

if [ condition your testing ]





相关问题
Signed executables under Linux

For security reasons, it is desirable to check the integrity of code before execution, avoiding tampered software by an attacker. So, my question is How to sign executable code and run only trusted ...

encoding of file shell script

How can I check the file encoding in a shell script? I need to know if a file is encoded in utf-8 or iso-8859-1. Thanks

How to write a Remote DataModule to run on a linux server?

i would like to know if there are any solution to do this. Does anyone? The big picture: I want to access data over the web, using my delphi thin clients. But i´would like to keep my server/service ...

How can I use exit codes to run shell scripts sequentially?

Since cruise control is full of bugs that have wasted my entire week, I have decided the existing shell scripts I have are simpler and thus better. Here is what I have so far svn update /var/www/...

Good, free, easy-to-use C graphics libraries? [closed]

I was wondering if there were any good free graphics libraries for C that are easy to use? It s for plotting 2d and 3d graphs and then saving to a file. It s on a Linux system and there s no gnuplot ...

热门标签