class Heel::Server - heel-3.1.0 Documentation

# class Heel::Server

### Attributes

options[RW]
parsed_options[RW]
stderr[R]
stdin[R]
stdout[R]

### Public Class Methods

new(argv = []) click to toggle source

    # File lib/heel/server.rb, line 32
    def initialize(argv = [])
      argv ||= []

      set_io

      @options         = default_options
      @parsed_options  = ::OpenStruct.new
      @parser          = option_parser
      @error_message   = nil

      begin
        @parser.parse!(argv)
      rescue ::OptionParser::ParseError => pe
        msg = ["#{@parser.program_name}: #{pe}",
               "Try `#{@parser.program_name} --help` for more information"]
        @error_message = msg.join("\n")
      end
    end

### Public Instance Methods

default_directory() click to toggle source

    # File lib/heel/server.rb, line 65
    def default_directory
      ENV["HEEL_DEFAULT_DIRECTORY"] || File.join(::Heel::Server.home_directory,".heel")
    end

default_options() click to toggle source

    # File lib/heel/server.rb, line 51
    def default_options
      defaults                 = ::OpenStruct.new
      defaults.show_version    = false
      defaults.show_help       = false
      defaults.address         = "0.0.0.0"
      defaults.port            = 4331
      defaults.document_root   = Dir.pwd
      defaults.daemonize       = false
      defaults.highlighting    = false
      defaults.kill            = false
      defaults.launch_browser  = true
      return defaults
    end

ensure_not_running() click to toggle source

make sure that if we are daemonizing the process is not running

    # File lib/heel/server.rb, line 198
    def ensure_not_running
      if File.exist?(pid_file) then
        @stdout.puts "ERROR: PID File #{pid_file} already exists. Heel may already be running."
        @stdout.puts "ERROR: Check the Log file #{log_file}"
        @stdout.puts "ERROR: Heel will not start until the .pid file is cleared (`heel --kill --port #{options.port}' to clean it up)."
        exit 1
      end
    end

error_version_help_kill() click to toggle source

if Version or Help options are set, then output the appropriate information instead of running the server.

    # File lib/heel/server.rb, line 152
    def error_version_help_kill
      if @parsed_options.show_version then
        @stdout.puts "#{@parser.program_name}: version #{Heel::VERSION}"
        exit 0
      elsif @parsed_options.show_help then
        @stdout.puts @parser.to_s
        exit 0
      elsif @error_message then
        @stdout.puts @error_message
        exit 1
      elsif @parsed_options.kill then
        kill_existing_proc
      end
    end

heel_app() click to toggle source

    # File lib/heel/server.rb, line 219
    def heel_app
      app = Heel::RackApp.new({ :document_root => options.document_root,
                                :highlighting  => options.highlighting})
      stack = Rack::Builder.new {
        map "/" do
          run app
        end
        map "/heel_css" do
          run Rack::File.new(Heel::Configuration.data_path( "css" ))
        end
        map "/heel_icons" do
          run Rack::File.new(Heel::Configuration.data_path("famfamfam", "icons"))
        end
      }
      return stack.to_app
    end

java?() click to toggle source

    # File lib/heel/server.rb, line 81
    def java?
      RUBY_PLATFORM =~ /java/
    end

kill_existing_proc() click to toggle source

kill an already running background heel process

    # File lib/heel/server.rb, line 168
    def kill_existing_proc
      if File.exists?(pid_file) then
        begin
          pid = open(pid_file).read.to_i
          @stdout.puts "Sending TERM to process #{pid}"
          Process.kill("TERM", pid)
        rescue Errno::ESRCH
          @stdout.puts "Unable to kill process with pid #{pid}.  Process does not exist.  Removing stale pid file."
          File.unlink(pid_file)
        rescue Errno::EPERM
          @stdout.puts "Unable to kill process with pid #{pid}.  No permissions to kill process."
        end
      else
        @stdout.puts "No pid file exists for server running on port #{options.port}, no process to kill"
      end
      @stdout.puts "Done."
      exit 0
    end

launch_browser() click to toggle source

    # File lib/heel/server.rb, line 207
    def launch_browser
      Thread.new do
        print "Launching your browser"
        if options.daemonize then
          puts " at http://#{options.address}:#{options.port}/"
        else
          puts "..."
        end
        ::Launchy.open("http://#{options.address}:#{options.port}/")
      end
    end

log_file() click to toggle source

    # File lib/heel/server.rb, line 73
    def log_file
      File.join(default_directory,"heel.#{options.port}.log")
    end

merge_options() click to toggle source

    # File lib/heel/server.rb, line 135
    def merge_options
      options = default_options.marshal_dump
      options.merge!( @parsed_options.marshal_dump )

      @options = OpenStruct.new(options)
    end

option_parser() click to toggle source

    # File lib/heel/server.rb, line 85
    def option_parser
      OptionParser.new do |op|
        op.separator ""

        op.on("-a", "--address ADDRESS", "Address to bind to",
                                        "  (default: #{default_options.address})") do |add|
          @parsed_options.address = add
        end

        op.on("-d", "--daemonize", "Run daemonized in the background") do
          raise ::OptionParser::ParseError, "Daemonizing is not supported on windows" if win?
          raise ::OptionParser::ParseError, "Daemonizing is not supported on java" if java?
          @parsed_options.daemonize = true
        end

        op.on("-h", "--help", "Display this text") do
          @parsed_options.show_help = true
        end

        op.on("-k", "--kill", "Kill an existing daemonized heel process") do
          @parsed_options.kill = true
        end

        op.on("--[no-]highlighting", "Turn on or off syntax highlighting",
                                             "  (default: off)") do |highlighting|
          @parsed_options.highlighting = highlighting
        end

        op.on("--[no-]launch-browser", "Turn on or off automatic browser launch",
                                               "  (default: on)") do |l|
          @parsed_options.launch_browser = l
        end

        op.on("-p", "--port PORT", Integer, "Port to bind to",
                                        "  (default: #{default_options.port})") do |port|
          @parsed_options.port = port
        end

        op.on("-r","--root ROOT",
                      "Set the document root"," (default: #{default_options.document_root})") do |document_root|
          @parsed_options.document_root = File.expand_path(document_root)
          raise ::OptionParser::ParseError, "#{@parsed_options.document_root} is not a valid directory" if not File.directory?(@parsed_options.document_root)
        end

        op.on("-v", "--version", "Show version") do
          @parsed_options.show_version = true
        end
      end
    end

pid_file() click to toggle source

    # File lib/heel/server.rb, line 69
    def pid_file
      File.join(default_directory,"heel.#{options.port}.pid")
    end

run() click to toggle source

run the heel server with the current options.

    # File lib/heel/server.rb, line 266
    def run

      merge_options
      error_version_help_kill
      setup_heel_dir
      ensure_not_running

      server_thread = start_server

      if options.launch_browser then
        launch_browser.join
      end
      server_thread.join
    end

server_options() click to toggle source

    # File lib/heel/server.rb, line 253
    def server_options
      {
        :app  => heel_app,
        :pid  => pid_file,
        :Port => options.port,
        :Host => options.address,
        :environment => 'deployment',
        :server => 'puma',
        :daemonize => options.daemonize
      }
    end

set_io(stdin = $stdin, stdout = $stdout ,setderr = $stderr) click to toggle source

set the IO objects in a single method call. This is really only for testing instrumentation

    # File lib/heel/server.rb, line 144
    def set_io(stdin = $stdin, stdout = $stdout ,setderr = $stderr)
      @stdin  = stdin
      @stdout = stdout
      @stderr = stderr
    end

setup_heel_dir() click to toggle source

setup the directory that heel will use as the location to run from, where its logs willbe stored and its PID file if backgrounded.

    # File lib/heel/server.rb, line 189
    def setup_heel_dir
      if not File.exists?(default_directory) then
        FileUtils.mkdir_p(default_directory)
        @stdout.puts "Created #{default_directory}"
        @stdout.puts "heel's PID (#{pid_file}) and log file (#{log_file}) are stored here"
      end
    end

start_server() click to toggle source

    # File lib/heel/server.rb, line 236
    def start_server
      server_thread = Thread.new do
        if options.daemonize then
          if cpid = fork then
            Process.waitpid( cpid )
          else
            server = Rack::Server.new( server_options )
            server.start
          end
        else
          server = Rack::Server.new( server_options )
          server.start
        end
      end
      return server_thread
    end

win?() click to toggle source

    # File lib/heel/server.rb, line 77
    def win?
      RUBY_PLATFORM =~ /mswin|mingw/
    end