In this section, we will create a script
that will transform the Nginx daemon into an actual system service. This
will result in mainly two outcomes the daemon will be controllable
using standard commands, and more importantly, it will automatically be
launched on system startup.
System V scripts
Most Linux-based operating systems to date use a System-V style init daemon. In other words, their startup process is managed by a daemon called init, which functions in a way that is inherited from the old System V Unix-based operating system.
This daemon functions on the principle of runlevels, which represent the state of the computer. Here is a table representing the various runlevels and their signification:
Runlevel
|
State
|
---|
0
|
System is halted
|
1
|
Single-user mode (rescue mode)
|
2
|
Multiuser mode, without NFS support
|
3
|
Full multiuser mode
|
4
|
Not used
|
5
|
Graphical interface mode
|
6
|
System reboot
|
You can manually initiate a runlevel transition: use the telinit 0 command to shut down your computer or telinit 6 to reboot it.
For each runlevel transition, a set of services are executed.
This is the key concept to understand here: when your computer is
stopped, its runlevel is 0; when you turn it on, there will be a
transition from runlevel 0 to the default computer startup runlevel. The
default startup runlevel is defined by your own system configuration
(in the /etc/inittab file) and the default value depends on the
distribution you are using: Debian and Ubuntu use runlevel 2, Red Hat
and Fedora use runlevel 3 or 5, CentOS and Gentoo use runlevel 3, and so
on, as the list is long.
So let us summarize. When you start your computer
running CentOS, it operates a transition from runlevel 0 to runlevel 3.
That transition consists of starting all services that are scheduled for
runlevel 3. The question is how to schedule a service to be started at a
specific runlevel? For each runlevel, there is a directory containing
scripts to be executed.
If you enter these directories (rc0.d,rc1.d, to rc6.d) you will not find actual files, but rather symbolic links referring to scripts located in the init.d directory. Service startup scripts will indeed be placed in init.d, and links will be created by tools placing them in the proper directories.
What is an init script?
An init script, also known as service startup script or even sysv script
is a shell script respecting a certain standard. The script will
control a daemon application by responding to some commands such as
start, stop, and others, which are triggered at two levels. Firstly,
when the computer starts, if the service is scheduled to be started for
the system runlevel, the init daemon will run the script with the start
argument. The other possibility for you is to manually execute the
script by calling it from the shell.
[root@example.com ~]# service httpd start
Or if your system does not come with the service command:
[root@example.com ~]# /etc/init.d/httpd start
The script must accept at least the start and stop
commands as they will be used by the system to respectively start up and
shut down the service. However, for enlarging your field of action as a
system administrator, it is often interesting to provide further
options such as a reload argument to reload the service configuration or a restart argument to stop and start the service again.
Note that since service httpd start and /etc/init.d/httpd start
essentially do the same thing, with the exception that the second
command will work on all operating systems, we will make no further
mention of the service command and will exclusively use the /etc/init.d/ method.
Creating an init script for Nginx
We will thus create a shell script for starting and
stopping our Nginx daemon and also restarting and reloading it. The
purpose here is not to discuss Linux shell script programming, so we
will merely provide the source code of an existing init script, along
with some comments to help you understand it.
First, create a file called nginx with the text editor of your choice, and save it in the /etc/init.d/ directory (on some systems, /etc/init.d/ is actually a symbolic link to /etc/rc.d/init.d/).
In the file you just created, copy the following script carefully. Make
sure that you change the paths to make them correspond to your actual
setup.
You will need root permissions to save the script into the init.d directory.
#! /bin/sh
# Author: Ryan Norbauer http://norbauerinc.com
# Modified: Geoffrey Grosenbach http://topfunky.com
# Modified: Clement NEDELCU
# Reproduced with express authorization from its contributors
set e
PATH=/usr/local/sbin:/usr/local/bin:/sbin:/bin:/usr/sbin:/usr/bin
DESC="nginx daemon"
NAME=nginx
DAEMON=/usr/local/nginx/sbin/$NAME
SCRIPTNAME=/etc/init.d/$NAME
# If the daemon file is not found, terminate the script.
test -x $DAEMON || exit 0
d_start() {
$DAEMON || echo -n " already running"
}
d_stop() {
$DAEMON s quit || echo -n " not running"
}
d_reload() {
$DAEMON s reload || echo -n " could not reload"
}
case "$1" in
start)
echo -n "Starting $DESC: $NAME"
d_start
echo "."
;;
stop)
echo -n "Stopping $DESC: $NAME"
d_stop
echo "."
;;
reload)
echo -n "Reloading $DESC configuration..."
d_reload
Nginxinit script, creating forecho "reloaded."
;;
restart)
echo -n "Restarting $DESC: $NAME"
d_stop
# Sleep for two seconds before starting again, this should give the # Nginx daemon some time to perform a graceful stop.
sleep 2
d_start
echo "."
;;
*)
echo "Usage: $SCRIPTNAME {start|stop|restart|reload}" >&2
exit 3
;;
esac
exit 0
Installing the script
Placing the file in the init.d directory
does not complete our work. There are additional steps that will be
required for enabling the service. First of all, you need to make the
script executable. So far, it is only a piece of text that the system
refuses to run. Granting executable permissions on the script is done
with the chmod command:
[root@example.com ~]# chmod +x /etc/init.d/nginx
Note that if you created the file as the root user, you will need to be logged in as root to change the file permissions.
At this point, you should already be able to start the service using service nginx start or /etc/init.d/nginx start, as well as stopping, restarting, or reloading the service.
The last step here will be to make it so the script
is automatically started at the proper runlevels. Unfortunately, doing
this entirely depends on what operating system you are using. We will
cover the two most popular families Debian/Ubuntu/other Debian-based
distributions and Red Hat/Fedora/CentOS/other Red Hat-derived systems.
Debian-based distributions
For the first one, a simple command will enable the init script for the system runlevel:
[root@example.com ~]# update-rc.d f nginx defaults
This command will create links in the default system runlevel folders: for the reboot and shutdown runlevels, the script will be executed with the stop argument; for all other runlevels, the script will be executed with start. You can now restart your system and see your Nginx service being launched during the boot sequence.
Red Hat-based distributions
For the Red Hat-based systems family, the command
differs, but you get an additional tool for managing system startup.
Adding the service can be done via the following command:
[root@example.com ~]# chkconfig --add nginx
Once that is done, you can then verify the runlevels for the service:
[root@example.com ~]# chkconfig --list nginx
Nginx 0:off 1:off 2:on 3:off 4:on 5:on 6:off
Another tool will be useful to you for managing system services, namely, ntsysv. It lists all services scheduled to be executed on system startup and allows you to enable or disable them at will.
Note that you must first run the chkconfig --add nginx command, otherwise nginx will not appear in the list of services.