#!/usr/bin/env ruby
require 'rubygems'
require "daemons"
#require 'yaml'
#require 'erb'
#
#gem 'activesupport', '>=3.0.0.beta4'
#require 'active_support'

# For some reason, ActiveSupport 3.0.0 doesn't load.
# Load needed extension directly for now.
#require "active_support/core_ext/object"
#require "active_support/core_ext/hash"

dir = File.expand_path(File.join(File.dirname(__FILE__), '..'))

daemon_options = {
  :multiple   => false,
  :dir_mode   => :normal,
  :dir        => File.join(dir, 'tmp', 'pids'),
  :backtrace  => true,
  :monitor    => false,
  :ontop      => false,
  :log_output => false,
  :log_dir    => File.join(dir, 'log')
}

#daemon_options[:dir_mode] = daemon_options[:dir_mode].to_sym

######## RUN_PROC
dir = File.expand_path(File.join(File.dirname(__FILE__), '..'))
Daemons.run_proc("onapp_daemon.rb", daemon_options) do
  Dir.chdir(dir)
  # Run for 'production' env by default
  ENV["RAILS_ENV"] ||= "production"
  # Skip dashboard client
  SKIP_DASHBOARD_CLIENT = true
  # Require Rails app configuration
  require File.expand_path('../../config/environment', __FILE__)
  # Enable threaded mode
  Rails.configuration.threadsafe!
  # Require libraries
  require File.expand_path('../../lib/daemons/daemon_tasker', __FILE__)
  require File.expand_path('../../lib/spawn/init', __FILE__)
  require File.expand_path('../../lib/transactions', __FILE__)

  include Spawn
  OnApp.redefine_application_logger!('onapp_daemon')
  @@logger = Rails.logger

  def init_taskers
    begin
      OnApp.configuration.load_from_file
      taskers = [
          DaemonTasks::DaemonTransactionRunner.new(@@logger, OnApp.configuration.simultaneous_transactions, OnApp.configuration.transaction_runner_delay),
          DaemonTasks::DaemonBackupTaker.new(@@logger, OnApp.configuration.simultaneous_backups, OnApp.configuration.backup_taker_delay),
          DaemonTasks::DaemonScheduleRunner.new(@@logger, 1, OnApp.configuration.schedule_runner_delay),
          DaemonTasks::DaemonHypervisorMonitor.new(@@logger, 1, OnApp.configuration.hypervisor_monitor_delay),
          DaemonTasks::DaemonBillingStatUpdater.new(@@logger, 1, OnApp.configuration.billing_stat_updater_delay),
          DaemonTasks::DaemonClusterMonitor.new(@@logger, 1, OnApp.configuration.cluster_monitor_delay)
      ]
    rescue Exception => e
      @@logger.error "ERROR \n #{e.message}"
      @@logger.error e.backtrace
      taskers = []
    end
    return taskers
  end

  $running = true
  Signal.trap("TERM") do
    @@logger.info "Received TERM signal"
    $running = false
  end

  Signal.trap("HUP") do
    $taskers = init_taskers
    @@logger.info "Received HUP signal to update configuration data. New settings for:"
    @@logger.info "backups = " + OnApp.configuration.simultaneous_backups.to_s
    @@logger.info "transactions = " + OnApp.configuration.simultaneous_transactions.to_s
  end

  $count = []
  $taskers = init_taskers

  while ($running) do
    $taskers.each do |tasker|
      if tasker.can_start?
        tasks_count = tasker.tasks_count

        while tasker.can_fork? and tasks_count > 0 do
          spawn_id = spawn_block(:argv => tasker.class.app_name) do
            tasker.execute!
          end
          tasker.add_pid(spawn_id.handle)
          tasker.next_task
          tasks_count -= 1
        end

        tasker.last_execute = Time.now
      end
    end
    sleep 1
  end
end
