diff --git a/.changeset/real-cars-sell.md b/.changeset/real-cars-sell.md
new file mode 100644
index 00000000000..b54a36c0553
--- /dev/null
+++ b/.changeset/real-cars-sell.md
@@ -0,0 +1,22 @@
+---
+"thirdweb": minor
+---
+
+Add SiteLink component for creating wallet-aware links between thirdweb-enabled sites. This component automatically adds wallet connection parameters to the target URL when a wallet is connected, enabling seamless wallet state sharing between sites.
+
+Example:
+```tsx
+import { SiteLink } from "thirdweb/react";
+
+function App() {
+ return (
+
+ Visit thirdweb.com with connected wallet
+
+ );
+}
+```
diff --git a/packages/thirdweb/src/exports/react.ts b/packages/thirdweb/src/exports/react.ts
index 69f34dac43a..8ba3756c8c4 100644
--- a/packages/thirdweb/src/exports/react.ts
+++ b/packages/thirdweb/src/exports/react.ts
@@ -196,5 +196,6 @@ export type {
LensProfile,
} from "../social/types.js";
-// Site Embed
+// Site Embed and Linking
export { SiteEmbed } from "../react/web/ui/SiteEmbed.js";
+export { SiteLink } from "../react/web/ui/SiteLink.js";
diff --git a/packages/thirdweb/src/react/web/ui/SiteEmbed.tsx b/packages/thirdweb/src/react/web/ui/SiteEmbed.tsx
index 041dc148d48..0327b0cb4df 100644
--- a/packages/thirdweb/src/react/web/ui/SiteEmbed.tsx
+++ b/packages/thirdweb/src/react/web/ui/SiteEmbed.tsx
@@ -17,14 +17,14 @@ import { useActiveWallet } from "../../core/hooks/wallets/useActiveWallet.js";
*
* @param {Object} props - The props to pass to the iframe
* @param {String} props.src - The URL of the site to embed
- * @param {ThirdwebClient} props.client - The client to use for the embedded site
- * @param {Ecosystem} [props.ecosystem] - The ecosystem to use for the embedded site
+ * @param {ThirdwebClient} props.client - The current site's thirdweb client
+ * @param {Ecosystem} [props.ecosystem] - The ecosystem to use for the wallet connection in the embedded site
*
* @example
* ```tsx
* import { SiteEmbed } from "thirdweb/react";
*
- *
+ *
* ```
*/
export function SiteEmbed({
diff --git a/packages/thirdweb/src/react/web/ui/SiteLink.test.tsx b/packages/thirdweb/src/react/web/ui/SiteLink.test.tsx
new file mode 100644
index 00000000000..4dea470b0dd
--- /dev/null
+++ b/packages/thirdweb/src/react/web/ui/SiteLink.test.tsx
@@ -0,0 +1,48 @@
+import { describe, expect, it } from "vitest";
+import { render, waitFor } from "../../../../test/src/react-render.js";
+import { TEST_CLIENT } from "../../../../test/src/test-clients.js";
+import { SiteLink } from "./SiteLink.js";
+
+describe("SiteLink", () => {
+ it("renders anchor with correct href", () => {
+ const testUrl = "https://example.com/";
+ const { container } = render(
+
+ Test Link
+ ,
+ );
+
+ const anchor = container.querySelector("a");
+ expect(anchor).toBeTruthy();
+ expect(anchor?.href).toBe(testUrl);
+ expect(anchor?.textContent).toBe("Test Link");
+ });
+
+ it("throws error if clientId is not provided", () => {
+ const testUrl = "https://example.com/";
+ expect(() =>
+ render(
+ // biome-ignore lint/suspicious/noExplicitAny: testing invalid input
+
+ Test Link
+ ,
+ ),
+ ).toThrow("The SiteLink client must have a clientId");
+ });
+
+ it("adds wallet params to url when wallet is connected", async () => {
+ const testUrl = "https://example.com/";
+ const { container } = render(
+
+ Test Link
+ ,
+ {
+ setConnectedWallet: true,
+ },
+ );
+
+ const anchor = container.querySelector("a");
+ expect(anchor).toBeTruthy();
+ await waitFor(() => expect(anchor?.href).toContain("walletId="));
+ });
+});
diff --git a/packages/thirdweb/src/react/web/ui/SiteLink.tsx b/packages/thirdweb/src/react/web/ui/SiteLink.tsx
new file mode 100644
index 00000000000..f41a77989dd
--- /dev/null
+++ b/packages/thirdweb/src/react/web/ui/SiteLink.tsx
@@ -0,0 +1,86 @@
+"use client";
+import { useQuery } from "@tanstack/react-query";
+import type { ThirdwebClient } from "../../../client/client.js";
+import { getLastAuthProvider } from "../../../react/core/utils/storage.js";
+import { webLocalStorage } from "../../../utils/storage/webStorage.js";
+import { isEcosystemWallet } from "../../../wallets/ecosystem/is-ecosystem-wallet.js";
+import { ClientScopedStorage } from "../../../wallets/in-app/core/authentication/client-scoped-storage.js";
+import type { Ecosystem } from "../../../wallets/in-app/core/wallet/types.js";
+import { useActiveWallet } from "../../core/hooks/wallets/useActiveWallet.js";
+
+/**
+ * Creates a link to another thirdweb-supported site with wallet connection parameters.
+ *
+ * @note The target site must support the connected wallet (ecosystem or in-app).
+ *
+ * @param {Object} props - The props to pass to the anchor tag
+ * @param {String} props.href - The URL of the site to link to
+ * @param {ThirdwebClient} props.client - The current site's thirdweb client
+ * @param {Ecosystem} [props.ecosystem] - The ecosystem to use for the wallet connection in the target site
+ * @param {React.ReactNode} props.children - The content to render inside the link
+ *
+ * @example
+ * ```tsx
+ * import { SiteLink } from "thirdweb/react";
+ *
+ *
+ * Visit Site
+ *
+ * ```
+ */
+export function SiteLink({
+ href,
+ client,
+ ecosystem,
+ children,
+ ...props
+}: {
+ href: string;
+ client: ThirdwebClient;
+ ecosystem?: Ecosystem;
+ children: React.ReactNode;
+} & Omit, "href">) {
+ if (!client.clientId) {
+ throw new Error("The SiteLink client must have a clientId");
+ }
+
+ const activeWallet = useActiveWallet();
+ const walletId = activeWallet?.id;
+
+ const {
+ data: { authProvider, authCookie } = {},
+ } = useQuery({
+ queryKey: ["site-link", walletId, href, client.clientId, ecosystem],
+ enabled:
+ activeWallet && (isEcosystemWallet(activeWallet) || walletId === "inApp"),
+ queryFn: async () => {
+ const storage = new ClientScopedStorage({
+ storage: webLocalStorage,
+ clientId: client.clientId,
+ ecosystem,
+ });
+
+ const authProvider = await getLastAuthProvider(webLocalStorage);
+ const authCookie = await storage.getAuthCookie();
+
+ return { authProvider, authCookie };
+ },
+ });
+
+ const url = new URL(href);
+ if (walletId) {
+ url.searchParams.set("walletId", walletId);
+ }
+ if (authProvider) {
+ url.searchParams.set("authProvider", authProvider);
+ }
+ if (authCookie) {
+ url.searchParams.set("authCookie", authCookie);
+ }
+
+ return (
+
+ {children}
+
+ );
+}