lib/automate-em/device/device_connection.rb in automate-em-0.0.2 vs lib/automate-em/device/device_connection.rb in automate-em-0.0.3
- old
+ new
@@ -26,11 +26,14 @@
@config = {
:max_buffer => 524288, # 512kb
:clear_queue_on_disconnect => false,
:flush_buffer_on_disconnect => false,
- :priority_bonus => 20
+ :priority_bonus => 20,
+ :inactivity_timeout => 0 # part of make and break options
+ # :response_length # an alternative to response_delimiter (lower priority)
+ # :response_delimiter # here instead of a function call
}
#
# Queues
@@ -249,33 +252,42 @@
# NOTE: The buffer cannot be defered otherwise there are concurrency issues
#
def do_receive_data(data)
@last_recieve_at = Time.now.to_f
- if @parent.respond_to?(:response_delimiter)
- begin
+ begin
+ if @config[:response_delimiter].present?
if @buf.nil?
- del = @parent.response_delimiter
+ del = @config[:response_delimiter]
if del.class == Array
del = array_to_str(del)
elsif del.class == Fixnum
del = "" << del #array_to_str([del & 0xFF])
end
@buf = BufferedTokenizer.new(del, @config[:max_buffer]) # Call back for character
end
data = @buf.extract(data)
- rescue => e
- @buf = nil # clear the buffer
- EM.defer do # Error in a thread
- AutomateEm.print_error(logger, e, {
- :message => "module #{@parent.class} error whilst setting delimiter",
- :level => Logger::ERROR
- })
+ elsif @config[:response_length].present?
+ (@buf ||= "") << data
+ data = @buf.scan(/.{1,#{@config[:response_length]}}/)
+ if data[-1].length == @config[:response_length]
+ @buf = nil
+ else
+ @buf = data[-1]
+ data = data[0..-2]
end
+ else
data = [data]
end
- else
+ rescue => e
+ @buf = nil # clear the buffer
+ EM.defer do # Error in a thread
+ AutomateEm.print_error(logger, e, {
+ :message => "module #{@parent.class} error whilst setting delimiter",
+ :level => Logger::ERROR
+ })
+ end
data = [data]
end
if @waiting && data.length > 0
if @processing
@@ -295,11 +307,11 @@
end
end
#
- # Caled from recieve
+ # Called from receive
#
def process_response(response, command)
EM.defer do
do_process_response(response, command)
end
@@ -436,11 +448,11 @@
end
end
end
def process_response_complete
- if (@make_break && @send_queue.empty?) || @command[:force_disconnect]
+ if (@make_break && @config[:inactivity_timeout] == 0 && @send_queue.empty?) || @command[:force_disconnect]
if @connected
close_connection_after_writing
@disconnecting = true
end
@com_paused = true
@@ -481,11 +493,11 @@
}
#
# Make sure we are sending appropriately formatted data
#
- if data.class == Array
+ if data.is_a?(Array)
data = array_to_str(data)
elsif options[:hex_string] == true
data = hex_to_byte(data)
end
@@ -589,45 +601,48 @@
#
# Connection state
#
- def call_connected(*args) # Called from a deferred thread
+ def call_connected(*args)
#
# NOTE:: Same as add parent in device module!!!
# TODO:: Should break into a module and include it
#
+ set_comm_inactivity_timeout(@config[:inactivity_timeout])
@task_queue.push lambda {
- @parent[:connected] = true
-
- begin
- @send_monitor.mon_synchronize { # Any sends in here are high priority (no emits as this function must return)
- @parent.connected(*args) if @parent.respond_to?(:connected)
- }
- rescue => e
- #
- # save from bad user code (don't want to deplete thread pool)
- #
- AutomateEm.print_error(logger, e, {
- :message => "module #{@parent.class} error whilst calling: connect",
- :level => Logger::ERROR
- })
- ensure
- EM.schedule do
+ EM.defer do
+ @parent[:connected] = true
+
+ begin
+ @send_monitor.mon_synchronize { # Any sends in here are high priority (no emits as this function must return)
+ @parent.connected(*args) if @parent.respond_to?(:connected)
+ }
+ rescue => e
#
- # First connect if no commands pushed then we disconnect asap
+ # save from bad user code (don't want to deplete thread pool)
#
- if @make_break && @first_connect && @send_queue.size == 0
- close_connection_after_writing
- @disconnecting = true
- @com_paused = true
- @first_connect = false
- elsif @com_paused
- @com_paused = false
- @wait_queue.push(nil)
- else
- EM.defer do
- logger.info "Reconnected, communications not paused."
+ AutomateEm.print_error(logger, e, {
+ :message => "module #{@parent.class} error whilst calling: connect",
+ :level => Logger::ERROR
+ })
+ ensure
+ EM.schedule do
+ #
+ # First connect if no commands pushed then we disconnect asap
+ #
+ if @make_break && @first_connect && @send_queue.size == 0
+ close_connection_after_writing
+ @disconnecting = true
+ @com_paused = true
+ @first_connect = false
+ elsif @com_paused
+ @com_paused = false
+ @wait_queue.push(nil)
+ else
+ EM.defer do
+ logger.info "Reconnected, communications not paused."
+ end
end
end
end
end
}
\ No newline at end of file