Skip to content

Commit

Permalink
chore: update erc777 realtime balance
Browse files Browse the repository at this point in the history
  • Loading branch information
Envoy-VC committed Jun 30, 2024
1 parent 771ea2f commit 7ef4672
Show file tree
Hide file tree
Showing 5 changed files with 171 additions and 82 deletions.
122 changes: 105 additions & 17 deletions apps/www/src/app/dashboard/_components/erc777-balance.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -7,25 +7,29 @@ import React, { useEffect, useState } from 'react';
import { useEthers } from '~/lib/hooks/use-ethers';

import { ChainNames } from '~/lib/chains';
import { truncate } from '~/lib/utils';
import { errorHandler, truncate } from '~/lib/utils';

import { type IRequestData } from '@requestnetwork/types/dist/client-types';
import sfMetadata from '@superfluid-finance/metadata';
import { Framework } from '@superfluid-finance/sdk-core';
import { useQuery } from '@tanstack/react-query';
import { BigNumber } from 'bignumber.js';
import StreamGIF from 'public/stream.gif';
import { toast } from 'sonner';

import { Button } from '~/components/ui/button';
import { Input } from '~/components/ui/input';
import { Skeleton } from '~/components/ui/skeleton';

interface Erc777BalanceProps {
request: IRequestData;
}

export const Erc777Balance = ({ request }: Erc777BalanceProps) => {
const { provider } = useEthers();
const { provider, signer } = useEthers();
const payeeAddress = request.payee?.value ?? '0x0';
const payerAddress = request.payer?.value ?? '0x0';
const [value, setValue] = useState<number>(0);

const [payerBalance, setPayerBalance] = useState<BigNumber>(BigNumber(0));
const [payeeBalance, setPayeeBalance] = useState<BigNumber>(BigNumber(0));
Expand All @@ -38,8 +42,8 @@ export const Erc777Balance = ({ request }: Erc777BalanceProps) => {
ChainNames.find((c) => c.id === request.currencyInfo.network)?.icon ??
'ethereum';

const { data, refetch } = useQuery({
enabled: false,
const { data, refetch, isPending } = useQuery({
enabled: Boolean(provider) && Boolean(network),
queryKey: [
'erc777-balance',
payeeAddress,
Expand Down Expand Up @@ -72,16 +76,33 @@ export const Erc777Balance = ({ request }: Erc777BalanceProps) => {
providerOrSigner: provider,
});

setPayerBalance(BigNumber(payerBalance).dividedBy(1e18));
setPayeeBalance(BigNumber(payeeBalance).dividedBy(1e18));
setValue(Math.abs(Number(flowRate.flowRate)));

const precision = 19 - Math.log10(Math.abs(Number(flowRate.flowRate)));

const b1 = BigNumber(
BigNumber(payerBalance).dividedBy(1e18).toFixed(precision)
);
const b2 = BigNumber(
BigNumber(payeeBalance).dividedBy(1e18).toFixed(precision)
);

setPayerBalance(b1);
setPayeeBalance(b2);

console.log({
framework: sf,
superToken,
precision,
flowRate,
payeeBalance,
payerBalance,
});

return {
framework: sf,
superToken,
precision,
flowRate,
payeeBalance,
payerBalance,
Expand All @@ -94,11 +115,11 @@ export const Erc777Balance = ({ request }: Erc777BalanceProps) => {
if (!data) return;
if (payeeBalance.isEqualTo(0) || payerBalance.isEqualTo(0)) return;

const multiplier = BigNumber(data.flowRate.flowRate).dividedBy(1e19);
const rate = BigNumber(data.flowRate.flowRate).dividedBy(1e19);

const interval = setInterval(() => {
const updatedPayeeBalance = payeeBalance.minus(multiplier);
const updatedPayerBalance = payerBalance.plus(multiplier);
const updatedPayeeBalance = payeeBalance.minus(rate);
const updatedPayerBalance = payerBalance.plus(rate);

setPayerBalance(updatedPayerBalance);
setPayeeBalance(updatedPayeeBalance);
Expand All @@ -123,7 +144,13 @@ export const Erc777Balance = ({ request }: Erc777BalanceProps) => {
src={`https://icons.llamao.fi/icons/chains/rsz_${chainLogo}?w=512&h=512`}
width={64}
/>
<div>0.000000003417126</div>
<div>
{isPending ? (
<Skeleton className='h-[64px] w-[400px] rounded-xl' />
) : (
<div>{payeeBalance.toFixed(data?.precision ?? 18)}</div>
)}
</div>
<div className='text-[#01A261]'>ETHx</div>
</div>
<div className='flex w-full max-w-3xl flex-row items-end py-8'>
Expand Down Expand Up @@ -165,14 +192,75 @@ export const Erc777Balance = ({ request }: Erc777BalanceProps) => {
</div>
</div>
</div>
<div className='flex flex-row items-center gap-2 text-lg font-semibold text-neutral-800'>
Flow Rate:{' '}
{isPending ? (
<Skeleton className='h-6 w-32' />
) : (
<div className='flex flex-row items-center gap-2'>
<Input
className='w-32'
value={value}
onChange={(e) => setValue(Number(e.target.value))}
/>
wei
<Button
className=''
variant='secondary'
onClick={async () => {
const id = toast.loading('Updating flow rate...');
try {
if (value === Math.abs(Number(data?.flowRate.flowRate))) {
throw new Error('Flow rate is already set to this value');
}
if (!data) {
throw new Error('Superfluid framework not initialized');
}
if (!signer) {
throw new Error('Connect wallet to update flow rate');
}
const operation = data.superToken.updateFlow({
flowRate: String(value),
sender: payerAddress,
receiver: payeeAddress,
});

const batchCall = data.framework.batchCall([operation]);
const operationStructArray = await Promise.all(
batchCall.getOperationStructArrayPromises
);
const txData =
batchCall.host.contract.interface.encodeFunctionData(
'batchCall',
[operationStructArray]
);

const params = {
data: txData,
to: data.framework.host.contract.address,
value: 0,
};

const tx = await signer.sendTransaction(params);
const receipt = await tx.wait(2);

toast.success('Flow rate updated', {
id,
description: receipt.transactionHash,
});

await refetch();
} catch (error) {
toast.error(errorHandler(error), { id });
}
}}
>
Update
</Button>
</div>
)}{' '}
</div>
</div>
<Button
onClick={() => {
void refetch();
}}
>
Refetch
</Button>
</div>
);
};
77 changes: 40 additions & 37 deletions apps/www/src/app/dashboard/_components/payer.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -5,7 +5,7 @@ import React, { useMemo, useState } from 'react';
import { getAllCurrencies } from '~/lib/currency';
import { useRequest } from '~/lib/hooks';

import { type Request } from '@requestnetwork/request-client.js';
import { type Request, Types } from '@requestnetwork/request-client.js';
import { RequestLogicTypes } from '@requestnetwork/types';
import { formatUnits, parseUnits } from 'viem';

Expand Down Expand Up @@ -51,44 +51,47 @@ export const Payer = ({ request }: PayerProps) => {
<div className='flex flex-col gap-2 py-6'>
<div className='flex flex-col gap-2'>
<div className='text-lg font-semibold text-neutral-700'>Pay Amount</div>
<div className='flex max-w-xl flex-row items-center gap-2'>
<Button
className=''
variant='outline'
onClick={() => setPayAmount(1000)}
>
Max
</Button>
<Slider
className='w-full'
defaultValue={[0]}
step={1}
value={[payAmount]}
max={Number(
formatUnits(
BigInt(
Number(requestData.expectedAmount) -
Number(requestData.balance?.balance ?? 0)
),
currency?.decimals ?? 18
)
)}
onValueChange={(v) => {
if (v[0]) {
setPayAmount(v[0]);
}
}}
/>
<div className='flex w-full flex-row items-center gap-2 text-base font-medium text-neutral-600'>
<Input
className='w-[6rem] border-none'
type='number'
value={payAmount}
onChange={(e) => setPayAmount(Number(e.target.value))}
{requestData.currencyInfo.type !==
Types.RequestLogic.CURRENCY.ERC777 && (
<div className='flex max-w-xl flex-row items-center gap-2'>
<Button
className=''
variant='outline'
onClick={() => setPayAmount(1000)}
>
Max
</Button>
<Slider
className='w-full'
defaultValue={[0]}
step={0.00001}
value={[payAmount]}
max={Number(
formatUnits(
BigInt(
Number(requestData.expectedAmount) -
Number(requestData.balance?.balance ?? 0)
),
currency?.decimals ?? 18
)
)}
onValueChange={(v) => {
if (v[0]) {
setPayAmount(v[0]);
}
}}
/>
{currency?.symbol}
<div className='flex w-full flex-row items-center gap-2 text-base font-medium text-neutral-600'>
<Input
className='w-[6rem] border-none'
type='number'
value={payAmount}
onChange={(e) => setPayAmount(Number(e.target.value))}
/>
{currency?.symbol}
</div>
</div>
</div>
)}
<Button className='w-fit' onClick={onPay}>
Pay
</Button>
Expand Down
48 changes: 25 additions & 23 deletions apps/www/src/app/dashboard/invoice/[id]/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -99,33 +99,35 @@ const InvoicePage = ({ params: { id } }: Params) => {
Download
</Button>

<div className='flex flex-row items-center gap-2'>
<div className='text-base font-semibold text-neutral-700'>
Payment Status:{' '}
</div>
<div className='text-base font-semibold text-neutral-700'>
{isComplete ? (
<div className='flex flex-row items-center gap-2'>
<CircleCheckBig className='h-6 w-6 text-green-500' />
Completed
</div>
) : (
<div className='flex flex-row items-center gap-2'>
{requestData.currencyInfo.type !== Types.RequestLogic.CURRENCY.ERC777 && (
<div className='flex flex-row items-center gap-2'>
<div className='text-base font-semibold text-neutral-700'>
Payment Status:{' '}
</div>
<div className='text-base font-semibold text-neutral-700'>
{isComplete ? (
<div className='flex flex-row items-center gap-2'>
<div className='w-24 rounded-md border border-neutral-300'>
<div
className='h-3 rounded-md bg-yellow-500'
style={{ width: `${progress}%` }}
/>
</div>
<div className='text-sm font-medium text-neutral-500'>
{progress}%
<CircleCheckBig className='h-6 w-6 text-green-500' />
Completed
</div>
) : (
<div className='flex flex-row items-center gap-2'>
<div className='flex flex-row items-center gap-2'>
<div className='w-24 rounded-md border border-neutral-300'>
<div
className='h-3 rounded-md bg-yellow-500'
style={{ width: `${progress}%` }}
/>
</div>
<div className='text-sm font-medium text-neutral-500'>
{progress}%
</div>
</div>
</div>
</div>
)}
)}
</div>
</div>
</div>
)}
{userType() === 'payer' ? <Payer request={request} /> : null}
</div>
);
Expand Down
4 changes: 0 additions & 4 deletions apps/www/src/lib/currency.ts
Original file line number Diff line number Diff line change
Expand Up @@ -53,10 +53,6 @@ export const getAllCurrencies = () => {
return [...filtered, ...toAdd];
};

export const getCurrencyManager = () => {
return new CurrencyManager(getAllCurrencies());
};

export function getCurrenciesForType(
type: RequestLogicTypes.CURRENCY
): CurrencyDefinition<CurrencyInput>[];
Expand Down
2 changes: 1 addition & 1 deletion apps/www/src/lib/hooks/use-request.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -2,11 +2,11 @@ import { useMemo } from 'react';

import {
approveErc20,
encodePayErc777StreamRequest,
hasErc20Approval,
payRequest,
prepareApproveErc20,
} from '@requestnetwork/payment-processor';
import { encodePayErc777StreamRequest } from '@requestnetwork/payment-processor';
import { validateRequest } from '@requestnetwork/payment-processor/dist/payment/utils';
import { RequestNetwork, Types } from '@requestnetwork/request-client.js';
import {
Expand Down

0 comments on commit 7ef4672

Please sign in to comment.