Created
June 18, 2013 22:27
-
-
Save danp/5810055 to your computer and use it in GitHub Desktop.
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
stop on (stopping <%= @name %> or <%= @name %>.stop TYPE=$TYPE) | |
respawn | |
respawn limit 10 5 | |
kill timeout 20 | |
<% if !@open_file_descriptor_limit.to_s.empty? %> | |
limit nofile <%= @open_file_descriptor_limit %> <%= @open_file_descriptor_limit %> | |
<% end %> | |
instance $INSTANCE | |
script | |
type_instance_index="$(echo "$INSTANCE" | cut -d. -f2)" | |
name="<%= @name %>-$TYPE-$type_instance_index" | |
logger -p local0.notice -t "$name[$$]" "Starting $INSTANCE" | |
PORT=$(/usr/bin/run-procfile port <%= @procfile_path %> <%= @port %> $TYPE $type_instance_index) | |
# This little dance pipes output into logger with three | |
# goals in mind: | |
# - Keep the process as a direct child of init (so upstart | |
# doesn't get confused). | |
# - Make sure logger isn't a child of the process (so it | |
# doesn't get confused). | |
# - Don't leave cruft sitting around in the filesystem. | |
# See `man 7 fifo` and `man 7 pipe` for more info. | |
mkdir -p /var/log/<%= @name %> | |
stdout_fifo="/var/log/<%= @name %>/$name-stdout-log.fifo" | |
stderr_fifo="/var/log/<%= @name %>/$name-stderr-log.fifo" | |
rm -f $stdout_fifo | |
rm -f $stderr_fifo | |
mkfifo $stdout_fifo | |
mkfifo $stderr_fifo | |
# Capture our pid so we can pass it to logger to record | |
# the pid of the actual job and not the pid of the logger | |
# background process. | |
job_pid=$$ | |
# Start logger reading from the fifos, in the background. | |
# The parens cause the logger process to be reparented to | |
# init, rather than remaining a child of the current proc. | |
# | |
# `setsid` will cause loggers to be in a different session | |
# and process group. If we let the loggers be in the same | |
# process group as the main process, they would be killed | |
# by upstart together with the main process, and all output | |
# would be suppressed during termination. | |
( exec setsid logger -p local0.notice -t "$name[$job_pid]" <$stdout_fifo & ) | |
( exec setsid logger -p local0.err -t "$name[$job_pid]" <$stderr_fifo & ) | |
# Redirect the current shell's output to the fifos. Now that | |
# we have open fds for those fifos, we don't need the file | |
# system entries any more... | |
exec >$stdout_fifo 2>$stderr_fifo | |
# ...so we'll remove them. | |
rm $stdout_fifo | |
rm $stderr_fifo | |
# Run the service in the usual way. Our output is already | |
# going to the fifos; that won't change when the new | |
# program executes. | |
upcase_type="$(echo "$TYPE" | tr a-z- A-Z_)" | |
exec sudo -u <%= @name %> PORT=$PORT PS="$INSTANCE" -i exec /usr/bin/run-procfile command <%= @procfile_path %> $TYPE | |
end script |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
task | |
script | |
name="<%= @name %>-$TYPE" | |
upcase_type="$(echo "$TYPE" | tr a-z- A-Z_)" | |
SCALE=$(su - <%= @name %> -c "echo \$${upcase_type}_SCALE") | |
if [ -z "$SCALE" ]; then | |
if [ "$TYPE" = "web" ]; then | |
logger -p local0.err -t "$name[$$]" "${upcase_type}_SCALE not set, defaulting to 1" | |
SCALE=1 | |
else | |
SCALE=0 | |
fi | |
fi | |
if [ $SCALE -eq 0 ]; then | |
logger -p local0.err -t "$name[$$]" "${upcase_type}_SCALE=0, not starting" | |
else | |
i=1 | |
while [ $i -le $SCALE ]; do | |
start <%= @name %>-instance INSTANCE=$TYPE.$i TYPE=$TYPE | |
i=$(( $i + 1 )) | |
done | |
fi | |
end script |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
description "<%= @name %> processes" | |
stop on runlevel [!234] | |
stop on starting rc RUNLEVEL=[016] | |
pre-start exec /usr/bin/run-procfile entries <%= @procfile_path %> <%= @name %> |
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
#!/usr/bin/env ruby | |
command, $procfile, *rest = ARGV | |
def usage | |
$stderr.puts "Usage:" | |
$stderr.puts " #{$0} entries <path to Procfile> <base name> -- start jobs for everything in Procfile" | |
$stderr.puts " #{$0} command <path to Procfile> <type> -- exec process of type" | |
$stderr.puts " #{$0} port <path to Procfile> <base port> <type> <index> -- return port number for type and index" | |
exit 1 | |
end | |
def procfile_entry_for_type(entries, type) | |
unless entry = entries.detect {|e| e[:type] == type } | |
$stderr.puts "Procfile `#{$procfile}` doesn't have an entry for `#{type}`" | |
exit 1 | |
end | |
entry | |
end | |
usage unless command && $procfile | |
unless File.readable?($procfile) | |
$stderr.puts "Procfile `#{$procfile}` doesn't exist or isn't readable" | |
exit 1 | |
end | |
procfile_entries = File.read($procfile).chomp.split("\n").grep(/^\w/).map do |line| | |
parts = line.split(/:\s+/, 2) | |
{ :type => parts[0], :command => parts[1] } | |
end | |
case command | |
when "entries" | |
usage unless process_base = rest.first | |
procfile_entries.each do |entry| | |
system("start", "#{process_base}-instances", "TYPE=#{entry[:type]}") | |
end | |
when "command" | |
usage unless type = rest.first | |
procfile_entry = procfile_entry_for_type(procfile_entries, type) | |
$stdout.sync = true | |
puts "Starting process with command `#{procfile_entry[:command]}`" | |
Dir.chdir(File.dirname($procfile)) | |
exec ["bash", "bash"], "--login", "-c", procfile_entry[:command] | |
when "port" | |
base_port, type, index = rest | |
usage unless base_port && type && index | |
base_port = Integer(base_port) | |
index = Integer(index) | |
procfile_entry = procfile_entry_for_type(procfile_entries, type) | |
port = base_port + (procfile_entries.index(procfile_entry) * 100) + (index - 1) | |
puts port | |
end |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment