最新消息:Welcome to the puzzle paradise for programmers! Here, a well-designed puzzle awaits you. From code logic puzzles to algorithmic challenges, each level is closely centered on the programmer's expertise and skills. Whether you're a novice programmer or an experienced tech guru, you'll find your own challenges on this site. In the process of solving puzzles, you can not only exercise your thinking skills, but also deepen your understanding and application of programming knowledge. Come to start this puzzle journey full of wisdom and challenges, with many programmers to compete with each other and show your programming wisdom! Translated with DeepL.com (free version)

javascript - NextJS 13+ Infinite Loops for routes with dynamic params - Stack Overflow

matteradmin7PV0评论

im having some issues with dynamic routing in Next. For example a route like /api/chat/[id] or would cause an infinite loop.

Here is the code:

"use client"

import React, {useEffect} from 'react';
import { useAuth } from "@/context/AuthContext";
import { useMsal } from "@azure/msal-react";

const TestPage = () => {
    const { acquireToken } = useAuth();
    const { accounts } = useMsal();

    useEffect(() => {
        const fetchData = async () => {
            const token = await acquireToken(accounts[0], "id");
            const res = await fetch("/api/clients/b00b24ba-2933-4d5e-919d-835cc05057a6", {
                method: "GET",
                headers: {
                    Authorization: `Bearer ${token}`,
                },
            });

            const data = await res.json()
            console.log(data)
        }

        fetchData();
    })

  return (
    <div>
      <h1>Test Page</h1>
      <p>This is a test page for the application.</p>
    </div>
  );
};

export default TestPage;
import { NextRequest, NextResponse } from "next/server";
import { createServerSupabaseClient } from "@/lib/supabase/supabaseServer";

export async function GET(
  req: NextRequest,
  { params }: { params: { clientId: string } },
) {
  try {
    const supabase = createServerSupabaseClient();
    const { clientId } = params;

    const { data, error } = await supabase
      .from("clients")
      .select("*")
      .eq("id", clientId)
      .single();

    if (error) throw error;

    return NextResponse.json(data, { status: 200 });
  } catch (error: any) {
    return NextResponse.json({ error: error.message }, { status: 500 });
  }
}

The path is app/api/clients/[clientId]/route.ts

Seems like nothing fancy.

My current fix is sending my dynamic id through a query instead of param

/api/clients/client?clientId=b00b24ba-2933-4d5e-919d-835cc05057a6

but i dont want to do that.

Am i missing something? I am somewhat new to Next.

Thanks!

EDIT: I have created a new route in app/(routes)/exampe-route/[id]/route.ts and i dont get an infinite loop. However, app/api/exampe-route/[id]/route.ts causes a 508. I have no middleware, this is bizarre.

Here is the endpoint, its very simple.


export async function GET(
    request: Request,
    { params }: { params: { id: string } }
) {
    console.log("API route handler called with ID:", params.id);
    return NextResponse.json({
        message: `You requested the resource with ID: ${params.id}`,
    });
}

UPDATE: After going through the entire codebase i realized there was an async rewrites in our next config that was forwarding our api calls to another version of the codebase, which explains a lot.

im having some issues with dynamic routing in Next. For example a route like /api/chat/[id] or would cause an infinite loop.

Here is the code:

"use client"

import React, {useEffect} from 'react';
import { useAuth } from "@/context/AuthContext";
import { useMsal } from "@azure/msal-react";

const TestPage = () => {
    const { acquireToken } = useAuth();
    const { accounts } = useMsal();

    useEffect(() => {
        const fetchData = async () => {
            const token = await acquireToken(accounts[0], "id");
            const res = await fetch("/api/clients/b00b24ba-2933-4d5e-919d-835cc05057a6", {
                method: "GET",
                headers: {
                    Authorization: `Bearer ${token}`,
                },
            });

            const data = await res.json()
            console.log(data)
        }

        fetchData();
    })

  return (
    <div>
      <h1>Test Page</h1>
      <p>This is a test page for the application.</p>
    </div>
  );
};

export default TestPage;
import { NextRequest, NextResponse } from "next/server";
import { createServerSupabaseClient } from "@/lib/supabase/supabaseServer";

export async function GET(
  req: NextRequest,
  { params }: { params: { clientId: string } },
) {
  try {
    const supabase = createServerSupabaseClient();
    const { clientId } = params;

    const { data, error } = await supabase
      .from("clients")
      .select("*")
      .eq("id", clientId)
      .single();

    if (error) throw error;

    return NextResponse.json(data, { status: 200 });
  } catch (error: any) {
    return NextResponse.json({ error: error.message }, { status: 500 });
  }
}

The path is app/api/clients/[clientId]/route.ts

Seems like nothing fancy.

My current fix is sending my dynamic id through a query instead of param

/api/clients/client?clientId=b00b24ba-2933-4d5e-919d-835cc05057a6

but i dont want to do that.

Am i missing something? I am somewhat new to Next.

Thanks!

EDIT: I have created a new route in app/(routes)/exampe-route/[id]/route.ts and i dont get an infinite loop. However, app/api/exampe-route/[id]/route.ts causes a 508. I have no middleware, this is bizarre.

Here is the endpoint, its very simple.


export async function GET(
    request: Request,
    { params }: { params: { id: string } }
) {
    console.log("API route handler called with ID:", params.id);
    return NextResponse.json({
        message: `You requested the resource with ID: ${params.id}`,
    });
}

UPDATE: After going through the entire codebase i realized there was an async rewrites in our next config that was forwarding our api calls to another version of the codebase, which explains a lot.

Share Improve this question edited Nov 18, 2024 at 21:48 Nico asked Nov 15, 2024 at 21:11 NicoNico 13 bronze badges 2
  • The useEffect has no dependency array so it will run on every render. You're also updating state inside it. – evolutionxbox Commented Nov 15, 2024 at 21:27
  • i did miss that and added an empty dependency array. I dumbed it down to not use any hooks either. Still same issue. It works fine on routes without params, but with params It bugs out. – Nico Commented Nov 15, 2024 at 21:43
Add a comment  | 

2 Answers 2

Reset to default 0

Your useEffect hook does not have a dependency array ([]). Without the dependency array, fetchData() is called on every render, causing an infinite loop.

Your fetch request uses a static path instead of the dynamic route /api/clients/[clientId], which might not resolve properly and could contribute to the issue.

Instead of hardcoding the path in fetch, use a dynamic id parameter in your route:

useEffect(() => { 
  const fetchData = async () => {
  const token = await acquireToken(accounts[0], "id");
  const clientId = "b00b24ba-2933-4d5e-919d-835cc05057a6";

  const res = await fetch(`/api/clients/${clientId}`, {
    method: "GET",
    headers: {
        Authorization: `Bearer ${token}`,
      },
    });

    const data = await res.json();
    console.log(data);
  }

  fetchData();
},[]) //Add an Empty array here

The reason directly using the static path "/api/clients/b00b24ba-2933-4d5e-919d-835cc05057a6" in your fetch request causes an infinite loop probably is due to a route conflict between your Next.js API routes and page routes.

  • In Next.js, especially with the App Router (app directory), both pages and API routes can coexist in the same directory structure.
  • If you have a page and an API route at the same path, Next.js may prioritize the page over the API route when resolving requests.
  • In your case, requesting "/api/clients/b00b24ba-2933-4d5e-919d-835cc05057a6" directly might be hitting a page route instead of the intended API route.

So, double-check your app directory to ensure there are no unintended page files (page.tsx) under the /api/clients/[clientId] path, correct structure should be something like this:

app
├── api
│   └── clients
│       └── [clientId]
│           └── route.ts  // API Route
├── clients
│   └── [clientId]
│       └── page.tsx     // Page Component
async rewrites() {
    return [
        {
            source: "/api/:path*",
            destination: "https://example-prod-url/api/:path*",
        },
    ];
},

I found this was in our next config. Which makes a lot of sense now why this was behaving the way it was.

Post a comment

comment list (0)

  1. No comments so far