Class: IB::Flex

Inherits:
Object
  • Object
show all
Defined in:
lib/ib/flex.rb

Overview

Instance Method Summary collapse

Constructor Details

#initialize(query_id: nil, token: nil, format: :xml, verbose: false, return_hash: false) {|_self| ... } ⇒ Flex

:return_hash => true / false (default)

Yields:

  • (_self)

Yield Parameters:

  • _self (IB::Flex)

    the object that the method was called on



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
# File 'lib/ib/flex.rb', line 42

def initialize query_id: nil ,  # must be specified
							 token: nil ,	# must be specified once
							 format: :xml,# or :csv
							 verbose:  false,
							 return_hash: false	

    # By default, uri is a well known FLEX Web Service URI
	self.uri =
		'https://gdcdyn.interactivebrokers.com/Universal/servlet/FlexStatementService.SendRequest'

	# convert parameters into instance-variables and assign them
	method(__method__).parameters.each do |type, k|
		next unless type == :key
		case k
		when :token
			self.token = token unless token.nil?
		else
			v = eval(k.to_s)
			instance_variable_set("@#{k}", v) unless v.nil?
		end
	end

	error "Token not set", :flex if Flex.token.nil?
	error "query_id not set", :flex if @query_id.nil?
	yield self if block_given?
end

Instance Method Details

#get_content(address, fields) ⇒ Object

Helper method to get (and parse XML) responses from IB Flex Web Service



112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
# File 'lib/ib/flex.rb', line 112

def get_content address, fields
get = -> ( the_uri ) do
server = Net::HTTP.new(the_uri.host, the_uri.port)
server.use_ssl =  true
server.verify_mode = OpenSSL::SSL::VERIFY_NONE if server.use_ssl? # Avoid OpenSSL failures
server.start{ |http| http.request( Net::HTTP::Get.new(the_uri.request_uri) ) }
			end
		
  text_ok = fields.delete(:text_ok)
  the_uri = URI("#{address}?" + fields.map { |k, v| "#{k}=#{URI.encode(v.to_s)}" }.join('&'))
			response = get[ the_uri ] 

  error("URI responded with #{response.code}", :flex) unless response.code.to_i == 200
			if text_ok
response.body
			else
Ox.parse response.body
			end
end

#runObject

Run a pre-defined Flex query against IB Flex Web Service Returns a (parsed) report or raises FlexError in case of problems



71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
# File 'lib/ib/flex.rb', line 71

def run
  # Initiate FLEX request at a known FLEX Web Service URI
			# get_content returns an Ox-Element-Object
			# Nodes > FlexStatementResponse and
			#			  > if Status is other then 'suscess'  ErrorCode and ErrorMessage
			#			  > otherwise Uri and  ReferenceCode

  statement = get_content( Flex.uri, :t => Flex.token, :q => @query_id, :v => 3)
			if @verbose
puts "the Statement returned by the request of the query"	
puts Ox.load(Ox.dump( statement), mode: :hash)  
			end
			error("Flex Query is invalid", :flex )  unless statement.value == 'FlexStatementResponse'
			error("#{statement.ErrorCode.ox.to_i}: #{statement.ErrorMessage.ox}", :flex) if statement.Status.ox != 'Success'
			#
  # Retrieve the FLEX report
  report = nil
  until report do
    sleep 5  # wait for the report to be prepared 
    report = get_content(statement.Url.ox,:t => Flex.token, :q => statement.ReferenceCode.ox, :v => 3,
                           :text_ok => @format != :xml)

      # If Status is specified, returned xml contains only error message, not actual report
      if report.nodes.include?('Status') && report.Status.ox =~ /Fail|Warn/
        error_code = report.ErrorCode.ox.to_i
        error_message = "#{error_code}: #{report.ErrorMessage.ox}"

        case error_code
        when 1001..1009, 1018, 1019, 1021
          # Report is just not ready yet, wait and retry
          puts error_message if @verbose
          report = nil
        else # Fatal error
          error error_message, :flex
        end
      end
  end
  @return_hash ? Ox.load( Ox.dump(report),  mode: :hash)  : report  # return hash or the Ox-Element
end