bitfinex-rb 0.0.3 → 0.0.4
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +4 -4
- data/lib/bitfinex.rb +1 -0
- data/lib/bitfinex/account_info.rb +15 -2
- data/lib/bitfinex/client.rb +1 -0
- data/lib/bitfinex/configurable.rb +4 -2
- data/lib/bitfinex/connection.rb +1 -1
- data/lib/bitfinex/deposit.rb +3 -3
- data/lib/bitfinex/errors.rb +1 -0
- data/lib/bitfinex/funding_book.rb +2 -2
- data/lib/bitfinex/historical_data.rb +7 -7
- data/lib/bitfinex/lends.rb +2 -2
- data/lib/bitfinex/margin_funding.rb +10 -11
- data/lib/bitfinex/orderbook.rb +17 -0
- data/lib/bitfinex/orders.rb +18 -17
- data/lib/bitfinex/ticker.rb +13 -0
- data/lib/bitfinex/trades.rb +13 -0
- data/lib/bitfinex/version.rb +1 -1
- data/lib/bitfinex/websocket_connection.rb +190 -0
- metadata +37 -4
- data/lib/bitfinex/websocket.rb +0 -64
- data/lib/bitfinex/websocket/em_client.rb +0 -60
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 83b15f4ee0948a7bfa5d093d22db01a31d5b950f
|
4
|
+
data.tar.gz: c5ba58927b2ce63f008e2d7ff3b2be183b30777b
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9814f5265c77c6cdd01392324ef796cea7ab1b2ab33041d9c8e9ba8f79070a8b1a28e18ac7b1d1611dc7844cf544d6d4fffe7ce5ba2fe18e9b97cb74cd43a777
|
7
|
+
data.tar.gz: e3224dc050ea43d595f4f25aa7b7c803bc2101c749355e3311eb4726d6ace17c643d50dbf95dc38716c63d6b6e0338772c4b3274cdfb9c50006c8f6ded03546a
|
data/lib/bitfinex.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
module Bitfinex
|
2
2
|
|
3
|
-
module AccountInfoClient
|
4
|
-
|
3
|
+
module AccountInfoClient
|
4
|
+
|
5
5
|
# Get account information
|
6
6
|
#
|
7
7
|
# @return [Hash] your account information
|
@@ -11,6 +11,19 @@ module Bitfinex
|
|
11
11
|
resp = authenticated_post("account_infos")
|
12
12
|
resp.body
|
13
13
|
end
|
14
|
+
|
15
|
+
|
16
|
+
# Call block passing all account related specific messages sent via websocket
|
17
|
+
#
|
18
|
+
# @param block [Block] The code to be executed when new message is received
|
19
|
+
# @example:
|
20
|
+
# client.listen_account do |message|
|
21
|
+
# puts message.inspect
|
22
|
+
# end
|
23
|
+
def listen_account(&block)
|
24
|
+
raise BlockMissingError unless block_given?
|
25
|
+
ws_auth(&block)
|
26
|
+
end
|
14
27
|
end
|
15
28
|
|
16
29
|
end
|
data/lib/bitfinex/client.rb
CHANGED
@@ -3,7 +3,7 @@ module Bitfinex
|
|
3
3
|
def self.included(base)
|
4
4
|
base.extend(ClassMethods)
|
5
5
|
end
|
6
|
-
|
6
|
+
|
7
7
|
def config
|
8
8
|
self.class.config
|
9
9
|
end
|
@@ -20,10 +20,12 @@ module Bitfinex
|
|
20
20
|
end
|
21
21
|
|
22
22
|
class Configuration
|
23
|
-
attr_accessor :api_endpoint, :debug, :debug_connection, :secret, :api_key
|
23
|
+
attr_accessor :api_endpoint, :debug, :debug_connection, :secret, :api_key, :websocket_api_endpoint
|
24
24
|
def initialize
|
25
25
|
self.api_endpoint = "https://api.bitfinex.com/v1/"
|
26
|
+
self.websocket_api_endpoint = "wss://api2.bitfinex.com:3000/ws"
|
26
27
|
self.debug = false
|
28
|
+
|
27
29
|
self.debug_connection = false
|
28
30
|
end
|
29
31
|
end
|
data/lib/bitfinex/connection.rb
CHANGED
data/lib/bitfinex/deposit.rb
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
module Bitfinex
|
2
2
|
module DepositClient
|
3
3
|
# Return your deposit address to make a new deposit.
|
4
|
-
#
|
4
|
+
#
|
5
5
|
# @param method [string] Method of deposit (methods accepted: “bitcoin”, “litecoin”, “darkcoin”, “mastercoin” (tethers)).
|
6
6
|
# @param wallet_name [string] Wallet to deposit in (accepted: “trading”, “exchange”, “deposit”). Your wallet needs to already exist
|
7
7
|
# @params renew [integer] (optional) Default is 0. If set to 1, will return a new unused deposit address
|
@@ -11,8 +11,8 @@ module Bitfinex
|
|
11
11
|
# client.deposit("bitcoin", "exchange")
|
12
12
|
def deposit method, wallet_name, renew=0
|
13
13
|
params = {
|
14
|
-
method: method,
|
15
|
-
wallet_name: wallet_name,
|
14
|
+
method: method,
|
15
|
+
wallet_name: wallet_name,
|
16
16
|
renew: renew
|
17
17
|
}
|
18
18
|
|
data/lib/bitfinex/errors.rb
CHANGED
@@ -6,9 +6,9 @@ module Bitfinex
|
|
6
6
|
# @param currency [string] (optional) Speficy the currency, default "USD"
|
7
7
|
# @param params :limit_bids [int] (optional) Limit the number of funding bids returned. May be 0 in which case the array of bids is empty.
|
8
8
|
# @param params :limit_asks [int] (optional) Limit the number of funding offers returned. May be 0 in which case the array of asks is empty.
|
9
|
-
# @return [Hash] of :bids and :asks arrays
|
9
|
+
# @return [Hash] of :bids and :asks arrays
|
10
10
|
# @example:
|
11
|
-
# client.funding_book
|
11
|
+
# client.funding_book
|
12
12
|
def funding_book(currency="usd", params = {})
|
13
13
|
check_params(params, %i{limit_bids limit_asks})
|
14
14
|
get("lendbook/#{currency}", params).body
|
@@ -2,7 +2,7 @@ module Bitfinex
|
|
2
2
|
module HistoricalDataClient
|
3
3
|
|
4
4
|
# View all of your balance ledger entries.
|
5
|
-
#
|
5
|
+
#
|
6
6
|
# @param currency [string] (optional) Specify the currency, default "USD"
|
7
7
|
# @param params :since [time] (optional) Return only the history after this timestamp.
|
8
8
|
# @param params :until [time] (optional) Return only the history before this timestamp.
|
@@ -12,13 +12,13 @@ module Bitfinex
|
|
12
12
|
# @example:
|
13
13
|
# client.history
|
14
14
|
def history(currency="usd", params = {})
|
15
|
-
check_params(params, %i{since until limit wallet})
|
15
|
+
check_params(params, %i{since until limit wallet})
|
16
16
|
params.merge!({currency: currency})
|
17
|
-
authenticated_post("history", params).body
|
17
|
+
authenticated_post("history", params: params).body
|
18
18
|
end
|
19
19
|
|
20
20
|
# View your past deposits/withdrawals.
|
21
|
-
#
|
21
|
+
#
|
22
22
|
# @param currency [string] (optional) Specify the currency, default "USD"
|
23
23
|
# @param params :method (optional) The method of the deposit/withdrawal (can be “bitcoin”, “litecoin”, “darkcoin”, “wire”)
|
24
24
|
# @param params :since (optional) Return only the history after this timestamp
|
@@ -30,11 +30,11 @@ module Bitfinex
|
|
30
30
|
def movements(currency="usd", params = {})
|
31
31
|
check_params(params, %i{method since until limit})
|
32
32
|
params.merge!({currency: currency})
|
33
|
-
authenticated_post("history/movements", params).body
|
33
|
+
authenticated_post("history/movements", params: params).body
|
34
34
|
end
|
35
35
|
|
36
36
|
# View your past trades.
|
37
|
-
#
|
37
|
+
#
|
38
38
|
# @param symbol The pair traded (BTCUSD, LTCUSD, LTCBTC)
|
39
39
|
# @param params :until [time] (optional) Return only the history before this timestamp.
|
40
40
|
# @param params :timestamp [time] (optional) Trades made before this timestamp won’t be returned
|
@@ -47,7 +47,7 @@ module Bitfinex
|
|
47
47
|
def mytrades(symbol, params = {})
|
48
48
|
check_params(params, %i{until limit_trades reverse timestamp})
|
49
49
|
params.merge!({symbol: symbol})
|
50
|
-
authenticated_post("mytrades", params).body
|
50
|
+
authenticated_post("mytrades", params: params).body
|
51
51
|
end
|
52
52
|
end
|
53
53
|
end
|
data/lib/bitfinex/lends.rb
CHANGED
@@ -1,9 +1,9 @@
|
|
1
1
|
module Bitfinex
|
2
|
-
module LendsClient
|
2
|
+
module LendsClient
|
3
3
|
|
4
4
|
# Get a list of the most recent funding data for the given currency: total amount provided and Flash Return Rate (in % by 365 days) over time.
|
5
5
|
#
|
6
|
-
# @param currency [string] (optional) Specify the currency, default "USD"
|
6
|
+
# @param currency [string] (optional) Specify the currency, default "USD"
|
7
7
|
# @param params :timestamp [time] (optional) Only show data at or after this timestamp
|
8
8
|
# @param params :limit_lends [int] (optional) Limit the amount of funding data returned. Must be > 1, default 50
|
9
9
|
# @return [Array]
|
@@ -12,15 +12,14 @@ module Bitfinex
|
|
12
12
|
# @example:
|
13
13
|
# client.new_offer("btc", 10.0, 20, 365, "lend")
|
14
14
|
def new_offer(currency, amount, rate, period, direction)
|
15
|
-
params = {
|
15
|
+
params = {
|
16
16
|
currency: currency,
|
17
|
-
amount: amount,
|
18
|
-
rate: rate,
|
19
|
-
period: period,
|
17
|
+
amount: amount.to_s,
|
18
|
+
rate: rate.to_s,
|
19
|
+
period: period.to_i,
|
20
20
|
direction: direction
|
21
21
|
}
|
22
|
-
|
23
|
-
authenticated_post("offer/new", params).body
|
22
|
+
authenticated_post("offer/new", params: params).body
|
24
23
|
end
|
25
24
|
|
26
25
|
# Cancel an offer
|
@@ -31,7 +30,7 @@ module Bitfinex
|
|
31
30
|
# client.cancel_offer(1000)
|
32
31
|
def cancel_offer(offer_id)
|
33
32
|
authenticated_post("offer/cancel", {offer_id: offer_id}).body
|
34
|
-
end
|
33
|
+
end
|
35
34
|
|
36
35
|
# Get the status of an offer. Is it active? Was it cancelled? To what extent has it been executed? etc.
|
37
36
|
#
|
@@ -44,7 +43,7 @@ module Bitfinex
|
|
44
43
|
end
|
45
44
|
|
46
45
|
# View your funds currently taken (active credits)
|
47
|
-
#
|
46
|
+
#
|
48
47
|
# @return [Array]
|
49
48
|
# @example:
|
50
49
|
# client.credits
|
@@ -71,7 +70,7 @@ module Bitfinex
|
|
71
70
|
end
|
72
71
|
|
73
72
|
# View your funding currently borrowed and not used (available for a new margin position).
|
74
|
-
#
|
73
|
+
#
|
75
74
|
# @return [Array] An array of your active unused margin funds
|
76
75
|
# @example:
|
77
76
|
# client.unused_taken_funds
|
@@ -80,7 +79,7 @@ module Bitfinex
|
|
80
79
|
end
|
81
80
|
|
82
81
|
# View the total of your active funding used in your position(s).
|
83
|
-
#
|
82
|
+
#
|
84
83
|
# @return [Array] An array of your active funding
|
85
84
|
# @example:
|
86
85
|
# client.total_taken_funds
|
@@ -90,7 +89,7 @@ module Bitfinex
|
|
90
89
|
|
91
90
|
# Allow you to close an unused or used taken fund
|
92
91
|
#
|
93
|
-
# @param swap_id [int] The ID given by `#taken_funds` or `#unused_taken_funds
|
92
|
+
# @param swap_id [int] The ID given by `#taken_funds` or `#unused_taken_funds
|
94
93
|
# @return [Hash]
|
95
94
|
# @example:
|
96
95
|
# client.close_funding(1000)
|
data/lib/bitfinex/orderbook.rb
CHANGED
@@ -14,5 +14,22 @@ module Bitfinex
|
|
14
14
|
check_params(params, %i{limit_bids limit_asks group})
|
15
15
|
get("book/#{symbol}",params).body
|
16
16
|
end
|
17
|
+
|
18
|
+
|
19
|
+
# Get the order book changes using websocket
|
20
|
+
#
|
21
|
+
# @param pair [string]
|
22
|
+
# @param prec [string] Level of price aggregation (P0, P1, P2, P3). The default is P0.
|
23
|
+
# @param freq [string] Frequency of updates (F0, F1, F2, F3). F0=realtime / F1=2sec / F2=5sec / F3=10sec
|
24
|
+
# @param len [int] Number of price points (“25”, “100”) [default=“25”]
|
25
|
+
# @param block [Block] The code to be executed when a new order is submitted
|
26
|
+
# @example:
|
27
|
+
# client.listen_book do |order|
|
28
|
+
# puts order.inspect
|
29
|
+
# end
|
30
|
+
def listen_book(pair="BTCUSD", prec='P0', freq='F0',len=25, &block)
|
31
|
+
raise BlockMissingError unless block_given?
|
32
|
+
register_channel pair:pair, channel: 'book', prec: prec, freq: freq, len: len, &block
|
33
|
+
end
|
17
34
|
end
|
18
35
|
end
|
data/lib/bitfinex/orders.rb
CHANGED
@@ -11,27 +11,28 @@ module Bitfinex
|
|
11
11
|
# @param params :is_hidden [bool] (optional) true if the order should be hidden. Default is false
|
12
12
|
# @param params :is_postonly [bool] (optional) true if the order should be post only. Default is false. Only relevant for limit orders
|
13
13
|
# @param params :ocoorder [bool] Set an additional STOP OCO order that will be linked with the current order
|
14
|
-
# @param params :buy_price_oco [decimal] If ocoorder is true, this field represent the price of the OCO stop order to place
|
14
|
+
# @param params :buy_price_oco [decimal] If ocoorder is true, this field represent the price of the OCO stop order to place
|
15
15
|
# @return [Hash]
|
16
16
|
# @example:
|
17
|
-
# client.new_order("usdbtc", 100, "market", "sell", 0)
|
18
|
-
def new_order(symbol, amount, type, side, price = nil, params = {})
|
17
|
+
# client.new_order("usdbtc", 100, "market", "sell", 0)
|
18
|
+
def new_order(symbol, amount, type, side, price = nil, params = {})
|
19
19
|
check_params(params, %i{is_hidden is_postonly ocoorder buy_price_oco})
|
20
20
|
|
21
21
|
params.merge!({
|
22
|
-
symbol: symbol,
|
23
|
-
amount: amount,
|
22
|
+
symbol: symbol,
|
23
|
+
amount: amount.to_s,
|
24
24
|
type: type,
|
25
25
|
side: side,
|
26
26
|
exchange: 'bitfinex',
|
27
|
-
price: price
|
27
|
+
price: price.to_s
|
28
|
+
})
|
28
29
|
|
29
30
|
authenticated_post("order/new", params: params).body
|
30
31
|
end
|
31
32
|
|
32
33
|
# Submit several new orders at once
|
33
34
|
#
|
34
|
-
# @param orders [Array] Array of Hash with the following elements
|
35
|
+
# @param orders [Array] Array of Hash with the following elements
|
35
36
|
# @param orders :symbol [string] The name of the symbol
|
36
37
|
# @param orders :amount [decimal] Order size: how much to buy or sell
|
37
38
|
# @param orders :price [decimal] Price to buy or sell at. May omit if a market order
|
@@ -47,7 +48,7 @@ module Bitfinex
|
|
47
48
|
|
48
49
|
# Cancel an order
|
49
50
|
#
|
50
|
-
# @param ids [Array] or [integer] or nil
|
51
|
+
# @param ids [Array] or [integer] or nil
|
51
52
|
# if it's Array it's supposed to specify a list of IDS
|
52
53
|
# if it's an integer it's supposed to be a single ID
|
53
54
|
# if it's not specified it deletes all the orders placed
|
@@ -56,7 +57,7 @@ module Bitfinex
|
|
56
57
|
# client.cancel_orders([100,231,400])
|
57
58
|
def cancel_orders(ids=nil)
|
58
59
|
case ids
|
59
|
-
when Array
|
60
|
+
when Array
|
60
61
|
authenticated_post("order/cancel/multi", {order_ids: ids}).body
|
61
62
|
when Numeric
|
62
63
|
authenticated_post("order/cancel", {order_id: ids}).body
|
@@ -68,27 +69,27 @@ module Bitfinex
|
|
68
69
|
end
|
69
70
|
|
70
71
|
# Replace an orders with a new one
|
71
|
-
#
|
72
|
+
#
|
72
73
|
# @param id [int] the ID of the order to replace
|
73
74
|
# @param symbol [string] the name of the symbol
|
74
75
|
# @param amount [decimal] Order size: how much to buy or sell
|
75
|
-
# @param type [string] Either “market” / “limit” / “stop” / “trailing-stop” / “fill-or-kill” / “exchange market” / “exchange limit” / “exchange stop” / “exchange trailing-stop” / “exchange fill-or-kill”. (type starting by “exchange ” are exchange orders, others are margin trading orders)
|
76
|
+
# @param type [string] Either “market” / “limit” / “stop” / “trailing-stop” / “fill-or-kill” / “exchange market” / “exchange limit” / “exchange stop” / “exchange trailing-stop” / “exchange fill-or-kill”. (type starting by “exchange ” are exchange orders, others are margin trading orders)
|
76
77
|
# @param side [string] Either “buy” or “sell”
|
77
78
|
# @param price [decimal] Price to buy or sell at. May omit if a market order
|
78
79
|
# @param is_hidden [bool] (optional) true if the order should be hidden. Default is false
|
79
80
|
# @return [Hash] the order
|
80
|
-
# @example:
|
81
|
+
# @example:
|
81
82
|
# client.replace_order(100,"usdbtc", 10, "market", "buy", 0)
|
82
83
|
def replace_order(id, symbol, amount, type, side, price, is_hidden=false)
|
83
84
|
params = {
|
84
|
-
order_id: id,
|
85
|
-
symbol: symbol,
|
86
|
-
amount: amount,
|
85
|
+
order_id: id.to_i,
|
86
|
+
symbol: symbol,
|
87
|
+
amount: amount.to_s,
|
87
88
|
type: type,
|
88
89
|
side: side,
|
89
90
|
exchange: 'bitfinex',
|
90
91
|
is_hidden: is_hidden,
|
91
|
-
price: price
|
92
|
+
price: price.to_s
|
92
93
|
}
|
93
94
|
authenticated_post("order/cancel/replace", params).body
|
94
95
|
end
|
@@ -112,6 +113,6 @@ module Bitfinex
|
|
112
113
|
def orders
|
113
114
|
authenticated_post("orders").body
|
114
115
|
end
|
115
|
-
|
116
|
+
|
116
117
|
end
|
117
118
|
end
|
data/lib/bitfinex/ticker.rb
CHANGED
@@ -10,5 +10,18 @@ module Bitfinex
|
|
10
10
|
def ticker(symbol = "btcusd")
|
11
11
|
get("pubticker/#{symbol}").body
|
12
12
|
end
|
13
|
+
|
14
|
+
# Call the specified block passing tickers, it uses websocket
|
15
|
+
#
|
16
|
+
# @param pair [string]
|
17
|
+
# @param block [Block] The code to be executed when a new ticker is sent by the server
|
18
|
+
# @example:
|
19
|
+
# client.listen_ticker do |tick|
|
20
|
+
# puts tick.inspect
|
21
|
+
# end
|
22
|
+
def listen_ticker(pair="BTCUSD", &block)
|
23
|
+
raise BlockMissingError unless block_given?
|
24
|
+
register_channel pair: pair, channel: "ticker", &block
|
25
|
+
end
|
13
26
|
end
|
14
27
|
end
|
data/lib/bitfinex/trades.rb
CHANGED
@@ -14,5 +14,18 @@ module Bitfinex
|
|
14
14
|
get("trades/#{symbol}", params: params).body
|
15
15
|
end
|
16
16
|
|
17
|
+
# Listen to the trades using websocket.
|
18
|
+
#
|
19
|
+
# @param pair [string]
|
20
|
+
# @param block [Block] The code to be executed when a new trade is executed
|
21
|
+
# @example:
|
22
|
+
# client.listen_trades do |trade|
|
23
|
+
# puts trade.inspect
|
24
|
+
# end
|
25
|
+
def listen_trades(pair="BTCUSD", &block)
|
26
|
+
raise BlockMissingError unless block_given?
|
27
|
+
register_channel pair:pair, channel: 'trades', &block
|
28
|
+
end
|
29
|
+
|
17
30
|
end
|
18
31
|
end
|
data/lib/bitfinex/version.rb
CHANGED
@@ -0,0 +1,190 @@
|
|
1
|
+
require 'eventmachine'
|
2
|
+
require 'faye/websocket'
|
3
|
+
require 'json'
|
4
|
+
|
5
|
+
module Bitfinex
|
6
|
+
module WebsocketConnection
|
7
|
+
|
8
|
+
def listen!
|
9
|
+
subscribe_to_channels
|
10
|
+
listen
|
11
|
+
ws_client.run!
|
12
|
+
end
|
13
|
+
|
14
|
+
def ws_send(msg)
|
15
|
+
ws_client.send msg
|
16
|
+
end
|
17
|
+
|
18
|
+
def ws_close_all
|
19
|
+
ws_client.close!
|
20
|
+
@ws_open = false
|
21
|
+
ws_reset_channels
|
22
|
+
end
|
23
|
+
|
24
|
+
def ws_auth(&block)
|
25
|
+
unless @ws_auth
|
26
|
+
payload = 'AUTH' + (Time.now.to_f * 10_000).to_i.to_s
|
27
|
+
signature = sign(payload)
|
28
|
+
add_callback(:auth, &block)
|
29
|
+
save_channel_id(:auth, 0)
|
30
|
+
ws_safe_send({
|
31
|
+
apiKey: config.api_key,
|
32
|
+
authSig: sign(payload),
|
33
|
+
authPayload: payload,
|
34
|
+
event: 'auth'
|
35
|
+
})
|
36
|
+
@ws_auth = true
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def ws_unauth
|
41
|
+
ws_safe_send({event: 'unauth'})
|
42
|
+
end
|
43
|
+
|
44
|
+
private
|
45
|
+
|
46
|
+
def ws_reset_channels
|
47
|
+
@chan_ids = []
|
48
|
+
@ws_registration_messages = []
|
49
|
+
@callbacks = {}
|
50
|
+
end
|
51
|
+
|
52
|
+
def ws_client
|
53
|
+
@ws_client ||= WSClient.new(url:config.websocket_api_endpoint)
|
54
|
+
end
|
55
|
+
|
56
|
+
def chan_ids
|
57
|
+
@chan_ids ||= []
|
58
|
+
end
|
59
|
+
|
60
|
+
def ws_open
|
61
|
+
@ws_open ||= false
|
62
|
+
end
|
63
|
+
|
64
|
+
def ws_registration_messages
|
65
|
+
@ws_registration_messages ||= []
|
66
|
+
end
|
67
|
+
|
68
|
+
def callbacks
|
69
|
+
@callbacks ||= {}
|
70
|
+
end
|
71
|
+
|
72
|
+
def add_callback(channel, &block)
|
73
|
+
callbacks[channel] = { block: block, chan_id: nil }
|
74
|
+
end
|
75
|
+
|
76
|
+
def register_authenticated_channel(msg, &block)
|
77
|
+
add_callback(fingerprint(msg),&block)
|
78
|
+
ws_safe_send(msg.merge(event:'subscribe'))
|
79
|
+
end
|
80
|
+
|
81
|
+
def ws_safe_send(msg)
|
82
|
+
if ws_open
|
83
|
+
ws_client.send msg
|
84
|
+
else
|
85
|
+
ws_registration_messages.push msg
|
86
|
+
end
|
87
|
+
end
|
88
|
+
|
89
|
+
def register_channel(msg, &block)
|
90
|
+
add_callback(fingerprint(msg),&block)
|
91
|
+
if ws_open
|
92
|
+
ws_client.send msg.merge(event: 'subscribe')
|
93
|
+
else
|
94
|
+
ws_registration_messages.push msg.merge(event: 'subscribe')
|
95
|
+
end
|
96
|
+
end
|
97
|
+
|
98
|
+
def fingerprint(msg)
|
99
|
+
msg.reject{|k,v| [:event,'chanId','event'].include?(k) }.
|
100
|
+
inject({}){|h, (k,v)| h[k.to_sym]=v.to_s; h}
|
101
|
+
end
|
102
|
+
|
103
|
+
def listen
|
104
|
+
ws_client.on(:message) do |rmsg|
|
105
|
+
msg = JSON.parse(rmsg)
|
106
|
+
if msg.kind_of?(Hash) && msg["event"] == "subscribed"
|
107
|
+
save_channel_id(fingerprint(msg), msg["chanId"])
|
108
|
+
elsif msg.kind_of?(Array)
|
109
|
+
exec_callback_for(msg)
|
110
|
+
end
|
111
|
+
end
|
112
|
+
end
|
113
|
+
|
114
|
+
def save_channel_id(chan,id)
|
115
|
+
callbacks[chan][:chan_id] = id
|
116
|
+
chan_ids[id.to_i] = chan
|
117
|
+
end
|
118
|
+
|
119
|
+
def exec_callback_for(msg)
|
120
|
+
return if msg[1] == 'hb' #ignore heartbeat
|
121
|
+
id = msg[0]
|
122
|
+
callbacks[chan_ids[id.to_i]][:block].call(msg)
|
123
|
+
end
|
124
|
+
|
125
|
+
def subscribe_to_channels
|
126
|
+
ws_client.on(:open) do
|
127
|
+
@ws_open = true
|
128
|
+
ws_registration_messages.each do |msg|
|
129
|
+
ws_client.send(msg)
|
130
|
+
end
|
131
|
+
end
|
132
|
+
end
|
133
|
+
|
134
|
+
class WSClient
|
135
|
+
def initialize(options = {})
|
136
|
+
# set some defaults
|
137
|
+
@url = options[:url] || 'ws://dev2.bitfinex.com:3001/ws'
|
138
|
+
@reconnect = options[:reconenct] || false
|
139
|
+
end
|
140
|
+
|
141
|
+
def on(msg, &blk)
|
142
|
+
ivar = "@#{msg}_cb"
|
143
|
+
instance_variable_set(ivar.to_sym, blk)
|
144
|
+
end
|
145
|
+
|
146
|
+
def run!
|
147
|
+
if EventMachine.reactor_running?
|
148
|
+
connect!
|
149
|
+
else
|
150
|
+
EM.run { connect! }
|
151
|
+
end
|
152
|
+
end
|
153
|
+
|
154
|
+
def stop!
|
155
|
+
@ws.close
|
156
|
+
end
|
157
|
+
|
158
|
+
def connect!
|
159
|
+
@ws = Faye::WebSocket::Client.new(@url)
|
160
|
+
@ws.onopen = method(:ws_opened)
|
161
|
+
@ws.onmessage = method(:ws_receive)
|
162
|
+
@ws.onclose = method(:ws_closed)
|
163
|
+
@ws.onerror = method(:ws_error)
|
164
|
+
end
|
165
|
+
|
166
|
+
def send(msg)
|
167
|
+
msg = msg.is_a?(Hash) ? msg.to_json : msg
|
168
|
+
@ws.send(msg)
|
169
|
+
end
|
170
|
+
|
171
|
+
private
|
172
|
+
|
173
|
+
def ws_opened(event)
|
174
|
+
@open_cb.call(event) if @open_cb
|
175
|
+
end
|
176
|
+
|
177
|
+
def ws_receive(event)
|
178
|
+
@message_cb.call(event.data) if @message_cb
|
179
|
+
end
|
180
|
+
|
181
|
+
def ws_closed(_event)
|
182
|
+
EM.stop
|
183
|
+
end
|
184
|
+
|
185
|
+
def ws_error(event)
|
186
|
+
fail event
|
187
|
+
end
|
188
|
+
end
|
189
|
+
end
|
190
|
+
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: bitfinex-rb
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.0.
|
4
|
+
version: 0.0.4
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Bitfinex
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2016-03-
|
11
|
+
date: 2016-03-16 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: faraday
|
@@ -30,6 +30,26 @@ dependencies:
|
|
30
30
|
- - ">="
|
31
31
|
- !ruby/object:Gem::Version
|
32
32
|
version: 0.9.2
|
33
|
+
- !ruby/object:Gem::Dependency
|
34
|
+
name: eventmachine
|
35
|
+
requirement: !ruby/object:Gem::Requirement
|
36
|
+
requirements:
|
37
|
+
- - "~>"
|
38
|
+
- !ruby/object:Gem::Version
|
39
|
+
version: '1.0'
|
40
|
+
- - ">="
|
41
|
+
- !ruby/object:Gem::Version
|
42
|
+
version: 1.0.9.1
|
43
|
+
type: :runtime
|
44
|
+
prerelease: false
|
45
|
+
version_requirements: !ruby/object:Gem::Requirement
|
46
|
+
requirements:
|
47
|
+
- - "~>"
|
48
|
+
- !ruby/object:Gem::Version
|
49
|
+
version: '1.0'
|
50
|
+
- - ">="
|
51
|
+
- !ruby/object:Gem::Version
|
52
|
+
version: 1.0.9.1
|
33
53
|
- !ruby/object:Gem::Dependency
|
34
54
|
name: faraday-detailed_logger
|
35
55
|
requirement: !ruby/object:Gem::Requirement
|
@@ -50,6 +70,20 @@ dependencies:
|
|
50
70
|
- - ">="
|
51
71
|
- !ruby/object:Gem::Version
|
52
72
|
version: 1.0.0
|
73
|
+
- !ruby/object:Gem::Dependency
|
74
|
+
name: faye-websocket
|
75
|
+
requirement: !ruby/object:Gem::Requirement
|
76
|
+
requirements:
|
77
|
+
- - "~>"
|
78
|
+
- !ruby/object:Gem::Version
|
79
|
+
version: 0.10.3
|
80
|
+
type: :runtime
|
81
|
+
prerelease: false
|
82
|
+
version_requirements: !ruby/object:Gem::Requirement
|
83
|
+
requirements:
|
84
|
+
- - "~>"
|
85
|
+
- !ruby/object:Gem::Version
|
86
|
+
version: 0.10.3
|
53
87
|
- !ruby/object:Gem::Dependency
|
54
88
|
name: json
|
55
89
|
requirement: !ruby/object:Gem::Requirement
|
@@ -138,8 +172,7 @@ files:
|
|
138
172
|
- lib/bitfinex/trades.rb
|
139
173
|
- lib/bitfinex/version.rb
|
140
174
|
- lib/bitfinex/wallet.rb
|
141
|
-
- lib/bitfinex/
|
142
|
-
- lib/bitfinex/websocket/em_client.rb
|
175
|
+
- lib/bitfinex/websocket_connection.rb
|
143
176
|
homepage: https://www.bitfinex.com/
|
144
177
|
licenses:
|
145
178
|
- MIT
|
data/lib/bitfinex/websocket.rb
DELETED
@@ -1,64 +0,0 @@
|
|
1
|
-
require 'eventmachine'
|
2
|
-
require 'faye/websocket'
|
3
|
-
require 'json'
|
4
|
-
|
5
|
-
module Bitfinex
|
6
|
-
module Websocket
|
7
|
-
|
8
|
-
class EMClient
|
9
|
-
def initialize(options = {})
|
10
|
-
# set some defaults
|
11
|
-
@url = options[:url] || 'wss://api2.bitfinex.com:3000/ws'
|
12
|
-
@reconnect = options[:reconenct] || false
|
13
|
-
end
|
14
|
-
|
15
|
-
def on(msg, &blk)
|
16
|
-
ivar = "@#{msg}_cb"
|
17
|
-
instance_variable_set(ivar.to_sym, blk)
|
18
|
-
end
|
19
|
-
|
20
|
-
def run!
|
21
|
-
if EventMachine.reactor_running?
|
22
|
-
connect!
|
23
|
-
else
|
24
|
-
EM.run { connect! }
|
25
|
-
end
|
26
|
-
end
|
27
|
-
|
28
|
-
def stop!
|
29
|
-
@ws.close
|
30
|
-
end
|
31
|
-
|
32
|
-
def connect!
|
33
|
-
@ws = Faye::WebSocket::Client.new(@url)
|
34
|
-
@ws.onopen = method(:ws_opened)
|
35
|
-
@ws.onmessage = method(:ws_receive)
|
36
|
-
@ws.onclose = method(:ws_closed)
|
37
|
-
@ws.onerror = method(:ws_error)
|
38
|
-
end
|
39
|
-
|
40
|
-
def send(msg)
|
41
|
-
msg = msg.is_a?(Hash) ? msg.to_json : msg
|
42
|
-
@ws.send(msg)
|
43
|
-
end
|
44
|
-
|
45
|
-
private
|
46
|
-
|
47
|
-
def ws_opened(event)
|
48
|
-
@open_cb.call(event) if @open_cb
|
49
|
-
end
|
50
|
-
|
51
|
-
def ws_receive(event)
|
52
|
-
@message_cb.call(event.data) if @message_cb
|
53
|
-
end
|
54
|
-
|
55
|
-
def ws_closed(_event)
|
56
|
-
EM.stop
|
57
|
-
end
|
58
|
-
|
59
|
-
def ws_error(event)
|
60
|
-
fail event
|
61
|
-
end
|
62
|
-
end
|
63
|
-
end
|
64
|
-
end
|
@@ -1,60 +0,0 @@
|
|
1
|
-
module Bitfinex
|
2
|
-
module Websocket
|
3
|
-
|
4
|
-
class EMClient
|
5
|
-
def initialize(options = {})
|
6
|
-
# set some defaults
|
7
|
-
@url = options[:url] || 'wss://api2.bitfinex.com:3000/ws'
|
8
|
-
@reconnect = options[:reconenct] || false
|
9
|
-
end
|
10
|
-
|
11
|
-
def on(msg, &blk)
|
12
|
-
ivar = "@#{msg}_cb"
|
13
|
-
instance_variable_set(ivar.to_sym, blk)
|
14
|
-
end
|
15
|
-
|
16
|
-
def run!
|
17
|
-
if EventMachine.reactor_running?
|
18
|
-
connect!
|
19
|
-
else
|
20
|
-
EM.run { connect! }
|
21
|
-
end
|
22
|
-
end
|
23
|
-
|
24
|
-
def stop!
|
25
|
-
@ws.close
|
26
|
-
end
|
27
|
-
|
28
|
-
def connect!
|
29
|
-
@ws = Faye::WebSocket::Client.new(@url)
|
30
|
-
@ws.onopen = method(:ws_opened)
|
31
|
-
@ws.onmessage = method(:ws_receive)
|
32
|
-
@ws.onclose = method(:ws_closed)
|
33
|
-
@ws.onerror = method(:ws_error)
|
34
|
-
end
|
35
|
-
|
36
|
-
def send(msg)
|
37
|
-
msg = msg.is_a?(Hash) ? msg.to_json : msg
|
38
|
-
@ws.send(msg)
|
39
|
-
end
|
40
|
-
|
41
|
-
private
|
42
|
-
|
43
|
-
def ws_opened(event)
|
44
|
-
@open_cb.call(event) if @open_cb
|
45
|
-
end
|
46
|
-
|
47
|
-
def ws_receive(event)
|
48
|
-
@message_cb.call(event.data) if @message_cb
|
49
|
-
end
|
50
|
-
|
51
|
-
def ws_closed(_event)
|
52
|
-
EM.stop
|
53
|
-
end
|
54
|
-
|
55
|
-
def ws_error(event)
|
56
|
-
fail event
|
57
|
-
end
|
58
|
-
end
|
59
|
-
end
|
60
|
-
end
|