diff options
-rw-r--r-- | packages/connect/src/http_client.ts | 50 | ||||
-rw-r--r-- | packages/connect/src/index.ts | 8 | ||||
-rw-r--r-- | packages/connect/src/orders_channel_factory.ts | 4 | ||||
-rw-r--r-- | packages/connect/src/schemas/schemas.ts | 2 | ||||
-rw-r--r-- | packages/connect/src/types.ts | 4 | ||||
-rw-r--r-- | packages/connect/test/orderbook_channel_factory_test.ts | 17 | ||||
-rw-r--r-- | packages/connect/test/ws_orderbook_channel_test.ts | 18 |
7 files changed, 64 insertions, 39 deletions
diff --git a/packages/connect/src/http_client.ts b/packages/connect/src/http_client.ts index 5aeba19dd..8f7825253 100644 --- a/packages/connect/src/http_client.ts +++ b/packages/connect/src/http_client.ts @@ -21,6 +21,7 @@ import { OrdersRequestOpts, OrdersResponse, PagedRequestOpts, + RequestOpts, } from './types'; import { relayerResponseJsonParsers } from './utils/relayer_response_json_parsers'; @@ -29,6 +30,9 @@ const DEFAULT_PAGED_REQUEST_OPTS: PagedRequestOpts = { page: 1, perPage: 100, }; +const DEFAULT_REQUEST_OPTS: RequestOpts = { + networkId: 1, +}; /** * This class includes all the functionality related to interacting with a set of HTTP endpoints @@ -62,13 +66,14 @@ export class HttpClient implements Client { * @param requestOpts Options specifying assetData information to retrieve and page information, defaults to { page: 1, perPage: 100 } * @return The resulting AssetPairsItems that match the request */ - public async getAssetPairsAsync(requestOpts?: AssetPairsRequestOpts & PagedRequestOpts): Promise<AssetPairsResponse> { + public async getAssetPairsAsync(requestOpts?: RequestOpts & AssetPairsRequestOpts & PagedRequestOpts): Promise<AssetPairsResponse> { if (!_.isUndefined(requestOpts)) { assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.assetPairsRequestOptsSchema); assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.pagedRequestOptsSchema); + assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.requestOptsSchema); } const httpRequestOpts = { - params: _.defaults({}, requestOpts, DEFAULT_PAGED_REQUEST_OPTS), + params: _.defaults({}, requestOpts, DEFAULT_REQUEST_OPTS, DEFAULT_PAGED_REQUEST_OPTS), }; const responseJson = await this._requestAsync('/asset_pairs', HttpRequestType.Get, httpRequestOpts); const assetDataPairs = relayerResponseJsonParsers.parseAssetDataPairsJson(responseJson); @@ -79,13 +84,14 @@ export class HttpClient implements Client { * @param requestOpts Options specifying orders to retrieve and page information, defaults to { page: 1, perPage: 100 } * @return The resulting SignedOrders that match the request */ - public async getOrdersAsync(requestOpts?: OrdersRequestOpts & PagedRequestOpts): Promise<OrdersResponse> { + public async getOrdersAsync(requestOpts?: RequestOpts & OrdersRequestOpts & PagedRequestOpts): Promise<OrdersResponse> { if (!_.isUndefined(requestOpts)) { assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.ordersRequestOptsSchema); assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.pagedRequestOptsSchema); + assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.requestOptsSchema); } const httpRequestOpts = { - params: _.defaults({}, requestOpts, DEFAULT_PAGED_REQUEST_OPTS), + params: _.defaults({}, requestOpts, DEFAULT_REQUEST_OPTS, DEFAULT_PAGED_REQUEST_OPTS), }; const responseJson = await this._requestAsync(`/orders`, HttpRequestType.Get, httpRequestOpts); const orders = relayerResponseJsonParsers.parseOrdersJson(responseJson); @@ -96,9 +102,15 @@ export class HttpClient implements Client { * @param orderHash An orderHash generated from the desired order * @return The SignedOrder that matches the supplied orderHash */ - public async getOrderAsync(orderHash: string): Promise<APIOrder> { + public async getOrderAsync(orderHash: string, requestOpts?: RequestOpts): Promise<APIOrder> { + if (!_.isUndefined(requestOpts)) { + assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.requestOptsSchema); + } assert.doesConformToSchema('orderHash', orderHash, schemas.orderHashSchema); - const responseJson = await this._requestAsync(`/order/${orderHash}`, HttpRequestType.Get); + const httpRequestOpts = { + params: _.defaults({}, requestOpts, DEFAULT_REQUEST_OPTS), + }; + const responseJson = await this._requestAsync(`/order/${orderHash}`, HttpRequestType.Get, httpRequestOpts); const order = relayerResponseJsonParsers.parseAPIOrderJson(responseJson); return order; } @@ -110,14 +122,15 @@ export class HttpClient implements Client { */ public async getOrderbookAsync( request: OrderbookRequest, - requestOpts?: PagedRequestOpts, + requestOpts?: RequestOpts & PagedRequestOpts, ): Promise<OrderbookResponse> { assert.doesConformToSchema('request', request, clientSchemas.orderBookRequestSchema); if (!_.isUndefined(requestOpts)) { assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.pagedRequestOptsSchema); + assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.requestOptsSchema); } const httpRequestOpts = { - params: _.defaults({}, request, requestOpts, DEFAULT_PAGED_REQUEST_OPTS), + params: _.defaults({}, request, requestOpts, DEFAULT_REQUEST_OPTS, DEFAULT_PAGED_REQUEST_OPTS), }; const responseJson = await this._requestAsync('/orderbook', HttpRequestType.Get, httpRequestOpts); const orderbook = relayerResponseJsonParsers.parseOrderbookResponseJson(responseJson); @@ -128,9 +141,13 @@ export class HttpClient implements Client { * @param request A OrderConfigRequest instance describing the specific fees to retrieve * @return The resulting OrderConfigResponse that matches the request */ - public async getOrderConfigAsync(request: OrderConfigRequest): Promise<OrderConfigResponse> { + public async getOrderConfigAsync(request: OrderConfigRequest, requestOpts?: RequestOpts): Promise<OrderConfigResponse> { + if (!_.isUndefined(requestOpts)) { + assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.requestOptsSchema); + } assert.doesConformToSchema('request', request, clientSchemas.orderConfigRequestSchema); const httpRequestOpts = { + params: _.defaults({}, requestOpts, DEFAULT_REQUEST_OPTS), payload: request, }; const responseJson = await this._requestAsync('/order_config', HttpRequestType.Post, httpRequestOpts); @@ -140,11 +157,15 @@ export class HttpClient implements Client { /** * Retrieve the list of fee recipient addresses used by */ - public async getFeeRecipientsAsync(requestOpts?: PagedRequestOpts): Promise<FeeRecipientsResponse> { + public async getFeeRecipientsAsync(requestOpts?: RequestOpts & PagedRequestOpts): Promise<FeeRecipientsResponse> { if (!_.isUndefined(requestOpts)) { assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.pagedRequestOptsSchema); + assert.doesConformToSchema('requestOpts', requestOpts, clientSchemas.requestOptsSchema); } - const feeRecipients = await this._requestAsync('/fee_recipients', HttpRequestType.Get); + const httpRequestOpts = { + params: _.defaults({}, requestOpts, DEFAULT_REQUEST_OPTS, DEFAULT_PAGED_REQUEST_OPTS), + }; + const feeRecipients = await this._requestAsync('/fee_recipients', HttpRequestType.Get, httpRequestOpts); assert.doesConformToSchema('feeRecipients', feeRecipients, schemas.relayerApiFeeRecipientsResponseSchema); return feeRecipients; } @@ -152,12 +173,13 @@ export class HttpClient implements Client { * Submit a signed order to the API * @param signedOrder A SignedOrder instance to submit */ - public async submitOrderAsync(signedOrder: SignedOrder): Promise<void> { + public async submitOrderAsync(signedOrder: SignedOrder, requestOpts?: RequestOpts): Promise<void> { assert.doesConformToSchema('signedOrder', signedOrder, schemas.signedOrderSchema); - const requestOpts = { + const httpRequestOpts = { + params: _.defaults({}, requestOpts, DEFAULT_REQUEST_OPTS), payload: signedOrder, }; - await this._requestAsync('/order', HttpRequestType.Post, requestOpts); + await this._requestAsync('/order', HttpRequestType.Post, httpRequestOpts); } private async _requestAsync( path: string, diff --git a/packages/connect/src/index.ts b/packages/connect/src/index.ts index e0c4293d9..33e1222b0 100644 --- a/packages/connect/src/index.ts +++ b/packages/connect/src/index.ts @@ -1,12 +1,12 @@ export { HttpClient } from './http_client'; -export { orderbookChannelFactory } from './orderbook_channel_factory'; +export { ordersChannelFactory } from './orders_channel_factory'; export { Client, OrderConfigRequest, OrderConfigResponse, - OrderbookChannel, - OrderbookChannelHandler, - OrderbookChannelSubscriptionOpts, + OrdersChannel, + OrdersChannelHandler, + OrdersChannelSubscriptionOpts, OrderbookRequest, OrderbookResponse, OrdersRequestOpts, diff --git a/packages/connect/src/orders_channel_factory.ts b/packages/connect/src/orders_channel_factory.ts index 4e9b74b2c..fae5cab8c 100644 --- a/packages/connect/src/orders_channel_factory.ts +++ b/packages/connect/src/orders_channel_factory.ts @@ -10,14 +10,14 @@ export const ordersChannelFactory = { * @param url The relayer API base WS url you would like to interact with * @param handler An OrderbookChannelHandler instance that responds to various * channel updates - * @return An OrderbookChannel Promise + * @return An OrdersChannel Promise */ async createWebSocketOrdersChannelAsync( url: string, handler: OrdersChannelHandler, ): Promise<OrdersChannel> { assert.isUri('url', url); - assert.isOrderbookChannelHandler('handler', handler); + assert.isOrdersChannelHandler('handler', handler); return new Promise<OrdersChannel>((resolve, reject) => { const client = new WebSocket.w3cwebsocket(url); client.onopen = () => { diff --git a/packages/connect/src/schemas/schemas.ts b/packages/connect/src/schemas/schemas.ts index a7e968a01..8d101ed6f 100644 --- a/packages/connect/src/schemas/schemas.ts +++ b/packages/connect/src/schemas/schemas.ts @@ -3,11 +3,13 @@ import { orderConfigRequestSchema } from './order_config_request_schema'; import { orderBookRequestSchema } from './orderbook_request_schema'; import { ordersRequestOptsSchema } from './orders_request_opts_schema'; import { pagedRequestOptsSchema } from './paged_request_opts_schema'; +import { requestOptsSchema } from './request_opts_schema'; export const schemas = { orderConfigRequestSchema, orderBookRequestSchema, ordersRequestOptsSchema, pagedRequestOptsSchema, + requestOptsSchema, assetPairsRequestOptsSchema, }; diff --git a/packages/connect/src/types.ts b/packages/connect/src/types.ts index e85a0542c..f90f0808d 100644 --- a/packages/connect/src/types.ts +++ b/packages/connect/src/types.ts @@ -147,6 +147,10 @@ export interface OrderConfigResponse { export type FeeRecipientsResponse = PaginatedCollection<string>; +export interface RequestOpts { + networkId?: number; +} + export interface PagedRequestOpts { page?: number; perPage?: number; diff --git a/packages/connect/test/orderbook_channel_factory_test.ts b/packages/connect/test/orderbook_channel_factory_test.ts index 2ce361bd2..66394cdc9 100644 --- a/packages/connect/test/orderbook_channel_factory_test.ts +++ b/packages/connect/test/orderbook_channel_factory_test.ts @@ -3,15 +3,12 @@ import * as dirtyChai from 'dirty-chai'; import * as _ from 'lodash'; import 'mocha'; -import { orderbookChannelFactory } from '../src/orderbook_channel_factory'; +import { ordersChannelFactory } from '../src/orders_channel_factory'; chai.config.includeStack = true; chai.use(dirtyChai); const expect = chai.expect; -const emptyOrderbookChannelHandler = { - onSnapshot: () => { - _.noop(); - }, +const emptyOrdersChannelHandler = { onUpdate: () => { _.noop(); }, @@ -23,22 +20,22 @@ const emptyOrderbookChannelHandler = { }, }; -describe('orderbookChannelFactory', () => { +describe('ordersChannelFactory', () => { const websocketUrl = 'ws://localhost:8080'; - describe('#createWebSocketOrderbookChannelAsync', () => { + describe('#createWebSocketOrdersChannelAsync', () => { it('throws when input is not a url', () => { const badUrlInput = 54; expect( - orderbookChannelFactory.createWebSocketOrderbookChannelAsync( + ordersChannelFactory.createWebSocketOrdersChannelAsync( badUrlInput as any, - emptyOrderbookChannelHandler, + emptyOrdersChannelHandler, ), ).to.be.rejected(); }); it('throws when handler has the incorrect members', () => { const badHandlerInput = {}; expect( - orderbookChannelFactory.createWebSocketOrderbookChannelAsync(websocketUrl, badHandlerInput as any), + ordersChannelFactory.createWebSocketOrdersChannelAsync(websocketUrl, badHandlerInput as any), ).to.be.rejected(); }); }); diff --git a/packages/connect/test/ws_orderbook_channel_test.ts b/packages/connect/test/ws_orderbook_channel_test.ts index b5682af36..de097c295 100644 --- a/packages/connect/test/ws_orderbook_channel_test.ts +++ b/packages/connect/test/ws_orderbook_channel_test.ts @@ -5,12 +5,12 @@ import 'mocha'; import * as Sinon from 'sinon'; import * as WebSocket from 'websocket'; -import { WebSocketOrderbookChannel } from '../src/ws_orderbook_channel'; +import { WebSocketOrdersChannel } from '../src/ws_orders_channel'; chai.config.includeStack = true; chai.use(dirtyChai); const expect = chai.expect; -const emptyOrderbookChannelHandler = { +const emptyOrdersChannelHandler = { onSnapshot: () => { _.noop(); }, @@ -25,12 +25,12 @@ const emptyOrderbookChannelHandler = { }, }; -describe('WebSocketOrderbookChannel', () => { +describe('WebSocketOrdersChannel', () => { const websocketUrl = 'ws://localhost:8080'; const openClient = new WebSocket.w3cwebsocket(websocketUrl); Sinon.stub(openClient, 'readyState').get(() => WebSocket.w3cwebsocket.OPEN); Sinon.stub(openClient, 'send').callsFake(_.noop.bind(_)); - const openOrderbookChannel = new WebSocketOrderbookChannel(openClient, emptyOrderbookChannelHandler); + const openOrdersChannel = new WebSocketOrdersChannel(openClient, emptyOrdersChannelHandler); const subscriptionOpts = { baseAssetData: '0x323b5d4c32345ced77393b3530b1eed0f346429d', quoteAssetData: '0xef7fff64389b814a946f3e92105513705ca6b990', @@ -39,20 +39,20 @@ describe('WebSocketOrderbookChannel', () => { }; describe('#subscribe', () => { it('throws when subscriptionOpts does not conform to schema', () => { - const badSubscribeCall = openOrderbookChannel.subscribe.bind(openOrderbookChannel, {}); + const badSubscribeCall = openOrdersChannel.subscribe.bind(openOrdersChannel, {}); expect(badSubscribeCall).throws( - 'Expected subscriptionOpts to conform to schema /RelayerApiOrderbookChannelSubscribePayload\nEncountered: {}\nValidation errors: instance requires property "baseAssetData", instance requires property "quoteAssetData"', + 'Expected subscriptionOpts to conform to schema /RelayerApiOrdersChannelSubscribePayload\nEncountered: {}\nValidation errors: instance requires property "baseAssetData", instance requires property "quoteAssetData"', ); }); it('does not throw when inputs are of correct types', () => { - const goodSubscribeCall = openOrderbookChannel.subscribe.bind(openOrderbookChannel, subscriptionOpts); + const goodSubscribeCall = openOrdersChannel.subscribe.bind(openOrdersChannel, subscriptionOpts); expect(goodSubscribeCall).to.not.throw(); }); it('throws when client is closed', () => { const closedClient = new WebSocket.w3cwebsocket(websocketUrl); Sinon.stub(closedClient, 'readyState').get(() => WebSocket.w3cwebsocket.CLOSED); - const closedOrderbookChannel = new WebSocketOrderbookChannel(closedClient, emptyOrderbookChannelHandler); - const badSubscribeCall = closedOrderbookChannel.subscribe.bind(closedOrderbookChannel, subscriptionOpts); + const closedOrdersChannel = new WebSocketOrdersChannel(closedClient, emptyOrdersChannelHandler); + const badSubscribeCall = closedOrdersChannel.subscribe.bind(closedOrdersChannel, subscriptionOpts); expect(badSubscribeCall).throws('WebSocket connection is closed'); }); }); |