Reputation: 7829
Consider the following simple Next.js app: https://codesandbox.io/p/sandbox/next-js-app-router-1bvd7d?file=README.md
We have a API route (/api/hello
):
export default function handler(req, res) {
res.status(204).end();
}
And a fetch in a React Server Component (RSC):
export default async function Home() {
let res;
try {
res = await fetch("https://rpvequ-3000.csb.app/api/hello");
console.log("res.status", res.status);
console.log("res", res);
} catch (error) {
console.log("res in error", res);
console.log("error", error);
}
return (
<main>
<p>HELLO WORLD</p>
</main>
);
}
The fetch throws the following error message:
TypeError: Response constructor: Invalid response status code 204
If we change the HTTP response from 204 to 202, for instance, the fetch no longer throws an error.
How come we get an error with 204? Is there any way to check if the response was 204 inside the RSC, so we can handle it as needed?
PS: If you are testing it in the Codesandbox or otherwise, remember to delete the .next
folder every time you restart the dev server (otherwise fetch()
just uses what was cached last time).
Side Note:
The same fetch()
in a React Client Component does for some reason not throw an error:
"use client";
import React, { useEffect } from "react";
const ClientComp = ({ children }) => {
useEffect(() => {
let res;
(async () => {
try {
res = await fetch("http://localhost:3000/api/hello");
console.log("res.status", res.status);
console.log("res", res);
} catch (error) {
console.log("res in error", res);
console.log("error", error);
}
})();
}, []);
return <div>{children}</div>;
};
export default ClientComp;
In other words, a HTTP response with status code 204 only throws an error when received by a fetch()
in a React Server Component, not in a React Client Component.
Upvotes: 3
Views: 2955
Reputation: 34
This was a bug in Next.js and it was fixed in this PR https://github.com/vercel/next.js/pull/48354
Upvotes: 1