[Date Prev][Date Next] [Thread Prev][Thread Next] [Date Index] [Thread Index]

Re: start-stop-daemon and java



On Fri, Dec 09, 2005 at 10:26:46PM -0800, Scott Muir wrote:
> Have a question which i think relates to s-s-d more than java but as i've
> been learning, what do i know?
> 
> part of my init.d script.
> ------------
> APPDIR="/usr/jsyncmanager"
> APPUSER="jsync"
> ARGS="-Xmx256M -jar jsyncmanager.jar --server"
> PIDFILE="/var/run/jsyncmanager.pid"
> 
> # Carry out specific functions when asked to by the system
> case "$1" in
>   start)
>     echo "Starting jsyncmanager"
>     start-stop-daemon -Sbm -p $PIDFILE  -c $APPUSER -d $APPDIR  -x
> "/usr/bin/java" -- $ARGS
> ------------
> 
> this was derived from a command line
> 
> java -Xmx256M -jar jsyncmanager.jar --server 2>>out2 &
> 
> The problem is getting a java application to start using an init.d script,
> honouring the pidfile to keep it from running more than once (which the
> s-s-d does) but also trap stderr in a log file.
> 
> if I modify $ARGS to include ...--server 2>>/home/jsync/out2.txt
> 
> the out2.txt file never gets created or added to.

This is a more general problem, not particularly related to java.
Actually, there's two ways to fix this, a good one and an easy one --
the latter one first:

Generally, at the risk of sounding repetitive: try "eval" if your shell
command doesn't behave as expected... :)   (see my recent post
http://lists.debian.org/debian-user/2005/12/msg00590.html -- not saying
you should've read it, just to make clear what I'm referring to)

A simple example:

  ARGS="foo bar >stdout 2>stderr"
  echo $ARGS

is not the same as either of those

  echo foo bar >stdout 2>stderr
or
  ARGS="foo bar"
  echo $ARGS >stdout 2>stderr

If you want it to be the same, you have to write

  ARGS="foo bar >stdout 2>stderr"
  eval echo $ARGS

>From this it follows that the trivial way to fix your redirection
problem would be to either write

ARGS="-Xmx256M -jar jsyncmanager.jar --server"
...
    start-stop-daemon -Sbm -p $PIDFILE  -c $APPUSER -d $APPDIR  -x "/usr/bin/java" -- $ARGS  2>>/home/jsync/out2.txt

or

ARGS="-Xmx256M -jar jsyncmanager.jar --server 2>>/home/jsync/out2.txt"
...
    eval start-stop-daemon -Sbm -p $PIDFILE  -c $APPUSER -d $APPDIR  -x "/usr/bin/java" -- $ARGS

Although this would probably work in your specific case, the ugly
thing about it is, that redirection here does apply to the entire
start-stop-daemon command, not only to the java command being run.
If the start-stop-daemon were to write anything on stderr, it would
also end up in out2.txt. 

OTOH, as you probably know, redirection operators like ">>" always need
a shell to be interpreted.  Yet, the start-stop-daemon itself is not
executing stuff via some subshell (it uses the system call execve(2)). 

So, as you have it now, the last argument just gets passed through to
java, as the verbatim string "2>>/home/jsync/out2.txt", and java simply
doesn't know what to do with it... 

To do it properly, you'll have to use a seperate dedicated shell, for
example like this

APPDIR="/usr/jsyncmanager"
APPUSER="jsync"
EXE=/usr/bin/java
ARGS="-Xmx256M -jar jsyncmanager.jar --server"
JCMD="exec $EXE $ARGS 2>>/home/jsync/out2.txt"
PIDFILE="/var/run/jsyncmanager.pid"

# Carry out specific functions when asked to by the system
case "$1" in
  start)
    echo "Starting jsyncmanager"
    start-stop-daemon -Sbm -p $PIDFILE  -c $APPUSER -d $APPDIR  -x $EXE -a /bin/sh -- -c "$JCMD"
  ...

The remaining ugliness is that the name of the process would be
reported as "/usr/bin/java", which is not most informative, e.g.

$ /etc/init.d/jsyncmanager start
Starting jsyncmanager
/usr/bin/java already running.

One way to work around this would be to create a dummy link
/usr/bin/jsyncmanager -> /usr/bin/java, and then specify this as
the executable.

Also, in case you're still having problems, make sure the java-related
environment settings are identical to what you have when you run the
command normally...

Cheers,
Almut



Reply to: