diff --git a/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/CookieBannerSnippetPage.tsx b/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/CookieBannerSnippetPage.tsx index 397ec7100..84d2174b2 100644 --- a/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/CookieBannerSnippetPage.tsx +++ b/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/CookieBannerSnippetPage.tsx @@ -15,12 +15,36 @@ import { useTranslate } from "@probo/i18n"; import { Card } from "@probo/ui"; import type { ReactNode } from "react"; +import { type PreloadedQuery, usePreloadedQuery } from "react-relay"; +import { graphql } from "relay-runtime"; + +import type { CookieBannerSnippetPageQuery } from "#/__generated__/core/CookieBannerSnippetPageQuery.graphql"; import { CodeSnippets } from "./_components/CodeSnippets"; import { ThemePreview } from "./_components/ThemePreview"; -export default function CookieBannerSnippetPage() { +export const cookieBannerSnippetPageQuery = graphql` + query CookieBannerSnippetPageQuery($cookieBannerId: ID!) { + node(id: $cookieBannerId) { + __typename + ... on CookieBanner { + ...ThemePreview_cookieBanner + } + } + } +`; + +interface CookieBannerSnippetPageProps { + queryRef: PreloadedQuery; +} + +export default function CookieBannerSnippetPage({ queryRef }: CookieBannerSnippetPageProps) { const { __ } = useTranslate(); + const data = usePreloadedQuery(cookieBannerSnippetPageQuery, queryRef); + + if (data.node.__typename !== "CookieBanner") { + throw new Error("invalid type for node"); + } return (
@@ -37,7 +61,7 @@ export default function CookieBannerSnippetPage() { title={__("Customize the theme")} description={__("Adjust colors, fonts, and spacing to match your brand. The generated CSS snippet can be added to your website to override the default banner styles.")} > - + . +// +// Permission to use, copy, modify, and/or distribute this software for any +// purpose with or without fee is hereby granted, provided that the above +// copyright notice and this permission notice appear in all copies. +// +// THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES WITH +// REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF MERCHANTABILITY +// AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR ANY SPECIAL, DIRECT, +// INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES WHATSOEVER RESULTING FROM +// LOSS OF USE, DATA OR PROFITS, WHETHER IN AN ACTION OF CONTRACT, NEGLIGENCE OR +// OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR +// PERFORMANCE OF THIS SOFTWARE. + +import { Suspense, useEffect } from "react"; +import { useQueryLoader } from "react-relay"; +import { useParams } from "react-router"; + +import type { CookieBannerSnippetPageQuery } from "#/__generated__/core/CookieBannerSnippetPageQuery.graphql"; +import { PageSkeleton } from "#/components/skeletons/PageSkeleton"; + +import CookieBannerSnippetPage, { cookieBannerSnippetPageQuery } from "./CookieBannerSnippetPage"; + +export default function CookieBannerSnippetPageLoader() { + const { cookieBannerId } = useParams<{ cookieBannerId: string }>(); + const [queryRef, loadQuery] = useQueryLoader(cookieBannerSnippetPageQuery); + + useEffect(() => { + if (cookieBannerId) { + loadQuery({ cookieBannerId }); + } + }, [loadQuery, cookieBannerId]); + + if (!queryRef) { + return ; + } + + return ( + }> + + + ); +} diff --git a/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/_components/ThemePreview.tsx b/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/_components/ThemePreview.tsx index 87839406d..b7bdacd44 100644 --- a/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/_components/ThemePreview.tsx +++ b/apps/console/src/pages/organizations/cookie-banners/configuration/snippet/_components/ThemePreview.tsx @@ -15,6 +15,10 @@ import { useTranslate } from "@probo/i18n"; import { Button, Card, Field, Input, useToast } from "@probo/ui"; import { useCallback, useMemo, useState } from "react"; +import { useFragment } from "react-relay"; +import { graphql } from "relay-runtime"; + +import type { ThemePreview_cookieBanner$key } from "#/__generated__/core/ThemePreview_cookieBanner.graphql"; type CSSVariable = { key: string; @@ -49,7 +53,19 @@ function buildCSSSnippet(values: Record): string { return `probo-cookie-banner {\n${overrides.join("\n")}\n}`; } -export function ThemePreview() { +export const themePreviewFragment = graphql` + fragment ThemePreview_cookieBanner on CookieBanner { + showBranding + } +`; + +interface ThemePreviewProps { + cookieBannerKey: ThemePreview_cookieBanner$key; +} + +export function ThemePreview({ cookieBannerKey }: ThemePreviewProps) { + const cookieBanner = useFragment(themePreviewFragment, cookieBannerKey); + const { showBranding } = cookieBanner; const { __ } = useTranslate(); const { toast } = useToast(); @@ -148,7 +164,7 @@ export function ThemePreview() { className="relative flex items-end justify-center bg-[repeating-conic-gradient(#e5e7eb_0%_25%,transparent_0%_50%)] bg-size-[20px_20px] p-8" style={{ minHeight: 280, ...previewStyle }} > - +
@@ -168,7 +184,7 @@ export function ThemePreview() { ); } -function BannerPreview() { +function BannerPreview({ showBranding }: { showBranding: boolean }) { return (
-
- Privacy by - {" "} - - {" "} - Probo -
+ {showBranding && ( +
+ Privacy by + {" "} + + {" "} + Probo +
+ )} ); } diff --git a/apps/console/src/pages/organizations/cookie-banners/routes.ts b/apps/console/src/pages/organizations/cookie-banners/routes.ts index 4c6e76ee2..25b6912fb 100644 --- a/apps/console/src/pages/organizations/cookie-banners/routes.ts +++ b/apps/console/src/pages/organizations/cookie-banners/routes.ts @@ -57,7 +57,7 @@ export const cookieBannerRoutes = [ { path: "snippet", Fallback: LinkCardSkeleton, - Component: lazy(() => import("#/pages/organizations/cookie-banners/configuration/snippet/CookieBannerSnippetPage")), + Component: lazy(() => import("#/pages/organizations/cookie-banners/configuration/snippet/CookieBannerSnippetPageLoader")), }, ], }, diff --git a/pkg/server/api/console/v1/graphql/cookie_banner.graphql b/pkg/server/api/console/v1/graphql/cookie_banner.graphql index 6eadb1895..29a37a238 100644 --- a/pkg/server/api/console/v1/graphql/cookie_banner.graphql +++ b/pkg/server/api/console/v1/graphql/cookie_banner.graphql @@ -84,6 +84,7 @@ type CookieBanner implements Node { privacyPolicyUrl: String! consentExpiryDays: Int! consentMode: CookieConsentMode! + showBranding: Boolean! organization: Organization @goField(forceResolver: true) diff --git a/pkg/server/api/console/v1/types/cookie_banner.go b/pkg/server/api/console/v1/types/cookie_banner.go index 286871b5b..1fb613004 100644 --- a/pkg/server/api/console/v1/types/cookie_banner.go +++ b/pkg/server/api/console/v1/types/cookie_banner.go @@ -72,6 +72,7 @@ func NewCookieBanner(b *coredata.CookieBanner) *CookieBanner { PrivacyPolicyURL: b.PrivacyPolicyURL, ConsentExpiryDays: b.ConsentExpiryDays, ConsentMode: b.ConsentMode, + ShowBranding: b.ShowBranding, CreatedAt: b.CreatedAt, UpdatedAt: b.UpdatedAt, }