class ClientForPoslynx::Net::EMC

A ClientForPoslynx::Net::EM_Connector object is associated with a specific POSLynx host (lane) and provides a convenient means of connecting or re-connecting to the host any number of times within an Event Manager run loop.

An instance of ClientForPoslynx::Net::EM_Connector may be created either inside or outside of a run loop, but it must be used from within a run loop to make or interact with connections since that's the only context in which Event Manager connections are applicable.

Attributes

em_system[R]

The Event Manager system that will be called on for making connections.

handler_class[R]

The connection handler class to be passed as the handler argument to EM::connect.

latest_request[R]

An instance of EM_Connector::RequestCall containing the request data and result callbacks from the most recent #send_request or #get_response call.

port[R]

The server port through which to connected.

server[R]

The POSLynx server to be conected to.

Public Class Methods

CallbackMap(*args) click to toggle source
# File lib/client_for_poslynx/net/em_connector/callback_map.rb, line 7
def self.CallbackMap(*args)
  if args.length == 1 && EMC::CallbackMap === args.first
    return args.first
  else
    EMC::CallbackMap.new( *args )
  end
end
RequestCall(*args) click to toggle source
# File lib/client_for_poslynx/net/em_connector/request_call.rb, line 7
def self.RequestCall(*args)
  if args.length == 1 && self::RequestCall === args.first
    args.first
  elsif args.first.nil?
    RequestCall.new(nil, {})
  else
    RequestCall.new( *args )
  end
end
new(server, port, opts={}) click to toggle source

Creates a new ClientForPoslynx::Net::EM_Connector instance.

The server and port arguments are passed to Event Manager's methods for connecting or reconnecting to the poslynx lane as needed.

Options

  • :encryption<tt> - <tt>:use_ssl if SSL if the connection should be encrypted using SSL. :none if the connection should not be encrypted. Defaults to :none.

  • :handler<tt> - The class given as the handler argument to the <tt>::connect call to the Event Machine system (normally ::EM). Defaults to ClientForPoslynx::Net::EM_Connector::ConnectionHandler This should generally be a subclass of ClientForPoslynx::Net::EM_Connector::ConnectionHandler or be a class that includes ClientforPoslynx::Net::EM_Connector::HandlesConnection and is a subclass of EM::Connection. When using a substitute for ::EM as the Event Machine system, this might not need to be a subclass of EM::Connection, though it will need to supply substitute implementations of several of the EM::Connection methods in that case.

  • :em_system - The event machine system that will be called on for making connections. Defaults to ::EM. Must implement the ::connect method. This is used for dependency injection in unit tests and may be useful for inserting instrumentation arround the ::connect call within an application.

# File lib/client_for_poslynx/net/em_connector.rb, line 71
def initialize(server, port, opts={})
  @server = server
  @port   = port
  state.encryption = opts.fetch( :encryption, :none )
  @handler_class = opts.fetch( :handler,   EMC::ConnectionHandler )
  @em_system     = opts.fetch( :em_system, ::EM )
  state.connection_status ||= :initial
  state.status_of_request ||= :initial
end

Public Instance Methods

connect(result_callbacks={}) click to toggle source

Asynchronously attempts to open an EventMachine connection to the POSLynx lane.

The underlying connection instance is available via #connection immediately after the call returns, though it might not yet represent a completed, open connection.

If the connector already has a currently open connection, then the call to #connect succeeds immediately and synchronously.

Once the connection is completed or fails, the #call method of the apporopriate callback object (if supplied) is invoked with no arguments.

If another #connect request is already pending, then the the new request is combined with the pending for request, and the appropriate callback will be invoked each of those when the connection attempt is subsequently concluded.

Result callback options

  • :on_success - An object to receive #call when the connection is successfully opened.

  • :on_failure - An object to receive #call when the connection attempt fails.

# File lib/client_for_poslynx/net/em_connector.rb, line 179
def connect(result_callbacks={})
  result_callbacks = EMC.CallbackMap(result_callbacks)
  if connection_initial?
    make_initial_connection result_callbacks
  elsif connected?
    result_callbacks.call :on_success
  elsif connecting?
    piggyback_connect result_callbacks
  else
    reconnect result_callbacks
  end
end
connection() click to toggle source

The connection handler instance (connection) after the first call to #connect. It will be an instance of the connection handler class.

# File lib/client_for_poslynx/net/em_connector.rb, line 93
def connection
  state.connection
end
disconnect(result_callbacks={}) click to toggle source

When called from within an EventManager event-handling loop, asynchronously attempts to disconnect the current EventMachine connection to the POSLynx lane.

If there is no currently open connection, then the call to #disconnect succeeds immediately and synchronously.

Note that you might never have reason to call this since Event Machine automatically closes connections when the run loop is stopped.

Result callback options

  • :on_completed - An object to receive #call when finished disconnecting.

# File lib/client_for_poslynx/net/em_connector.rb, line 207
def disconnect(result_callbacks={})
  result_callbacks = EMC.CallbackMap( result_callbacks )
  if connected?
    connection.event_dispatcher =
      EMC::EventDispatcher.for_disconnect( connection, result_callbacks )
    state.connection_status = :disconnecting
    connection.close_connection
  else
    result_callbacks.call :on_completed
  end
end
get_response(result_callbacks={}) click to toggle source

This methid exists to support 2 special-case scenarios that client code may need to handle.

Scenario A:

A request is in progress, and the original result handlers must be replaced with new handlers. For instance, a PIN Pad Reset may have been in progress to initate one workflow, and that workflow is being aborted to initiate a different workflow.

Scenario B:

An attempt was made to cancel a previous pending request by sending another request, but a response to the original request was subsequently received because it was already in transit. Now, we need to resume waiting for the response to the second request since it is actually still pending.

The options for #get_response are the same as for #send_request and have the same meanings, but since no new request is to be made, there is no request_data argument.

If the #status_of_request is :got_response before the invocation, then it is reverted to # :pending.

# File lib/client_for_poslynx/net/em_connector.rb, line 291
def get_response(result_callbacks={})
  result_callbacks = EMC.CallbackMap( result_callbacks )
  unless connected? && ( request_pending? || got_response? )
    result_callbacks.call :on_failure
    return
  end
  self.latest_request = EMC.RequestCall( latest_request.request_data, result_callbacks )
  state.status_of_request = :pending
  connection.event_dispatcher = EMC::EventDispatcher.for_send_request(
    connection, result_callbacks
  )
end
send_request(request_data, result_callbacks={}) click to toggle source

When called with an open connection, asynchronously sends a request to the POSLynx with the given request data.

When the response is received, the response data is passed to the #call method of the :on_response handler.

If #send_request is called without an open connection or when the connection is lost before any response is received, the #call method of the :on_failure callback is invoked.

  • request_data - The request to be sent. Should be an instance of one of the ClientForPoslynx::Data::Requests::... classes.

  • result_callbacks - A hash map of objects, each of which handles a response condition when it receives #call

Result callback options

  • :on_response - An object to receive #call with the response data when the response is received.

  • :on_failure - An object to receive #call if there is no open connection or when the connection is lost.

  • Any other callback(s) that might need to be received from a collaborator via #latest_request data while the request is pending. EMSession may invoke an :on_detached callback, for example.

# File lib/client_for_poslynx/net/em_connector.rb, line 249
def send_request(request_data, result_callbacks={})
  result_callbacks = EMC.CallbackMap( result_callbacks )
  unless connected?
    result_callbacks.call :on_failure
    return
  end
  self.latest_request = EMC.RequestCall( request_data, result_callbacks )
  state.status_of_request = :pending
  connection.event_dispatcher = EMC::EventDispatcher.for_send_request(
    connection, result_callbacks
  )
  connection.send_request request_data
end

Private Instance Methods

latest_request=(value) click to toggle source
# File lib/client_for_poslynx/net/em_connector.rb, line 310
def latest_request=(value)
  args = Array(value)
  @latest_request = EMC.RequestCall( *args )
end
make_initial_connection(result_callbacks) click to toggle source
# File lib/client_for_poslynx/net/em_connector.rb, line 315
def make_initial_connection(result_callbacks)
  state.connection_status = :connecting
  em_system.connect \
    server, port,
    handler_class, state
  connection.event_dispatcher = EMC::EventDispatcher.for_connect(
    connection, result_callbacks
  )
end
piggyback_connect(response_callbacks) click to toggle source
# File lib/client_for_poslynx/net/em_connector.rb, line 333
def piggyback_connect(response_callbacks)
  response_callbacks = response_callbacks.merge(
    original_dispatcher: connection.event_dispatcher
  )
  connection.event_dispatcher = EMC::EventDispatcher.for_connect(
    connection, response_callbacks
  )
end
reconnect(connect_event_dispatch_opts) click to toggle source
# File lib/client_for_poslynx/net/em_connector.rb, line 325
def reconnect(connect_event_dispatch_opts)
  state.connection_status = :connecting
  connection.event_dispatcher = EMC::EventDispatcher.for_connect(
    connection, connect_event_dispatch_opts
  )
  connection.reconnect server, port
end
state() click to toggle source
# File lib/client_for_poslynx/net/em_connector.rb, line 306
def state
  @state ||= State.new
end