Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Adds subaccount feature #3

Open
wants to merge 13 commits into
base: main
Choose a base branch
from
Open
2 changes: 1 addition & 1 deletion app/app/investments/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -97,7 +97,7 @@ export default function Investments() {
const [fromToken, setFromToken] = useState<number>(1);
const [balance, setBalance] = useState<string>("0");
const [layerZeroHash, setLayerZeroHash] = useState<string>("");
const [targetToken, setTargetToken] = useState<number>(1);
const [targetToken, setTargetToken] = useState<number>(2);
const [targetTokenValue, setTargetTokenValue] = useState<string>("");
const [selectedVault, setSelectedVault] = useState<any>();
const [frequency, setFrequency] = useState<number>(0);
Expand Down
2 changes: 1 addition & 1 deletion app/app/layout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -11,7 +11,7 @@ export default function AppLayout({
<ZapperProvider>
<div className="flex flex-row gap-0 items-start justify-start px-4 py-4 md:py-4 md:px-4 w-full min-h-screen">
<Sidebar />
<div className="flex flex-col gap-6 md:gap-8 justify-start items-start w-full h-screen md:h-[97vh] flex-grow md:border md:border-l-0 border-accent md:p-5">
<div className="flex flex-col gap-6 md:gap-8 justify-start items-start w-full h-screen md:h-[97vh] flex-grow md:border md:border-l-0 border-accent pt-10 md:pt-0 md:p-5">
<Topbar />
{children}
</div>
Expand Down
154 changes: 92 additions & 62 deletions app/app/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -26,27 +26,27 @@ import {
PopoverTrigger,
} from "@/components/ui/popover";
import Image from "next/image";

import { Checkbox } from "@/components/ui/checkbox";
import { formatNumberCommas } from "../utils/commas";
import PieChartComponent from "../components/PieChart/PieChart";
import { ZapperContext } from "../context/ZapperProvider";
import {
getIconbySymbol,
getNetworkLogobyName,
Networks,
} from "../utils/Zapper";
import { set } from "date-fns";
import NumberTicker from "@/components/magicui/number-ticker";
import { Networks } from "../utils/Zapper";
import useAccountStore from "../store/account/account.store";
import { getJsonRpcProvider } from "../logic/web3";
import { gasChainsTokens, getChainById } from "../utils/tokens";
import { fixDecimal, getTokenBalance, getVaultBalance } from "../logic/utils";
import { formatEther, ZeroAddress } from "ethers";
import { useRouter } from "next/navigation";
import {
Dialog,
DialogContent,
DialogDescription,
DialogHeader,
DialogTitle,
} from "@/components/ui/dialog";
import Confetti from "react-confetti";
import { useWindowSize } from "react-use";

export default function App() {
const { chainId, setChainId } = useAccountStore();
const { chainId } = useAccountStore();
const router = useRouter();
const [tokenDetails, setTokenDetails]: any = useState([]);
const [tokenVaultDetails, setTokenVaultDetails]: any = useState([]);
Expand All @@ -55,23 +55,18 @@ export default function App() {
const [openShowQR, setOpenShowQR] = useState(false);
const { address } = useAccount();
const { ensname, ensavatar } = useContext(LoginContext);

const [openClaim, setOpenClaim] = useState(false);
//Zapper Data

const {
NFTData,
DefiData,
isZapperLoading,
DefiTotal,
totalBalance,
selectedNetworks,
setSelectedNetworks,
tokensByNetwork,
refresh,
setRefresh,
tokenDataError,
DeFiDataError,
NftDataError,
setIsZapperLoading,
} = useContext(ZapperContext);

Expand All @@ -87,47 +82,45 @@ export default function App() {

let updatedTokens = [];


if(address) {

updatedTokens = await Promise.all(
tokens!.map(async (token) => {
const balance =
token.address == ZeroAddress
? formatEther(await provider.getBalance(address))
: await getTokenBalance(token.address!, address, provider);

return {
...token,
balance, // Add the balance to each token
};
})
);

setTokenDetails(updatedTokens);

let tokensWithVault = updatedTokens?.filter(
(token: any) => token.vault != undefined
);

if (tokensWithVault) {
if (address) {
updatedTokens = await Promise.all(
tokensWithVault.map(async (token) => {
const vaultBalance = await getVaultBalance(
token.vault!,
address,
provider
);
tokens!.map(async (token) => {
const balance =
token.address == ZeroAddress
? formatEther(await provider.getBalance(address))
: await getTokenBalance(token.address!, address, provider);

return {
...token,
vaultBalance, // Add the vault balance to each token
balance, // Add the balance to each token
};
})
);
console.log(updatedTokens);
setTokenVaultDetails(updatedTokens); // Tokens now contain their respective vault balances

setTokenDetails(updatedTokens);

let tokensWithVault = updatedTokens?.filter(
(token: any) => token.vault != undefined
);

if (tokensWithVault) {
updatedTokens = await Promise.all(
tokensWithVault.map(async (token) => {
const vaultBalance = await getVaultBalance(
token.vault!,
address,
provider
);
return {
...token,
vaultBalance, // Add the vault balance to each token
};
})
);
console.log(updatedTokens);
setTokenVaultDetails(updatedTokens); // Tokens now contain their respective vault balances
}
}
}
})();
}, [chainId, address]);

Expand All @@ -144,11 +137,20 @@ export default function App() {
return newSelectedNetworks;
});
}

const [showConfetti, setShowConfetti] = useState(false);
const { width, height } = useWindowSize();

const handleCelebrate = () => {
setOpenClaim(false);
setShowConfetti(true);
setTimeout(() => setShowConfetti(false), 20000); // Stop after 5 seconds
};
return (
<div className=" flex flex-col items-start justify-center gap-6 w-full h-full">
<div className="w-full border border-accent flex flex-col gap-6 px-4 py-4 md:py-6">
<div className="w-full flex flex-col md:flex-row gap-4 justify-between items-center relative">
<div className="flex flex-col md:flex-row gap-4 justify-start items-start md:items-center w-full">
<div className="flex flex-col md:flex-row gap-4 justify-between items-start md:items-center w-full">
{ensavatar ? (
<img
className="rounded-full"
Expand All @@ -169,10 +171,11 @@ export default function App() {
<div className="flex flex-col-reverse justify-start items-start gap-1">
<div className="flex flex-row justify-center items-start gap-2">
<h1 className="text-4xl font-black text-white">


{ tokenDetails[0] ? `${fixDecimal(tokenDetails[0]?.balance, 2)} ${tokenDetails[0]?.name}` : null }

{tokenDetails[0]
? `${fixDecimal(tokenDetails[0]?.balance, 2)} ${
tokenDetails[0]?.name
}`
: null}
</h1>
<button
className="mt-1"
Expand Down Expand Up @@ -222,9 +225,41 @@ export default function App() {
</div>
</div>
</div>
{/* <button
onClick={() => setOpenClaim(true)}
className="flex flex-row justify-center items-center gap-2 bg-gradient text-black px-6 py-2 font-bold rounded-full"
>
Claim Badge
</button> */}
<Dialog open={openClaim} onOpenChange={setOpenClaim}>
<DialogContent className="bg-black text-white dark:bg-white flex flex-col justify-start items-start gap-4 rounded-none sm:rounded-none max-w-lg mx-auto border border-accent">
<DialogHeader>
<DialogTitle>Early Adoptor Badge</DialogTitle>
<DialogDescription>
You are eligible for an early adopter badge. Will
distinguish you from others.
</DialogDescription>
</DialogHeader>
<div className="flex flex-col justify-center items-center w-full gap-4">
<Image
src={"/badges/Brewit - Early Adaptor.png"}
width={400}
height={400}
alt="Brewit - Early Adaptor"
/>
<button
onClick={handleCelebrate}
className="bg-transparent py-3 w-full text-white font-semibold border border-accent bg-gradient hover:bg-transparent hover:text-white text-lg"
>
Claim
</button>
</div>
</DialogContent>
</Dialog>
</div>
</div>
</div>
{showConfetti && <Confetti width={width} height={height} />}
<Tabs defaultValue="Tokens" className="w-full flex flex-col gap-4 h-full">
<div className="flex flex-col-reverse md:flex-row md:justify-between items-end md:items-center gap-2">
<TabsList className="rounded-none h-fit p-0 divide-x divide-accent border border-accent grid grid-cols-3 md:max-w-md w-full gap-0 bg-black text-white data-[state=active]:bg-gradient data-[state=active]:text-black data-[state=active]:font-bold">
Expand Down Expand Up @@ -418,12 +453,7 @@ export default function App() {
).toFixed(2)}
</div> */}
<div className="text-left md:text-right uppercase md:w-32">
{(
<span>
{fixDecimal(token.balance, 6)}
</span>
) }{" "}
{token.name}
{<span>{fixDecimal(token.balance, 6)}</span>} {token.name}
</div>
<div className="md:w-36">
<div className="grid grid-cols-3 place-items-center gap-1">
Expand Down
69 changes: 52 additions & 17 deletions app/app/send/page.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -19,7 +19,7 @@ import {
useAccount,
useLoginProvider,
} from "../../context/LoginProvider";
import { buildUseSmartSession, getSpendPolicy, sendTransaction, Transaction } from "@/app/logic/module";
import { buildUseSmartSession, getSpendPolicy, passkeySessionValidator, sendTransaction, Transaction } from "@/app/logic/module";
import { getJsonRpcProvider } from "@/app/logic/web3";
import { ZeroAddress, formatEther, parseEther, parseUnits } from "ethers";
import {
Expand All @@ -35,6 +35,9 @@ import LoadingIndicator from "@/components/ui/loader";
import { privateKeyToAccount } from "viem/accounts";
import { loadAccountInfo } from "@/app/utils/storage";
import { computeConfigId, getActionId, getPermissionId } from "@/app/logic/smartsessions/smartsessions";
import { encodeValidationData, OWNABLE_VALIDATOR_ADDRESS } from "@rhinestone/module-sdk";
import { getPassKeySessionValidator, getPKeySessionValidator } from "@/app/logic/auth";
import { toast } from "@/components/ui/use-toast";

interface GasChainType {
name: string;
Expand All @@ -49,7 +52,7 @@ export default function Bridge() {
);
useState<number>(0);
const [selectedTokenID, setSelectedTokenID] = useState<number>(0);
const accountInfo = loadAccountInfo()
const [ accountInfo, setAccountInfo ] = useState<any>();

const [balance, setBalance] = useState<string>("0");
const [spendableBalance, setSpendableBalance] = useState<string>("0");
Expand All @@ -62,7 +65,9 @@ export default function Bridge() {

const { setChainId, chainId } = useAccountStore();
const { address } = useAccount();
const { validator } = useLoginProvider();
const { validator, pKeyValidator } = useLoginProvider();
const [ sessionValidator, setSessionValidator ] = useState<any>();


async function sendAsset() {

Expand Down Expand Up @@ -97,29 +102,43 @@ export default function Bridge() {
}


// if(accountInfo.selected!= 0) {

// const sessionPk = "0xdd1db445a79e51f16d08c4e5dc5810c4b5f29882b8610058cfecd425ac293712"
// const sessionOwner = privateKeyToAccount(sessionPk)
// const useSmartSession = await buildUseSmartSession(chainId.toString(), sessionOwner)
// await sendTransaction(chainId.toString(), [call], sessionOwner, address, "sessionkey", useSmartSession)
if(accountInfo.selected != 0) {


const useSmartSession = await buildUseSmartSession(chainId.toString(), sessionValidator)
await sendTransaction(chainId.toString(), [call], accountInfo.selected == 1 ? pKeyValidator : validator, address, accountInfo.selected == 1 ? "ownable" : "passkey" , "session", useSmartSession)

// } else {
} else {
const result = await sendTransaction(
chainId.toString(),
[call],
validator,
address
);
// }
}

toast({
success: true,
title: "Hooray! Transfer Successful! 🎉", // Fun title with emojis
description: "Your assets have zoomed away! 🚀💰 Enjoy your new treasures!"
});
} catch (e) {
toast({
success: false,
title: "Oops! Transfer Failed!",
description: "Looks like you don't have the magic permission or enough assets to make this transfer happen. Try again!"

});
console.log("error", e);
}
setSending(false);
}

useEffect(() => {
(async () => {

setAccountInfo(loadAccountInfo());
try {
const provider = await getJsonRpcProvider(chainId.toString());
const token = getChainById(chainId)?.tokens[selectedTokenID].address;
Expand All @@ -128,8 +147,19 @@ export default function Bridge() {
} else {
setBalance(await getTokenBalance(token!, address, provider));

// setSpendableBalance((await getSpendableTokenInfo(chainId.toString(), token!, address)).balance)


let sessionValidator;
if(accountInfo.selected ==1 ) {
sessionValidator = await getPKeySessionValidator(pKeyValidator);
}
else if(accountInfo.selected ==2) {
sessionValidator = await getPassKeySessionValidator(validator);

}
if (sessionValidator) {
setSessionValidator(sessionValidator);
setSpendableBalance((await getSpendableTokenInfo(chainId.toString(), token!, address, sessionValidator)).balance);
}
}
}
catch(e) {
Expand All @@ -148,14 +178,19 @@ export default function Bridge() {
</div>
<div className="flex flex-col gap-4 px-4 md:px-6 pb-6 pt-7 relative">
<div className="flex flex-col gap-2">
<div className="flex flex-row justify-end items-center text-sm absolute top-1.5 right-6">
<div className="flex flex-row justify-end items-center text-sm absolute top-1.5 right-6 mb-2">
<div className="flex flex-row justify-center items-center gap-1">
{/* <div>{`${fixDecimal(balance, 4)} (Spendable: ${fixDecimal(spendableBalance, 4)} ) ${getChainById(chainId)?.tokens[selectedTokenID]?.name}`} </div> */}
<div>{`${fixDecimal(balance, 4)} ${getChainById(chainId)?.tokens[selectedTokenID]?.name}`} </div>
<button className="font-bold" onClick={()=> { setTokenValue(balance)}}>Max</button>
<div> {`${fixDecimal(balance, 4)} `}
{` ${getChainById(chainId)?.tokens[selectedTokenID]?.name}`} </div>
{sessionValidator && (
<span className="text-green-800 bg-green-100 px-2 py-1 rounded-full text-xs font-medium">
Spendable: {fixDecimal(spendableBalance, 4)}
</span>
)}
<button className="font-bold" onClick={()=> { setTokenValue(spendableBalance)}}>Max</button>
</div>
</div>
<div className="grid grid-cols-2 md:grid-cols-3">
<div className="grid grid-cols-2 md:grid-cols-3 mt-2">
<div className="flex flex-row col-span-2 divide-x divide-accent border-r border-accent">
<Select
value={chainId.toString()}
Expand Down
Loading