Avoiding Duplicate API Requests in generateMetadata and Page When Using cookies() or headers()
Answered
Black Caiman posted this in #help-forum
Black CaimanOP
I have an API endpoint that only needs to be called once to fetch both the SEO and the data required for rendering. Therefore, I called this function in both generateMetadata and Page. However, I noticed that when I use cookies() or headers(), this request gets made twice. How can I make this request occur only once? I tried using cache and next: { revalidate: 3600 } in fetch, but it didn't cache.
Answered by ᴉuɐpɹɐɐ
where is the
try
cache()?try
const cachedGetData = cache(async () => {
const cookiesObj = cookies()
return await getdata(cookiesObj)
})17 Replies
@Black Caiman I have an API endpoint that only needs to be called once to fetch both the SEO and the data required for rendering. Therefore, I called this function in both generateMetadata and Page. However, I noticed that when I use cookies() or headers(), this request gets made twice. How can I make this request occur only once? I tried using cache and next: { revalidate: 3600 } in fetch, but it didn't cache.
try wrapping your function wth
cache() from "react"@ᴉuɐpɹɐɐ try wrapping your function wth `cache()` from "react"
Black CaimanOP
oh thx, tried but not useful
@Black Caiman oh thx, tried but not useful
what did your code looks like?
Black CaimanOP
export async function generateMetadata(
{ params, searchParams },
parent,
) {
const cookiesStore = cookies();
cookiesStore.getAll().forEach((item) => {
cookiesObj[item.name] = item.value;
});
const data = await getData(cookiesObj);
return {
title: ${data.page_meta_title}
}
}
export default async function Page({
params,
searchParams,
}) {
const cookiesStore = cookies();
cookiesStore.getAll().forEach((item) => {
cookiesObj[item.name] = item.value;
});
const data = await getData(cookiesObj);
return #Unknown Channel...</>
}
{ params, searchParams },
parent,
) {
const cookiesStore = cookies();
cookiesStore.getAll().forEach((item) => {
cookiesObj[item.name] = item.value;
});
const data = await getData(cookiesObj);
return {
title: ${data.page_meta_title}
}
}
export default async function Page({
params,
searchParams,
}) {
const cookiesStore = cookies();
cookiesStore.getAll().forEach((item) => {
cookiesObj[item.name] = item.value;
});
const data = await getData(cookiesObj);
return #Unknown Channel...</>
}
@ᴉuɐpɹɐɐ what did your code looks like?
Black CaimanOP
like this
@ᴉuɐpɹɐɐ what did your code looks like?
Black CaimanOP
sry, the code posted is missing a cookiesObj
@Black Caiman export async function generateMetadata(
{ params, searchParams },
parent,
) {
const cookiesStore = cookies();
cookiesStore.getAll().forEach((item) => {
cookiesObj[item.name] = item.value;
});
const data = await getData(cookiesObj);
return {
title: ${data.page_meta_title}
}
}
export default async function Page({
params,
searchParams,
}) {
const cookiesStore = cookies();
cookiesStore.getAll().forEach((item) => {
cookiesObj[item.name] = item.value;
});
const data = await getData(**cookiesObj**);
return <>...</>
}
where is the
try
cache()?try
const cachedGetData = cache(async () => {
const cookiesObj = cookies()
return await getdata(cookiesObj)
})Answer
then use the cachedGetData in generateMetadata and the page
@ᴉuɐpɹɐɐ where is the `cache()`?
try
tsx
const cachedGetData = cache(async () => {
const cookiesObj = cookies()
return await getdata(cookiesObj)
})
Black CaimanOP
This is useful, thank you very much
note that its not caching in between requests, but only a single request
@ᴉuɐpɹɐɐ note that its not caching in between requests, but only a single request
Black CaimanOP
Do you mean that what is being cached is the function, not the request? I'm a bit confused
@Black Caiman Do you mean that what is being cached is the function, not the request? I'm a bit confused
I meant that it only cache within a single request. It does not keep the cache until the next time user make the request
so within a single request
user A access
call
call
call
call
then getData is only called once
if user B access
user A access
/ thencall
getData()call
getData()call
getData()call
getData()then getData is only called once
if user B access
/ then it will be called once againoo
okay