Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
18 changes: 18 additions & 0 deletions docs/frontend/01-overview.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,18 @@
---
sidebar_position: 1
slug: overview
title: Frontend Guides
authors: [nikerzetic]
description: Introduction to frontend guides.
tags: [quickstart, ethereum, flare-smart-accounts]
keywords: [ethereum, evm, flare-network]
unlisted: false
---

Flare Fronted provides a comprehensive overview of the front-end architecture and workflows used across the Flare ecosystem.
This documentation serves as a central reference for developers working on Flare's user-facing interfaces and related applications.

Flare Fronted is built with **React** as the core UI library, structured using **Next.js** for routing and server-side rendering, and integrates **TanStack Query** to handle data fetching, caching, and synchronization efficiently.
Together, these technologies provide a robust, scalable, and performant framework for building interfaces that interact seamlessly with the Flare blockchain—the blockchain for data.

Within this section, you'll find guides covering core concepts, recommended practices, and implementation details to ensure consistency, reliability, and maintainability across Flare's front-end projects.
35 changes: 35 additions & 0 deletions docs/frontend/02-tanstack-query-prepare-request.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,35 @@
---
sidebar_position: 1
slug: tanstack-query-prepare-request
title: Prepare request (TanStack Query)
authors: [nikerzetic]
description: Prepare an FDC request through a Verifier server using TanStack Query.
tags: [quickstart, ethereum, flare-smart-accounts]
keywords:
[
flare-fdc,
ethereum,
flare-smart-accounts,
evm,
flare-network,
account-abstraction,
]
unlisted: false
---

import { PrepareWeb2JsonRequestApp } from "@site/src/components/Frontend/PrepareWeb2JsonRequestCard";
import CodeBlock from "@theme/CodeBlock";
import BrowserOnly from "@docusaurus/BrowserOnly";

In this guide we will prepare an ABI encoded request that can be submitted to the FDC.
This is a core step of the [FDC process](/fdc/overview).
In order to be able to submit request data to the protocol, we need to encode it in a specific way.
While this process can be done manually, it is recommended that the data is encoded through a special verifier server.
Besides encoding the data, the server also checks its validity.
Thus, it is a useful tool for catching user error.

We will make the request to the verifier server with the [TanStack Query](https://tanstack.com/query/latest/docs/framework/react/overview) library.
Because we want the request to be sent only when the user presses a button, we will not employ its `useQuery` hook.
Instead, we will utilize [`useMutation`](https://tanstack.com/query/latest/docs/framework/react/guides/mutations).

<BrowserOnly>{() => <PrepareWeb2JsonRequestApp />}</BrowserOnly>
38 changes: 38 additions & 0 deletions docs/frontend/tanstack-query/02-prepare-request.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,38 @@
---
sidebar_position: 1
slug: prepare-request
title: Prepare request
authors: [nikerzetic]
description: Prepare an FDC request through a Verifier server using TanStack Query.
tags: [quickstart, ethereum, flare-smart-accounts]
keywords:
[
flare-fdc,
ethereum,
flare-smart-accounts,
evm,
flare-network,
account-abstraction,
]
unlisted: false
---

import { PrepareWeb2JsonRequestApp } from "@site/src/components/Frontend/PrepareWeb2JsonRequestCard";
import CodeBlock from "@theme/CodeBlock";
import BrowserOnly from "@docusaurus/BrowserOnly";

In the following series of guides we will prepare different ABI encoded requests that can be submitted to the FDC.
The guides will showcase code for making a request of each [attestation type](/fdc/attestation-types/).
They will also include an interactive widget for testing the code.
While we could pack all of these into a single component with selectable tabs, we believe it would make for a less understandable code.
For that reason, each guide will cover only one attestation type.

Preparing the request is a core step of the [FDC process](/fdc/overview).
In order to be able to submit request data to the protocol, we need to encode it in a specific way.
While this process can be done manually, it is recommended that the data is encoded through a special verifier server.
Besides encoding the data, the server also checks its validity.
Thus, it is a useful tool for catching user error.

We will make the request to the verifier server with the [TanStack Query](https://tanstack.com/query/latest/docs/framework/react/overview) library.
Because we want the request to be sent only when the user presses a button, we will not employ its `useQuery` hook.
Instead, we will utilize [`useMutation`](https://tanstack.com/query/latest/docs/framework/react/guides/mutations).
182 changes: 182 additions & 0 deletions docs/frontend/tanstack-query/03-prepare-web2json-request.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,182 @@
---
sidebar_position: 1
slug: prepare-web2json-request
title: Prepare Web2Json request
authors: [nikerzetic]
description: Prepare an FDC request through a Verifier server using TanStack Query.
tags: [quickstart, ethereum, flare-smart-accounts]
keywords:
[
flare-fdc,
ethereum,
flare-smart-accounts,
evm,
flare-network,
account-abstraction,
]
unlisted: false
---

import { PrepareWeb2JsonRequestApp } from "@site/src/components/Frontend/PrepareWeb2JsonRequestCard";
import CodeBlock from "@theme/CodeBlock";
import BrowserOnly from "@docusaurus/BrowserOnly";
import PrepareWeb2JsonRequestCode from "!!raw-loader!/src/components/Frontend/PrepareWeb2JsonRequestCard";

In this guide, we will prepare a [Web2Json](/fdc/attestation-types/web2-json) attestation type request.
Shown below is a card component that accepts user input and makes the request with those parameters.

{/* TODO:(Nik) why did this stop working */}

<BrowserOnly>{() => <PrepareWeb2JsonRequestApp />}</BrowserOnly>

We will focus only on the part of the component that defines and calls the TanStack Query mutation.
The remainder of the code is mostly HTML boilerplate, though the full source code is available at the end of the guide.

Let us take a look at how we invoke the `useMutation` hook.
We provide two parameters, the `mutationFn` and `onSuccess` functions.
In a production application, we should at least also define the `onError` side effect.
You can see the full list of parameters in the [TanStack Query documentation](https://tanstack.com/query/latest/docs/framework/react/guides/mutations).

The `useMutation` hook is called within the main body of the component.
We take the `mutate` return value and call it when the `Prepare ABI-encoded request` button is clicked.
It is an async function that will run in the background.
When it succeeds, the `onSuccess` side effect is triggered.

```tsx
const { mutate } = useMutation({
mutationFn: async () => {
...
},
onSuccess: (result) => {
...
},
});
```

The mutation function constructs a request body from the parameters input in the form.
Their values are stored as React states (`useState` hook), and updated when the field values change.

```tsx
const requestBody = {
url: url,
httpMethod: httpMethod,
headers: headers,
queryParams: queryParams,
body: body,
postProcessJq: postProcessJq,
abiSignature: abiSignature,
};
```

Two additional values are necessary for the request: the attestation type and source ID.
They are UTF8 hex encoded strings, padded to 32 bytes, of `Web2Json` and `PublicWeb2` respectively.

```tsx
const attestationType = toUtf8HexString(attestationTypeBase);
const sourceId = toUtf8HexString(sourceIdBase);
```

The encoding function is as follows.

```tsx
export function toHex(data: string) {
let result = "";
for (let i = 0; i < data.length; i++) {
result += data.charCodeAt(i).toString(16);
}
return result.padEnd(64, "0");
}

export function toUtf8HexString(data: string) {
return "0x" + toHex(data);
}
```

Out of these three values - the attestation type, source ID, and request body - the mutation function constructs the request.

```tsx
const request = {
attestationType: attestationType,
sourceId: sourceId,
requestBody: requestBody,
};
```

The request is sent to the `/Web2Json/prepareRequest` endpoint at the verifier URL `https://web2json-verifier-test.flare.rocks`.
An API key needs to be provided as a header.
Though custom keys are available, the public key `00000000-0000-0000-0000-000000000000` can provide a rate-limited access.

```tsx
const response = await fetch(`${verifierUrlBase}/Web2Json/prepareRequest`, {
method: "POST",
headers: {
"X-API-KEY": apiKey,
"Content-Type": "application/json",
"Access-Control-Allow-Origin": "*",
},
body: JSON.stringify(request),
});
```

Finally, the response is returned as a JSON.
The entire `mutationFn` parameter is as follows.

```tsx
mutationFn: async () => {
const requestBody = {
url: url,
httpMethod: httpMethod,
headers: headers,
queryParams: queryParams,
body: body,
postProcessJq: postProcessJq,
abiSignature: abiSignature,
};
const attestationType = toUtf8HexString(attestationTypeBase);
const sourceId = toUtf8HexString(sourceIdBase);

const request = {
attestationType: attestationType,
sourceId: sourceId,
requestBody: requestBody,
};
const response = await fetch(
`${verifierUrlBase}/Web2Json/prepareRequest`,
{
method: "POST",
headers: {
"X-API-KEY": apiKey,
"Content-Type": "application/json",
"Access-Control-Allow-Origin": "*",
},
body: JSON.stringify(request),
}
);
return response.json();
},
```

The `onSuccess` side effect is much simpler.
It only sets the `abiEncodedRequest` React state to whatever the value of the `abiEncodedRequest` field of the result is.

```tsx
onSuccess: (result) => {
setAbiEncodedRequest(result.abiEncodedRequest);
},
```

The `abiEncodedRequest` state is then read and displayed within the component.

:::warning
In order for the `useMutation` hook to work, the app needs to be wrapped in a [`QueryClientProvider`](https://tanstack.com/query/latest/docs/framework/react/reference/QueryClientProvider) component.
Ideally, that is done at the root level of the app.
:::

The full code for the component is included here.

<CodeBlock
language="tsx"
title="Code for the PrepareWeb2JsonRequestApp component"
>
{PrepareWeb2JsonRequestCode}
</CodeBlock>
91 changes: 91 additions & 0 deletions docs/frontend/wagmi/02-get-official-contract-address.mdx
Original file line number Diff line number Diff line change
@@ -0,0 +1,91 @@
---
sidebar_position: 1
slug: get-official-contract-address
title: Get official Flare contract addresses
authors: [nikerzetic]
description: Get the addresses of official Flare smart contracts using Wagmi and the FlareContractRegistry.
tags: [intermediate, frontend, react, wagmi]
keywords: [ethereum, evm, flare-network, wagmi, tanstack-query, frontend, react]
unlisted: false
---

import useFlareContractRegistryCode from "!!raw-loader!/src/hooks/useFlareContractRegistry";
import { GetAddressApp } from "@site/src/components/Frontend/GetAddressCard";
import { AllOfficialContractsTableApp } from "@site/src/components/Frontend/AllOfficialContractsTable";
import GetAddressCardCode from "!!raw-loader!/src/components/Frontend/GetAddressCard";
import FlareContractRegistryAbi from "!!raw-loader!/src/abis/FlareContractRegistry.ts";
import ContractsListCode from "!!raw-loader!/src/components/Frontend/AllOfficialContractsTable";
import CodeBlock from "@theme/CodeBlock";
import BrowserOnly from "@docusaurus/BrowserOnly";

In this guide we will use the `useReadContract` hook from the Wagmi framework to get addresses of official Flare contracts.
The addresses could be hardcoded into the frontend, but that approach is error prone and requires manual updates.
Instead, it is recommended that the `FlareContractRegistry` contract is queried for the addresses of the official contracts.

The `FlareContractRegistry` is an official Flare contract, storing a list of contracts and their addresses.
It is deployed on the same address on each of the four Flare chains.
Its `getContractAddressByName` function maps a contract name to the corresponding contract's address.
This allows for official contracts to be easily updated in the future.

We will use the [`useReadContract`](https://wagmi.sh/react/api/hooks/useReadContract) hook from the Wagmi framework to call the `getContractAddressByName` function.
The hook takes in the following required parameters:

- `abi`: the abi of the contract being calling
- `address`: the address of the contract being called
- `functionName`: the name of the function on the called contract
- `args`: an array of parameters that the above function accepts

For additional parameters and return values, look at the [Wagmi documentation](https://wagmi.sh/react/api/hooks/useReadContract).

The values we will be passing to the hook are:

- `address`: the `FlareContractRegistry` address `0xaD67FE66660Fb8dFE9d6b1b4240d8650e30F6019` (the same on all Flare chain)
- `functionName`: `getContractAddressByName`
- `args`: the name of the contract the address of which we want to retrieve; we will input these dynamically
- `abi`:

<details>
<summary>FlareContractRegistry ABI</summary>
<CodeBlock language="ts">{FlareContractRegistryAbi}</CodeBlock>
</details>

With that, we can define a simple hook for retrieving a contract address using the `FlareContractRegistry` contract.

<CodeBlock language="tsx" title="useFlareContractRegistry.tsx">
{useFlareContractRegistryCode}
</CodeBlock>

It takes the `contractName` string parameter.
Then, it invokes the `useReadContract` Wagmi hook, and returns the result.

We can demonstrate how the `useFlareContractRegistry` hook can be used on a simple input card.
The full code for this example as well as a list of all registered contract are available bellow.

<BrowserOnly>{() => <GetAddressApp />}</BrowserOnly>

The card accepts a contract name as input.
When the `Get contract address` button is pressed, the input data is saved to the state, which triggers a rerender of the `result` component.
The `useFlareContractRegistry` hook is called and a new address fetched.
It is saved to the `contractAddress` state, and displayed at the bottom of the card.

<CodeBlock language="tsx" title="GetAddressCard.tsx">
{GetAddressCardCode}
</CodeBlock>

To enable the `useReadContract` hook, the card is wrapped in a `QueryClientProvider` and a `WagmiProvider` component.
In a real project, those would be placed at the root level of the app.
To learn more about these, look at the [TanStack Query](https://tanstack.com/query/latest/docs/framework/react/reference/QueryClientProvider) and [Wagmi](https://wagmi.sh/react/api/WagmiProvider) documentation for the corresponding components.

<details >

<summary>List of available official contracts</summary>

<BrowserOnly>{() => <AllOfficialContractsTableApp />}</BrowserOnly>

This list is also prepared dynamically.
The contract names are fetched from the `FlareContractRegistry`, by calling its `getAllContracts` function.

<CodeBlock language="tsx">
{ContractsListCode}
</CodeBlock>
</details>
8 changes: 8 additions & 0 deletions docs/tags.yml
Original file line number Diff line number Diff line change
Expand Up @@ -40,3 +40,11 @@ infrastructure:
label: infrastructure
flare-smart-accounts:
label: flare-smart-accounts
frontend:
label: frontend
react:
label: react
wagmi:
label: wagmi
tanstack-query:
label: tanstack-query
Loading