Initial commit

This commit is contained in:
Yaser
2026-08-13 19:50:53 +03:30
commit 38084458fe
879 changed files with 95198 additions and 0 deletions

View File

@@ -0,0 +1,288 @@
# encoding: UTF-8
# frozen_string_literal: true
describe API::V2::Market::Trades, type: :request do
let(:member) do
create(:member, :level_3).tap do |m|
m.get_account(:btc).update_attributes(balance: 12.13, locked: 3.14)
m.get_account(:usd).update_attributes(balance: 2014.47, locked: 0)
end
end
before do
Ability.stubs(:user_permissions).returns({'member'=>{'read'=>['Trade']}})
end
let(:token) { jwt_for(member) }
let(:level_0_member) { create(:member, :level_0) }
let(:level_0_member_token) { jwt_for(level_0_member) }
let(:btcusd_ask) do
create(
:order_ask,
:btcusd,
price: '12.32'.to_d,
volume: '123.12345678',
member: member
)
end
let(:btceth_ask) do
create(
:order_ask,
:btceth,
price: '12.32'.to_d,
volume: '123.1234',
member: member
)
end
let(:btcusd_bid) do
create(
:order_bid,
:btcusd,
price: '12.32'.to_d,
volume: '123.12345678',
member: member
)
end
let(:btceth_bid) do
create(
:order_bid,
:btceth,
price: '12.32'.to_d,
volume: '123.1234',
member: member
)
end
let(:btcusd_bid_maker) do
create(
:order_bid,
:btcusd,
price: '12.32'.to_d,
volume: '123.12345678',
member: member
)
end
let(:btceth_ask_taker) do
create(
:order_ask,
:btceth,
price: '12.32'.to_d,
volume: '123.1234',
member: member
)
end
let(:btceth_bid_taker) do
create(
:order_bid,
:btceth,
price: '12.32'.to_d,
volume: '123.1234',
member: member
)
end
let!(:btcusd_ask_trade) { create(:trade, :btcusd, maker_order: btcusd_ask, created_at: 2.days.ago) }
let!(:btceth_ask_trade) { create(:trade, :btceth, maker_order: btceth_ask, created_at: 2.days.ago) }
let!(:btcusd_bid_trade) { create(:trade, :btcusd, taker_order: btcusd_bid, created_at: 23.hours.ago) }
let!(:btceth_bid_trade) { create(:trade, :btceth, taker_order: btceth_bid, taker: member, created_at: 23.hours.ago) }
describe 'GET /api/v2/market/trades' do
it 'requires authentication' do
get '/api/v2/market/trades', params: { market: 'btcusd' }
expect(response.code).to eq '401'
expect(response).to include_api_error('jwt.decode_and_verify')
end
it 'returns all my recent trades' do
api_get '/api/v2/market/trades', token: token
expect(response).to be_successful
result = JSON.parse(response.body)
expect(result.size).to eq 4
expect(result.find { |t| t['id'] == btcusd_ask_trade.id }['side']).to eq 'sell'
expect(result.find { |t| t['id'] == btcusd_ask_trade.id }['order_id']).to eq btcusd_ask.id
expect(result.find { |t| t['id'] == btceth_ask_trade.id }['side']).to eq 'sell'
expect(result.find { |t| t['id'] == btceth_ask_trade.id }['order_id']).to eq btceth_ask.id
expect(result.find { |t| t['id'] == btcusd_bid_trade.id }['side']).to eq 'buy'
expect(result.find { |t| t['id'] == btcusd_bid_trade.id }['order_id']).to eq btcusd_bid.id
expect(result.find { |t| t['id'] == btceth_bid_trade.id }['side']).to eq 'buy'
expect(result.find { |t| t['id'] == btceth_bid_trade.id }['order_id']).to eq btceth_bid.id
end
it 'returns all my recent trades for btcusd market' do
api_get '/api/v2/market/trades', params: { market: 'btcusd' }, token: token
expect(response).to be_successful
result = JSON.parse(response.body)
expect(result.size).to eq 2
expect(result.find { |t| t['id'] == btcusd_ask_trade.id }['side']).to eq 'sell'
expect(result.find { |t| t['id'] == btcusd_ask_trade.id }['order_id']).to eq btcusd_ask.id
expect(result.find { |t| t['id'] == btcusd_bid_trade.id }['side']).to eq 'buy'
expect(result.find { |t| t['id'] == btcusd_bid_trade.id }['order_id']).to eq btcusd_bid.id
end
it 'returns trades for several markets' do
api_get '/api/v2/market/trades', params: { market: ['btcusd', 'btceth'] }, token: token
result = JSON.parse(response.body)
expect(response).to be_successful
expect(result.size).to eq 4
end
it 'returns 1 trade' do
api_get '/api/v2/market/trades', params: { market: 'btcusd', limit: 1 }, token: token
result = JSON.parse(response.body)
expect(response).to be_successful
expect(result.size).to eq 1
end
it 'returns trades for last 24h' do
create(:trade, :btcusd, maker: member, created_at: 6.hours.ago)
api_get '/api/v2/market/trades', params: { time_from: 1.day.ago.to_i }, token: token
result = JSON.parse(response.body)
expect(response).to be_successful
expect(result.size).to eq 3
end
it 'returns trades older than 1 day' do
api_get '/api/v2/market/trades', params: { time_to: 1.day.ago.to_i }, token: token
result = JSON.parse(response.body)
expect(response).to be_successful
expect(result.size).to eq 2
end
it 'returns trades for specific hour' do
create(:trade, :btcusd, maker: member, created_at: 6.hours.ago)
api_get '/api/v2/market/trades', params: { time_from: 7.hours.ago.to_i, time_to: 5.hours.ago.to_i }, token: token
result = JSON.parse(response.body)
expect(response).to be_successful
expect(result.size).to eq 1
end
it 'returns limit out of range error' do
api_get '/api/v2/market/trades', params: { market: 'btcusd', limit: 1024 }, token: token
expect(response.code).to eq '422'
expect(response).to include_api_error('market.trade.invalid_limit')
end
it 'denies access to unverified member' do
api_get '/api/v2/market/trades', params: { market: 'btcusd' }, token: level_0_member_token
expect(response.code).to eq '403'
expect(response).to include_api_error('market.trade.not_permitted')
end
it 'fee calculation for buy order' do
api_get '/api/v2/market/trades', params: { market: 'btcusd' }, token: token
result = JSON.parse(response.body).find { |t| t['side'] == 'buy' }
expect(result['order_id']).to eq btcusd_bid.id
expect(result['fee_amount']).to eq((btcusd_bid.taker_fee * btcusd_bid_trade.amount).to_s)
expect(result['fee']).to eq btcusd_bid.taker_fee.to_s
end
it 'fee calculation for sell order' do
api_get '/api/v2/market/trades', params: { market: 'btcusd' }, token: token
result = JSON.parse(response.body).find { |t| t['side'] == 'sell' }
expect(result['order_id']).to eq btcusd_ask.id
expect(result['fee_amount']).to eq((btcusd_ask.taker_fee * btcusd_ask_trade.total).to_s)
expect(result['fee']).to eq btcusd_ask.taker_fee.to_s
end
it 'fee currency for buy order' do
api_get '/api/v2/market/trades', params: { market: 'btcusd' }, token: token
result = JSON.parse(response.body).find { |t| t['side'] == 'buy' }
expect(result['order_id']).to eq btcusd_bid.id
expect(result['fee_currency']).to eq 'btc'
end
it 'fee currency for sell order' do
api_get '/api/v2/market/trades', params: { market: 'btcusd' }, token: token
result = JSON.parse(response.body).find { |t| t['side'] == 'sell' }
expect(result['order_id']).to eq btcusd_ask.id
expect(result['fee_currency']).to eq 'usd'
end
context 'type filtering' do
context 'sell orders' do
let!(:btceth_ask_trade_taker) { create(:trade, :btceth, taker_order: btceth_ask_taker, created_at: 2.hours.ago) }
let!(:btcusd_bid_trade_maker) { create(:trade, :btcusd, maker_order: btcusd_bid_maker, created_at: 2.hours.ago) }
it 'with taker_id = user_id and taker_type = sell' do
api_get '/api/v2/market/trades', params: { market: 'btceth', type: 'sell' }, token: token
result = JSON.parse(response.body)
expect(result.size).to eq 2
expect(result.find { |t| t['id'] == btceth_ask_trade.id }['side']).to eq 'sell'
expect(result.find { |t| t['id'] == btceth_ask_trade.id }['order_id']).to eq btceth_ask.id
expect(result.find { |t| t['id'] == btceth_ask_trade_taker.id }['side']).to eq 'sell'
expect(result.find { |t| t['id'] == btceth_ask_trade_taker.id }['order_id']).to eq btceth_ask_taker.id
end
it 'with maker_id = user_id and taker_type = buy' do
api_get '/api/v2/market/trades', params: { market: 'btcusd', type: 'sell' }, token: token
result = JSON.parse(response.body)
expect(result.size).to eq 2
expect(result.find { |t| t['id'] == btcusd_ask_trade.id }['side']).to eq 'sell'
expect(result.find { |t| t['id'] == btcusd_ask_trade.id }['order_id']).to eq btcusd_ask.id
expect(result.find { |t| t['id'] == btcusd_bid_trade_maker.id }['side']).to eq 'buy'
expect(result.find { |t| t['id'] == btcusd_bid_trade_maker.id }['order_id']).to eq btcusd_bid_maker.id
end
end
context 'buy orders' do
let!(:btceth_bid_trade_taker) { create(:trade, :btceth, taker_order: btceth_bid_taker, created_at: 2.hours.ago) }
it 'with taker_id = user_id and taker_type = buy' do
api_get '/api/v2/market/trades', params: { market: 'btceth', type: 'buy' }, token: token
result = JSON.parse(response.body)
expect(result.size).to eq 2
expect(result.find { |t| t['id'] == btceth_bid_trade.id }['side']).to eq 'buy'
expect(result.find { |t| t['id'] == btceth_bid_trade.id }['order_id']).to eq btceth_bid.id
expect(result.find { |t| t['id'] == btceth_bid_trade_taker.id }['side']).to eq 'buy'
expect(result.find { |t| t['id'] == btceth_bid_trade_taker.id }['order_id']).to eq btceth_bid_taker.id
end
it 'with maker_id = user_id and taker_type = sell' do
api_get '/api/v2/market/trades', params: { market: 'btcusd', type: 'buy' }, token: token
result = JSON.parse(response.body)
expect(result.size).to eq 1
expect(result.find { |t| t['id'] == btcusd_bid_trade.id }['side']).to eq 'buy'
expect(result.find { |t| t['id'] == btcusd_bid_trade.id }['order_id']).to eq btcusd_bid.id
end
end
end
context 'unauthorized' do
before do
Ability.stubs(:user_permissions).returns([])
end
it 'renders unauthorized error' do
api_get '/api/v2/market/trades', params: { market: 'btcusd' }, token: token
expect(response).to have_http_status 403
expect(response).to include_api_error('user.ability.not_permitted')
end
end
end
end