11import type { Metadata } from "next" ;
2+ import Image from "next/image" ;
23import { defineChain , getContract } from "thirdweb" ;
34import { getCurrencyMetadata } from "thirdweb/extensions/erc20" ;
5+ import { resolveScheme } from "thirdweb/storage" ;
46import { checksumAddress } from "thirdweb/utils" ;
57import { getPaymentLink } from "@/api/universal-bridge/links" ;
8+ import { NEXT_PUBLIC_THIRDWEB_API_HOST } from "@/constants/public-envs" ;
9+ import { API_SERVER_SECRET } from "@/constants/server-envs" ;
610import { getClientThirdwebClient } from "@/constants/thirdweb-client.client" ;
711import { PayPageWidget } from "../components/client/PayPageWidget.client" ;
12+ import { payAppThirdwebClient } from "../constants" ;
813
914const title = "thirdweb Pay" ;
1015const description = "Fast, secure, and simple payments." ;
@@ -38,13 +43,15 @@ export default async function PayPage({
3843 chain : defineChain ( Number ( paymentLink . destinationToken . chainId ) ) ,
3944 client : getClientThirdwebClient ( undefined ) ,
4045 } ) ;
41- const {
42- symbol,
43- decimals,
44- name : tokenName ,
45- } = await getCurrencyMetadata ( {
46+ const currencyMetadataPromise = getCurrencyMetadata ( {
4647 contract : tokenContract ,
4748 } ) ;
49+
50+ const projectMetadataPromise = getProjectMetadata ( paymentLink . clientId ) ;
51+
52+ const [ { symbol, decimals, name : tokenName } , projectMetadata ] =
53+ await Promise . all ( [ currencyMetadataPromise , projectMetadataPromise ] ) ;
54+
4855 const token = {
4956 address : checksumAddress ( paymentLink . destinationToken . address ) ,
5057 chainId : Number ( paymentLink . destinationToken . chainId ) ,
@@ -54,18 +61,62 @@ export default async function PayPage({
5461 } ;
5562
5663 return (
57- < PayPageWidget
58- amount = { paymentLink . amount ? BigInt ( paymentLink . amount ) : undefined }
59- chainId = { Number ( paymentLink . destinationToken . chainId ) }
60- clientId = { undefined } // Payment links don't need to use the same client ID to be executed
61- image = { paymentLink . imageUrl }
62- name = { paymentLink . title }
63- paymentLinkId = { id }
64- purchaseData = { paymentLink . purchaseData }
65- recipientAddress = { paymentLink . receiver }
66- redirectUri = { redirectUri }
67- theme = { theme }
68- token = { token }
69- />
64+ < div className = "flex z-10 flex-col lg:flex-row h-full w-full" >
65+ < header className = "min-w-full lg:min-w-[500px] border-b lg:border-r lg:h-full bg-card flex flex-col gap-4 items-start p-4 lg:p-8" >
66+ < div className = "flex flex-row items-center justify-center gap-4" >
67+ { projectMetadata . image && (
68+ < Image
69+ src = { resolveScheme ( {
70+ uri : projectMetadata . image ,
71+ client : payAppThirdwebClient ,
72+ } ) }
73+ alt = { projectMetadata . name }
74+ width = { 25 }
75+ height = { 25 }
76+ className = "rounded-full overflow-hidden"
77+ />
78+ ) }
79+ < h2 className = "text-xl font-bold" > { projectMetadata . name } </ h2 >
80+ </ div >
81+ { projectMetadata . description && (
82+ < p className = "text-sm text-muted-foreground" >
83+ { projectMetadata . description }
84+ </ p >
85+ ) }
86+ </ header >
87+ < main className = "flex justify-center p-12 w-full items-center" >
88+ < PayPageWidget
89+ amount = { paymentLink . amount ? BigInt ( paymentLink . amount ) : undefined }
90+ chainId = { Number ( paymentLink . destinationToken . chainId ) }
91+ clientId = { undefined } // Payment links don't need to use the same client ID to be executed
92+ image = { paymentLink . imageUrl }
93+ name = { paymentLink . title }
94+ paymentLinkId = { id }
95+ purchaseData = { paymentLink . purchaseData }
96+ recipientAddress = { paymentLink . receiver }
97+ redirectUri = { redirectUri }
98+ theme = { theme }
99+ token = { token }
100+ />
101+ </ main >
102+ </ div >
70103 ) ;
71104}
105+
106+ async function getProjectMetadata ( clientId : string ) {
107+ const url = new URL ( `${ NEXT_PUBLIC_THIRDWEB_API_HOST } /v2/keys/lookup` ) ;
108+ url . searchParams . append ( "clientId" , clientId ) ;
109+ const response = await fetch ( url . toString ( ) , {
110+ headers : {
111+ "x-service-api-key" : API_SERVER_SECRET ,
112+ } ,
113+ } ) ;
114+ if ( ! response . ok ) {
115+ throw new Error ( "Failed to fetch project" ) ;
116+ }
117+
118+ const { data } = ( await response . json ( ) ) as {
119+ data : { name : string ; image : string | null ; description : string | null } ;
120+ } ;
121+ return data ;
122+ }
0 commit comments