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

# Sharing an Entire Thread

> Let users generate a shareable link for the full conversation thread.

<Note>
  This guide assumes that you have completed the [Quickstart](/guides/conversational/getting-started).
</Note>

<Tip>
  An example project demonstrating implementation of this guide can be found
  [here](https://github.com/thesysdev/examples/tree/main/sharing-generated-ui).
</Tip>

Enable thread-level sharing with the `C1ShareThread` component. You provide a `generateShareLink(messages)` function; the SDK gathers messages, opens a modal, and handles copying/confirmation.

<Steps>
  <Step title="Frontend: Add a Thread Share trigger">
    First, destructure the `C1Chat` component as explained the [Integrating Custom Components](/guides/custom-components) guide, so that you can integrate a custom header. Next,
    use the `C1ShareThread` component to display a share button in your chat header, which automatically opens a modal to generate a share link using the `generateShareLink` function you defined.

    The updated code for the chat page will look something like this:

    ```tsx page.tsx [expandable] theme={null}
    // ... imports

    export default function Home() {
      // ... create a threadManager and threadListManager here

      const selectedThreadId = threadListManager.selectedThreadId;

      return (
        <ChatProvider
          threadListManager={threadListManager}
          threadManager={threadManager}
        >
          <Container
            logoUrl={"https://www.thesys.dev/favicon.ico"}
            agentName="C1Chat"
          >
            <SidebarContainer>
              <SidebarHeader />
              <SidebarContent>
                <NewChatButton />
                <SidebarSeparator />
                <ThreadList />
              </SidebarContent>
            </SidebarContainer>
            <ThreadContainer>
              <MobileHeader />
              <div className="flex w-full items-center justify-end p-4">
                <C1ShareThread
                  generateShareLink={
                    !selectedThreadId
                      ? undefined
                      : async () => {
                          const baseUrl = window.location.origin;
                          return `${baseUrl}/shared/${selectedThreadId}`;
                        }
                  }
                />
              </div>
              <ScrollArea>
                <Messages />
              </ScrollArea>
              <Composer />
            </ThreadContainer>
          </Container>
        </ChatProvider>
      );
    }
    ```

    <Tip>
      For details on how to create a `threadManager` and a `threadListManager`,
      refer to [this guide](/guides/conversational/persistence)
    </Tip>

    <Tip>
      Want a custom button? Provide `customTrigger` to `C1ShareThread`:

      ```tsx theme={null}
      <C1ShareThread
        customTrigger={<button>Share Thread</button>}
        generateShareLink={
          !selectedThreadId
            ? undefined
            : async () => {
                const baseUrl = window.location.origin;
                return `${baseUrl}/shared/${selectedThreadId}`;
              }
        }
      />
      ```
    </Tip>
  </Step>

  <Step title="Frontend: Add a component to render the shared thread">
    Create a route and component on the frontend to render the shared thread:

    ```tsx /app/shared/[threadId]/page.tsx [expandable] theme={null}
    "use client";

    import type { Message } from "@crayonai/react-core";
    import { C1ChatViewer } from "@thesysai/genui-sdk";
    import { use, useEffect, useState } from "react";
    import "@crayonai/react-ui/styles/index.css";
    import { Loader } from "@/app/components/Loader";

    export default function ViewSharedPage({
      params,
    }: {
      params: Promise<{ threadId: string }>;
    }) {
      const { threadId } = use(params);
      const [messages, setMessages] = useState<Message[]>([]);

      useEffect(() => {
        const fetchMessages = async () => {
          const response = await fetch(`/api/share/${threadId}`);
          const messages = await response.json();
          setMessages(messages);
        };
        fetchMessages();
      }, [threadId]);

      if (!messages || !messages.length) return <Loader fullScreen />;

      return <C1ChatViewer messages={messages} />;
    }
    ```
  </Step>

  <Step title="Backend: Implement the thread share endpoint">
    Implement an endpoint that returns the thread for a given `threadId`.

    <Note>
      Implement a message store to store the message history. If you've followed the [Quickstart](/guides/conversational/getting-started), you'll have a message store already, which you can move
      to a common location (such as `/lib/messageStore.ts`) and modify it to persist message history across API routes and requests as follows:

      ```ts /lib/messageStore.ts [expandable] theme={null}
      import OpenAI from "openai";

      export type DBMessage = OpenAI.Chat.ChatCompletionMessageParam & {
        id?: string;
      };

      const messagesStore: {
        [threadId: string]: DBMessage[];
      } = {};

      export const getMessageStore = (id: string) => {
        const messageList = await fetchMessagesFromDB(id); // fetch from db here
        return {
          addMessage: (message: DBMessage) => {
            // save to db here
          },
          messageList,
        };
      };
      ```
    </Note>

    ```ts /app/api/share/[threadId]/route.ts theme={null}
    import { NextRequest, NextResponse } from "next/server";
    import { getMessageStore } from "@/lib/messageStore";

    export async function GET(
      req: NextRequest,
      { params }: { params: Promise<{ threadId: string }> }
    ) {
      const { threadId } = await params;

      if (!threadId) {
        return NextResponse.json(
          { error: "Thread ID is required" },
          { status: 400 }
        );
      }

      const messageStore = getMessageStore(threadId);

      return NextResponse.json(messageStore.messageList);
    }
    ```
  </Step>

  <Step title="Test">
    * Open a conversation with multiple messages.
    * Click the thread share button.
    * Generate and copy the link from the modal.

    <Frame>
      <img src="https://mintcdn.com/thesys/3DUVqK628WbZ1Rok/guides/conversational/sharing/assets/sharing-thread.jpeg?fit=max&auto=format&n=3DUVqK628WbZ1Rok&q=85&s=61e02a6f12d198b27181e295b78e70c1" alt="Sharing a chat thread" width="5088" height="3448" data-path="guides/conversational/sharing/assets/sharing-thread.jpeg" />
    </Frame>
  </Step>
</Steps>
