bibox 0.1.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +7 -0
- data/.DS_Store +0 -0
- data/.gitignore +15 -0
- data/.rspec +3 -0
- data/.travis.yml +5 -0
- data/CODE_OF_CONDUCT.md +74 -0
- data/Gemfile +6 -0
- data/Gemfile.lock +67 -0
- data/LICENSE.txt +21 -0
- data/README.md +67 -0
- data/Rakefile +6 -0
- data/bibox.gemspec +36 -0
- data/bin/console +31 -0
- data/bin/setup +8 -0
- data/bin/websocket +71 -0
- data/credentials.yml.example +7 -0
- data/lib/.DS_Store +0 -0
- data/lib/bibox.rb +74 -0
- data/lib/bibox/.DS_Store +0 -0
- data/lib/bibox/configuration.rb +21 -0
- data/lib/bibox/constants.rb +6 -0
- data/lib/bibox/errors.rb +17 -0
- data/lib/bibox/extensions/string.rb +13 -0
- data/lib/bibox/models/asset.rb +29 -0
- data/lib/bibox/models/base.rb +26 -0
- data/lib/bibox/models/bill.rb +26 -0
- data/lib/bibox/models/ohlcv.rb +16 -0
- data/lib/bibox/models/order.rb +38 -0
- data/lib/bibox/models/order_book.rb +29 -0
- data/lib/bibox/models/pair.rb +24 -0
- data/lib/bibox/models/ticker.rb +18 -0
- data/lib/bibox/models/trade.rb +13 -0
- data/lib/bibox/models/transfer.rb +26 -0
- data/lib/bibox/models/user_assets.rb +23 -0
- data/lib/bibox/rest/client.rb +97 -0
- data/lib/bibox/rest/errors.rb +16 -0
- data/lib/bibox/rest/private/assets.rb +33 -0
- data/lib/bibox/rest/private/bills.rb +31 -0
- data/lib/bibox/rest/private/order_book.rb +21 -0
- data/lib/bibox/rest/private/orders.rb +131 -0
- data/lib/bibox/rest/private/transfers.rb +49 -0
- data/lib/bibox/rest/public/klines.rb +22 -0
- data/lib/bibox/rest/public/order_book.rb +16 -0
- data/lib/bibox/rest/public/pairs.rb +23 -0
- data/lib/bibox/rest/public/ticker.rb +16 -0
- data/lib/bibox/rest/public/trades.rb +16 -0
- data/lib/bibox/utilities.rb +68 -0
- data/lib/bibox/version.rb +3 -0
- data/lib/bibox/websocket/client.rb +149 -0
- metadata +232 -0
@@ -0,0 +1,16 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Errors
|
4
|
+
|
5
|
+
def error?(response)
|
6
|
+
if response.is_a?(Hash) && response.has_key?("error")
|
7
|
+
error = response.fetch("error", {})
|
8
|
+
code = error.fetch("code", nil)
|
9
|
+
message = error.fetch("msg", nil)
|
10
|
+
::Bibox::Errors::MAPPING.fetch(code, nil)&.call
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,33 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Private
|
4
|
+
module Assets
|
5
|
+
|
6
|
+
def coin_list(options: {})
|
7
|
+
payload = [
|
8
|
+
{
|
9
|
+
cmd: "transfer/coinList",
|
10
|
+
body: {}
|
11
|
+
}
|
12
|
+
]
|
13
|
+
|
14
|
+
response = parse(post("/transfer", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", [])
|
15
|
+
::Bibox::Models::Asset.parse(response) if response&.any?
|
16
|
+
end
|
17
|
+
|
18
|
+
def assets(options: {})
|
19
|
+
payload = [
|
20
|
+
{
|
21
|
+
cmd: "transfer/assets",
|
22
|
+
body: {select: 1}
|
23
|
+
}
|
24
|
+
]
|
25
|
+
|
26
|
+
response = parse(post("/transfer", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", {})
|
27
|
+
::Bibox::Models::UserAssets.new(response) if response
|
28
|
+
end
|
29
|
+
|
30
|
+
end
|
31
|
+
end
|
32
|
+
end
|
33
|
+
end
|
@@ -0,0 +1,31 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Private
|
4
|
+
module Bills
|
5
|
+
|
6
|
+
def bills(coin_id: 0, type: :all, days: 30, page: 1, size: 50, options: {})
|
7
|
+
params = {
|
8
|
+
coin_id: coin_id,
|
9
|
+
type: ::Bibox::Models::Bill::BILL_TYPES[type],
|
10
|
+
days: days,
|
11
|
+
page: page,
|
12
|
+
size: size
|
13
|
+
}
|
14
|
+
|
15
|
+
params.delete_if { |key, value| value.nil? }
|
16
|
+
|
17
|
+
payload = [
|
18
|
+
{
|
19
|
+
cmd: "transfer/bills",
|
20
|
+
body: params
|
21
|
+
}
|
22
|
+
]
|
23
|
+
|
24
|
+
response = parse(post("/transfer", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", {})&.fetch("items", [])
|
25
|
+
::Bibox::Models::Bill.parse(response) if response&.any?
|
26
|
+
end
|
27
|
+
|
28
|
+
end
|
29
|
+
end
|
30
|
+
end
|
31
|
+
end
|
@@ -0,0 +1,21 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Private
|
4
|
+
module OrderBook
|
5
|
+
|
6
|
+
def extended_order_book(pair: "BIX_ETH", size: 200, options: {})
|
7
|
+
payload = [
|
8
|
+
{
|
9
|
+
cmd: "api/depth",
|
10
|
+
body: {pair: pair, size: size}
|
11
|
+
}
|
12
|
+
]
|
13
|
+
|
14
|
+
response = parse(post("/mdata", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", {})
|
15
|
+
::Bibox::Models::OrderBook.new(response) if response
|
16
|
+
end
|
17
|
+
|
18
|
+
end
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
@@ -0,0 +1,131 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Private
|
4
|
+
module Orders
|
5
|
+
|
6
|
+
def buy(pair:, price:, amount:, order_type: :limit, pay_fees_with_bix: true, options: {})
|
7
|
+
perform_order(
|
8
|
+
pair: pair,
|
9
|
+
price: price,
|
10
|
+
amount: amount,
|
11
|
+
order_side: :buy,
|
12
|
+
order_type: order_type,
|
13
|
+
pay_fees_with_bix: pay_fees_with_bix,
|
14
|
+
options: options
|
15
|
+
)
|
16
|
+
end
|
17
|
+
|
18
|
+
def sell(pair:, price:, amount:, order_type: :limit, pay_fees_with_bix: true, options: {})
|
19
|
+
perform_order(
|
20
|
+
pair: pair,
|
21
|
+
price: price,
|
22
|
+
amount: amount,
|
23
|
+
order_side: :sell,
|
24
|
+
order_type: order_type,
|
25
|
+
pay_fees_with_bix: pay_fees_with_bix,
|
26
|
+
options: options
|
27
|
+
)
|
28
|
+
end
|
29
|
+
|
30
|
+
def perform_order(pair:, price:, amount:, order_side: :buy, order_type: :limit, account_type: 0, pay_fees_with_bix: true, options: {})
|
31
|
+
params = {
|
32
|
+
pair: pair,
|
33
|
+
account_type: account_type,
|
34
|
+
order_type: Bibox::Models::Order::ORDER_TYPES[order_type],
|
35
|
+
order_side: Bibox::Models::Order::ORDER_SIDES[order_side],
|
36
|
+
pay_bix: pay_fees_with_bix.eql?(true) ? 1 : 0,
|
37
|
+
price: price,
|
38
|
+
amount: amount,
|
39
|
+
money: (price * amount),
|
40
|
+
}
|
41
|
+
|
42
|
+
payload = [
|
43
|
+
{
|
44
|
+
cmd: "orderpending/trade",
|
45
|
+
body: params
|
46
|
+
}
|
47
|
+
]
|
48
|
+
|
49
|
+
response = parse(post("/orderpending", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", {})&.to_s
|
50
|
+
end
|
51
|
+
|
52
|
+
def cancel_order(order_id, options: {})
|
53
|
+
payload = [
|
54
|
+
{
|
55
|
+
cmd: "orderpending/cancelTrade",
|
56
|
+
body: {orders_id: order_id}
|
57
|
+
}
|
58
|
+
]
|
59
|
+
|
60
|
+
response = parse(post("/orderpending", data: payload, options: options))
|
61
|
+
|
62
|
+
return true
|
63
|
+
end
|
64
|
+
|
65
|
+
# A currency pair can be specified using its code, e.g. BIX_ETH
|
66
|
+
# Or separately using coin_symbol and currency_symbol (which the Bibox UI seems to use)
|
67
|
+
|
68
|
+
def pending_orders(pair: nil, page: 1, size: 10, coin_symbol: nil, currency_symbol: nil, order_side: nil, account_type: nil, options: {})
|
69
|
+
params = {
|
70
|
+
pair: pair,
|
71
|
+
page: page,
|
72
|
+
size: size,
|
73
|
+
coin_symbol: coin_symbol,
|
74
|
+
currency_symbol: currency_symbol,
|
75
|
+
order_side: order_side,
|
76
|
+
account_type: account_type,
|
77
|
+
}
|
78
|
+
|
79
|
+
return list_orders(type: :pending, params: params, options: options)
|
80
|
+
end
|
81
|
+
|
82
|
+
def order_history(pair: nil, page: 1, size: 10, hide_cancel: nil, coin_symbol: nil, currency_symbol: nil, order_side: nil, account_type: nil, options: {})
|
83
|
+
params = {
|
84
|
+
pair: pair,
|
85
|
+
page: page,
|
86
|
+
size: size,
|
87
|
+
hide_cancel: hide_cancel,
|
88
|
+
coin_symbol: coin_symbol,
|
89
|
+
currency_symbol: currency_symbol,
|
90
|
+
order_side: order_side,
|
91
|
+
account_type: account_type,
|
92
|
+
}
|
93
|
+
|
94
|
+
return list_orders(type: :history, params: params, options: options)
|
95
|
+
end
|
96
|
+
|
97
|
+
def list_orders(type: :pending, params: {}, options: {})
|
98
|
+
params[:page] ||= 1
|
99
|
+
params[:size] ||= 10
|
100
|
+
|
101
|
+
command = case type
|
102
|
+
when :pending
|
103
|
+
"orderpending/orderPendingList"
|
104
|
+
when :history
|
105
|
+
"orderpending/orderHistoryList"
|
106
|
+
end
|
107
|
+
|
108
|
+
params.delete_if { |key, value| value.nil? }
|
109
|
+
|
110
|
+
case params[:order_side]
|
111
|
+
when 1, :buy
|
112
|
+
params[:order_side] = ::Bibox::Constants::BUY_ORDER
|
113
|
+
when 2, :sell
|
114
|
+
params[:order_side] = ::Bibox::Constants::SELL_ORDER
|
115
|
+
end
|
116
|
+
|
117
|
+
payload = [
|
118
|
+
{
|
119
|
+
cmd: command,
|
120
|
+
body: params
|
121
|
+
}
|
122
|
+
]
|
123
|
+
|
124
|
+
response = parse(post("/orderpending", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", {})&.fetch("items", [])
|
125
|
+
::Bibox::Models::Order.parse(response) if response&.any?
|
126
|
+
end
|
127
|
+
|
128
|
+
end
|
129
|
+
end
|
130
|
+
end
|
131
|
+
end
|
@@ -0,0 +1,49 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Private
|
4
|
+
module Transfers
|
5
|
+
|
6
|
+
def deposit_address(symbol = "BTC", options: {})
|
7
|
+
payload = [
|
8
|
+
{
|
9
|
+
cmd: "transfer/transferIn",
|
10
|
+
body: {coin_symbol: symbol}
|
11
|
+
}
|
12
|
+
]
|
13
|
+
|
14
|
+
response = parse(post("/transfer", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", {})
|
15
|
+
end
|
16
|
+
|
17
|
+
def deposits(page: 1, size: 10, filter_type: :all, search: nil, options: {})
|
18
|
+
transfers(command: "transfer/transferInList", page: page, size: size, filter_type: filter_type, search: search, options: options)
|
19
|
+
end
|
20
|
+
|
21
|
+
def withdrawals(page: 1, size: 10, filter_type: :all, search: nil, options: {})
|
22
|
+
transfers(command: "transfer/transferOutList", page: page, size: size, filter_type: filter_type, search: search, options: options)
|
23
|
+
end
|
24
|
+
|
25
|
+
def transfers(command:, page: 1, size: 10, filter_type: :all, search: nil, options: {})
|
26
|
+
params = {
|
27
|
+
page: page,
|
28
|
+
size: size,
|
29
|
+
filter_type: ::Bibox::Models::Transfer::STATUSES[filter_type],
|
30
|
+
search: search,
|
31
|
+
}
|
32
|
+
|
33
|
+
params.delete_if { |key, value| value.nil? }
|
34
|
+
|
35
|
+
payload = [
|
36
|
+
{
|
37
|
+
cmd: command,
|
38
|
+
body: params
|
39
|
+
}
|
40
|
+
]
|
41
|
+
|
42
|
+
response = parse(post("/transfer", data: payload, options: options))&.fetch("result", [])&.first&.fetch("result", {})&.fetch("items", [])
|
43
|
+
::Bibox::Models::Transfer.parse(response) if response
|
44
|
+
end
|
45
|
+
|
46
|
+
end
|
47
|
+
end
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,22 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Public
|
4
|
+
module Klines
|
5
|
+
|
6
|
+
# Pair: pair to lookup data OHLCV data for
|
7
|
+
# Period: specific interval/period to group data for
|
8
|
+
# Minutes: '1min', '5min', '10min', '15min' etc.
|
9
|
+
# Hours: '1hour' etc.
|
10
|
+
# Days: 'day'
|
11
|
+
# Size: number of data points to return (1000 is maximum)
|
12
|
+
def klines(pair: "BIX_ETH", period: '1min', size: 1_000, options: {})
|
13
|
+
path = "/mdata"
|
14
|
+
params = {cmd: "kline", pair: pair, period: period, size: size}
|
15
|
+
response = parse(get(path, params: params, options: options))&.fetch("result", {})
|
16
|
+
::Bibox::Models::OHLCV.parse(response) if response
|
17
|
+
end
|
18
|
+
|
19
|
+
end
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Public
|
4
|
+
module OrderBook
|
5
|
+
|
6
|
+
def order_book(pair: "BIX_ETH", size: 200, options: {})
|
7
|
+
path = "/mdata"
|
8
|
+
params = {cmd: "depth", pair: pair, size: size}
|
9
|
+
response = parse(get(path, params: params, options: options))&.fetch("result", {})
|
10
|
+
::Bibox::Models::OrderBook.new(response) if response
|
11
|
+
end
|
12
|
+
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,23 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Public
|
4
|
+
module Pairs
|
5
|
+
|
6
|
+
def pair(pair: "BIX_ETH", options: {})
|
7
|
+
path = "/mdata"
|
8
|
+
params = {cmd: "market", pair: pair}
|
9
|
+
response = parse(get(path, params: params, options: options))&.fetch("result", {})
|
10
|
+
::Bibox::Models::Pair.new(response) if response
|
11
|
+
end
|
12
|
+
|
13
|
+
def pairs(options: {})
|
14
|
+
path = "/mdata"
|
15
|
+
params = {cmd: "marketAll"}
|
16
|
+
response = parse(get(path, params: params, options: options))&.fetch("result", {})
|
17
|
+
::Bibox::Models::Pair.parse(response) if response
|
18
|
+
end
|
19
|
+
|
20
|
+
end
|
21
|
+
end
|
22
|
+
end
|
23
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Public
|
4
|
+
module Ticker
|
5
|
+
|
6
|
+
def ticker(pair: "BIX_ETH", options: {})
|
7
|
+
path = "/mdata"
|
8
|
+
params = {cmd: "ticker", pair: pair}
|
9
|
+
response = parse(get(path, params: params, options: options))&.fetch("result", {})
|
10
|
+
::Bibox::Models::Ticker.new(response) if response
|
11
|
+
end
|
12
|
+
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,16 @@
|
|
1
|
+
module Bibox
|
2
|
+
module Rest
|
3
|
+
module Public
|
4
|
+
module Trades
|
5
|
+
|
6
|
+
def trades(pair: "BIX_ETH", size: 200, options: {})
|
7
|
+
path = "/mdata"
|
8
|
+
params = {cmd: "deals", pair: pair, size: size}
|
9
|
+
response = parse(get(path, params: params, options: options))&.fetch("result", {})
|
10
|
+
::Bibox::Models::Trade.parse(response) if response
|
11
|
+
end
|
12
|
+
|
13
|
+
end
|
14
|
+
end
|
15
|
+
end
|
16
|
+
end
|
@@ -0,0 +1,68 @@
|
|
1
|
+
module Bibox
|
2
|
+
class Utilities
|
3
|
+
|
4
|
+
class << self
|
5
|
+
def convert_value(value, type, use_ms_for_time: true)
|
6
|
+
if type.is_a?(Symbol)
|
7
|
+
return case type
|
8
|
+
when :string
|
9
|
+
value.to_s
|
10
|
+
when :integer
|
11
|
+
value.to_i
|
12
|
+
when :float
|
13
|
+
value.to_f
|
14
|
+
when :decimal
|
15
|
+
to_decimal(value)
|
16
|
+
when :boolean
|
17
|
+
["true", "1"].include?(value.to_s.downcase)
|
18
|
+
when :datetime
|
19
|
+
DateTime.parse(value)
|
20
|
+
when :time
|
21
|
+
epoch_to_time(value, ms: use_ms_for_time)
|
22
|
+
when :hash
|
23
|
+
value.symbolize_keys
|
24
|
+
else
|
25
|
+
value
|
26
|
+
end
|
27
|
+
elsif type.is_a?(Hash)
|
28
|
+
return case type.keys.first
|
29
|
+
when :enum
|
30
|
+
type[:enum][value.to_i]
|
31
|
+
else
|
32
|
+
value
|
33
|
+
end
|
34
|
+
end
|
35
|
+
end
|
36
|
+
|
37
|
+
def time_to_epoch(time, ms: false)
|
38
|
+
ms ? (time.to_i * 1_000) : time.to_i
|
39
|
+
end
|
40
|
+
|
41
|
+
def epoch_to_time(epoch, ms: false)
|
42
|
+
ms ? ::Time.at(epoch.to_i / 1_000).utc : ::Time.at(epoch.to_i).utc
|
43
|
+
end
|
44
|
+
|
45
|
+
def numeric?(string)
|
46
|
+
!!Kernel.Float(string)
|
47
|
+
rescue TypeError, ArgumentError
|
48
|
+
false
|
49
|
+
end
|
50
|
+
|
51
|
+
def to_decimal(number)
|
52
|
+
if number
|
53
|
+
num = number.to_s
|
54
|
+
num.empty? ? nil : BigDecimal.new(num)
|
55
|
+
else
|
56
|
+
nil
|
57
|
+
end
|
58
|
+
end
|
59
|
+
|
60
|
+
def divide(number, divisor)
|
61
|
+
result = number / divisor
|
62
|
+
result.nan? || result.infinite? ? 0 : result
|
63
|
+
end
|
64
|
+
|
65
|
+
end
|
66
|
+
|
67
|
+
end
|
68
|
+
end
|