aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--packages/instant/public/index.html8
-rw-r--r--packages/instant/src/components/zero_ex_instant.tsx28
-rw-r--r--packages/instant/src/index.umd.ts6
-rw-r--r--packages/instant/src/redux/actions.ts4
-rw-r--r--packages/instant/src/redux/async_data.ts25
-rw-r--r--packages/instant/src/redux/reducer.ts9
-rw-r--r--packages/instant/src/util/assert.ts8
-rw-r--r--packages/instant/src/util/asset.ts41
8 files changed, 100 insertions, 29 deletions
diff --git a/packages/instant/public/index.html b/packages/instant/public/index.html
index 9f1dfdb64..74975678a 100644
--- a/packages/instant/public/index.html
+++ b/packages/instant/public/index.html
@@ -55,15 +55,17 @@
};
const queryParams = new Uri(window.location.search);
const renderOptionsDefaults = {
- liquiditySource: 'https://api.radarrelay.com/0x/v2/',
+ orderSource: 'https://api.radarrelay.com/0x/v2/',
assetData: '0xf47261b0000000000000000000000000e41d2489571d322189246dafa5ebde1f4699f498',
}
- const liquiditySourceOverride = queryParams.getQueryParamValue('liquiditySource');
+ const orderSourceOverride = queryParams.getQueryParamValue('orderSource');
const renderOptionsOverrides = {
- liquiditySource: liquiditySourceOverride === 'provided' ? [providedOrder] : liquiditySourceOverride,
+ orderSource: orderSourceOverride === 'provided' ? [providedOrder] : orderSourceOverride,
assetData: queryParams.getQueryParamValue('assetData'),
networkId: +queryParams.getQueryParamValue('networkId') || undefined,
defaultAssetBuyAmount: +queryParams.getQueryParamValue('defaultAssetBuyAmount') || undefined,
+ availableAssetIdentifiers: JSON.parse(queryParams.getQueryParamValue('availableAssetIdentifiers') || '[]'),
+ defaultSelectedAssetIdentifier: queryParams.getQueryParamValue('defaultSelectedAssetIdentifier'),
}
const renderOptions = Object.assign({}, renderOptionsDefaults, removeUndefined(renderOptionsOverrides));
zeroExInstant.render(renderOptions);
diff --git a/packages/instant/src/components/zero_ex_instant.tsx b/packages/instant/src/components/zero_ex_instant.tsx
index d54dfc153..ab6350010 100644
--- a/packages/instant/src/components/zero_ex_instant.tsx
+++ b/packages/instant/src/components/zero_ex_instant.tsx
@@ -24,13 +24,13 @@ fonts.include();
export type ZeroExInstantProps = ZeroExInstantRequiredProps & Partial<ZeroExInstantOptionalProps>;
export interface ZeroExInstantRequiredProps {
- // TODO: Change API when we allow the selection of different assetDatas
- assetData: string;
- liquiditySource: string | SignedOrder[];
+ orderSource: string | SignedOrder[];
}
export interface ZeroExInstantOptionalProps {
+ availableAssetDatas: string[];
defaultAssetBuyAmount?: number;
+ defaultSelectedAssetData?: string;
additionalAssetMetaDataMap: ObjectMap<AssetMetaData>;
networkId: Network;
}
@@ -45,14 +45,14 @@ export class ZeroExInstant extends React.Component<ZeroExInstantProps> {
networkId,
};
let assetBuyer;
- if (_.isString(props.liquiditySource)) {
+ if (_.isString(props.orderSource)) {
assetBuyer = AssetBuyer.getAssetBuyerForStandardRelayerAPIUrl(
provider,
- props.liquiditySource,
+ props.orderSource,
assetBuyerOptions,
);
} else {
- assetBuyer = AssetBuyer.getAssetBuyerForProvidedOrders(provider, props.liquiditySource, assetBuyerOptions);
+ assetBuyer = AssetBuyer.getAssetBuyerForProvidedOrders(provider, props.orderSource, assetBuyerOptions);
}
const completeAssetMetaDataMap = {
...props.additionalAssetMetaDataMap,
@@ -62,7 +62,13 @@ export class ZeroExInstant extends React.Component<ZeroExInstantProps> {
...state,
assetBuyer,
network: networkId,
- selectedAsset: assetUtils.createAssetFromAssetData(props.assetData, completeAssetMetaDataMap, networkId),
+ selectedAsset: _.isUndefined(props.defaultSelectedAssetData)
+ ? undefined
+ : assetUtils.createAssetFromAssetDataOrThrow(
+ props.defaultSelectedAssetData,
+ completeAssetMetaDataMap,
+ networkId,
+ ),
selectedAssetAmount: _.isUndefined(props.defaultAssetBuyAmount)
? state.selectedAssetAmount
: new BigNumberInput(props.defaultAssetBuyAmount),
@@ -77,8 +83,14 @@ export class ZeroExInstant extends React.Component<ZeroExInstantProps> {
}
public componentDidMount(): void {
+ const state = this._store.getState();
// tslint:disable-next-line:no-floating-promises
- asyncData.fetchAndDispatchToStore(this._store);
+ asyncData.fetchEthPriceAndDispatchToStore(this._store);
+ // fetch available assets if none are specified
+ if (_.isEmpty(state.availableAssets)) {
+ // tslint:disable-next-line:no-floating-promises
+ asyncData.fetchAvailableAssetDatasAndDispatchToStore(this._store);
+ }
// warm up the gas price estimator cache just in case we can't
// grab the gas price estimate when submitting the transaction
diff --git a/packages/instant/src/index.umd.ts b/packages/instant/src/index.umd.ts
index dabd45cae..77bdb66e1 100644
--- a/packages/instant/src/index.umd.ts
+++ b/packages/instant/src/index.umd.ts
@@ -7,8 +7,10 @@ import { ZeroExInstant, ZeroExInstantProps } from './index';
import { assert } from './util/assert';
export const render = (props: ZeroExInstantProps, selector: string = DEFAULT_ZERO_EX_CONTAINER_SELECTOR) => {
- assert.isHexString('assetData', props.assetData);
- assert.isValidLiquiditySource('liquiditySource', props.liquiditySource);
+ assert.isValidOrderSource('orderSource', props.orderSource);
+ if (!_.isUndefined(props.defaultSelectedAssetData)) {
+ assert.isHexString('defaultSelectedAssetData', props.defaultSelectedAssetData);
+ }
if (!_.isUndefined(props.additionalAssetMetaDataMap)) {
assert.isValidAssetMetaDataMap('additionalAssetMetaDataMap', props.additionalAssetMetaDataMap);
}
diff --git a/packages/instant/src/redux/actions.ts b/packages/instant/src/redux/actions.ts
index bfae68e2b..eadd8b42c 100644
--- a/packages/instant/src/redux/actions.ts
+++ b/packages/instant/src/redux/actions.ts
@@ -4,7 +4,7 @@ import * as _ from 'lodash';
import { BigNumberInput } from '../util/big_number_input';
-import { ActionsUnion, OrderState } from '../types';
+import { ActionsUnion, Asset, OrderState } from '../types';
export interface PlainAction<T extends string> {
type: T;
@@ -28,6 +28,7 @@ export enum ActionTypes {
UPDATE_BUY_ORDER_STATE = 'UPDATE_BUY_ORDER_STATE',
UPDATE_LATEST_BUY_QUOTE = 'UPDATE_LATEST_BUY_QUOTE',
UPDATE_SELECTED_ASSET = 'UPDATE_SELECTED_ASSET',
+ SET_AVAILABLE_ASSETS = 'SET_AVAILABLE_ASSETS',
SET_QUOTE_REQUEST_STATE_PENDING = 'SET_QUOTE_REQUEST_STATE_PENDING',
SET_QUOTE_REQUEST_STATE_FAILURE = 'SET_QUOTE_REQUEST_STATE_FAILURE',
SET_ERROR_MESSAGE = 'SET_ERROR_MESSAGE',
@@ -43,6 +44,7 @@ export const actions = {
updateBuyOrderState: (orderState: OrderState) => createAction(ActionTypes.UPDATE_BUY_ORDER_STATE, orderState),
updateLatestBuyQuote: (buyQuote?: BuyQuote) => createAction(ActionTypes.UPDATE_LATEST_BUY_QUOTE, buyQuote),
updateSelectedAsset: (assetData?: string) => createAction(ActionTypes.UPDATE_SELECTED_ASSET, assetData),
+ setAvailableAssets: (availableAssets: Asset[]) => createAction(ActionTypes.SET_AVAILABLE_ASSETS, availableAssets),
setQuoteRequestStatePending: () => createAction(ActionTypes.SET_QUOTE_REQUEST_STATE_PENDING),
setQuoteRequestStateFailure: () => createAction(ActionTypes.SET_QUOTE_REQUEST_STATE_FAILURE),
setErrorMessage: (errorMessage: string) => createAction(ActionTypes.SET_ERROR_MESSAGE, errorMessage),
diff --git a/packages/instant/src/redux/async_data.ts b/packages/instant/src/redux/async_data.ts
index 4ed89bdc3..f8dbe9fd4 100644
--- a/packages/instant/src/redux/async_data.ts
+++ b/packages/instant/src/redux/async_data.ts
@@ -1,22 +1,33 @@
+import * as _ from 'lodash';
+
import { BIG_NUMBER_ZERO } from '../constants';
+import { assetUtils } from '../util/asset';
import { coinbaseApi } from '../util/coinbase_api';
-import { ActionTypes } from './actions';
-
+import { actions } from './actions';
import { Store } from './store';
export const asyncData = {
- fetchAndDispatchToStore: async (store: Store) => {
+ fetchEthPriceAndDispatchToStore: async (store: Store) => {
let ethUsdPrice = BIG_NUMBER_ZERO;
try {
ethUsdPrice = await coinbaseApi.getEthUsdPrice();
} catch (e) {
// ignore
} finally {
- store.dispatch({
- type: ActionTypes.UPDATE_ETH_USD_PRICE,
- data: ethUsdPrice,
- });
+ store.dispatch(actions.updateEthUsdPrice(ethUsdPrice));
+ }
+ },
+ fetchAvailableAssetDatasAndDispatchToStore: async (store: Store) => {
+ const { assetBuyer, assetMetaDataMap, network } = store.getState();
+ if (!_.isUndefined(assetBuyer)) {
+ try {
+ const assetDatas = await assetBuyer.getAvailableAssetDatasAsync();
+ const assets = assetUtils.createAssetsFromAssetDatas(assetDatas, assetMetaDataMap, network);
+ store.dispatch(actions.setAvailableAssets(assets));
+ } catch (e) {
+ // ignore
+ }
}
},
};
diff --git a/packages/instant/src/redux/reducer.ts b/packages/instant/src/redux/reducer.ts
index dd9403052..c0a8c1771 100644
--- a/packages/instant/src/redux/reducer.ts
+++ b/packages/instant/src/redux/reducer.ts
@@ -24,6 +24,7 @@ export interface State {
assetBuyer?: AssetBuyer;
assetMetaDataMap: ObjectMap<AssetMetaData>;
selectedAsset?: Asset;
+ availableAssets: Asset[];
selectedAssetAmount?: BigNumberInput;
buyOrderState: OrderState;
ethUsdPrice?: BigNumber;
@@ -36,6 +37,7 @@ export interface State {
export const INITIAL_STATE: State = {
network: Network.Mainnet,
selectedAssetAmount: undefined,
+ availableAssets: [],
assetMetaDataMap,
buyOrderState: { processState: OrderProcessState.NONE },
ethUsdPrice: undefined,
@@ -109,7 +111,7 @@ export const reducer = (state: State = INITIAL_STATE, action: Action): State =>
const newSelectedAssetData = action.data;
let newSelectedAsset: Asset | undefined;
if (!_.isUndefined(newSelectedAssetData)) {
- newSelectedAsset = assetUtils.createAssetFromAssetData(
+ newSelectedAsset = assetUtils.createAssetFromAssetDataOrThrow(
newSelectedAssetData,
state.assetMetaDataMap,
state.network,
@@ -127,6 +129,11 @@ export const reducer = (state: State = INITIAL_STATE, action: Action): State =>
buyOrderState: { processState: OrderProcessState.NONE },
selectedAssetAmount: undefined,
};
+ case ActionTypes.SET_AVAILABLE_ASSETS:
+ return {
+ ...state,
+ availableAssets: action.data,
+ };
default:
return state;
}
diff --git a/packages/instant/src/util/assert.ts b/packages/instant/src/util/assert.ts
index 584d3d4b1..1267a1d23 100644
--- a/packages/instant/src/util/assert.ts
+++ b/packages/instant/src/util/assert.ts
@@ -8,12 +8,12 @@ import { AssetMetaData } from '../types';
export const assert = {
...sharedAssert,
- isValidLiquiditySource(variableName: string, liquiditySource: string | SignedOrder[]): void {
- if (_.isString(liquiditySource)) {
- sharedAssert.isUri(variableName, liquiditySource);
+ isValidOrderSource(variableName: string, orderSource: string | SignedOrder[]): void {
+ if (_.isString(orderSource)) {
+ sharedAssert.isUri(variableName, orderSource);
return;
}
- sharedAssert.doesConformToSchema(variableName, liquiditySource, schemas.signedOrdersSchema);
+ sharedAssert.doesConformToSchema(variableName, orderSource, schemas.signedOrdersSchema);
},
isValidAssetMetaDataMap(variableName: string, metaDataMap: ObjectMap<AssetMetaData>): void {
_.forEach(metaDataMap, (metaData, assetData) => {
diff --git a/packages/instant/src/util/asset.ts b/packages/instant/src/util/asset.ts
index 630103c7b..0576a7b60 100644
--- a/packages/instant/src/util/asset.ts
+++ b/packages/instant/src/util/asset.ts
@@ -5,7 +5,31 @@ import { assetDataNetworkMapping } from '../data/asset_data_network_mapping';
import { Asset, AssetMetaData, ERC20Asset, Network, ZeroExInstantError } from '../types';
export const assetUtils = {
- createAssetFromAssetData: (
+ createAssetsFromAssetDatas: (
+ assetDatas: string[],
+ assetMetaDataMap: ObjectMap<AssetMetaData>,
+ network: Network,
+ ): Asset[] => {
+ const arrayOfAssetOrUndefined = _.map(assetDatas, assetData =>
+ assetUtils.createAssetFromAssetDataIfExists(assetData, assetMetaDataMap, network),
+ );
+ return _.compact(arrayOfAssetOrUndefined);
+ },
+ createAssetFromAssetDataIfExists: (
+ assetData: string,
+ assetMetaDataMap: ObjectMap<AssetMetaData>,
+ network: Network,
+ ): Asset | undefined => {
+ const metaData = assetUtils.getMetaDataIfExists(assetData, assetMetaDataMap, network);
+ if (_.isUndefined(metaData)) {
+ return;
+ }
+ return {
+ assetData,
+ metaData,
+ };
+ },
+ createAssetFromAssetDataOrThrow: (
assetData: string,
assetMetaDataMap: ObjectMap<AssetMetaData>,
network: Network,
@@ -16,6 +40,17 @@ export const assetUtils = {
};
},
getMetaDataOrThrow: (assetData: string, metaDataMap: ObjectMap<AssetMetaData>, network: Network): AssetMetaData => {
+ const metaDataIfExists = assetUtils.getMetaDataIfExists(assetData, metaDataMap, network);
+ if (_.isUndefined(metaDataIfExists)) {
+ throw new Error(ZeroExInstantError.AssetMetaDataNotAvailable);
+ }
+ return metaDataIfExists;
+ },
+ getMetaDataIfExists: (
+ assetData: string,
+ metaDataMap: ObjectMap<AssetMetaData>,
+ network: Network,
+ ): AssetMetaData | undefined => {
let mainnetAssetData: string | undefined = assetData;
if (network !== Network.Mainnet) {
const mainnetAssetDataIfExists = assetUtils.getAssociatedAssetDataIfExists(assetData, network);
@@ -24,11 +59,11 @@ export const assetUtils = {
mainnetAssetData = mainnetAssetDataIfExists || assetData;
}
if (_.isUndefined(mainnetAssetData)) {
- throw new Error(ZeroExInstantError.AssetMetaDataNotAvailable);
+ return;
}
const metaData = metaDataMap[mainnetAssetData];
if (_.isUndefined(metaData)) {
- throw new Error(ZeroExInstantError.AssetMetaDataNotAvailable);
+ return;
}
return metaData;
},