-
Notifications
You must be signed in to change notification settings - Fork 258
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
Use ProviderSupportStore for bityProvider
- Loading branch information
Showing
1 changed file
with
86 additions
and
83 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
|
@@ -18,10 +18,9 @@ import { | |
FiatProviderFactory, | ||
FiatProviderFactoryParams, | ||
FiatProviderGetQuoteParams, | ||
FiatProviderGetTokenId, | ||
FiatProviderQuote | ||
} from '../fiatProviderTypes' | ||
import { addTokenToArray } from '../util/providerUtils' | ||
import { ProviderSupportStore } from './ProviderSupportStore' | ||
|
||
const providerId = 'bity' | ||
const storeId = 'com.bity' | ||
|
@@ -32,11 +31,6 @@ const supportEmail = '[email protected]' | |
const supportedPaymentType: FiatPaymentType = 'sepa' | ||
const partnerFee = 0.005 | ||
|
||
const allowedCurrencyCodes: Record<FiatDirection, FiatProviderAssetMap> = { | ||
buy: { providerId, fiat: {}, crypto: {} }, | ||
sell: { providerId, fiat: {}, crypto: {} } | ||
} | ||
|
||
const noKycCurrencyCodes: Record<FiatDirection, FiatProviderAssetMap> = { | ||
buy: { | ||
providerId, | ||
|
@@ -58,38 +52,38 @@ const noKycCurrencyCodes: Record<FiatDirection, FiatProviderAssetMap> = { | |
} | ||
} | ||
|
||
const allowedCountryCodes: { readonly [code: string]: boolean } = { | ||
AT: true, | ||
BE: true, | ||
BG: true, | ||
CH: true, | ||
CZ: true, | ||
DK: true, | ||
EE: true, | ||
FI: true, | ||
FR: true, | ||
DE: true, | ||
GR: true, | ||
HU: true, | ||
IE: true, // Ireland | ||
IT: true, | ||
LV: true, | ||
LT: true, | ||
LU: true, | ||
NL: true, | ||
PL: true, | ||
PT: true, | ||
RO: true, | ||
SK: true, | ||
SI: true, | ||
ES: true, | ||
SE: true, | ||
HR: true, | ||
LI: true, | ||
NO: true, | ||
SM: true, | ||
GB: true | ||
} | ||
const supportedRegionCodes = [ | ||
'AT', | ||
'BE', | ||
'BG', | ||
'CH', | ||
'CZ', | ||
'DK', | ||
'EE', | ||
'FI', | ||
'FR', | ||
'DE', | ||
'GR', | ||
'HU', | ||
'IE', // Ireland | ||
'IT', | ||
'LV', | ||
'LT', | ||
'LU', | ||
'NL', | ||
'PL', | ||
'PT', | ||
'RO', | ||
'SK', | ||
'SI', | ||
'ES', | ||
'SE', | ||
'HR', | ||
'LI', | ||
'NO', | ||
'SM', | ||
'GB' | ||
] | ||
|
||
const CURRENCY_PLUGINID_MAP: StringMap = { | ||
BTC: 'bitcoin', | ||
|
@@ -370,18 +364,30 @@ export const bityProvider: FiatProviderFactory = { | |
const { apiKeys, getTokenId } = params | ||
const clientId = asBityApiKeys(apiKeys).clientId | ||
|
||
const supportedAssets = new ProviderSupportStore(providerId) | ||
|
||
supportedRegionCodes.forEach(region => { | ||
supportedAssets.add.direction('*').region(region) | ||
}) | ||
|
||
const out: FiatProvider = { | ||
providerId, | ||
partnerIcon, | ||
pluginDisplayName, | ||
getSupportedAssets: async ({ direction, paymentTypes }): Promise<FiatProviderAssetMap> => { | ||
getSupportedAssets: async ({ direction, paymentTypes, regionCode }): Promise<FiatProviderAssetMap> => { | ||
if (!supportedAssets.is.direction('*').region(regionCode.countryCode).supported) | ||
throw new FiatProviderError({ providerId, errorType: 'regionRestricted' }) | ||
// Return nothing if 'sepa' is not included in the props | ||
if (!paymentTypes.includes(supportedPaymentType)) throw new FiatProviderError({ providerId, errorType: 'paymentUnsupported' }) | ||
|
||
const response = await fetch(`https://exchange.api.bity.com/v2/currencies`).catch(e => undefined) | ||
if (response == null || !response.ok) { | ||
console.error(`Bity getSupportedAssets response error: ${await response?.text()}`) | ||
return allowedCurrencyCodes[direction] | ||
return supportedAssets.getFiatProviderAssetMap({ | ||
direction, | ||
region: `*`, | ||
payment: supportedPaymentType | ||
}) | ||
} | ||
|
||
const result = await response.json() | ||
|
@@ -390,32 +396,45 @@ export const bityProvider: FiatProviderFactory = { | |
bityCurrencies = asBityCurrencyResponse(result).currencies | ||
} catch (error: any) { | ||
console.error(error) | ||
return allowedCurrencyCodes[direction] | ||
return supportedAssets.getFiatProviderAssetMap({ | ||
direction, | ||
region: `*`, | ||
payment: supportedPaymentType | ||
}) | ||
} | ||
|
||
for (const currency of bityCurrencies) { | ||
let isAddCurrencySuccess = false | ||
if (currency.tags.length === 1 && currency.tags[0] === 'fiat') { | ||
allowedCurrencyCodes[direction].fiat['iso:' + currency.code.toUpperCase()] = currency | ||
isAddCurrencySuccess = true | ||
const fiatCurrencyCode = 'iso:' + currency.code.toUpperCase() | ||
supportedAssets.add.direction(direction).region('*').fiat(fiatCurrencyCode).payment(supportedPaymentType) | ||
supportedAssets.addFiatInfo(fiatCurrencyCode, currency) | ||
} else if (currency.tags.includes('crypto')) { | ||
// Bity reports cryptos with a set of multiple tags such that there is | ||
// overlap, such as USDC being 'crypto', 'ethereum', 'erc20'. | ||
if (currency.tags.includes('erc20') && currency.tags.includes('ethereum')) { | ||
// ETH tokens | ||
addToAllowedCurrencies(direction, getTokenId, 'ethereum', currency, currency.code) | ||
isAddCurrencySuccess = true | ||
} else if (Object.keys(CURRENCY_PLUGINID_MAP).includes(currency.code)) { | ||
// Mainnet currencies | ||
addToAllowedCurrencies(direction, getTokenId, CURRENCY_PLUGINID_MAP[currency.code], currency, currency.code) | ||
isAddCurrencySuccess = true | ||
const pluginId = currency.tags.includes('erc20') && currency.tags.includes('ethereum') ? 'ethereum' : CURRENCY_PLUGINID_MAP[currency.code] | ||
if (pluginId == null) continue | ||
|
||
const tokenId = getTokenId(pluginId, currency.code) | ||
if (tokenId === undefined) continue | ||
|
||
// If token is not in the no-KYC list do not add it | ||
const list = noKycCurrencyCodes[direction].crypto[pluginId] | ||
if (list == null || !list.some(t => t.tokenId === tokenId)) { | ||
continue | ||
} | ||
} | ||
|
||
// Unhandled combination not caught by cleaner. Skip to be safe. | ||
if (!isAddCurrencySuccess) console.log('Unhandled Bity supported currency: ', currency) | ||
const crypto = `${pluginId}:${tokenId}` | ||
supportedAssets.add.direction('*').region('*').fiat('*').payment(supportedPaymentType).crypto(crypto) | ||
supportedAssets.addCryptoInfo(crypto, currency) | ||
} else { | ||
// Unhandled combination not caught by cleaner. Skip to be safe. | ||
console.log('Unhandled Bity supported currency: ', currency) | ||
} | ||
} | ||
|
||
return allowedCurrencyCodes[direction] | ||
const assetMap = supportedAssets.getFiatProviderAssetMap({ direction, region: '*', payment: supportedPaymentType }) | ||
|
||
return assetMap | ||
}, | ||
getQuote: async (params: FiatProviderGetQuoteParams): Promise<FiatProviderQuote> => { | ||
const { | ||
|
@@ -430,12 +449,17 @@ export const bityProvider: FiatProviderFactory = { | |
displayCurrencyCode | ||
} = params | ||
const isBuy = direction === 'buy' | ||
if (!allowedCountryCodes[regionCode.countryCode]) throw new FiatProviderError({ providerId, errorType: 'regionRestricted', displayCurrencyCode }) | ||
if (!paymentTypes.includes(supportedPaymentType)) throw new FiatProviderError({ providerId, errorType: 'paymentUnsupported' }) | ||
|
||
const bityCurrency = allowedCurrencyCodes[direction].crypto[pluginId].find(t => t.tokenId === tokenId) | ||
const cryptoCurrencyObj = asBityCurrency(bityCurrency?.otherInfo) | ||
const fiatCurrencyObj = asBityCurrency(allowedCurrencyCodes[direction].fiat[fiatCurrencyCode]) | ||
if (!supportedAssets.is.direction(direction).region(regionCode.countryCode).supported) | ||
throw new FiatProviderError({ providerId, errorType: 'regionRestricted', displayCurrencyCode }) | ||
if (!supportedAssets.is.direction(direction).region(regionCode.countryCode).fiat('*').payment(supportedPaymentType).supported) | ||
throw new FiatProviderError({ providerId, errorType: 'regionRestricted', displayCurrencyCode }) | ||
|
||
const cryptoOtherInfo = supportedAssets.getCryptoInfo(`${pluginId}:${tokenId}`) | ||
const cryptoCurrencyObj = asBityCurrency(cryptoOtherInfo) | ||
|
||
const fiatOtherInfo = supportedAssets.getFiatInfo(fiatCurrencyCode) | ||
const fiatCurrencyObj = asBityCurrency(fiatOtherInfo) | ||
|
||
if (cryptoCurrencyObj == null || fiatCurrencyObj == null) throw new Error('Bity: Could not query supported currencies') | ||
const cryptoCode = cryptoCurrencyObj.code | ||
|
@@ -639,27 +663,6 @@ export const bityProvider: FiatProviderFactory = { | |
} | ||
} | ||
|
||
const addToAllowedCurrencies = ( | ||
direction: FiatDirection, | ||
getTokenId: FiatProviderGetTokenId, | ||
pluginId: string, | ||
currency: BityCurrency, | ||
currencyCode: string | ||
) => { | ||
if (allowedCurrencyCodes[direction].crypto[pluginId] == null) allowedCurrencyCodes[direction].crypto[pluginId] = [] | ||
const tokenId = getTokenId(pluginId, currencyCode) | ||
if (tokenId === undefined) return | ||
|
||
const tokens = allowedCurrencyCodes[direction].crypto[pluginId] | ||
|
||
// If token is not in the no-KYC list do not add it | ||
const list = noKycCurrencyCodes[direction].crypto[pluginId] | ||
if (list == null || !list.some(t => t.tokenId === tokenId)) { | ||
return | ||
} | ||
addTokenToArray({ tokenId, otherInfo: currency }, tokens) | ||
} | ||
|
||
/** | ||
* Transition to the send scene pre-populted with the payment address from the | ||
* previously opened/approved sell order | ||
|