aws-amplify / amplify-hosting

AWS Amplify Hosting provides a Git-based workflow for deploying and hosting fullstack serverless web applications.
https://aws.amazon.com/amplify/hosting/
Apache License 2.0
461 stars 116 forks source link

DNS Resolution Issue with API Requests in Next.js App on AWS Amplify #3871

Open mustafadalga opened 11 months ago

mustafadalga commented 11 months ago

Before opening, please confirm:

App Id

arn:aws:amplify:eu-central-1:392145163496:apps/du9vxmpr1v1e5

AWS Region

us-east-1

Amplify Hosting feature

Build settings, Custom build image, Custom headers, Deployments, Frontend builds

Frontend framework

Next.js

Next.js version

13.5.5

Next.js router

App Router

Describe the bug

I am experiencing an issue with my Next.js application hosted on AWS Amplify where API requests to https://api-test.example.com/login fail due to a DNS resolution error (getaddrinfo ENOTFOUND). This issue does not occur in my local environment or in vercel.com, suggesting it's specific to the Amplify environment.

Expected behavior

Reproduction steps

  1. Host a Next.js application on AWS Amplify.
  2. Make a POST request to an external API (https://api-test.example.com/login) from the application.
  3. Observe the error in the response.

Build Settings

version: 1
frontend:
  phases:
    preBuild:
      commands:
        - npm ci
    build:
      commands:
        - npm run build
  artifacts:
    baseDirectory: .next
    files:
      - '**/*'

  cache:
    paths:
      - node_modules/**/*

Log output

``` The API request fails with the following error: { "message": "Please try again!", "details": { "method": "POST", "url": "https://api-test.example.com/login", "message": "getaddrinfo ENOTFOUND api-test.example.com" } } ```

Additional information

Troubleshooting Steps Undertaken

  1. Dynamic Routing Configuration:

    • Tried both with and without force-dynamic in the API route configuration. The issue persists regardless of this setting.
  2. Build Image Changes:

    • Switched the build image to Amazon Linux 2023 and also tried a custom image (public.ecr.aws/docker/library/node:18.17.0). Neither change resolved the issue.
  3. Custom HTTP Configuration:

    • Removed the custom HTTP configuration (customHttp.yml) to check its impact. The issue still occurred without this configuration.
  4. Intermittent Behavior:

    • The API sometimes works but often returns a 408 timeout error. This behavior is inconsistent and only observed in the Amplify environment, not locally or on Vercel.
  5. Build Image for Unit Tests:

    • Using Amazon Linux 2023 and the custom Node.js image was necessary for running unit tests, as they do not work with the default image.

Custom HTTP Configuration (customHttp.yml):

customHeaders:
  - pattern: '**/*'
    headers:
      - key: Cache-Control
        value: no-store
      - key: Pragma
        value: no-cache
      - key: Expires
        value: '0'

Api Route

import { NextResponse } from "next/server";
import api from "@/_services/loginApiService";
import handleAxiosError from "@/_utilities/handleAxiosError";

export const dynamic = "force-dynamic"

export async function POST(request: Request) {
    const body = await request.json();
    const {
        username,
        password,
    } = body;

    try {
        const response = await api.post(“my-api/login”, {
            username,
            password,
        });

        const { access_token: jwt, exp: jwtExpirationTime } = response.data.data;

        return createNextResponse({ jwt, jwtExpirationTime }, 200);

    } catch (error) {
        const {
            message,
            status,
            details
        } = handleAxiosError(error, "Please try again!");
        return createNextResponse({ message, details }, status);
    }
}

function createNextResponse(data: Record<string, any>, status: number): NextResponse {
    const nextResponse = NextResponse.json(data, { status });
    nextResponse.headers.set('Cache-Control', 'no-store, max-age=0');
    return nextResponse;
}