import axios from 'axios' ; import _ from 'lodash/fp' ; import { OrderBulk } from '../api' ; import { AccessToken , Affiliate , Announcement , APIKey , Chat , ChatChannel , CommunicationToken , ConnectedUsers , Execution , Funding , GlobalNotification , IndexComposite , Instrument , InstrumentInterval , Insurance , Leaderboard , Liquidation , Margin , Order , OrderBookL2 , Position , Quote , QuoteFillRatio , QuoteValueRatio , Settlement , Stats , StatsHistory , StatsUSD , Trade , TradeBin , Transaction , User , UserCommissionsBySymbol , UserEvent , Wallet , XAny , } from './types' ; type Routes = 'bulkOrders' | 'order' | 'getBalance' | 'getOrders' ; type RequestPayload < T > = { method ? : string ; } & T ; export type RequestParams = Omit < RequestInit , 'body' | 'method' > & { secure ? : boolean ; } ; export type RequestQueryParamsType = Record < string | number , any > ; interface ApiConfig < SecurityDataType > { baseUrl ? : string ; baseApiParams ? : RequestParams ; securityWorker ? : ( securityData : SecurityDataType ) => RequestParams ; } export interface HttpResponse < D extends unknown , E extends unknown = unknown > extends Response { data : D ; error : E ; } enum BodyType { Json , FormData } export class HttpClient < SecurityDataType = unknown > { public baseUrl = '//www.bitmex.com/api/v1' ; private securityData : SecurityDataType = null as any ; private securityWorker : null | ApiConfig < SecurityDataType > [ 'securityWorker' ] = null ; private baseApiParams : RequestParams = { credentials : 'same-origin' , headers : { 'Content-Type' : 'application/json' , } , redirect : 'follow' , referrerPolicy : 'no-referrer' , } ; constructor ( apiConfig = { } ) { Object . assign ( this , apiConfig ) ; } public setSecurityData = ( data ) => { this . securityData = data ; } ; private addQueryParam ( query , key ) { return ( encodeURIComponent ( key ) + '=' + encodeURIComponent ( Array . isArray ( query [ key ] ) ? query [ key ] . join ( ',' ) : query [ key ] ) ) ; } protected addQueryParams ( rawQuery ? ) { const query = rawQuery || { } ; const keys = Object . keys ( query ) . filter ( ( key ) => 'undefined' !== typeof query [ key ] ) ; return keys . length ? `?${ keys . map ( ( key ) => typeof query [ key ] === 'object' && ! Array . isArray ( query [ key ] ) ? this . addQueryParams ( query [ key ] as object ) . substring ( 1 ) : this . addQueryParam ( query , key ) ) . join ( '&' ) }` : '' ; } private bodyFormatters : Record < BodyType , ( input : any ) => any > = { [ BodyType . Json ] : JSON . stringify , [ BodyType . FormData ] : ( input ) => Object . keys ( input ) . reduce ( ( data , key ) => { data . append ( key , input [ key ] ) ; return data ; } , new FormData ( ) ) , } ; private mergeRequestOptions ( params , securityParams ? ) { return { ... this . baseApiParams , ... params , ... ( securityParams || { } ) , headers : { ... ( this . baseApiParams . headers || { } ) , ... ( params . headers || { } ) , ... ( ( securityParams && securityParams . headers ) || { } ) , } , } ; } private safeParseResponse = < T = any , E = any > ( response ) : Promise < HttpResponse < T , E > > => { const r = response as HttpResponse < T , E > ; r . data = null as unknown as T ; r . error = null as unknown as E ; return response . json ( ) . then ( ( data ) => { if ( r . ok ) { r . data = data ; } else { r . error = data ; } return r ; } ) . catch ( ( e ) => { r . error = e ; return r ; } ) ; } ; public request = < T = any , E = any > ( path , method , { secure , ... params } = { } , body ? , bodyType ? , secureByDefault ? ) : Promise < HttpResponse < T > > => { const requestUrl = `${ this . baseUrl }${ path }` ; const secureOptions = ( secureByDefault || secure ) && this . securityWorker ? this . securityWorker ( this . securityData ) : { } ; const requestOptions = { ... this . mergeRequestOptions ( params , secureOptions ) , method , body : body ? this . bodyFormatters [ bodyType || BodyType . Json ] ( body ) : null , } ; return fetch ( requestUrl , requestOptions ) . then ( async ( response ) => { const data = await this . safeParseResponse < T , E > ( response ) ; if ( ! response . ok ) throw data ; return data ; } ) ; } ; } class MyHTTPClient { constructor ( private exchange ) { } private addQueryParam ( query , key ) { return ( encodeURIComponent ( key ) + '=' + encodeURIComponent ( Array . isArray ( query [ key ] ) ? query [ key ] . join ( ',' ) : query [ key ] ) ) ; } protected addQueryParams ( rawQuery ? ) { const query = rawQuery || { } ; const keys = Object . keys ( query ) . filter ( ( key ) => 'undefined' !== typeof query [ key ] ) ; return keys . length ? `?${ keys . map ( ( key ) => typeof query [ key ] === 'object' && ! Array . isArray ( query [ key ] ) ? this . addQueryParams ( query [ key ] as object ) . substring ( 1 ) : this . addQueryParam ( query , key ) ) . join ( '&' ) }` : '' ; } async _makeRequest < P = any > ( path , payload ) { return axios . post ( path , payload ) ; } _parseData < D , Args extends string > ( data , args = [ ] ) { const parsedData = typeof data === 'string' ? JSON . parse ( data ) : data ; const dataElement = ! Array . isArray ( parsedData ) ? parsedData : parsedData [ 0 ] ; return _ . pick ( [ ... args , 'text' ] , dataElement ) ; } async request < P = any , _E = any > ( path , method , { secure , ... params } = { } , body ? , bodyType ? , secureByDefault ? ) { const payload = { data : body , method , exchange : this . exchange , } ; return await this . _makeRequest ( `/${ this . exchange }${ path }` as Routes , payload ) ; } } title version baseUrl export class Api < _SecurityDataType = any > extends MyHTTPClient { constructor ( ) { super ( 'bitmex' ) ; } announcement = { tags name summary request secure announcementGet : ( query ? , params ? ) => this . request < Announcement [ ] , Error > ( `/announcement${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure announcementGetUrgent : ( params ? ) => this . request < Announcement [ ] , Error > ( `/announcement/urgent` , 'GET' , params , null , BodyType . Json , true ) , } ; apiKey = { tags name summary request secure apiKeyGet : ( query ? , params ? ) => this . request < APIKey [ ] , Error > ( `/apiKey${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; chat = { tags name summary request secure chatGet : ( query ? , params ? ) => this . request < Chat [ ] , Error > ( `/chat${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure chatNew : ( data , params ? ) => this . request < Chat , Error > ( `/chat` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure chatGetChannels : ( params ? ) => this . request < ChatChannel [ ] , Error > ( `/chat/channels` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure chatGetConnected : ( params ? ) => this . request < ConnectedUsers , Error > ( `/chat/connected` , 'GET' , params , null , BodyType . Json , true ) , } ; execution = { description tags name summary request secure executionGet : ( query ? , params ? ) => this . request < Execution [ ] , Error > ( `/execution${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure executionGetTradeHistory : ( query ? , params ? ) => this . request < Execution [ ] , Error > ( `/execution/tradeHistory${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; funding = { tags name summary request secure fundingGet : ( query ? , params ? ) => this . request < Funding [ ] , Error > ( `/funding${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; instrument = { description tags name summary request secure instrumentGet : ( query ? , params ? ) => this . request < Instrument [ ] , Error > ( `/instrument${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure instrumentGetActive : ( params ? ) => this . request < Instrument [ ] , Error > ( `/instrument/active` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure instrumentGetIndices : ( params ? ) => this . request < Instrument [ ] , Error > ( `/instrument/indices` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure instrumentGetActiveAndIndices : ( params ? ) => this . request < Instrument [ ] , Error > ( `/instrument/activeAndIndices` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure instrumentGetActiveIntervals : ( params ? ) => this . request < InstrumentInterval , Error > ( `/instrument/activeIntervals` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure instrumentGetCompositeIndex : ( query ? , params ? ) => this . request < IndexComposite [ ] , Error > ( `/instrument/compositeIndex${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; insurance = { tags name summary request secure insuranceGet : ( query ? , params ? ) => this . request < Insurance [ ] , Error > ( `/insurance${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; leaderboard = { tags name summary request secure leaderboardGet : ( query ? , params ? ) => this . request < Leaderboard [ ] , Error > ( `/leaderboard${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure leaderboardGetName : ( params ? ) => this . request < { name ? : string ; } , Error > ( `/leaderboard/name` , 'GET' , params , null , BodyType . Json , true ) , } ; liquidation = { tags name summary request secure liquidationGet : ( query ? , params ? ) => this . request < Liquidation [ ] , Error > ( `/liquidation${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; globalNotification = { description tags name summary request secure globalNotificationGet : ( params ? ) => this . request < GlobalNotification [ ] , Error > ( `/globalNotification` , 'GET' , params , null , BodyType . Json , true ) , } ; order = { description tags name summary request secure orderGetOrders : ( query ? , params ? ) => this . request < Order [ ] , Error > ( `/order${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure orderNew : ( data , params ? ) => this . request < Order , Error > ( `/order` , 'POST' , params , data , BodyType . Json , true ) , description tags name summary request secure orderAmend : ( data , params ? ) => this . request < Order , Error > ( `/order` , 'PUT' , params , data , BodyType . Json , true ) , description tags name summary request secure orderCancel : ( data , params ? ) => this . request < Order [ ] , Error > ( `/order` , 'DELETE' , params , data , BodyType . Json , true ) , description tags name summary request secure orderNewBulk : ( data , params ? ) => this . request < Order [ ] , Error > ( `/order/bulk` , 'POST' , params , data , BodyType . Json , true ) , description tags name summary request secure orderAmendBulk : ( data , params ? ) => this . request < Order [ ] , Error > ( `/order/bulk` , 'PUT' , params , data , BodyType . Json , true ) , description tags name summary request secure orderClosePosition : ( data , params ? ) => this . request < Order , Error > ( `/order/closePosition` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure orderCancelAll : ( data , params ? ) => this . request < Order [ ] , Error > ( `/order/all` , 'DELETE' , params , data , BodyType . Json , true ) , description tags name summary request secure orderCancelAllAfter : ( data , params ? ) => this . request < XAny , Error > ( `/order/cancelAllAfter` , 'POST' , params , data , BodyType . Json , true ) , } ; orderBook = { tags name summary request secure orderBookGetL2 : ( query , params ? ) => this . request < OrderBookL2 [ ] , Error > ( `/orderBook/L2${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; position = { description tags name summary request secure positionGet : ( query ? , params ? ) => this . request < Position [ ] , Error > ( `/position${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure positionIsolateMargin : ( data , params ? ) => this . request < Position , Error > ( `/position/isolate` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure positionUpdateRiskLimit : ( data , params ? ) => this . request < Position , Error > ( `/position/riskLimit` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure positionTransferIsolatedMargin : ( data , params ? ) => this . request < Position , Error > ( `/position/transferMargin` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure positionUpdateLeverage : ( data , params ? ) => this . request < Position , Error > ( `/position/leverage` , 'POST' , params , data , BodyType . Json , true ) , } ; quote = { tags name summary request secure quoteGet : ( query ? , params ? ) => this . request < Quote [ ] , Error > ( `/quote${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure quoteGetBucketed : ( query ? , params ? ) => this . request < Quote [ ] , Error > ( `/quote/bucketed${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; schema = { tags name summary request secure schemaGet : ( query ? , params ? ) => this . request < XAny , Error > ( `/schema${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure schemaWebsocketHelp : ( params ? ) => this . request < XAny , Error > ( `/schema/websocketHelp` , 'GET' , params , null , BodyType . Json , true ) , } ; settlement = { tags name summary request secure settlementGet : ( query ? , params ? ) => this . request < Settlement [ ] , Error > ( `/settlement${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; stats = { tags name summary request secure statsGet : ( params ? ) => this . request < Stats [ ] , Error > ( `/stats` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure statsHistory : ( params ? ) => this . request < StatsHistory [ ] , Error > ( `/stats/history` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure statsHistoryUsd : ( params ? ) => this . request < StatsUSD [ ] , Error > ( `/stats/historyUSD` , 'GET' , params , null , BodyType . Json , true ) , } ; trade = { description tags name summary request secure tradeGet : ( query ? , params ? ) => this . request < Trade [ ] , Error > ( `/trade${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure tradeGetBucketed : ( query ? , params ? ) => this . request < TradeBin [ ] , Error > ( `/trade/bucketed${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; user = { tags name summary request secure userGetDepositAddress : ( query ? , params ? ) => this . request < string , Error > ( `/user/depositAddress${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetWallet : ( query ? , params ? ) => this . request < Wallet , Error > ( `/user/wallet${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetWalletHistory : ( query ? , params ? ) => this . request < Transaction [ ] , Error > ( `/user/walletHistory${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetWalletSummary : ( query ? , params ? ) => this . request < Transaction [ ] , Error > ( `/user/walletSummary${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetExecutionHistory : ( query , params ? ) => this . request < XAny , Error > ( `/user/executionHistory${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure userMinWithdrawalFee : ( query ? , params ? ) => this . request < XAny , Error > ( `/user/minWithdrawalFee${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure userRequestWithdrawal : ( data , params ? ) => this . request < Transaction , Error > ( `/user/requestWithdrawal` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure userCancelWithdrawal : ( data , params ? ) => this . request < Transaction , Error > ( `/user/cancelWithdrawal` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure userConfirmWithdrawal : ( data , params ? ) => this . request < Transaction , Error > ( `/user/confirmWithdrawal` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure userConfirm : ( data , params ? ) => this . request < AccessToken , Error > ( `/user/confirmEmail` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure userGetAffiliateStatus : ( params ? ) => this . request < Affiliate , Error > ( `/user/affiliateStatus` , 'GET' , params , null , BodyType . Json , true ) , description tags name summary request secure userCheckReferralCode : ( query ? , params ? ) => this . request < number , Error > ( `/user/checkReferralCode${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetQuoteFillRatio : ( params ? ) => this . request < QuoteFillRatio , Error > ( `/user/quoteFillRatio` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetQuoteValueRatio : ( params ? ) => this . request < QuoteValueRatio , Error > ( `/user/quoteValueRatio` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userLogout : ( params ? ) => this . request < any , Error > ( `/user/logout` , 'POST' , params , null , BodyType . Json , true ) , tags name summary request secure userSavePreferences : ( data , params ? ) => this . request < User , Error > ( `/user/preferences` , 'POST' , params , data , BodyType . Json , true ) , tags name summary request secure userGet : ( params ? ) => this . request < User , Error > ( `/user` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetCommission : ( params ? ) => this . request < UserCommissionsBySymbol , Error > ( `/user/commission` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userGetMargin : ( query ? , params ? ) => this . request < Margin , Error > ( `/user/margin${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , tags name summary request secure userCommunicationToken : ( data , params ? ) => this . request < CommunicationToken [ ] , Error > ( `/user/communicationToken` , 'POST' , params , data , BodyType . Json , true ) , } ; userEvent = { tags name summary request secure userEventGet : ( query ? , params ? ) => this . request < UserEvent [ ] , Error > ( `/userEvent${ this . addQueryParams ( query ) }` , 'GET' , params , null , BodyType . Json , true ) , } ; }