> ## Documentation Index
> Fetch the complete documentation index at: https://docs.agg.market/llms.txt
> Use this file to discover all available pages before exploring further.

> ## Agent Instructions
> To integrate AGG, start with Quickstart: REST (https://docs.agg.market/quickstart/rest), then Order lifecycle & statuses (https://docs.agg.market/concepts/order-lifecycle).
> Track every trade until it reaches a terminal status. Before retrying a failed or timed-out call, read Errors, retries & idempotency (https://docs.agg.market/concepts/errors).
> The API reference is generated from https://docs.agg.market/openapi/openapi.json.

# Quickstart: React

> Wire the AGG client, provider, sign-in, and a first trade into a React app

<Info>
  **You'll need:** an app ID ([Base URL, app IDs & API keys](/environments)), your site's
  origin in the app's allowed origins, and React 18 or later.
  **Result:** a React app with AGG data, sign-in, and a buy that is tracked to a final state.
</Info>

Install the packages you need. See the [Packages overview](/packages/overview) for what each one
does and its peer dependencies. Every layer uses the same client from `@agg-build/sdk`.

## 1. Create the client and provider

Pick the layer that fits your app.

<Tabs>
  <Tab title="Hooks (bring your own UI)">
    Hooks handle WebSocket subscriptions, caching, and cleanup.

    ```tsx theme={null}
    import { AggProvider, QueryClient, QueryClientProvider } from "@agg-build/hooks";
    import { createAggClient } from "@agg-build/sdk";

    const client = createAggClient({
      baseUrl: "https://api.agg.market",
      appId: "your-app-id",
      wsUrl: "wss://ws.agg.market/ws",
    });

    const queryClient = new QueryClient();

    function App() {
      return (
        <QueryClientProvider client={queryClient}>
          <AggProvider client={client}>
            <MyApp />
          </AggProvider>
        </QueryClientProvider>
      );
    }
    ```

    Then use hooks in any component:

    ```tsx theme={null}
    import { useLiveMarket, useMarketChart, useSmartRoute } from "@agg-build/hooks";

    function MarketView({ venueMarketId, venueMarketOutcomeId }) {
      const { orderbook } = useLiveMarket(venueMarketId);
      const { data: chart } = useMarketChart({
        marketId: venueMarketOutcomeId,
        interval: "5m",
        startTs: Date.now() - 86_400_000,
        endTs: Date.now(),
      });
      const { data: route } = useSmartRoute({
        venueMarketOutcomeId,
        tradeSide: "buy",
        maxSpend: 50,
      });

      const primaryVenue = chart?.primaryVenue;
      const candles = primaryVenue ? chart.venues[primaryVenue]?.candles ?? [] : [];

      return <YourChart data={candles} orderbook={orderbook} route={route} />;
    }
    ```

    | Hook | What it does |
    | - | - |
    | `useLiveMarket(id)` | Live orderbook via WebSocket |
    | `useMarketChart({ marketId, interval, startTs, endTs, countBack })` | Outcome chart history, under `data.primaryVenue` |
    | `useSmartRoute({ venueMarketOutcomeId, tradeSide, maxSpend/sellShares })` | Quote across available liquidity |
    | `useLiveTrades(id)` | Real-time trade feed |
    | `useMarketOrderbook({ marketId })` | Aggregated orderbook and venue breakdown |
    | `useMarketArb(marketId)` | Live cross-venue arbitrage return for one market |
    | `useArbFeed()` | Live arbitrage returns for many markets |
  </Tab>

  <Tab title="UI components">
    Pre-built, themed components.

    ```tsx theme={null}
    import "@agg-build/ui/styles.css";
    import { QueryClient, QueryClientProvider } from "@agg-build/hooks";
    import { createAggClient } from "@agg-build/sdk";
    import { AggProvider } from "@agg-build/ui";

    const client = createAggClient({
      baseUrl: "https://api.agg.market",
      appId: "your-app-id",
      wsUrl: "wss://ws.agg.market/ws",
    });

    const queryClient = new QueryClient();

    function App() {
      return (
        <QueryClientProvider client={queryClient}>
          <AggProvider
            client={client}
            config={{
              general: { locale: "en-US", theme: "light" },
              features: { enableAnimations: true, enableLiveUpdates: true },
            }}
          >
            <MyApp />
          </AggProvider>
        </QueryClientProvider>
      );
    }
    ```

    Then use components:

    ```tsx theme={null}
    import { EventMarketPage } from "@agg-build/ui/pages";
    import { MarketDetails } from "@agg-build/ui/events";
    import { LineChart } from "@agg-build/ui/primitives";

    // Full event page: hero chart, market cards, orderbooks, all live
    <EventMarketPage eventId="..." />

    // Or individual components
    <MarketDetails event={event} marketId={marketId} defaultTab="graph" />
    <LineChart series={series} chartType="candlestick" height={320} live />
    ```

    See the [Event Market Page](/components/pages/event-market-page) and
    [Market Details](/components/events/market-details) references, and
    [Customize UI](/components/customization) for fonts, colors, copy, and slots.
  </Tab>
</Tabs>

## 2. Sign the user in

`@agg-build/auth` adds a connect button and sign-in methods on top of the provider. Trading calls
need a signed-in user.

```tsx theme={null}
import "@agg-build/ui/styles.css";
import { QueryClient, QueryClientProvider } from "@agg-build/hooks";
import { createAggClient } from "@agg-build/sdk";
import { AggProvider } from "@agg-build/ui";
import { AggAuthProvider, ConnectButton, createGoogleAuthMethod } from "@agg-build/auth";
import { useSiweAuthMethod } from "@agg-build/auth/siwe";
import { WagmiProvider } from "wagmi";
import { wagmiConfig } from "./wagmi-config";

const client = createAggClient({
  baseUrl: "https://api.agg.market",
  appId: "your-app-id",
  wsUrl: "wss://ws.agg.market/ws",
});

const queryClient = new QueryClient();

function AuthButton() {
  const siwe = useSiweAuthMethod({ statement: "Sign in" });
  return (
    <AggAuthProvider methods={[siwe, createGoogleAuthMethod()]}>
      <ConnectButton />
    </AggAuthProvider>
  );
}

function App() {
  return (
    <WagmiProvider config={wagmiConfig}>
      <QueryClientProvider client={queryClient}>
        <AggProvider client={client}>
          <AuthButton />
        </AggProvider>
      </QueryClientProvider>
    </WagmiProvider>
  );
}
```

See the [Connect Button reference](/components/auth/connect-button) and
[Authentication & sessions](/concepts/authentication) for every provider.

## 3. Buy and track to a final state

The user needs a balance first. See [Funding & withdrawals](/concepts/funding) for deposit
addresses. Then quote, fill, and poll the execution status until `terminal` is `true`.

```tsx theme={null}
import { useState } from "react";
import { useQuery } from "@tanstack/react-query";
import { useAggClient, useExecuteManaged, useSmartRoute } from "@agg-build/hooks";

function BuyButton({ venueMarketOutcomeId }: { venueMarketOutcomeId: string }) {
  const client = useAggClient();
  const [quoteId, setQuoteId] = useState<string | null>(null);

  const { data: quote } = useSmartRoute({ venueMarketOutcomeId, tradeSide: "buy", maxSpend: 5 });
  const execute = useExecuteManaged({ onSuccess: (fill) => setQuoteId(fill.quoteId) });

  const { data: status } = useQuery({
    queryKey: ["execution-status", quoteId],
    queryFn: () => client.getExecutionStatus({ quoteId: quoteId! }),
    enabled: !!quoteId,
    // Poll at the interval the API suggests; stop once the trade is terminal.
    refetchInterval: (query) =>
      query.state.data?.terminal ? false : (query.state.data?.pollAfterMs ?? 1000),
  });

  if (status?.terminal) return <p>Done: {status.overallState}</p>;
  if (quoteId) return <p>Executing: {status?.overallState ?? "created"}</p>;

  return (
    <button
      className="cursor-pointer disabled:cursor-not-allowed"
      disabled={quote?.status !== "ok" || execute.isPending}
      onClick={() => quote && execute.mutate({ quoteId: quote.quoteId })}
    >
      Buy $5
    </button>
  );
}
```

Stop polling when `terminal` is `true`. `overallState` then reads `filled`, `partially_filled`,
`failed`, `cancelled`, or `expired`. Read [Order lifecycle & statuses](/concepts/order-lifecycle)
for what each state means.

## WebSocket endpoint

The SDK and hooks manage the socket, reconnection, resnapshots, and orderbook integrity checks.
If you open raw sockets yourself, connect to:

```
wss://ws.agg.market/ws?appId=YOUR_APP_ID
```

See [WebSocket Protocol](/api/websocket).

## Next steps

<CardGroup cols={2}>
  <Card title="Quickstart: REST" icon="terminal" href="/quickstart/rest">
    The same flow with curl, for backends and agents.
  </Card>

  <Card title="Order lifecycle" icon="list-check" href="/concepts/order-lifecycle">
    Every order status and how to track it.
  </Card>

  <Card title="Real-Time Orderbook" icon="code" href="/recipes/websocket-orderbook">
    Live orderbook rendering with the SDK, hooks, and UI.
  </Card>

  <Card title="Customize UI" icon="paintbrush" href="/components/customization">
    Brand AGG components with CSS variables, labels, formatting, and slots.
  </Card>
</CardGroup>
