Skip to content

Commit

Permalink
feat: improve claiming rewards flow
Browse files Browse the repository at this point in the history
  • Loading branch information
icfor committed Mar 7, 2024
1 parent 2bb43e1 commit a932710
Show file tree
Hide file tree
Showing 7 changed files with 39 additions and 15 deletions.
2 changes: 1 addition & 1 deletion src/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -25,4 +25,4 @@ export const defaultAvatar = `${basePath}/default-avatar.svg`;
export const unbondingDays = isTestnet ? 3 : 21;

// Arbitrary value to avoid using a bigger fee than the actual reward
export const minClaimableXion = 0.0001;
export const minClaimableXion = 0.00001;
12 changes: 7 additions & 5 deletions src/features/staking/components/delegation-details.tsx
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
import BigNumber from "bignumber.js";
import type { Validator } from "cosmjs-types/cosmos/staking/v1beta1/staking";
import { memo, useEffect, useState } from "react";

Expand All @@ -21,6 +22,7 @@ import {
import type { StakingContextType, StakingState } from "../context/state";
import { useValidatorLogo } from "../hooks";
import { coinIsPositive } from "../lib/core/coins";
import { getCanClaimRewards } from "../lib/core/tx";
import {
formatCoin,
formatCommission,
Expand Down Expand Up @@ -156,7 +158,7 @@ const DelegationRowBase = ({
<FloatingDropdown Trigger={Menu} id={`delegation-${index}`}>
<div className="flex flex-col gap-[12px] rounded-[8px] bg-bg-600 py-[4px]">
<ButtonLink
disabled={disabled}
disabled={!getCanClaimRewards(delegation?.rewards) || disabled}
onClick={() => {
if (!validator) return;

Expand Down Expand Up @@ -319,16 +321,16 @@ const DelegationDetails = () => {
case "staked-asc":
case "staked-desc":
return sortUtil(
a.balance.amount,
b.balance.amount,
new BigNumber(a.balance.amount),
new BigNumber(b.balance.amount),
delegationsSortMethod === "staked-asc",
);

case "rewards-asc":
case "rewards-desc":
return sortUtil(
a.rewards.amount,
b.rewards.amount,
new BigNumber(a.rewards.amount),
new BigNumber(b.rewards.amount),
delegationsSortMethod === "rewards-asc",
);

Expand Down
9 changes: 9 additions & 0 deletions src/features/staking/components/modals/rewards.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,8 @@
import BigNumber from "bignumber.js";
import { memo, useEffect, useRef, useState } from "react";
import { toast } from "react-toastify";

import { minClaimableXion } from "@/constants";
import { Button, HeroText } from "@/features/core/components/base";
import CommonModal, {
ModalDescription,
Expand All @@ -9,6 +11,7 @@ import CommonModal, {
import { fetchUserDataAction } from "../../context/actions";
import { useStaking } from "../../context/hooks";
import { setModalOpened } from "../../context/reducer";
import { normaliseCoin } from "../../lib/core/coins";
import { claimRewards } from "../../lib/core/tx";

type Step = "completed" | "loading";
Expand All @@ -34,6 +37,12 @@ const claimRewardsLoop = async (
.reduce(async (promise, delegation) => {
await promise;

const normalised = normaliseCoin(delegation.rewards);

if (new BigNumber(normalised.amount).lt(minClaimableXion)) {
return;
}

const addresses = {
delegator: delegatorAddress,
validator: delegation.validatorAddress,
Expand Down
4 changes: 2 additions & 2 deletions src/features/staking/components/staking-overview.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -15,11 +15,11 @@ import { useStaking } from "../context/hooks";
import { setModalOpened } from "../context/reducer";
import {
getAPR,
getCanClaimAnyRewards,
getTotalDelegation,
getTotalRewards,
} from "../context/selectors";
import { getEmptyXionCoin } from "../lib/core/coins";
import { getIsMinimumClaimable } from "../lib/core/tx";
import { formatAPR, formatCoin, formatXionToUSD } from "../lib/formatters";
import { DivisorVertical } from "./divisor";

Expand Down Expand Up @@ -78,7 +78,7 @@ const StakingOverview = () => {
<Heading8>Claimable Rewards</Heading8>
<div className="flex flex-row items-center gap-4">
<Heading2>{formatXionToUSD(totalRewards)}</Heading2>
{getIsMinimumClaimable(totalRewards) && (
{getCanClaimAnyRewards(staking.state) && (
<ButtonPill
onClick={() => {
staking.dispatch(
Expand Down
8 changes: 3 additions & 5 deletions src/features/staking/components/validator-delegation.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -18,6 +18,7 @@ import { getValidatorDetailsAction } from "../context/actions";
import { useStaking } from "../context/hooks";
import { setModalOpened } from "../context/reducer";
import {
getCanClaimAnyRewards,
getTokensAvailableBG,
getTotalDelegation,
getTotalRewards,
Expand Down Expand Up @@ -67,10 +68,7 @@ export default function ValidatorDelegation() {

const userTotalUnbondings = getTotalUnbonding(staking.state, null);

const totalRewards = getTotalRewards(
validatorDetails.operatorAddress,
staking.state,
);
const totalRewards = getTotalRewards(null, staking.state);

const canShowDetail = getCanShowDetails(staking.state);

Expand All @@ -94,7 +92,7 @@ export default function ValidatorDelegation() {
<Heading8>Claimable Rewards</Heading8>
<div className="mb-[8px] mt-[12px] flex flex-row items-center gap-[8px]">
<Heading2>{formatXionToUSD(totalRewards)}</Heading2>
{totalRewards && totalRewards?.amount !== "0" && (
{getCanClaimAnyRewards(staking.state) && (
<ButtonPill
onClick={() => {
staking.dispatch(
Expand Down
11 changes: 11 additions & 0 deletions src/features/staking/context/selectors.ts
Original file line number Diff line number Diff line change
Expand Up @@ -2,6 +2,7 @@ import BigNumber from "bignumber.js";
import type { Validator } from "cosmjs-types/cosmos/staking/v1beta1/staking";

import { normaliseCoin, sumAllCoins } from "../lib/core/coins";
import { getCanClaimRewards } from "../lib/core/tx";
import type { StakingState } from "./state";

export const getTotalDelegation = (
Expand Down Expand Up @@ -88,6 +89,16 @@ export const getVotingPowerPerc = (
.toNumber();
};

export const getCanClaimAnyRewards = (state: StakingState) => {
const { delegations } = state;

if (!delegations?.items.length) {
return false;
}

return delegations.items.some((d) => getCanClaimRewards(d?.rewards));
};

export const getAllValidators = (
state: StakingState,
): Record<string, undefined | Validator> =>
Expand Down
8 changes: 6 additions & 2 deletions src/features/staking/lib/core/tx.ts
Original file line number Diff line number Diff line change
Expand Up @@ -153,8 +153,12 @@ export const claimRewards = async (
.catch(handleTxError);
};

export const getIsMinimumClaimable = (amount: Coin) => {
const normalised = normaliseCoin(amount);
export const getCanClaimRewards = (rewards?: Coin) => {
if (!rewards) {
return false;
}

const normalised = normaliseCoin(rewards);

return new BigNumber(normalised.amount).gte(minClaimableXion);
};
Expand Down

0 comments on commit a932710

Please sign in to comment.