# Guide: Using ChainRender with React

`@chainrender/client/react` provides a component and a hook for rendering on-chain apps in React. React is an
**optional peer dependency** — install it alongside the SDK:

```bash
npm install @chainrender/client react react-dom
```

## The `<ChainRenderView>` component

Drop-in rendering of a deployed app, with loading and fail-closed states handled:

```tsx
import { ChainRenderView } from "@chainrender/client/react";

const deployment = { rpc: "https://…", router: "0xRenderRouter" };

export function App() {
  return <ChainRenderView deployment={deployment} hash="0xAppHash" />;
}
```

Props: `deployment` ({ rpc, router }), `hash`, and optional `resolvers`, `styleSheet`, `className`.

## The `useChainRenderComponent` hook

For custom rendering, the hook gives you the resolved HTML plus loading/error state:

```tsx
import { useChainRenderComponent } from "@chainrender/client/react";

function MyView() {
  const { html, loading, error } = useChainRenderComponent(deployment, "0xAppHash");
  if (loading) return <Spinner />;
  if (error) return <Fallback error={error} />;
  return <div dangerouslySetInnerHTML={{ __html: html! }} />;
}
```

The HTML comes from the chain (a free `eth_call`) and is safe by construction — the interpreter escapes all
resolver output, so there's no injection risk in the `__html`.

## Authoring in React

Compose and grade with the core SDK (framework-agnostic), then render with the React layer:

```tsx
import { compose, compileComponent, grade } from "@chainrender/client";

const app = compose.box([ compose.heading("Hi"), compose.text("On-chain.") ]);
const built = compileComponent(app);
const g = grade(app);   // show a live grade badge in your UI
```

## Related
- **[Reference → React API](../reference/react.md)** · **[Build, Grade & Style Before Deploy](./test-before-deploy.md)**

## React is the shell, not the renderer

Use React for chrome — routing, wallet connection, layout — but let ChainRender render the actual UI: call
`renderComponent`, get on-chain HTML, display it. React should **not** re-implement what the component renders, and
you should **not** fetch on-chain data with viem and hand-render it (that bypasses ChainRender entirely). See
**[Building Correctly](../concepts/building-correctly.md)**.
