#!/usr/bin/env jruby
require 'rubygems'
require 'spoon'
# ### Review : Fork will not work under JRuby
# require 'daemons'
# Daemons.run('./Services/core.rb')
# require File.expand_path("./Services/core.rb",File.dirname(__FILE__))
# Spoon.spawn File.expand_path("./Services/core.rb",File.dirname(__FILE__)), *ARGV

# ### See : https://gist.github.com/ik5/448884
EXEC      = File.expand_path("./Services/core.rb",File.dirname(__FILE__))
PID_PATH  = File.expand_path("./System/Temporary/server.pid",File.dirname(__FILE__))
WORK_PATH = File.expand_path("./System/Temporary",File.dirname(__FILE__))

def create_pid(pid)
  begin
    open(PID_PATH, 'w') do |f|
      f.puts pid
    end
  rescue => e
    STDERR.puts "Error: Unable to open #{PID_PATH} for writing:\n\t" +
        "(#{e.class}) #{e.message}"
    exit!
  end
end

def get_pid
  pid = nil
  begin
    open(PID_PATH, 'r') do |f|
      pid = f.readline
      pid = pid.to_s.gsub(/[^0-9]/,'')
    end
  rescue => e
    # STDERR.puts "Error: Unable to open #{PID_PATH} for reading:\n\t" +
    #     "(#{e.class}) #{e.message}"
  end
  if pid
    pid.to_i
  else
    pid
  end
end

def remove_pidfile
 begin
   File.unlink(PID_PATH)
  rescue => e
    STDERR.puts "ERROR: Unable to unlink #{path}:\n\t" +
      "(#{e.class}) #{e.message}"
    exit
  end
end

def process_exists?
  begin
    pid = get_pid
    return false unless pid
    Process.kill(0, pid)
    true
  rescue Errno::ESRCH, TypeError # "PID is NOT running or is zombied
    false
  rescue Errno::EPERM
    STDERR.puts "No permission to query #{pid}!";
  rescue => e
    STDERR.puts "(#{e.class}) #{e.message}:\n\t" +
      "Unable to determine status for #{pid}."
    false
  end
end

def stop
    begin
        pid = get_pid
        STDERR.puts "pid : #{pid}"
        while true do
            Process.kill("TERM", pid)
            Process.wait(pid)
            sleep(0.1)
        end
        remove_pidfile
        STDOUT.puts 'Stopped the process'
    rescue Errno::ECHILD
        remove_pidfile
        STDOUT.puts 'Stopped the process'
        #
    rescue => e
        STDERR.puts "unable to terminate process: (#{e.class}) #{e.message}"
    end
end

def start
    #   if process_exists?
    #    STDERR.puts "The process #{EXEC} already running. Restarting the process"
    #    stop
    #   end
    unless process_exists?
        pid = Spoon.spawn EXEC, *ARGV
        create_pid(pid)
        # ### FIX : setsid not permitted EPERM error as www-data/etc
        # Process.setsid
        # at_exit do
        #     remove_pidfile
        # end
    
        Dir::chdir(WORK_PATH)
        File::umask(0)
        STDIN.reopen("/dev/null", 'r')
        STDOUT.reopen("/dev/null", "w")
        STDERR.reopen("/dev/null", "w")
    end
end

if ARGV[0] == 'start'
  start
elsif ARGV[0] == 'stop'
  stop
elsif ARGV[0] == 'restart'
  stop
  start
elsif ARGV[0] == 'status'
  if File.exist?(PID_PATH)
    puts "running"
  else
    puts "stopped"
  end
else
  STDERR.puts "Usage: server <start|stop|restart | status>"
  exit!
end