Skip to content

Commit

Permalink
feat: Multi-callee support for the frontend (#498)
Browse files Browse the repository at this point in the history
  • Loading branch information
aomafarag authored Nov 7, 2022
1 parent 24a1932 commit cbf5727
Show file tree
Hide file tree
Showing 7 changed files with 262 additions and 45 deletions.
24 changes: 12 additions & 12 deletions core/src/auctions.ts
Original file line number Diff line number Diff line change
Expand Up @@ -86,43 +86,42 @@ export const enrichMarketDataRecordsWithValues = async function (
for (const marketId in marketDataRecords) {
let marketData = marketDataRecords[marketId];
// enrich with values dependent on marketUnitPrice
if (marketData.marketUnitPrice.isNaN()) {
let marketUnitPrice = marketData.marketUnitPrice;
if (marketUnitPrice.isNaN()) {
enrichedMarketDataRecords = {
...enrichedMarketDataRecords,
[marketId]: { ...marketData },
};
continue;
}
marketUnitPrice = marketUnitPrice.plus(exchangeFeePerUnitDAI);
marketData = {
...marketData,
marketUnitPrice: marketData.marketUnitPrice.plus(exchangeFeePerUnitDAI),
marketUnitPrice,
marketUnitPriceToUnitPriceRatio: auction.approximateUnitPrice
.minus(marketData.marketUnitPrice)
.dividedBy(marketData.marketUnitPrice),
.minus(marketUnitPrice)
.dividedBy(marketUnitPrice),
...exchangeFees,
transactionGrossProfit: calculateTransactionGrossProfit(
marketData.marketUnitPrice,
marketUnitPrice,
amount,
auction.approximateUnitPrice
),
};
// enrich with values dependent on fees
if (marketData.transactionGrossProfit && auction.combinedSwapFeesDAI) {
const transactionGrossProfit = marketData.transactionGrossProfit;
marketData = {
...marketData,
transactionNetProfit: marketData.transactionGrossProfit.minus(auction.combinedSwapFeesDAI),
transactionNetProfit: transactionGrossProfit.minus(auction.combinedSwapFeesDAI),
};
}
// enrich with values dependent on currentDate
try {
const currentDate = await getNetworkDate(auction.network);
marketData = {
...marketData,
transactionGrossProfitDate: calculateTransactionGrossProfitDate(
auction,
marketData.marketUnitPrice,
currentDate
),
transactionGrossProfitDate: calculateTransactionGrossProfitDate(auction, marketUnitPrice, currentDate),
};
} catch {}
enrichedMarketDataRecords = {
Expand Down Expand Up @@ -159,13 +158,14 @@ export const enrichAuctionWithMarketDataRecords = async function (
const transactionNetProfit = enrichedMarketDataRecords[suggestedMarketId].transactionNetProfit;
return {
...auction,
collateralToCoverDebt,
suggestedMarketId,
marketUnitPrice,
marketUnitPriceToUnitPriceRatio,
transactionGrossProfit,
transactionGrossProfitDate,
transactionNetProfit: transactionNetProfit ? transactionNetProfit : new BigNumber(NaN),
marketDataRecords,
marketDataRecords: enrichedMarketDataRecords,
};
} catch (error: any) {
// since it's expected that some collaterals are not tradable on some networks
Expand Down
2 changes: 1 addition & 1 deletion core/src/calleeFunctions/index.ts
Original file line number Diff line number Diff line change
Expand Up @@ -108,7 +108,7 @@ export const getBestMarketId = async function (marketDataRecords: Record<string,
if (b[1].marketUnitPrice.isNaN()) {
return -1;
}
return a[1].marketUnitPrice.minus(b[1].marketUnitPrice).toNumber();
return a[1].marketUnitPrice.minus(b[1].marketUnitPrice).multipliedBy(-1).toNumber();
});
return marketDataRecordsSorted[0][0];
};
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,11 @@
type="error"
/>
<Alert v-if="auctionTransaction.isFinished" message="This auction is finished" type="error" />
<CollateralAuctionSwapTransactionTable :auction-transaction="auctionTransaction" class="mt-4" />
<CollateralAuctionSwapTransactionTable
:auction-transaction="auctionTransaction"
:market-id.sync="currentMarketId"
class="mt-4"
/>
<TextBlock class="TextBlock mt-4 mb-8">
Please note, the transaction fee is a suggested value based on the current gas prices on the market; the
Transaction Net Profit is also approximate, since it is extrapolated from the exchange rates and may change
Expand Down Expand Up @@ -87,7 +91,7 @@
@execute="
$emit('execute', {
id: auctionTransaction.id,
marketId: auctionTransaction.suggestedMarketId,
marketId: marketSuggestionOrSelection,
alternativeDestinationAddress: $event,
})
"
Expand Down Expand Up @@ -157,6 +161,7 @@ export default Vue.extend({
},
data() {
return {
currentMarketId: '',
isWalletConnectedCheck: false,
isWalletDAIAuthorizationCheckPassed: false,
isWalletCollateralAuthorizationCheckPassed: false,
Expand All @@ -183,6 +188,9 @@ export default Vue.extend({
}
return fees;
},
marketSuggestionOrSelection(): string | undefined {
return this.currentMarketId || this.auctionTransaction.suggestedMarketId;
},
},
});
</script>
Original file line number Diff line number Diff line change
Expand Up @@ -21,21 +21,12 @@
<span class="uppercase">{{ auctionTransaction.collateralSymbol }}</span>
</div>
</div>
<div class="flex w-full justify-between">
<div>Price On Uniswap</div>
<div class="RightInfo">
<template v-if="auctionTransaction.isActive && auctionTransaction.marketUnitPrice">
<FormatCurrency :value="auctionTransaction.marketUnitPrice" currency="DAI" /> per
<span class="uppercase">{{ auctionTransaction.collateralSymbol }}</span>
</template>
<span v-else class="opacity-50">Unknown</span>
</div>
</div>
<MarketPriceSelection :auction-transaction="auctionTransaction" :market-id.sync="currentMarketId" />
<div class="flex w-full justify-between">
<div>Market Difference</div>
<div class="RightInfo">
<template v-if="auctionTransaction.isActive && auctionTransaction.marketUnitPriceToUnitPriceRatio">
<FormatMarketValue :value="auctionTransaction.marketUnitPriceToUnitPriceRatio" />
<template v-if="auctionTransaction.isActive && marketUnitPriceToUnitPriceRatio">
<FormatMarketValue :value="marketUnitPriceToUnitPriceRatio" />
</template>
<span v-else class="opacity-50">Unknown</span>
</div>
Expand All @@ -50,9 +41,9 @@
<div>Transaction Gross Profit</div>
<div class="RightInfo">
<FormatCurrency
v-if="auctionTransaction.transactionGrossProfit"
v-if="transactionGrossProfit"
show-sign
:value="auctionTransaction.transactionGrossProfit"
:value="transactionGrossProfit"
currency="DAI"
/>
<span v-else class="opacity-50">Unknown</span>
Expand Down Expand Up @@ -84,9 +75,9 @@
<div class="font-extrabold">Transaction Net Profit</div>
<div class="RightInfo">
<FormatCurrency
v-if="auctionTransaction.transactionNetProfit"
v-if="transactionNetProfit"
show-sign
:value="auctionTransaction.transactionNetProfit"
:value="transactionNetProfit"
currency="DAI"
class="font-extrabold"
/>
Expand All @@ -97,20 +88,23 @@
</template>
<script lang="ts">
import Vue from 'vue';
import BigNumber from 'bignumber.js';
import PriceDropAnimation from '~/components/auction/collateral/PriceDropAnimation.vue';
import FormatCurrency from '~/components/common/formatters/FormatCurrency.vue';
import MarketPriceSelection from '~/components/auction/collateral/MarketPriceSelection.vue';
import TimeTillProfitable from '~/components/auction/collateral/TimeTillProfitable.vue';
import TimeTill from '~/components/common/formatters/TimeTill.vue';
import FormatCurrency from '~/components/common/formatters/FormatCurrency.vue';
import FormatMarketValue from '~/components/common/formatters/FormatMarketValue.vue';
import TextBlock from '~/components/common/other/TextBlock.vue';
import { AuctionTransaction } from '~/../core/src/types';
export default Vue.extend({
components: {
PriceDropAnimation,
FormatCurrency,
MarketPriceSelection,
TextBlock,
TimeTill,
FormatCurrency,
FormatMarketValue,
TimeTillProfitable,
},
Expand All @@ -119,6 +113,40 @@ export default Vue.extend({
type: Object as Vue.PropType<AuctionTransaction>,
required: true,
},
marketId: {
type: String,
default: '',
},
},
data() {
return {
currentMarketId: '',
};
},
computed: {
marketUnitPriceToUnitPriceRatio(): BigNumber | undefined {
if (!this.currentMarketId || !this.auctionTransaction.marketDataRecords) {
return this.auctionTransaction.marketUnitPriceToUnitPriceRatio;
}
return this.auctionTransaction.marketDataRecords[this.currentMarketId].marketUnitPriceToUnitPriceRatio;
},
transactionGrossProfit(): BigNumber | undefined {
if (!this.currentMarketId || !this.auctionTransaction.marketDataRecords) {
return this.auctionTransaction.transactionGrossProfit;
}
return this.auctionTransaction.marketDataRecords[this.currentMarketId].transactionGrossProfit;
},
transactionNetProfit(): BigNumber | undefined {
if (!this.currentMarketId || !this.auctionTransaction.marketDataRecords) {
return this.auctionTransaction.transactionNetProfit;
}
return this.auctionTransaction.marketDataRecords[this.currentMarketId].transactionNetProfit;
},
},
watch: {
currentMarketId(): void {
this.$emit('update:marketId', this.currentMarketId);
},
},
});
</script>
Expand Down
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
import { storiesOf } from '@storybook/vue';
import MarketPriceSelection from './MarketPriceSelection';
import { generateFakeAuctionTransaction } from '~/helpers/generateFakeAuction.ts';

const fakeAuctionTransaction = generateFakeAuctionTransaction();

const common = {
components: {
MarketPriceSelection,
},
data: () => ({
auctionTransaction: fakeAuctionTransaction,
marketId: '',
}),
template: `<MarketPriceSelection :auction-transaction="auctionTransaction" :market-id.sync="marketId" />`,
};

storiesOf('Auction/Collateral/MarketPriceSelection', module).add('Default', () => ({ ...common }));
120 changes: 120 additions & 0 deletions frontend/components/auction/collateral/MarketPriceSelection.vue
Original file line number Diff line number Diff line change
@@ -0,0 +1,120 @@
<template>
<div>
<div class="flex justify-between">
<button class="Title" type="button" @click="isExpanded = !isExpanded">
<Icon v-if="!isExpanded" type="caret-right" class="Icon" />
<Icon v-else type="caret-down" class="Icon" />
Market Unit Price
<span class="text-gray-300">({{ suggestionOrSelection }})</span>
</button>
<div v-show="!isExpanded">
<FormatCurrency :value="marketUnitPrice" currency="DAI" /> per
<span class="uppercase">{{ auctionTransaction.collateralSymbol }}</span>
</div>
</div>
<CollapseTransition>
<div v-show="isExpanded" class="Content overflow-x-auto">
<table class="table-auto">
<tbody>
<tr v-for="callee in callees" :key="callee[0]">
<td class="pr-2 whitespace-nowrap">{{ callee[0] }}</td>
<td class="pr-2 whitespace-nowrap">
<span v-for="currency in callee[1].route" :key="currency"
>{{ currency }} &#8594;
</span>
DAI
</td>
<td class="w-full text-right whitespace-nowrap">
<div v-if="callee[1].marketUnitPrice && !callee[1].marketUnitPrice.isNaN()">
<button type="button" @click="$emit('update:marketId', callee[0])">
<span v-if="suggestionOrSelection === callee[0]" class="opacity-50"
>Selected</span
>
<span v-else class="text-green-500">Select</span>
</button>
<span class="pl-1">
<FormatCurrency :value="callee[1].marketUnitPrice" currency="DAI" /> per
<span class="uppercase">{{ auctionTransaction.collateralSymbol }}</span>
</span>
</div>
<div v-else class="opacity-50">Unknown</div>
</td>
</tr>
</tbody>
</table>
</div>
</CollapseTransition>
</div>
</template>

<script lang="ts">
import Vue from 'vue';
import BigNumber from 'bignumber.js';
import { Icon } from 'ant-design-vue';
import CollapseTransition from '@ivanv/vue-collapse-transition';
import { AuctionTransaction, MarketData } from 'auctions-core/src/types';
import FormatCurrency from '~/components/common/formatters/FormatCurrency.vue';
export default Vue.extend({
components: {
Icon,
FormatCurrency,
CollapseTransition,
},
props: {
auctionTransaction: {
type: Object as Vue.PropType<AuctionTransaction>,
required: true,
},
marketId: {
type: String,
default: '',
},
},
data() {
return {
isExpanded: false,
};
},
computed: {
suggestionOrSelection(): string | undefined {
return this.marketId || this.auctionTransaction.suggestedMarketId;
},
marketUnitPrice(): BigNumber | undefined {
if (this.auctionTransaction.marketDataRecords && this.suggestionOrSelection) {
return this.auctionTransaction.marketDataRecords[this.suggestionOrSelection].marketUnitPrice;
}
return undefined;
},
callees(): [string, MarketData][] {
const marketDataRecordsSorted = Object.entries(this.auctionTransaction.marketDataRecords || {});
marketDataRecordsSorted.sort((a, b) => {
// push NaNs to the end
if (a[1].marketUnitPrice.isNaN() && b[1].marketUnitPrice.isNaN()) {
return 1;
}
if (a[1].marketUnitPrice.isNaN()) {
return 1;
}
if (b[1].marketUnitPrice.isNaN()) {
return -1;
}
return a[1].marketUnitPrice.minus(b[1].marketUnitPrice).multipliedBy(-1).toNumber();
});
return marketDataRecordsSorted;
},
},
});
</script>

<style scoped>
.Title {
@apply text-left text-green-500;
}
.Icon {
@apply inline;
}
.Content {
@apply pl-4;
}
</style>
Loading

0 comments on commit cbf5727

Please sign in to comment.