Skip to content

Commit

Permalink
react sdk docs and smool fix
Browse files Browse the repository at this point in the history
  • Loading branch information
BeroBurny committed Oct 1, 2024
1 parent 2121e83 commit b8656c9
Show file tree
Hide file tree
Showing 4 changed files with 236 additions and 19 deletions.
41 changes: 34 additions & 7 deletions packages/react/lib/context.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,5 @@
import {createContext, ReactNode, useEffect, useState} from "react";
import {type FetchOptions, Sprinter} from "@chainsafe/sprinter-sdk";
import {Sprinter} from "@chainsafe/sprinter-sdk";
import {useTokens} from "./internal/useTokens.ts";
import {useChains} from "./internal/useChains.ts";
import {useBalances} from "./internal/useBalances.ts";
Expand All @@ -10,12 +10,39 @@ type SprinterContext = ReturnType<typeof useBalances> & ReturnType<typeof useTok
export const Context = createContext<SprinterContext | null>(null);

interface SprinterContextProps {
children?: ReactNode | undefined;
fetchOptions?: Omit<FetchOptions, "signal">;
children?: ReactNode;
baseUrl?: string;
}

export function SprinterContext({ children, fetchOptions }: SprinterContextProps) {
const [sprinter] = useState(new Sprinter(fetchOptions));
/**
* SprinterContext is a context provider component that initializes a Sprinter instance
* and provides various functionalities for interacting with tokens, chains, balances,
* and bridging solutions through React Context.
*
* It fetches and provides tokens, chains, user balances, and bridging solutions to any
* component that consumes this context.
*
* @param {SprinterContextProps} props - The props for the component:
* - `children` (ReactNode): The child components that will have access to the context.
* - `baseUrl` (string, optional): The base URL to be used for all fetch requests in the Sprinter SDK.
*
* @returns {JSX.Element} A context provider that supplies tokens, chains, balances, and bridging solutions to its children.
*
* @example
* ```ts
* import { SprinterContext, Environment } from '@chainsafe/sprinter-react';
*
* function App() {
* return (
* <SprinterContext baseUrl={Environment.TESTNET}>
* <YourComponent />
* </SprinterContext>
* );
* }
* ```
*/
export function SprinterContext({ children, baseUrl }: SprinterContextProps) {
const [sprinter] = useState(new Sprinter({baseUrl}));

/** Balances */
const { balances, getUserBalances } = useBalances(sprinter);
Expand All @@ -27,7 +54,7 @@ export function SprinterContext({ children, fetchOptions }: SprinterContextProps
const { chains, getAvailableChains } = useChains(sprinter);

/** Solutions */
const { solution, getBridgeAndCall, getBridgeBalance, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall } = useBridge(sprinter);
const { solution, getBridgeAndCall, getBridge, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall } = useBridge(sprinter);

/** Initialization */
useEffect(() => {
Expand All @@ -39,6 +66,6 @@ export function SprinterContext({ children, fetchOptions }: SprinterContextProps
balances, getUserBalances,
tokens, getAvailableTokens,
chains, getAvailableChains,
solution, getBridgeAndCall, getBridgeBalance, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall,
solution, getBridgeAndCall, getBridge, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall,
}}>{children}</Context.Provider>;
}
205 changes: 198 additions & 7 deletions packages/react/lib/hooks.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,20 @@ import {Context} from "./context.tsx";
import {Address} from "@chainsafe/sprinter-sdk";
import {BalancesEntry} from "./internal/useBalances.ts";

/** Everything from context */
/**
* A hook to access the full Sprinter context, including balances, tokens, chains, and bridge solutions.
*
* @returns {SprinterContext} The current context value with Sprinter functionalities.
*
* @throws {Error} If the context is not available.
*
* @example
* ```ts
* import { useSprinter } from '@chainsafe/sprinter-react';
*
* const { balances, tokens, chains, solution } = useSprinter();
* ```
*/
export function useSprinter() {
const context = useContext(Context);

Expand All @@ -18,7 +31,51 @@ const balancesEmptyState = {
loading: false,
error: null,
};

/**
* A hook to retrieve the user's token balances and a function to fetch them.
*
* @param {Address} account - The user's wallet address.
*
* @returns {{
* balances: AsyncRequestState<BalancesEntry>,
* getUserBalances: () => void
* }}
* - `balances`: The state of the user's token balances for the specified account, including:
* - `data`: The token balances, or `null` if not yet fetched.
* - `loading`: A boolean indicating if the request is in progress.
* - `error`: An error message, or `null` if there is no error.
* - `getUserBalances`: A function to fetch the user's balances for the specified account.
*
* @example
* ```ts
* import React, { useEffect } from 'react';
* import { useSprinterBalances } from '@chainsafe/sprinter-react';
*
* function BalancesComponent() {
* const { balances, getUserBalances } = useSprinterBalances("0xYourAddress");
*
* useEffect(() => {
* getUserBalances();
* }, [getUserBalances]);
*
* if (balances.loading) {
* return <div>Loading...</div>;
* }
*
* if (balances.error) {
* return <div>Error: {balances.error}</div>;
* }
*
* return (
* <ul>
* {Object.entries(balances.data || {}).map(([symbol, balanceEntry]) => (
* <li key={symbol}>{symbol}: {balanceEntry.total}</li>
* ))}
* </ul>
* );
* }
* ```
*/
export function useSprinterBalances(account: Address) {
const { balances: _balances, getUserBalances: _getUserBalances } = useSprinter();

Expand All @@ -28,20 +85,154 @@ export function useSprinterBalances(account: Address) {
return { balances, getUserBalances };
}

/** Tokens */
/**
* A hook to retrieve available tokens and a function to fetch them.
*
* @returns {{
* tokens: AsyncRequestState<FungibleToken[]>,
* getAvailableTokens: () => void
* }}
* - `tokens`: The state of available tokens, including:
* - `data`: The list of available tokens, or `null` if not yet fetched.
* - `loading`: A boolean indicating if the request is in progress.
* - `error`: An error message, or `null` if there is no error.
* - `getAvailableTokens`: A function to fetch the available tokens.
*
* @example
* ```ts
* import React, { useEffect } from 'react';
* import { useSprinterTokens } from '@chainsafe/sprinter-react';
*
* function TokensComponent() {
* const { tokens, getAvailableTokens } = useSprinterTokens();
*
* useEffect(() => {
* getAvailableTokens();
* }, [getAvailableTokens]);
*
* if (tokens.loading) {
* return <div>Loading...</div>;
* }
*
* if (tokens.error) {
* return <div>Error: {tokens.error}</div>;
* }
*
* return (
* <ul>
* {tokens.data?.map(token => (
* <li key={token.symbol}>{token.name}</li>
* ))}
* </ul>
* );
* }
* ```
*/
export function useSprinterTokens() {
const { tokens, getAvailableTokens } = useSprinter();
return { tokens, getAvailableTokens };
}

/** Chains */
/**
* A hook to retrieve available chains and a function to fetch them.
*
* @returns {{
* chains: AsyncRequestState<Chain[]>,
* getAvailableChains: () => void
* }}
* - `chains`: The state of available chains, including:
* - `data`: The list of available chains, or `null` if not yet fetched.
* - `loading`: A boolean indicating if the request is in progress.
* - `error`: An error message, or `null` if there is no error.
* - `getAvailableChains`: A function to fetch the available chains.
*
* @example
* ```ts
* import React, { useEffect } from 'react';
* import { useSprinterChains } from '@chainsafe/sprinter-react';
*
* function ChainsComponent() {
* const { chains, getAvailableChains } = useSprinterChains();
*
* useEffect(() => {
* getAvailableChains();
* }, [getAvailableChains]);
*
* if (chains.loading) {
* return <div>Loading...</div>;
* }
*
* if (chains.error) {
* return <div>Error: {chains.error}</div>;
* }
*
* return (
* <ul>
* {chains.data?.map(chain => (
* <li key={chain.chainID}>{chain.name}</li>
* ))}
* </ul>
* );
* }
* ```
*/
export function useSprinterChains() {
const { chains, getAvailableChains } = useSprinter();
return { chains, getAvailableChains };
}

/** Solutions */
/**
* A hook to retrieve bridge solutions and functions to interact with the Sprinter.
*
* @returns {{
* solution: AsyncRequestState<SolutionResponse>,
* getBridgeAggregateBalance: (request: {
* account: string,
* destinationChain: number,
* token: string,
* amount: string
* }) => void
* }}
* - `solution`: The state of the bridge solution, including:
* - `data`: The bridge solution, or `null` if not yet fetched.
* - `loading`: A boolean indicating if the request is in progress.
* - `error`: An error message, or `null` if there is no error.
* - `getBridgeAggregateBalance`: A function to get the aggregate bridge balance based on the provided request.
*
* @example
* ```ts
* import React, { useEffect } from 'react';
* import { useSprinterBridge } from '@chainsafe/sprinter-react';
*
* function BridgeComponent() {
* const { solution, getBridgeAggregateBalance } = useSprinterBridge();
*
* useEffect(() => {
* getBridgeAggregateBalance({
* account: "0x3e101ec02e7a48d16dade204c96bff842e7e2519",
* destinationChain: 11155111,
* token: "0x036CbD53842c5426634e7929541eC2318f3dCF7e",
* amount: "100000000",
* });
* }, [getBridgeAggregateBalance]);
*
* if (solution.loading) {
* return <div>Loading...</div>;
* }
*
* if (solution.error) {
* return <div>Error: {solution.error}</div>;
* }
*
* return (
* <div>
* <pre>{JSON.stringify(solution.data, null, 2)}</pre>
* </div>
* );
* }
* ```
*/
export function useSprinterBridge() {
const { solution, getBridgeAndCall, getBridgeBalance, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall } = useSprinter();
return { solution, getBridgeAndCall, getBridgeBalance, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall };
const { solution, getBridgeAndCall, getBridge, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall } = useSprinter();
return { solution, getBridgeAndCall, getBridge, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall };
}
4 changes: 2 additions & 2 deletions packages/react/lib/internal/useBridge.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,13 +22,13 @@ export function useBridge(sprinter: Sprinter) {
makeRequest(sprinter.bridgeAggregateBalanceAndCall(settings));
}, [sprinter, makeRequest]);

const getBridgeBalance = useCallback((settings: Infer<typeof SingleHopSchema>) => {
const getBridge = useCallback((settings: Infer<typeof SingleHopSchema>) => {
makeRequest(sprinter.bridge(settings));
}, [sprinter, makeRequest]);

const getBridgeAndCall = useCallback((settings: Infer<typeof SingleHopWithContractSchema>) => {
makeRequest(sprinter.bridgeAndCall(settings));
}, [sprinter, makeRequest]);

return { solution, getBridgeBalance, getBridgeAndCall, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall };
return { solution, getBridge, getBridgeAndCall, getBridgeAggregateBalance, getBridgeAggregateBalanceAndCall };
}
5 changes: 2 additions & 3 deletions packages/react/lib/main.ts
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@ export {
useSprinterBalances,
useSprinter,
useSprinterChains,
useSprinterSolution,
useSprinterCallSolution,
useSprinterTokens
useSprinterTokens,
useSprinterBridge,
} from "./hooks";

0 comments on commit b8656c9

Please sign in to comment.