ib-ruby 0.5.21 → 0.6.1
Sign up to get free protection for your applications and to get access to all the features.
- data/HISTORY +8 -0
- data/README.md +46 -27
- data/TODO +13 -2
- data/VERSION +1 -1
- data/bin/generic_data.rb +26 -0
- data/bin/place_order +1 -1
- data/lib/ib-ruby/connection.rb +126 -65
- data/lib/ib-ruby/messages/incoming.rb +3 -3
- data/lib/ib-ruby/models/bar.rb +11 -11
- data/lib/ib-ruby/models/combo_leg.rb +23 -29
- data/lib/ib-ruby/models/contract/bag.rb +34 -2
- data/lib/ib-ruby/models/contract/option.rb +2 -2
- data/lib/ib-ruby/models/contract.rb +151 -197
- data/lib/ib-ruby/models/execution.rb +27 -45
- data/lib/ib-ruby/models/model.rb +10 -4
- data/lib/ib-ruby/models/model_properties.rb +63 -0
- data/lib/ib-ruby/models/order.rb +274 -320
- data/lib/ib-ruby/symbols/stocks.rb +11 -5
- data/spec/account_helper.rb +80 -0
- data/spec/ib-ruby/connection_spec.rb +195 -52
- data/spec/ib-ruby/messages/incoming_spec.rb +4 -4
- data/spec/ib-ruby/models/combo_leg_spec.rb +1 -0
- data/spec/ib-ruby/models/contract_spec.rb +1 -1
- data/spec/ib-ruby/models/execution_spec.rb +73 -0
- data/spec/integration/account_info_spec.rb +12 -59
- data/spec/integration/contract_info_spec.rb +23 -37
- data/spec/integration/depth_data_spec.rb +4 -4
- data/spec/integration/historic_data_spec.rb +15 -27
- data/spec/integration/market_data_spec.rb +74 -61
- data/spec/integration/option_data_spec.rb +5 -48
- data/spec/integration/orders/execution_spec.rb +26 -31
- data/spec/integration/orders/open_order +2 -0
- data/spec/integration/orders/placement_spec.rb +28 -28
- data/spec/integration/orders/valid_ids_spec.rb +11 -11
- data/spec/integration_helper.rb +46 -32
- data/spec/message_helper.rb +4 -38
- data/spec/spec_helper.rb +2 -3
- metadata +9 -2
@@ -4,8 +4,8 @@ describe "Request Contract Info", :connected => true, :integration => true do
|
|
4
4
|
|
5
5
|
before(:all) do
|
6
6
|
verify_account
|
7
|
-
|
8
|
-
wait_for
|
7
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
8
|
+
@ib.wait_for :NextValidId
|
9
9
|
end
|
10
10
|
|
11
11
|
after(:all) { close_connection }
|
@@ -15,20 +15,17 @@ describe "Request Contract Info", :connected => true, :integration => true do
|
|
15
15
|
before(:all) do
|
16
16
|
@contract = IB::Models::Contract.new :symbol => 'AAPL',
|
17
17
|
:sec_type => IB::SECURITY_TYPES[:stock]
|
18
|
-
@ib.send_message :RequestContractData,
|
19
|
-
|
20
|
-
:contract => @contract
|
21
|
-
|
22
|
-
wait_for(3) { received? :ContractDataEnd }
|
18
|
+
@ib.send_message :RequestContractData, :id => 111, :contract => @contract
|
19
|
+
@ib.wait_for 3, :ContractDataEnd
|
23
20
|
end
|
24
21
|
|
25
22
|
after(:all) { clean_connection } # Clear logs and message collector
|
26
23
|
|
27
|
-
it { @received[:ContractData].should have_exactly(2).contract_data }
|
28
|
-
it { @received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
24
|
+
it { @ib.received[:ContractData].should have_exactly(2).contract_data }
|
25
|
+
it { @ib.received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
29
26
|
|
30
27
|
it 'receives Contract Data for requested contract' do
|
31
|
-
msg = @received[:ContractData].first
|
28
|
+
msg = @ib.received[:ContractData].first
|
32
29
|
msg.request_id.should == 111
|
33
30
|
msg.contract.should == @contract
|
34
31
|
end
|
@@ -36,7 +33,7 @@ describe "Request Contract Info", :connected => true, :integration => true do
|
|
36
33
|
it 'receives Contract Data with extended fields' do
|
37
34
|
# Returns 2 contracts, one for NASDAQ and one for IBIS - internal crossing?
|
38
35
|
|
39
|
-
@received[:ContractData].each do |msg|
|
36
|
+
@ib.received[:ContractData].each do |msg|
|
40
37
|
contract = msg.contract
|
41
38
|
contract.symbol.should == 'AAPL'
|
42
39
|
|
@@ -68,19 +65,16 @@ describe "Request Contract Info", :connected => true, :integration => true do
|
|
68
65
|
:expiry => "201301",
|
69
66
|
:right => "CALL",
|
70
67
|
:strike => 500
|
71
|
-
@ib.send_message :RequestContractData,
|
72
|
-
|
73
|
-
:contract => @contract
|
74
|
-
|
75
|
-
wait_for(3) { received? :ContractDataEnd }
|
68
|
+
@ib.send_message :RequestContractData, :id => 123, :contract => @contract
|
69
|
+
@ib.wait_for 3, :ContractDataEnd
|
76
70
|
end
|
77
71
|
|
78
72
|
after(:all) { clean_connection } # Clear logs and message collector
|
79
73
|
|
80
|
-
subject { @received[:ContractData].first }
|
74
|
+
subject { @ib.received[:ContractData].first }
|
81
75
|
|
82
|
-
it { @received[:ContractData].should have_exactly(1).contract_data }
|
83
|
-
it { @received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
76
|
+
it { @ib.received[:ContractData].should have_exactly(1).contract_data }
|
77
|
+
it { @ib.received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
84
78
|
|
85
79
|
it 'receives Contract Data for requested contract' do
|
86
80
|
subject.request_id.should == 123
|
@@ -117,20 +111,16 @@ describe "Request Contract Info", :connected => true, :integration => true do
|
|
117
111
|
:currency => "USD",
|
118
112
|
:exchange => "IDEALPRO",
|
119
113
|
:sec_type => IB::SECURITY_TYPES[:forex]
|
120
|
-
|
121
|
-
@ib.
|
122
|
-
:id => 135,
|
123
|
-
:contract => @contract
|
124
|
-
|
125
|
-
wait_for(3) { received? :ContractDataEnd }
|
114
|
+
@ib.send_message :RequestContractData, :id => 135, :contract => @contract
|
115
|
+
@ib.wait_for 3, :ContractDataEnd
|
126
116
|
end
|
127
117
|
|
128
118
|
after(:all) { clean_connection } # Clear logs and message collector
|
129
119
|
|
130
|
-
subject { @received[:ContractData].first }
|
120
|
+
subject { @ib.received[:ContractData].first }
|
131
121
|
|
132
|
-
it { @received[:ContractData].should have_exactly(1).contract_data }
|
133
|
-
it { @received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
122
|
+
it { @ib.received[:ContractData].should have_exactly(1).contract_data }
|
123
|
+
it { @ib.received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
134
124
|
|
135
125
|
it 'receives Contract Data for requested contract' do
|
136
126
|
subject.request_id.should == 135
|
@@ -164,20 +154,16 @@ describe "Request Contract Info", :connected => true, :integration => true do
|
|
164
154
|
|
165
155
|
before(:all) do
|
166
156
|
@contract = IB::Symbols::Futures[:ym] # Mini Dow Jones Industrial
|
167
|
-
|
168
|
-
@ib.
|
169
|
-
:id => 147,
|
170
|
-
:contract => @contract
|
171
|
-
|
172
|
-
wait_for(3) { received? :ContractDataEnd }
|
157
|
+
@ib.send_message :RequestContractData, :id => 147, :contract => @contract
|
158
|
+
@ib.wait_for 3, :ContractDataEnd
|
173
159
|
end
|
174
160
|
|
175
161
|
after(:all) { clean_connection } # Clear logs and message collector
|
176
162
|
|
177
|
-
subject { @received[:ContractData].first }
|
163
|
+
subject { @ib.received[:ContractData].first }
|
178
164
|
|
179
|
-
it { @received[:ContractData].should have_exactly(1).contract_data }
|
180
|
-
it { @received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
165
|
+
it { @ib.received[:ContractData].should have_exactly(1).contract_data }
|
166
|
+
it { @ib.received[:ContractDataEnd].should have_exactly(1).contract_data_end }
|
181
167
|
|
182
168
|
it 'receives Contract Data for requested contract' do
|
183
169
|
subject.request_id.should == 147
|
@@ -5,12 +5,12 @@ describe 'Request Depth of Market Data', :connected => true,
|
|
5
5
|
|
6
6
|
before(:all) do
|
7
7
|
verify_account
|
8
|
-
|
8
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
9
9
|
|
10
10
|
@ib.send_message :RequestMarketDepth, :id => 456, :num_rows => 3,
|
11
11
|
:contract => IB::Symbols::Forex[:eurusd]
|
12
12
|
|
13
|
-
wait_for
|
13
|
+
@ib.wait_for 10, [:MarketDepth, 8]
|
14
14
|
end
|
15
15
|
|
16
16
|
after(:all) do
|
@@ -18,9 +18,9 @@ describe 'Request Depth of Market Data', :connected => true,
|
|
18
18
|
close_connection
|
19
19
|
end
|
20
20
|
|
21
|
-
subject { @received[:MarketDepth].last }
|
21
|
+
subject { @ib.received[:MarketDepth].last }
|
22
22
|
|
23
|
-
it { @received[:MarketDepth].should have_at_least(8).depth_data }
|
23
|
+
it { @ib.received[:MarketDepth].should have_at_least(8).depth_data }
|
24
24
|
|
25
25
|
it { should be_an IB::Messages::Incoming::MarketDepth }
|
26
26
|
its(:request_id) { should == 456 }
|
@@ -2,38 +2,33 @@ require 'integration_helper'
|
|
2
2
|
|
3
3
|
describe 'Request Historic Data', :connected => true, :integration => true do
|
4
4
|
|
5
|
+
CORRECT_OPTS = {:id => 456,
|
6
|
+
:contract => IB::Symbols::Stocks[:wfc],
|
7
|
+
:end_date_time => Time.now.to_ib,
|
8
|
+
:duration => '1 D',
|
9
|
+
:bar_size => '15 mins',
|
10
|
+
:what_to_show => :trades,
|
11
|
+
:format_date => 1}
|
5
12
|
before(:all) do
|
6
13
|
verify_account
|
7
|
-
|
14
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
8
15
|
end
|
9
16
|
|
10
17
|
after(:all) do
|
11
|
-
|
18
|
+
#@ib.send_message :CancelHistoricalData, :id => 456
|
12
19
|
close_connection
|
13
20
|
end
|
14
21
|
|
15
22
|
context 'Wrong Requests' do
|
16
23
|
it 'raises if incorrect bar size' do
|
17
24
|
expect do
|
18
|
-
@ib.send_message :RequestHistoricalData, :
|
19
|
-
:contract => IB::Symbols::Stocks[:wfc],
|
20
|
-
:end_date_time => Time.now.to_ib,
|
21
|
-
:duration => '1 D',
|
22
|
-
:bar_size => '11 min',
|
23
|
-
:what_to_show => :trades,
|
24
|
-
:format_date => 1
|
25
|
+
@ib.send_message :RequestHistoricalData, CORRECT_OPTS.merge(:bar_size => '11 min')
|
25
26
|
end.to raise_error /bar_size must be one of/
|
26
27
|
end
|
27
28
|
|
28
29
|
it 'raises if incorrect what_to_show' do
|
29
30
|
expect do
|
30
|
-
@ib.send_message :RequestHistoricalData, :
|
31
|
-
:contract => IB::Symbols::Stocks[:wfc],
|
32
|
-
:end_date_time => Time.now.to_ib,
|
33
|
-
:duration => '1 D',
|
34
|
-
:bar_size => '15 mins',
|
35
|
-
:what_to_show => :nonsense,
|
36
|
-
:format_date => 1
|
31
|
+
@ib.send_message :RequestHistoricalData, CORRECT_OPTS.merge(:what_to_show => :nonsense)
|
37
32
|
end.to raise_error /:what_to_show must be one of/
|
38
33
|
end
|
39
34
|
end
|
@@ -41,20 +36,13 @@ describe 'Request Historic Data', :connected => true, :integration => true do
|
|
41
36
|
context 'Correct Request' do
|
42
37
|
before(:all) do
|
43
38
|
# No historical data for GBP/CASH@IDEALPRO
|
44
|
-
@ib.send_message :RequestHistoricalData,
|
45
|
-
|
46
|
-
:end_date_time => Time.now.to_ib,
|
47
|
-
:duration => '1 D',
|
48
|
-
:bar_size => '15 mins',
|
49
|
-
:what_to_show => :trades,
|
50
|
-
:format_date => 1
|
51
|
-
|
52
|
-
wait_for(3) { received? :HistoricalData }
|
39
|
+
@ib.send_message :RequestHistoricalData, CORRECT_OPTS
|
40
|
+
@ib.wait_for 5, :HistoricalData
|
53
41
|
end
|
54
42
|
|
55
|
-
subject { @received[:HistoricalData].last }
|
43
|
+
subject { @ib.received[:HistoricalData].last }
|
56
44
|
|
57
|
-
it { @received[:HistoricalData].should have_at_least(1).historic_data }
|
45
|
+
it { @ib.received[:HistoricalData].should have_at_least(1).historic_data }
|
58
46
|
|
59
47
|
it { should be_an IB::Messages::Incoming::HistoricalData }
|
60
48
|
its(:request_id) { should == 456 }
|
@@ -1,17 +1,25 @@
|
|
1
1
|
require 'integration_helper'
|
2
|
+
#!/usr/bin/env ruby
|
2
3
|
|
4
|
+
require 'ib-ruby'
|
5
|
+
|
6
|
+
#OPTS[:silent] = false
|
3
7
|
describe 'Request Market Data', :connected => true, :integration => true do
|
4
8
|
|
5
|
-
|
9
|
+
require 'ib-ruby'
|
10
|
+
before(:all) { verify_account }
|
6
11
|
|
12
|
+
context 'US Stocks market', :if => :us_trading_hours do
|
7
13
|
before(:all) do
|
8
|
-
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
14
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
15
|
+
@contract = IB::Models::Contract.new(:symbol => 'AAPL',
|
16
|
+
:exchange => "Smart",
|
17
|
+
:currency => "USD",
|
18
|
+
:sec_type => IB::SECURITY_TYPES[:stock],
|
19
|
+
:description => "Apple"
|
20
|
+
)
|
21
|
+
@ib.send_message :RequestMarketData, :id => 456, :contract => @contract
|
22
|
+
@ib.wait_for 5, :TickSize, :TickString
|
15
23
|
end
|
16
24
|
|
17
25
|
after(:all) do
|
@@ -19,79 +27,84 @@ describe 'Request Market Data', :connected => true, :integration => true do
|
|
19
27
|
close_connection
|
20
28
|
end
|
21
29
|
|
22
|
-
|
23
|
-
subject { @received[:Alert].first }
|
30
|
+
it_behaves_like 'Received Market Data'
|
24
31
|
|
25
|
-
|
26
|
-
|
27
|
-
it { should_not be_error }
|
28
|
-
its(:code) { should be_an Integer }
|
29
|
-
its(:message) { should =~ /Market data farm connection is OK/ }
|
30
|
-
its(:to_human) { should =~ /TWS Warning/ }
|
31
|
-
end
|
32
|
+
context "received :TickString message" do
|
33
|
+
subject { @ib.received[:TickString].first }
|
32
34
|
|
33
|
-
|
34
|
-
subject { @received[:TickPrice].first }
|
35
|
-
|
36
|
-
it { should be_an IB::Messages::Incoming::TickPrice }
|
35
|
+
it { should be_an IB::Messages::Incoming::TickString }
|
37
36
|
its(:tick_type) { should be_an Integer }
|
38
37
|
its(:type) { should be_a Symbol }
|
39
|
-
its(:
|
40
|
-
its(:size) { should be_an Integer }
|
38
|
+
its(:value) { should be_a String }
|
41
39
|
its(:data) { should be_a Hash }
|
42
40
|
its(:ticker_id) { should == 456 } # ticker_id
|
43
|
-
its(:to_human) { should =~ /
|
41
|
+
its(:to_human) { should =~ /TickString/ }
|
44
42
|
end
|
43
|
+
end
|
44
|
+
|
45
|
+
context 'FOREX market' do
|
46
|
+
context 'when subscribed to :Tick... messages' do
|
45
47
|
|
46
|
-
context "received :TickSize message", :if => :forex_trading_hours do
|
47
48
|
before(:all) do
|
48
|
-
|
49
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
50
|
+
|
51
|
+
##TODO consider a follow the sun market lookup for windening the types tested
|
52
|
+
@ib.subscribe(:Alert, :TickPrice, :TickSize) {}
|
53
|
+
@ib.send_message :RequestMarketData, :id => 456,
|
54
|
+
:contract => IB::Symbols::Forex[:eurusd]
|
55
|
+
|
56
|
+
@ib.wait_for 3, :TickPrice, :TickSize
|
49
57
|
end
|
50
58
|
|
51
|
-
|
59
|
+
after(:all) do
|
60
|
+
@ib.send_message :CancelMarketData, :id => 456
|
61
|
+
close_connection
|
62
|
+
end
|
52
63
|
|
53
|
-
|
54
|
-
its(:type) { should_not be_nil }
|
55
|
-
its(:data) { should be_a Hash }
|
56
|
-
its(:tick_type) { should be_an Integer }
|
57
|
-
its(:type) { should be_a Symbol }
|
58
|
-
its(:size) { should be_an Integer }
|
59
|
-
its(:ticker_id) { should == 456 }
|
60
|
-
its(:to_human) { should =~ /TickSize/ }
|
61
|
-
end
|
62
|
-
end # when subscribed to :Tick... messages
|
64
|
+
it_behaves_like 'Received Market Data'
|
63
65
|
|
64
|
-
|
66
|
+
it 'logs no warning about unhandled :Alert message' do
|
67
|
+
should_not_log /No subscribers for message .*:Alert/
|
68
|
+
end
|
65
69
|
|
66
|
-
|
67
|
-
|
70
|
+
it 'logs no warning about unhandled :Tick... messages' do
|
71
|
+
should_not_log /No subscribers for message .*:TickPrice/
|
72
|
+
end
|
68
73
|
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
end
|
74
|
+
it 'logs no warning about unhandled :Tick... messages', :if => :forex_trading_hours do
|
75
|
+
should_not_log /No subscribers for message .*:TickSize/
|
76
|
+
end
|
73
77
|
|
74
|
-
|
75
|
-
@ib.send_message :CancelMarketData, :id => 456
|
76
|
-
close_connection
|
77
|
-
end
|
78
|
+
end # when subscribed to :Tick... messages
|
78
79
|
|
79
|
-
|
80
|
-
should_log /No subscribers for message .*:OpenOrderEnd/
|
81
|
-
end
|
80
|
+
context 'when NOT subscribed to :Tick... messages', :slow => true do
|
82
81
|
|
83
|
-
|
84
|
-
|
85
|
-
end
|
82
|
+
before(:all) do
|
83
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
86
84
|
|
87
|
-
|
88
|
-
|
89
|
-
|
85
|
+
@ib.send_message :RequestMarketData, :id => 456,
|
86
|
+
:contract => IB::Symbols::Forex[:eurusd]
|
87
|
+
@ib.wait_for 3, :TickPrice, :TickSize
|
88
|
+
end
|
90
89
|
|
91
|
-
|
92
|
-
|
93
|
-
|
90
|
+
after(:all) do
|
91
|
+
@ib.send_message :CancelMarketData, :id => 456
|
92
|
+
close_connection
|
93
|
+
end
|
94
|
+
|
95
|
+
it 'logs warning about unhandled :Alert message' do
|
96
|
+
should_log /No subscribers for message .*:Alert/
|
97
|
+
end
|
98
|
+
|
99
|
+
it 'logs warning about unhandled :Tick... messages' do
|
100
|
+
should_log /No subscribers for message .*:TickPrice/
|
101
|
+
end
|
102
|
+
|
103
|
+
it 'logs warning about unhandled :Tick... messages', :if => :forex_trading_hours do
|
104
|
+
should_log /No subscribers for message .*:TickSize/
|
105
|
+
end
|
94
106
|
|
95
|
-
|
107
|
+
end # NOT subscribed to :Tick... messages
|
108
|
+
end
|
96
109
|
|
97
110
|
end # Request Market Data
|
@@ -1,22 +1,15 @@
|
|
1
1
|
require 'integration_helper'
|
2
2
|
|
3
|
-
def wait_for_all_ticks
|
4
|
-
wait_for(5) do
|
5
|
-
received?(:TickPrice) && received?(:TickSize) &&
|
6
|
-
received?(:TickOption) && received?(:TickString)
|
7
|
-
end
|
8
|
-
end
|
9
|
-
|
10
3
|
describe 'Request Market Data for Options', :if => :us_trading_hours,
|
11
4
|
:connected => true, :integration => true do
|
12
5
|
|
13
6
|
before(:all) do
|
14
7
|
verify_account
|
15
|
-
|
8
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
16
9
|
|
17
10
|
@ib.send_message :RequestMarketData, :id => 456,
|
18
11
|
:contract => IB::Symbols::Options[:aapl500]
|
19
|
-
|
12
|
+
@ib.wait_for 5, :TickPrice, :TickSize, :TickString, :TickOption
|
20
13
|
end
|
21
14
|
|
22
15
|
after(:all) do
|
@@ -24,46 +17,10 @@ describe 'Request Market Data for Options', :if => :us_trading_hours,
|
|
24
17
|
close_connection
|
25
18
|
end
|
26
19
|
|
27
|
-
|
28
|
-
subject { @received[:Alert].first }
|
29
|
-
|
30
|
-
it { should be_an IB::Messages::Incoming::Alert }
|
31
|
-
it { should be_warning }
|
32
|
-
it { should_not be_error }
|
33
|
-
its(:code) { should be_an Integer }
|
34
|
-
its(:message) { should =~ /Market data farm connection is OK/ }
|
35
|
-
its(:to_human) { should =~ /TWS Warning/ }
|
36
|
-
end
|
37
|
-
|
38
|
-
context "received :TickPrice message" do
|
39
|
-
subject { @received[:TickPrice].first }
|
40
|
-
|
41
|
-
it { should be_an IB::Messages::Incoming::TickPrice }
|
42
|
-
its(:tick_type) { should be_an Integer }
|
43
|
-
its(:type) { should be_a Symbol }
|
44
|
-
its(:price) { should be_a Float }
|
45
|
-
its(:size) { should be_an Integer }
|
46
|
-
its(:can_auto_execute) { should be_an Integer }
|
47
|
-
its(:data) { should be_a Hash }
|
48
|
-
its(:ticker_id) { should == 456 } # ticker_id
|
49
|
-
its(:to_human) { should =~ /TickPrice/ }
|
50
|
-
end
|
51
|
-
|
52
|
-
context "received :TickSize message" do
|
53
|
-
subject { @received[:TickSize].first }
|
54
|
-
|
55
|
-
it { should be_an IB::Messages::Incoming::TickSize }
|
56
|
-
its(:type) { should_not be_nil }
|
57
|
-
its(:data) { should be_a Hash }
|
58
|
-
its(:tick_type) { should be_an Integer }
|
59
|
-
its(:type) { should be_a Symbol }
|
60
|
-
its(:size) { should be_an Integer }
|
61
|
-
its(:ticker_id) { should == 456 }
|
62
|
-
its(:to_human) { should =~ /TickSize/ }
|
63
|
-
end
|
20
|
+
it_behaves_like 'Received Market Data'
|
64
21
|
|
65
22
|
context "received :TickOption message" do
|
66
|
-
subject { @received[:TickOption].first }
|
23
|
+
subject { @ib.received[:TickOption].first }
|
67
24
|
|
68
25
|
it { should be_an IB::Messages::Incoming::TickOption }
|
69
26
|
its(:type) { should_not be_nil }
|
@@ -82,7 +39,7 @@ describe 'Request Market Data for Options', :if => :us_trading_hours,
|
|
82
39
|
end
|
83
40
|
|
84
41
|
context "received :TickString message" do
|
85
|
-
subject { @received[:TickString].first }
|
42
|
+
subject { @ib.received[:TickString].first }
|
86
43
|
|
87
44
|
it { should be_an IB::Messages::Incoming::TickString }
|
88
45
|
its(:type) { should_not be_nil }
|
@@ -1,14 +1,5 @@
|
|
1
1
|
require 'integration_helper'
|
2
2
|
|
3
|
-
# TODO: RequestExecutions (with filters?)
|
4
|
-
|
5
|
-
def wait_for_execution_and_commission
|
6
|
-
wait_for(5) do
|
7
|
-
received?(:ExecutionData) && received?(:OpenOrder) &&
|
8
|
-
@received[:OpenOrder].last.order.commission
|
9
|
-
end
|
10
|
-
end
|
11
|
-
|
12
3
|
describe "Trades", :connected => true, :integration => true, :slow => true do
|
13
4
|
|
14
5
|
before(:all) { verify_account }
|
@@ -17,9 +8,8 @@ describe "Trades", :connected => true, :integration => true, :slow => true do
|
|
17
8
|
|
18
9
|
before(:all) do
|
19
10
|
@contract = IB::Symbols::Forex[:eurusd]
|
20
|
-
|
21
|
-
|
22
|
-
wait_for { received? :NextValidID }
|
11
|
+
@ib = IB::Connection.new OPTS[:connection].merge(:logger => mock_logger)
|
12
|
+
@ib.wait_for :NextValidId
|
23
13
|
end
|
24
14
|
|
25
15
|
after(:all) { close_connection }
|
@@ -32,7 +22,9 @@ describe "Trades", :connected => true, :integration => true, :slow => true do
|
|
32
22
|
:limit_price => 2,
|
33
23
|
:action => 'BUY'
|
34
24
|
|
35
|
-
|
25
|
+
@ib.wait_for(5, :ExecutionData, :OpenOrder) do
|
26
|
+
@ib.received[:OpenOrder].last.order.commission
|
27
|
+
end
|
36
28
|
end
|
37
29
|
|
38
30
|
after(:all) do
|
@@ -45,19 +37,19 @@ describe "Trades", :connected => true, :integration => true, :slow => true do
|
|
45
37
|
@ib.next_order_id.should == @order_id_before + 1
|
46
38
|
end
|
47
39
|
|
48
|
-
it { @received[:OpenOrder].should have_at_least(1).open_order_message }
|
49
|
-
it { @received[:OrderStatus].should have_at_least(1).status_message }
|
50
|
-
it { @received[:ExecutionData].should have_exactly(1).execution_data }
|
51
|
-
it { @received[:ExecutionDataEnd].should be_empty }
|
40
|
+
it { @ib.received[:OpenOrder].should have_at_least(1).open_order_message }
|
41
|
+
it { @ib.received[:OrderStatus].should have_at_least(1).status_message }
|
42
|
+
it { @ib.received[:ExecutionData].should have_exactly(1).execution_data }
|
43
|
+
it { @ib.received[:ExecutionDataEnd].should be_empty }
|
52
44
|
|
53
45
|
it 'receives filled OpenOrder' do
|
54
46
|
open_order_should_be 'Filled', -1
|
55
|
-
msg = @received[:OpenOrder].last
|
47
|
+
msg = @ib.received[:OpenOrder].last
|
56
48
|
msg.order.commission.should == 2.5
|
57
49
|
end
|
58
50
|
|
59
51
|
it 'receives Execution Data' do
|
60
|
-
execution_should_be
|
52
|
+
execution_should_be :buy
|
61
53
|
end
|
62
54
|
|
63
55
|
it 'receives OrderStatus with fill details' do
|
@@ -73,7 +65,9 @@ describe "Trades", :connected => true, :integration => true, :slow => true do
|
|
73
65
|
:limit_price => 1,
|
74
66
|
:action => 'SELL'
|
75
67
|
|
76
|
-
|
68
|
+
@ib.wait_for(5, :ExecutionData, :OpenOrder) do
|
69
|
+
@ib.received[:OpenOrder].last.order.commission
|
70
|
+
end
|
77
71
|
end
|
78
72
|
|
79
73
|
after(:all) do
|
@@ -86,18 +80,18 @@ describe "Trades", :connected => true, :integration => true, :slow => true do
|
|
86
80
|
@ib.next_order_id.should == @order_id_before + 1
|
87
81
|
end
|
88
82
|
|
89
|
-
it { @received[:OpenOrder].should have_at_least(1).open_order_message }
|
90
|
-
it { @received[:OrderStatus].should have_at_least(1).status_message }
|
91
|
-
it { @received[:ExecutionData].should have_exactly(1).execution_data }
|
83
|
+
it { @ib.received[:OpenOrder].should have_at_least(1).open_order_message }
|
84
|
+
it { @ib.received[:OrderStatus].should have_at_least(1).status_message }
|
85
|
+
it { @ib.received[:ExecutionData].should have_exactly(1).execution_data }
|
92
86
|
|
93
87
|
it 'receives filled OpenOrder' do
|
94
88
|
open_order_should_be 'Filled', -1
|
95
|
-
msg = @received[:OpenOrder].last
|
89
|
+
msg = @ib.received[:OpenOrder].last
|
96
90
|
msg.order.commission.should == 2.5
|
97
91
|
end
|
98
92
|
|
99
93
|
it 'receives Execution Data' do
|
100
|
-
execution_should_be
|
94
|
+
execution_should_be :sell
|
101
95
|
end
|
102
96
|
|
103
97
|
it 'receives OrderStatus with fill details' do
|
@@ -106,28 +100,29 @@ describe "Trades", :connected => true, :integration => true, :slow => true do
|
|
106
100
|
end # Placing SELL
|
107
101
|
|
108
102
|
context "Request executions" do
|
103
|
+
# TODO: RequestExecutions with filters?
|
109
104
|
|
110
105
|
before(:all) do
|
111
106
|
@ib.send_message :RequestExecutions,
|
112
107
|
:request_id => 456,
|
113
108
|
:client_id => OPTS[:connection][:client_id],
|
114
|
-
:time => (Time.now-10).to_ib
|
115
|
-
wait_for
|
109
|
+
:time => (Time.now-10).to_ib # Time zone problems possible
|
110
|
+
@ib.wait_for 3, :ExecutionData
|
116
111
|
end
|
117
112
|
|
118
113
|
#after(:all) { clean_connection }
|
119
114
|
|
120
115
|
it 'does not receive Order-related messages' do
|
121
|
-
@received[:OpenOrder].should be_empty
|
122
|
-
@received[:OrderStatus].should be_empty
|
116
|
+
@ib.received[:OpenOrder].should be_empty
|
117
|
+
@ib.received[:OrderStatus].should be_empty
|
123
118
|
end
|
124
119
|
|
125
120
|
it 'receives ExecutionData messages' do
|
126
|
-
@received[:ExecutionData].should have_at_least(1).execution_data
|
121
|
+
@ib.received[:ExecutionData].should have_at_least(1).execution_data
|
127
122
|
end
|
128
123
|
|
129
124
|
it 'receives Execution Data' do
|
130
|
-
execution_should_be
|
125
|
+
execution_should_be :sell, :request_id => 456
|
131
126
|
end
|
132
127
|
end # Request executions
|
133
128
|
end # Forex order
|
@@ -1,3 +1,5 @@
|
|
1
|
+
This is just a dump file to compare received order messages:
|
2
|
+
|
1
3
|
[#<IB::Messages::Incoming::OpenOrder:0xfdc #<IB::Messages::Incoming::OpenOrder:0x10b8 #<IB::Messages::Incoming::OpenOrder:0x1198
|
2
4
|
@contract= @contract= @contract=
|
3
5
|
#<IB::Models::Contract:0xfe0 #<IB::Models::Contract:0x10bc #<IB::Models::Contract:0x119c
|