I'm using the following Upstart script to keep Nginx up and running on Ubuntu server:
start on (filesystem and net-device-up IFACE=lo)
stop on runlevel [!2345]
env DAEMON=/usr/sbin/nginx
env CONF=/etc/nginx/nginx.conf
respawn
respawn limit 10 5
pre-start script
$DAEMON -t
if [ $? -ne 0 ]; then
exit $?
fi
end script
exec $DAEMON -c $CONF -g "daemon off;" > /dev/null 2>&1
This script works fine except when I'm killing the Nginx master process using the kill command. After killing the master process /var/run/nginx.pid remains the same but Nginx pid keeps changing every few seconds (this means Nginx is restarting all the time?). Any idea how to fix this?
Related
I have a /bin/NginxWrapper script that runs NGINX:
#!/bin/env sh
export LD_LIBRARY_PATH=$ENVIRONMENT_ROOT/lib/:$LD_LIBRARY_PATH
/bin/nginx
Supervisord config command points the above script, so that when we kick off Nginx, supervisor will first call this script
[program:nginx]
command=/bin/NginxWrapper -c /nginx/nginx.conf -g "daemon off;"
The problem is, Superisord is now storing the PID of this script, instead of the PID of Nginx. And if i try to send HUP to Nginx, its unable to.
Is it possible to change the PID in supervisord so that it's Nginx's PID?
OR
Is there a way to chain Supersivord command so that i dont need the wrapper, and can just chain something like
[program:nginx]
command= export LD_LIBRARY_PATH=$ENVIRONMENT_ROOT/lib/:$LD_LIBRARY_PATH && /bin/NginxWrapper -c /nginx/nginx.conf -g "daemon off;"
Many thanks...
Change
/bin/nginx
to
exec /bin/nginx
My Dockerfile installs firebase emulators. When stop firebase emulators, it should export data before exit.
# Skip installation: https://firebase.google.com/docs/emulator-suite/install_and_configure
CMD ["firebase", "emulators:start", "--import=./data", "--export-on-exit"]
If I run docker run -ti --name my-firebase-tools my-firebase-tools and then press Crtl-C, firebase emulators stops gracefully before container stops. Everything is ok.
But normally, I want to run docker run -d -ti --name my-firebase-tools my-firebase-tools, so the container will run in background.
In this case, if I run docker stop my-firebase-tools, no signal is sent to firebase to terminal firebase emulators, therefore no data is exported. Container stops after 10s with exit code 137.
docker run -d -ti --stop-signal SIGINT --name my-firebase-tools my-firebase-tools doesn't help.
Tried with entrypoint.sh below:
pid=0
sigterm_handler() {
if [ $pid -ne 0 ]; then
kill -SIGTERM "$pid"
wait "$pid"
fi
exit 143; # 128 + 15 -- SIGTERM
}
trap 'kill ${!}; sigterm_handler' SIGTERM
firebase emulators:start --import=./data --export-on-exit &
pid="$!"
# wait forever
while true
do
tail -f /dev/null & wait ${!}
done
the signal is trapped, sigterm_handler is called, but firebase still doesn't receive the termination signal.
This entrypoint solve the problem.
#!/bin/bash
loopPid=0
pid=0
sigterm_handler() {
pkill -P "$pid"
wait "$pid"
echo "sigterm handled gracefully"
exit 0;
}
trap 'sigterm_handler' SIGTERM
sigint_handler() {
wait "$pid"
wait "$loopPid"
echo "sigint handled gracefully"
exit 0;
}
trap 'sigint_handler' SIGINT
exec firebase emulators:start --import=./data --export-on-exit &
pid="$!"
# wait forever
tail -f /dev/null &
loopPid="$!"
wait "$loopPid"
echo "Not a gracefully shutdown"
exit 1;
If I do :
docker run --name nginx -d nginx:alpine /bin/sh -c 'echo "Hello stdout" > /dev/stdout'
I can see "Hello stdout" when I do :
docker logs nginx
But when the container is running (docker run --name nginx -d nginx:alpine) and I do :
docker exec nginx /bin/sh -c 'echo "Hello stdout" > /dev/stdout'
or when I attach the container with :
docker exec -it nginx /bin/sh
and then :
echo "Hello stdout" > /dev/stdout
I can't see anything in docker logs. And since my Nginx access logs are redirected to /dev/stdout, I can't see them as well.
What is happening here with this stdout ?
When you docker exec you can see you have several process
/ # ps -ef
PID USER TIME COMMAND
1 root 0:00 nginx: master process nginx -g daemon off;
6 nginx 0:00 nginx: worker process
7 root 0:00 /bin/sh
17 root 0:00 ps -ef
/ #
and in Linux, each process has its own stdin, stdout, stderr (and other file descriptors), in /proc/pid/fd
and so, with your docker exec (pid 7) you display something in
/proc/7/fd/1
If you do ls -ltr /proc/7/fd/1, it displays something like
/proc/4608/fd/1 -> /dev/pts/2 which means output is being sent to terminal
while your nginx process (pid 1) displays his output in
/proc/1/fd/1
If you do ls -ltr /proc/1/fd/1, it displays something like /proc/1/fd/1 -> pipe:[184442508] which means output is being sent to docker logging driver
I have created a new service named some-service. The shell script is present in /etc/init.d/some-service I have the same shell script file in /usr/local/bin/some-service which is a copy of some-service.
i ran the below command to create a daemon service:
os-svc-daemon -i $INSTALLDIR -d some-service some-service root some-service
This created a /etc/init/some-service.conf
start on runlevel [2345]
stop on runlevel [016]
env OS_SVC_ENABLE_CONTROL=1
export OS_SVC_ENABLE_CONTROL
pre-start script
mkdir -p /var/run/some-service
chown -R root:root /var/run/some-service
end script
respawn
# the default post-start of 1 second sleep delays respawning enough to
# not hit the default of 10 times in 5 seconds. Make it 2 times in 5s.
respawn limit 2 5
exec start-stop-daemon --start -c root --exec **INSTALLDIR**/bin/some-service --
post-start exec sleep 1
to reload the changes ran the below command
initctl reload-configuration
in tried to start the service but it never runs.
initctl start some-service
What am i doing wrong here? Also is it safe to use shell script to start it and not a python bin file?
Use os-svc-enable servicename and try start servicename
I have two logrotate files:
/etc/logrotate.d/nginx-size
/var/log/nginx/*.log
/var/log/www/nginx/50x.log
{
missingok
rotate 3
size 2G
dateext
compress
compresscmd /usr/bin/bzip2
compressoptions -6
compressext .bz2
uncompresscmd /usr/bin/bunzip2
notifempty
create 640 nginx nginx
sharedscripts
postrotate
[ -f /var/run/nginx.pid ] && kill -USR1 `cat /var/run/nginx.pid`
endscript
}
and
/etc/logrotate.d/nginx-daily
/var/log/nginx/*.log
/var/log/www/nginx/50x.log
{
missingok
rotate 3
dateext
compress
compresscmd /usr/bin/bzip2
compressoptions -6
compressext .bz2
uncompresscmd /usr/bin/bunzip2
notifempty
create 640 nginx nginx
sharedscripts
postrotate
[ -f /var/run/nginx.pid ] && kill -USR1 `cat /var/run/nginx.pid`
endscript
}
Command logrotate -d -v /etc/logrotate.d/nginx-sizeoutput:
reading config file /etc/logrotate.d/nginx-size
compress_prog is now /usr/bin/bzip2
compress_options is now -6
compress_ext is now .bz2
uncompress_prog is now /usr/bin/bunzip2
Handling 1 logs
rotating pattern: /var/log/nginx/*.log
/var/log/www/nginx/50x.log
2147483648 bytes (3 rotations)
empty log files are not rotated, old logs are removed
considering log /var/log/nginx/access.log
log does not need rotating
considering log /var/log/nginx/error.log
log does not need rotating
considering log /var/log/nginx/get.access.log
log does not need rotating
considering log /var/log/nginx/post.access.log
log needs rotating
considering log /var/log/www/nginx/50x.log
log does not need rotating
rotating log /var/log/nginx/post.access.log, log->rotateCount is 3
dateext suffix '-20141204'
glob pattern '-[0-9][0-9][0-9][0-9][0-9][0-9][0-9][0-9]'
glob finding old rotated logs failed
renaming /var/log/nginx/post.access.log to /var/log/nginx/post.access.log-20141204
creating new /var/log/nginx/post.access.log mode = 0640 uid = 497 gid = 497
running postrotate script
running script with arg /var/log/nginx/*.log
/var/log/www/nginx/50x.log
: "
[ -f /var/run/nginx.pid ] && kill -USR1 `cat /var/run/nginx.pid`
"
compressing log with: /usr/bin/bzip2
Same (normal) output on ngnix-daily..
If I run from root command
logrotate -f /etc/logrotate.d/nginx-size
manually, it do all the thing. BUT! It don't run it automatically!
contab:
*/5 5-23 * * * root logrotate -f -v /etc/logrotate.d/nginx-size 2>&1 > /tmp/logrotate_size
00 04 * * * root logrotate -f -v /etc/logrotate.d/nginx-daily 2>&1 > /tmp/logrotate_daily
Also, files /tmp/logrotate_daily & /tmp/logrotate_size are always empty..
Cron don't give me any errors in /var/log/cron
Dec 4 14:45:01 (root) CMD (logrotate -f -v /etc/logrotate.d/nginx-rz-size 2>&1 > /tmp/logrotate_size )
Dec 4 14:50:01 (root) CMD (logrotate -f -v /etc/logrotate.d/nginx-rz-size 2>&1 > /tmp/logrotate_size )
What's wrong with dat thing?.. Centos 6.5 x86_64, Logrotate version 3.8.7 (out of source) + logrotate version 3.7.8 (via rpm).
Thx in advance.
Your redirections are incorrect in those cron lines. They will not output error information to those files.
Redirection order matters. You want >/tmp/logrotate_size 2>&1 to get what you want.
The underlying issue here is one of the things covered by the "Debugging crontab" section of the cron info page.
Namely "Making assumptions about the environment".
Making assumptions about the environment
Graphical programs (X11 apps), java programs, ssh and sudo are notoriously problematic to run as cron jobs. This is because they rely on things from interactive environments that may not be present in cron's environment.
To more closely model cron's environment interactively, run
env -i sh -c 'yourcommand'
This will clear all environment variables and run sh which may be more meager in features that your current shell.
Common problems uncovered this way:
foo: Command not found or just foo: not found.
Most likely $PATH is set in your .bashrc or similar interactive init file. Try specifying all commands by full path (or put source ~/.bashrc at the start of the script you're trying to run).