Skip to content

Commit

Permalink
Merge branch 'develop' of github.com:lidofinance/ethereum-staking-wid…
Browse files Browse the repository at this point in the history
…get into feature/si-1228-return-1inch-to-aggregators
  • Loading branch information
Jeday committed Feb 16, 2024
2 parents 3bf6076 + 347784b commit c1f1cd8
Show file tree
Hide file tree
Showing 44 changed files with 1,232 additions and 1,052 deletions.
2 changes: 1 addition & 1 deletion .github/workflows/ci-ipfs-test-production.yml
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ jobs:
- name: Install node
uses: actions/setup-node@v4
with:
node-version: 16
node-version: 20
cache: 'yarn'
- name: Install dependencies
run: |
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/ci-ipfs-testnet.yml
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,7 @@ jobs:
- name: Install node
uses: actions/setup-node@v4
with:
node-version: 16
node-version: 20
cache: 'yarn'
- name: Install dependencies
run: |
Expand Down
2 changes: 1 addition & 1 deletion .github/workflows/ci-ipfs.yml
Original file line number Diff line number Diff line change
Expand Up @@ -27,7 +27,7 @@ jobs:
- name: Install node
uses: actions/setup-node@v4
with:
node-version: 16
node-version: 20
cache: 'yarn'
- name: Set tag, commit and branch name
if: env.is_create_release == 'true'
Expand Down
4 changes: 2 additions & 2 deletions .github/workflows/tests.yml
Original file line number Diff line number Diff line change
Expand Up @@ -26,7 +26,7 @@ jobs:

- uses: actions/setup-node@v4
with:
node-version: '18'
node-version: 20

- name: Install dependencies
run: yarn install --immutable
Expand All @@ -42,7 +42,7 @@ jobs:
STAND_TYPE: ${{ inputs.stand_type }}
STAND_USER: ${{ secrets.PREVIEW_STAND_HTTP_AUTH_USER }}
STAND_PASSWORD: ${{ secrets.PREVIEW_STAND_HTTP_AUTH_PASSWORD }}

- name: Run tests on testnet/staging
if: ${{ !inputs.on_preview_stand }}
run: yarn test
Expand Down
1 change: 1 addition & 0 deletions .nvmrc
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
20
4 changes: 2 additions & 2 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
# build env
FROM node:16-alpine as build
FROM node:20-alpine as build

WORKDIR /app

Expand All @@ -13,7 +13,7 @@ RUN NODE_NO_BUILD_DYNAMICS=true yarn typechain && yarn build
RUN rm -rf /app/public/runtime && mkdir /app/public/runtime && chown node /app/public/runtime

# final image
FROM node:16-alpine as base
FROM node:20-alpine as base

ARG BASE_PATH=""
ARG SUPPORTED_CHAINS="1"
Expand Down
12 changes: 6 additions & 6 deletions config/tx.ts
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
export const STANDARD_GAS_LIMIT = 21000;
import { BigNumber } from 'ethers';

export const WSTETH_APPROVE_GAS_LIMIT = 78000;
export const WSTETH_APPROVE_GAS_LIMIT = BigNumber.from(78000);

export const WRAP_FROM_ETH_GAS_LIMIT = 100000;
export const WRAP_GAS_LIMIT = 140000;
export const WRAP_GAS_LIMIT_GOERLI = 120000;
export const UNWRAP_GAS_LIMIT = 115000;
export const WRAP_FROM_ETH_GAS_LIMIT = BigNumber.from(100000);
export const WRAP_GAS_LIMIT = BigNumber.from(140000);
export const WRAP_GAS_LIMIT_GOERLI = BigNumber.from(120000);
export const UNWRAP_GAS_LIMIT = BigNumber.from(115000);
2 changes: 1 addition & 1 deletion features/stake/stake-form/stake-form-context/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ export type StakeFormNetworkData = {
};

export type StakeFormValidationContext = {
active: boolean;
isWalletActive: boolean;
stakingLimitLevel: LIMIT_LEVEL;
currentStakeLimit: BigNumber;
gasCost: BigNumber;
Expand Down
61 changes: 14 additions & 47 deletions features/stake/stake-form/stake-form-context/validation.ts
Original file line number Diff line number Diff line change
@@ -1,14 +1,11 @@
import { useMemo } from 'react';
import invariant from 'tiny-invariant';
import { formatEther } from '@ethersproject/units';
import { useWeb3 } from 'reef-knot/web3-react';
import { Zero } from '@ethersproject/constants';

import { validateEtherAmount } from 'shared/hook-form/validation/validate-ether-amount';
import { VALIDATION_CONTEXT_TIMEOUT } from 'features/withdrawals/withdrawals-constants';
import { handleResolverValidationError } from 'shared/hook-form/validation/validation-error';
import { validateBignumberMax } from 'shared/hook-form/validation/validate-bignumber-max';
import { validateStakeLimit } from 'shared/hook-form/validation/validate-stake-limit';
import { awaitWithTimeout } from 'utils/await-with-timeout';
import { useAwaiter } from 'shared/hooks/use-awaiter';

Expand All @@ -18,6 +15,7 @@ import type {
StakeFormNetworkData,
StakeFormValidationContext,
} from './types';
import { validateStakeEth } from 'shared/hook-form/validation/validate-stake-eth';

export const stakeFormValidationResolver: Resolver<
StakeFormInput,
Expand All @@ -33,7 +31,7 @@ export const stakeFormValidationResolver: Resolver<
validateEtherAmount('amount', amount, 'ETH');

const {
active,
isWalletActive,
stakingLimitLevel,
currentStakeLimit,
etherBalance,
Expand All @@ -44,49 +42,18 @@ export const stakeFormValidationResolver: Resolver<
VALIDATION_CONTEXT_TIMEOUT,
);

validateStakeLimit('amount', stakingLimitLevel);

if (active) {
validateBignumberMax(
'amount',
amount,
etherBalance,
`Entered ETH amount exceeds your available balance of ${formatEther(
etherBalance,
)}`,
);

validateBignumberMax(
'amount',
amount,
currentStakeLimit,
`Entered ETH amount exceeds current staking limit of ${formatEther(
currentStakeLimit,
)}`,
);

if (!isMultisig) {
const gasPaddedBalance = etherBalance.sub(gasCost);

validateBignumberMax(
'amount',
Zero,
gasPaddedBalance,
`Ensure you have sufficient ETH to cover the gas cost of ${formatEther(
gasCost,
)}`,
);
validateStakeEth({
formField: 'amount',
amount,
isWalletActive,
stakingLimitLevel,
currentStakeLimit,
etherBalance,
gasCost,
isMultisig,
});

validateBignumberMax(
'amount',
amount,
gasPaddedBalance,
`Enter ETH amount less than ${formatEther(
gasPaddedBalance,
)} to ensure you leave enough ETH for gas fees`,
);
}
} else {
if (!isWalletActive) {
return {
values,
errors: { referral: 'wallet not connected' },
Expand Down Expand Up @@ -114,7 +81,7 @@ export const useStakeFormValidationContext = (
(!active || (etherBalance && gasCost && isMultisig !== undefined))
) {
return {
active,
isWalletActive: active,
stakingLimitLevel: stakingLimitInfo.stakeLimitLevel,
currentStakeLimit: stakingLimitInfo.currentStakeLimit,
// condition above guaranties stubs will only be passed when active = false
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,6 +22,7 @@ import {
import { ClaimFormHelperState, useHelperState } from './use-helper-state';
import { useClaimData } from 'features/withdrawals/contexts/claim-data-context';
import { useTransactionModal } from 'shared/transaction-modal';
import { useWeb3 } from 'reef-knot/web3-react';

type ClaimFormDataContextValueType = {
onSubmit: FormEventHandler<HTMLFormElement>;
Expand All @@ -39,6 +40,7 @@ export const useClaimFormData = () => {

export const ClaimFormProvider: FC<PropsWithChildren> = ({ children }) => {
const { dispatchModalState } = useTransactionModal();
const { active } = useWeb3();
const { data } = useClaimData();

const [shouldReset, setShouldReset] = useState<boolean>(false);
Expand All @@ -49,7 +51,7 @@ export const ClaimFormProvider: FC<PropsWithChildren> = ({ children }) => {
const formObject = useForm<ClaimFormInputType, ClaimFormValidationContext>({
defaultValues: getDefaultValues,
resolver: claimFormValidationResolver,
context: { maxSelectedRequestCount },
context: { maxSelectedRequestCount, isWalletActive: active },
mode: 'onChange',
reValidateMode: 'onChange',
});
Expand Down
1 change: 1 addition & 0 deletions features/withdrawals/claim/claim-form-context/types.ts
Original file line number Diff line number Diff line change
Expand Up @@ -5,6 +5,7 @@ import {

export type ClaimFormValidationContext = {
maxSelectedRequestCount: number;
isWalletActive: boolean;
};

export type ClaimFormInputType = {
Expand Down
12 changes: 11 additions & 1 deletion features/withdrawals/claim/claim-form-context/validation.ts
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ export const claimFormValidationResolver: Resolver<
> = async ({ requests }, context) => {
invariant(context);
try {
const { maxSelectedRequestCount } = context;
const { maxSelectedRequestCount, isWalletActive } = context;
const selectedTokens = requests
.filter((r) => r.checked)
.map((r) => r.status as RequestStatusClaimable);
Expand All @@ -27,6 +27,16 @@ export const claimFormValidationResolver: Resolver<
`Cannot claim more than ${maxSelectedRequestCount} requests at once`,
);

if (!isWalletActive) {
return {
values: {
requests,
selectedTokens,
},
errors: { selectedTokens: 'no wallet connected' },
};
}

return {
values: {
requests,
Expand Down
10 changes: 5 additions & 5 deletions features/withdrawals/claim/form/requests-list/requests-empty.tsx
Original file line number Diff line number Diff line change
@@ -1,11 +1,11 @@
import { useWeb3 } from 'reef-knot/web3-react';

import { EmptyText, WrapperEmpty } from './styles';

export const RequestsEmpty = () => {
const { active } = useWeb3();
type RequestsEmptyProps = {
isWalletConnected?: boolean;
};

if (!active) {
export const RequestsEmpty = ({ isWalletConnected }: RequestsEmptyProps) => {
if (!isWalletConnected) {
return (
<WrapperEmpty>
<EmptyText>Connect wallet to see your withdrawal requests</EmptyText>
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -4,8 +4,10 @@ import { Wrapper } from './styles';
import { RequestsLoader } from './requests-loader';
import { useFieldArray, useFormContext, useFormState } from 'react-hook-form';
import { ClaimFormInputType } from '../../claim-form-context';
import { useWeb3 } from 'reef-knot/web3-react';

export const RequestsList: React.FC = () => {
const { active } = useWeb3();
const { isLoading } = useFormState<ClaimFormInputType>();
const { register } = useFormContext<ClaimFormInputType>();
const { fields } = useFieldArray<ClaimFormInputType, 'requests'>({
Expand All @@ -16,8 +18,8 @@ export const RequestsList: React.FC = () => {
return <RequestsLoader />;
}

if (fields.length === 0) {
return <RequestsEmpty />;
if (!active || fields.length === 0) {
return <RequestsEmpty isWalletConnected={active} />;
}

return (
Expand Down
35 changes: 18 additions & 17 deletions features/withdrawals/hooks/useEthAmountByStethWsteth.ts
Original file line number Diff line number Diff line change
@@ -1,29 +1,30 @@
import { parseEther } from '@ethersproject/units';
import { BigNumber } from 'ethers';
import { useMemo } from 'react';
import { useContractSWR, useWSTETHContractRPC } from '@lido-sdk/react';

import { useStethByWsteth } from 'shared/hooks';
import { isValidEtherValue } from 'utils/isValidEtherValue';
import { STRATEGY_LAZY } from 'utils/swrStrategies';

type useEthAmountByInputProps = {
isSteth: boolean;
input?: string;
amount: BigNumber | null;
};

export const useEthAmountByStethWsteth = ({
isSteth,
input,
amount,
}: useEthAmountByInputProps) => {
const isValidValue =
input && !isNaN(Number(input)) && isValidEtherValue(input);
const inputBN = useMemo(
() => (isValidValue ? parseEther(input) : BigNumber.from(0)),
[input, isValidValue],
);
const wsteth = isSteth ? null : amount;
const { data: stethByWstethBalance, loading } = useContractSWR({
contract: useWSTETHContractRPC(),
method: 'getStETHByWstETH',
params: [wsteth],
shouldFetch: !!wsteth,
config: STRATEGY_LAZY,
});

const stethByWstethBalance = useStethByWsteth(isSteth ? undefined : inputBN);

if (!isValidValue) return undefined;
if (isSteth) return inputBN;
return stethByWstethBalance;
if (isSteth)
return {
amount: amount ?? undefined,
loading: false,
};
else return { amount: stethByWstethBalance, loading };
};
31 changes: 18 additions & 13 deletions features/withdrawals/request/form/options/lido-option.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,4 @@
import { useWatch } from 'react-hook-form';
import { formatEther } from '@ethersproject/units';

import { Tooltip, Question } from '@lidofinance/lido-ui';
import { TOKENS } from '@lido-sdk/constants';
Expand All @@ -18,6 +17,7 @@ import {
LidoIcon,
LidoOptionContainer,
LidoOptionValue,
LidoOptionInlineLoader,
} from './styles';

const TooltipWithdrawalAmount = () => {
Expand Down Expand Up @@ -55,24 +55,29 @@ export const LidoOption = () => {
name: ['token', 'amount'],
});

// TODO: refactor to use intermediate validation values
const ethAmount = useEthAmountByStethWsteth({
isSteth: token === TOKENS.STETH,
input: amount ? formatEther(amount) : undefined,
});
const { amount: ethAmount, loading: amountLoading } =
useEthAmountByStethWsteth({
isSteth: token === TOKENS.STETH,
amount,
});

return (
<LidoOptionContainer data-testid="lidoOptionSection">
<LidoIcon />
Lido
<LidoOptionValue data-testid="lidoOptionAmount">
<FormatTokenStyled
data-testid="lidoOptionAmount"
showAmountTip
amount={ethAmount}
symbol="ETH"
/>{' '}
<TooltipWithdrawalAmount />
{amountLoading && <LidoOptionInlineLoader />}
{!amountLoading && (
<>
<FormatTokenStyled
data-testid="lidoOptionAmount"
showAmountTip
amount={ethAmount}
symbol="ETH"
/>{' '}
<TooltipWithdrawalAmount />
</>
)}
</LidoOptionValue>
</LidoOptionContainer>
);
Expand Down
Loading

0 comments on commit c1f1cd8

Please sign in to comment.