├── .gitignore ├── README.md ├── examples └── node-upstart.conf └── node-upstart.key /.gitignore: -------------------------------------------------------------------------------- 1 | .DS_Store 2 | 3 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Running node.js Apps with Upstart 2 | 3 | # Introduction 4 | 5 | After developing my first node.js app, I realized the need to run it as a system service. Specifically I wanted to have the app start during boot, run in the background and, if the process died unexpectedly, have it respawn automatically. While researching how to do this on an Ubuntu system I came across Upstart. 6 | 7 | # What is Upstart? 8 | 9 | The official Upstart website defines Upstart as "an event-based replacement for the /sbin/init daemon which handles starting of tasks and services during boot, stopping them during shutdown and supervising them while the system is running." Through the creation of custom configuration files, called job definitions, we are able to "daemonize" a node.js app by assigning it behaviors common to system services. 10 | 11 | # Upstart Job Definitions 12 | 13 | Upstart Job Definitions are are defined in files located in /etc/init. The name of a job is the definition filename without the .conf extension. The following is an example job definition for a node.js app: 14 | 15 | # node-upstart - Example Upstart job definition for a node.js based app 16 | # 17 | 18 | description "Example Upstart job definition for a node.js based app" 19 | author "Chris Verwymeren" 20 | 21 | # When to start the service 22 | start on runlevel [2345] 23 | 24 | # When to stop the service 25 | stop on runlevel [06] 26 | 27 | # Prepare the environment 28 | # Create directories for logging and process management 29 | # Change ownership to the user running the process 30 | pre-start script 31 | mkdir -p /var/opt/node 32 | mkdir -p /var/opt/node/log 33 | mkdir -p /var/opt/node/run 34 | chown -R node:node /var/opt/node 35 | end script 36 | 37 | # If the process quits unexpectadly trigger a respawn 38 | respawn 39 | 40 | # Start the process 41 | exec start-stop-daemon --start --chuid node --make-pidfile --pidfile /var/opt/node/run/node-upstart.pid --exec /home/node/local/node/bin/node -- /home/node/apps/node-upstart.js >> /var/opt/node/log/node-upstart.log 2>&1 42 | 43 | The first section provides information about the job definition. In this instance a description of the app is provided along with the name and email address of the author who created the job definition. Similar to most other configuration files, comments are initiated by placing a # symbol at the beginning of a line of text. 44 | 45 | # node-upstart - Example Upstart job definition for a node.js based app 46 | # 47 | 48 | description "Example Upstart job definition for a node.js based app" 49 | author "Chris Verwymeren " 50 | 51 | The next section provides information on when to start and stop the job. In this example, the process will be automatically started on the various Multi-User Modes (2-5) and stopped on Halt (0) or Reboot (6). 52 | 53 | # When to start the service 54 | start on runlevel [2345] 55 | 56 | # When to stop the service 57 | stop on runlevel [06] 58 | 59 | pre-start allows the environment to be prepared before a job is started. In this example, the directories for logging and process management are created and assigned ownership. 60 | 61 | # Prepare the environment 62 | # Create directories for logging and process management 63 | # Change ownership to the user running the process 64 | pre-start script 65 | mkdir -p /var/opt/node 66 | mkdir -p /var/opt/node/log 67 | mkdir -p /var/opt/node/run 68 | chown -R node:node /var/opt/node 69 | end script 70 | 71 | Using the respawn command will restart the job if it quits unexpectadly. 72 | 73 | # If the process quits unexpectadly trigger a respawn 74 | respawn 75 | 76 | The last section handles the details of the job command which is run during the "start" action. 77 | 78 | # Start the process 79 | exec start-stop-daemon --start --chuid node --make-pidfile --pidfile /var/opt/node/run/node-upstart.pid --exec /home/node/local/node/bin/node -- /home/node/apps/node-upstart.js >> /var/opt/node/log/node-upstart.log 2>&1 80 | 81 | In the example above, the job command is run under the node user (--chuid node), a process id file is created at a specific location (--make-pidfile --pidfile /var/opt/node/run/node-upstart.pid) and the node.js app is executed with stdout and stderr logged to a file (--exec /home/node/local/node/bin/node -- /home/node/apps/node-upstart.js >> /var/opt/node/log/node-upstart.log 2>&1). 82 | 83 | In the above example, the name of the job definition file is node-upstart.conf therefore the name of the job is node-upstart. When using command line utilites to interact with the job, use the job name. 84 | 85 | After creating a job definition save the file to /etc/init. Then, use initctl to verify the job has been recognized by Upstart. 86 | 87 | $ initctl list | grep node-upstart 88 | node-upstart stop/waiting 89 | 90 | # Manual Job Control 91 | 92 | As an added bonus, Upstart allows for services to be controlled manually using the commands start, stop and status. For example, an administrator can start, stop and determine the status of the above job definition using the following commands: 93 | 94 | $ sudo start node-upstart 95 | node-upstart start/running, process 3410 96 | $ sudo status node-upstart 97 | node-upstart start/running, process 3410 98 | $ sudo stop node-upstart 99 | node-upstart stop/waiting 100 | $ sudo status node-upstart 101 | node-upstart stop/waiting 102 | 103 | # More Information 104 | 105 | ## Upstart 106 | 107 | * http://upstart.ubuntu.com/ 108 | 109 | ## Upstart Cookbook 110 | 111 | * http://upstart.ubuntu.com/cookbook/ 112 | 113 | ## Presentation and Examples 114 | 115 | * https://github.com/cvee/node-upstart 116 | 117 | ## Chris Verwymeren 118 | 119 | * cvee@me.com 120 | * https://twitter.com/cvee 121 | -------------------------------------------------------------------------------- /examples/node-upstart.conf: -------------------------------------------------------------------------------- 1 | # node-upstart - Example Upstart job definition for a node.js based app 2 | # 3 | 4 | description "Example Upstart job definition for a node.js based app" 5 | author "Chris Verwymeren" 6 | 7 | # When to start the service 8 | start on runlevel [2345] 9 | 10 | # When to stop the service 11 | stop on runlevel [06] 12 | 13 | # Prepare the environment 14 | # Create directories for logging and process management 15 | # Change ownership to the user running the process 16 | pre-start script 17 | mkdir -p /var/opt/node 18 | mkdir -p /var/opt/node/log 19 | mkdir -p /var/opt/node/run 20 | chown -R node:node /var/opt/node 21 | end script 22 | 23 | # If the process quits unexpectadly trigger a respawn 24 | respawn 25 | 26 | # Start the process 27 | exec start-stop-daemon --start --chuid node --make-pidfile --pidfile /var/opt/node/run/node-upstart.pid --exec /home/node/local/node/bin/node -- /home/node/apps/node-upstart.js >> /var/opt/node/log/node-upstart.log 2>&1 -------------------------------------------------------------------------------- /node-upstart.key: -------------------------------------------------------------------------------- https://raw.githubusercontent.com/cvee/node-upstart/16c6847e61bb7f51816dbc0230014968b1e959bc/node-upstart.key --------------------------------------------------------------------------------