Module: Smartcard::Iso::AutoConfigurator

Defined in:
lib/smartcard/iso/auto_configurator.rb

Overview

Automatic configuration code.

Constant Summary

ENVIRONMENT_VARIABLE_NAME =

The name of the environment variable that might supply the transport configuration.

'SCARD_PORT'
DEFAULT_CONFIGURATIONS =

The default configurations to be tried if no configuration is specified.

[
  { :class => JcopRemoteTransport,
    :opts => { :host => '127.0.0.1', :port => 8050} },
  { :class => PcscTransport, :opts => { :reader_index => 0 }}
]

Class Method Summary collapse

Class Method Details

.auto_transportObject

Creates a transport based on available configuration information.



24
25
26
27
28
29
30
31
32
33
# File 'lib/smartcard/iso/auto_configurator.rb', line 24

def self.auto_transport
  configuration = env_configuration
  return try_transport(configuration) if configuration
  
  DEFAULT_CONFIGURATIONS.each do |config|
    transport = try_transport(config)
    return transport if transport
  end
  return nil
end

.env_configurationObject

Retrieves transport configuration information from an environment variable.

:call-seq:

AutoConfigurator.env_configuration -> hash

The returned configuration has the keys required by AutoConfigurator#try_transport



42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
# File 'lib/smartcard/iso/auto_configurator.rb', line 42

def self.env_configuration
  return nil unless conf = ENV[ENVIRONMENT_VARIABLE_NAME]
  
  case conf[0]
  when ?:
    # :8050 -- JCOP emulator at port 8050
    transport_class = JcopRemoteTransport
    transport_opts = { :host => '127.0.0.1' }
    transport_opts[:port] = conf[1..-1].to_i
  when ?@
    # @127.0.0.1:8050 -- JCOP emulator at host 127.0.0.1 port 8050
    transport_class = JcopRemoteTransport
    port_index = conf.rindex(?:) || conf.length
    transport_opts = { :host => conf[1...port_index] }
    transport_opts[:port] = conf[(port_index + 1)..-1].to_i
  when ?#
    # #2 -- 2nd PC/SC reader in the system
    transport_class = PcscTransport
    transport_opts = { :reader_index => conf[1..-1].to_i - 1 }
  else
    # Reader Name -- the PC/SC reader with the given name
    transport_class = PcscTransport
    transport_opts = { :reader_name => conf }
  end
  
  transport_opts[:port] = 8050 if transport_opts[:port] == 0
  if transport_opts[:reader_index] and transport_opts[:reader_index] < 0
    transport_opts[:reader_index] = 0
  end
  { :class => transport_class, :opts => transport_opts }
end

.try_transport(configuration) ⇒ Object

Attempts to create a new ISO7816 transport with the given configuration. :call-seq:

AutoConfigurator.try_transport(configuration) -> Transport or nil

The configuration should have the following keys:

class:: the Ruby class implementing the transport
opts:: the options to be passed to the implementation's constructor


81
82
83
84
85
86
87
88
89
90
# File 'lib/smartcard/iso/auto_configurator.rb', line 81

def self.try_transport(configuration)
  raise 'No transport class specified' unless configuration[:class]
  begin
    transport = configuration[:class].new(configuration[:opts] || {})
    transport.connect
    return transport
  rescue Exception
    return nil
  end
end