class EaseEngine::Application

Attributes

exit_status[RW]
is_daemon[RW]
is_update[RW]
measure[RW]
options[RW]
socket_timer[RW]
timer[RW]
watcher[RW]

Public Class Methods

new( options ) click to toggle source
# File lib/ease_engine/application.rb, line 52
def initialize( options )
  @options = options
  if ! @options.key?( :watcher )
    @options[ :watcher ] = {}
  end
  if ! @options.key?( :timer )
    @options[ :timer ] = {}
  end
  if ! @options.key?( :socket_timer )
    @options[ :socket_timer ] = {
      :connect_timeout_usec   => 10000000,
      :connected_timeout_usec => 10000000,
    }
  end
  @options[ :is_daemon ] = false if ! @options.key?( :is_daemon )
  
  @exit_status = 0
  @is_update = false
  
  @watcher = EaseEngine::Watcher.new( @options[ :watcher ] )
  @measure = EaseEngine::Measure.new
  @timer = EaseEngine::Timer.new( @options[ :timer ] )
  @socket_timer = EaseEngine::Timer.new( @options[ :socket_timer ] )
  
  @is_daemon = @options[ :is_daemon ]
end
run( options = {} ) click to toggle source
# File lib/ease_engine/application.rb, line 13
def self.run( options = {} )
  EaseEngine::Log.inf( "EaseEngine #{EaseEngine::VERSION} options=#{options}" )
  application = new( options )
  begin
    application.on_start
  rescue => err
    application.on_error( err )
    
    application.is_update = false
  end
  
  while application.is_update
    begin
      EaseEngine::Frame.update{|sleep_time_usec, sleep_time_f|
        application.watcher.watch( sleep_time_f )
      }
      application.timer.update
      application.socket_timer.update
      application.on_update
    rescue => err
      application.on_error( err )
    end
  end
  
  begin
    application.on_end
  rescue => err
    application.on_error( err )
  end
  
  application.exit_status
end

Public Instance Methods

add_connect_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 161
def add_connect_socket( socket )
  application = self
  @watcher.add( socket, {
    :on_read => Proc.new{|socket|
      socket.err = SystemCallError.new( socket.errno )
      application.on_error_socket( socket )
      application.remove_socket( socket )
    },
    :on_write => Proc.new{|socket|
      application.remove_socket_timer( socket.to_i )
      
      socket.err = nil
      application.add_socket( socket )
      application.on_connected_socket( socket )
      
      if socket.is_heartbeat
        # connected timeout
        hash = {
          :socket       => socket,
          :timeout_usec => @options[ :socket_timer ][ :connected_timeout_usec ],
        }
        hash[ :callback ] = Proc.new{|hash|
          if hash[ :socket ].is_timeout
            application.timeout_socket( hash[ :socket ] )
            next
          end
          
          hash[ :socket ].is_timeout = true
          application.write_packet( socket, EaseEngine::HeartbeatBeginPacket.new )
          application.add_socket_timer( hash[ :socket ].to_i, hash[ :timeout_usec ], hash, hash[ :callback ] )
        }
        hash[ :callback ].call( hash )
      end
    },
    :on_remove => Proc.new{|socket|
      application.close_socket( socket )
    }
  })
  
  # connect timeout
  add_socket_timer( socket.to_i, @options[ :socket_timer ][ :connect_timeout_usec ], socket, Proc.new{|socket|
    application.timeout_socket( socket )
  })
end
add_server_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 137
def add_server_socket( socket )
  application = self
  @watcher.add( socket, {
    :on_read => Proc.new{|socket|
      application.on_accept_socket( socket )
    },
    :on_remove => Proc.new{|socket|
      application.close_socket( socket )
    }
  })
end
add_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 149
def add_socket( socket )
  application = self
  @watcher.add( socket, {
    :on_read => Proc.new{|socket|
      application.read_socket( socket )
    },
    :on_remove => Proc.new{|socket|
      application.close_socket( socket )
    }
  })
end
add_socket_timer( socket_id, timeout_usec, arg, callback ) click to toggle source
# File lib/ease_engine/application.rb, line 261
def add_socket_timer( socket_id, timeout_usec, arg, callback )
  @socket_timer.add( socket_id, timeout_usec, arg, callback )
end
add_timer( group_id, timeout_usec, arg, callback ) click to toggle source
# File lib/ease_engine/application.rb, line 253
def add_timer( group_id, timeout_usec, arg, callback )
  @timer.add( group_id, timeout_usec, arg, callback )
end
check_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 237
def check_socket( socket )
  on_error_socket( socket ) if ! socket.err.nil?
  remove_socket( socket ) if socket.is_disable
end
close_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 247
def close_socket( socket )
  remove_socket_timer( socket.to_i )
  on_close_socket( socket )
  socket.close
end
on_accept_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 102
def on_accept_socket( socket )
  accepted_socket = socket.accept
  if ! socket.err.nil?
    on_error_socket( socket )
    return
  end
  
  add_socket( accepted_socket )
  on_accepted_socket( accepted_socket, socket )
end
on_accepted_socket( accepted_socket, server_socket ) click to toggle source
# File lib/ease_engine/application.rb, line 113
def on_accepted_socket( accepted_socket, server_socket )
end
on_close_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 122
def on_close_socket( socket )
end
on_connected_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 116
def on_connected_socket( socket )
end
on_end() click to toggle source
# File lib/ease_engine/application.rb, line 96
def on_end
  @watcher.each{|info|
    @watcher.remove( info.io )
  }
end
on_error( err ) click to toggle source
# File lib/ease_engine/application.rb, line 133
def on_error( err )
  EaseEngine::Log.err( "on_error #{err.class.name}: #{err}\n#{err.backtrace}" )
end
on_error_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 129
def on_error_socket( socket )
  EaseEngine::Log.err( "on_error_socket #{socket} #{socket.err.class.name}: #{socket.err}\n#{socket.err.backtrace}" )
end
on_read_socket( socket, packet ) click to toggle source
# File lib/ease_engine/application.rb, line 119
def on_read_socket( socket, packet )
end
on_start() click to toggle source
# File lib/ease_engine/application.rb, line 79
def on_start
  trap( :INT ){
    @is_update = false
    @exit_status = :INT
  }
  
  trap( :TERM ){
    @is_update = false
    @exit_status = :TERM
  }
  
  trap( :PIPE ){}
end
on_timeout_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 125
def on_timeout_socket( socket )
  EaseEngine::Log.wrn( "on_timeout_socket #{socket}" )
end
on_update() click to toggle source
# File lib/ease_engine/application.rb, line 93
def on_update
end
read_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 210
def read_socket( socket )
  Packet.creates( socket ).each{|packet|
    case packet.packet_name
    when "EaseEngine.HeartbeatBeginPacket"
      write_packet( socket, EaseEngine::HeartbeatEndPacket.new )
    when "EaseEngine.HeartbeatEndPacket"
    else
      on_read_socket( socket, packet )
    end
  }
  check_socket( socket )
end
reflect_socket( socket, recv_flags = 0, send_flags = 0 ) click to toggle source
# File lib/ease_engine/application.rb, line 227
def reflect_socket( socket, recv_flags = 0, send_flags = 0 )
  buf = socket.recv( socket.read_max_size, recv_flags )
  if ! buf.empty?
    result = socket.send( buf, send_flags )
    return if result == buf.length
    EaseEngine::Log.err( "reflect_socket #{result} != #{buf.length}" ) if 0 < result && result != buf.length
  end
  check_socket( socket )
end
remove_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 206
def remove_socket( socket )
  @watcher.remove( socket )
end
remove_socket_timer( socket_id, timer_id = 0 ) click to toggle source
# File lib/ease_engine/application.rb, line 265
def remove_socket_timer( socket_id, timer_id = 0 )
  @socket_timer.remove( socket_id, timer_id )
end
remove_timer( group_id, timer_id = 0 ) click to toggle source
# File lib/ease_engine/application.rb, line 257
def remove_timer( group_id, timer_id = 0 )
  @timer.remove( group_id, timer_id )
end
timeout_socket( socket ) click to toggle source
# File lib/ease_engine/application.rb, line 242
def timeout_socket( socket )
  on_timeout_socket( socket )
  remove_socket( socket )
end
write_packet( socket, packet, flags = 0, *args ) click to toggle source
# File lib/ease_engine/application.rb, line 223
def write_packet( socket, packet, flags = 0, *args )
  packet.write( socket, flags, *args )
end