.../articles/
Deploying a Monorepo Next.js App (App Router) to AWS Amplify

Deploying a Monorepo Next.js App (App Router) to AWS Amplify

2023.12.09

Lately we've mostly been using Next.js for frontend application development here as well. When we use AWS for the cloud, we often host on Amplify, but when we tried to deploy a monorepo-managed Next.js (App Router) app, we ran into a few snags — so here's a summary.

Repository Layout Assumed in This Post

In this case, we manage applications for different user groups across multiple repositories within a monorepo. The shared UI is managed in the packages/ui directory, so it can be imported from each app.

We're using the official sample repository (also listed in the references) as our reference.

The repository structure is as follows:

├── README.md
├── amplify.yml
├── apps
│   ├── web // Directory for the general-user-facing application
│   │   ├── README.md
│   │   ├── next.config.js
│   │   ├── package.json
│   │   ├── postcss.config.js
│   │   ├── public
│   │   ├── src
│   │   │   ├── app
│   │   │   │   ├── omitted
│   │   │   │   ....
│   │   │   │   └── page.tsx
│   │   │   ├── components
│   │   │   ├── features // Contains custom hooks and other feature-related code
│   │   │   └── styles
│   │   ├── tailwind.config.ts
│   │   ├── tsconfig.json
│   │   └── yarn.lock
│   └── admin // Directory for the admin-facing application. Structure is the same as web, so omitted here
├── package.json
├── packages           // Directory holding files shared across applications (config files, UI components, etc.)
│   ├── eslint-config-custom
│   ├── tailwindconfig
│   ├── tsconfig
│   └── ui
├── turbo.json
└── yarn.lock

1. Change the amplify.yml Configuration

The default yml has no appRoot setting, but to use it with a monorepo, you need to add an appRoot entry for each application and configure environment variables on the Amplify side. We're using Turborepo as our build system here, so please adapt the build commands as needed for your own environment.

The key point here is that when the yml is written as below, you also need to set the environment variable AMPLIFY_MONOREPO_APP_ROOT = apps/web.

version: 1
applications:
  - appRoot: apps/web
    frontend:
      phases:
        preBuild:
          commands:
            - nvm use 18
            - node -v
            - yarn
        build:
          commands:
            - npx turbo run build --filter=web
      artifacts:
        baseDirectory: .next
        files:
          - "**/*"
      cache:
        paths:
          - node_modules/**/*
  - appRoot: apps/admin
    frontend:
      phases:
        preBuild:
          commands:
            - nvm use 18
            - node -v
            - yarn
        build:
          commands:
            - npx turbo run build --filter=admin
      artifacts:
        baseDirectory: .next
        files:
          - "**/*"
      cache:
        paths:
          - node_modules/**/*

2. Change the Amplify Infrastructure Settings

This is the part that took me the longest to figure out. When you create an application from the Amplify console and select monorepo, the infrastructure gets built with the platform set to "Web." Check the red-boxed area in the image below to see your current infrastructure state.

Since we're using Next.js in SSR mode here, we need to change it to "Web Compute." So we change the app and branch settings with the following commands:

# Change the Amplify App's infrastructure setting to "WEB_COMPUTE"
$ aws --profile {AWS_PROFILE} amplify update-app --app-id {APPLICATION_ID} --platform WEB_COMPUTE --region ap-northeast-1

# Change the Amplify Branch's infrastructure setting to "Next.js - SSR"
$ aws --profile {AWS_PROFILE} amplify update-branch --app-id {APPLICATION_ID}  --branch-name develop --framework 'Next.js - SSR' --region ap-northeast-1

Wrap-up

With the settings above in place, we were able to deploy to Amplify successfully. We hit a bit of a snag this time, but I really like Amplify — it also makes it easy to set up things like building an environment for every pull request, which lowers the cost of frontend review.

By the way, we're using Next.js 13 here, but if you use Next.js 14, you'll need to change the image due to Node.js's minimum support requirements, among other things. The following article may be helpful in that case:

Zenn: Tried out the new Amplify Hosting with a Next.js 14 app

Wishing you a great frontend development life 🙌

References

written by

.../article/

Articles

All articles

From Firebase to Vercel, Contentful to microCMS — a migration log written with Claude Code

From Firebase to Vercel, Contentful to microCMS — a migration log written with Claude Code

We moved our corporate site's hosting and CMS, and made it bilingual along the way. The constraints we only found by running against real data were more useful than the migration itself, so this post focuses on where we got stuck.

Can't Read POST Data with Firebase Functions × Remix?

Can't Read POST Data with Firebase Functions × Remix?

How to read POST data from a Remix action when running on Firebase Functions.

Generative AI for Executives and Leaders: An Approach to Self-Driven DX

Generative AI for Executives and Leaders: An Approach to Self-Driven DX

Building a structure where executives and leaders themselves can identify issues and evaluate solutions using generative AI. We introduce how combining this with our hands-on support dramatically improves both the quality and speed of digital transformation.

Deploying a Monorepo Next.js App (App Router) to AWS Amplify

Deploying a Monorepo Next.js App (App Router) to AWS Amplify

Notes on the obstacles we hit while deploying a Next.js app managed in a monorepo to AWS Amplify.

Keeping Production Running Smoothly with Remote Work and Online Meetings [Documentation]

Keeping Production Running Smoothly with Remote Work and Online Meetings [Documentation]

Many production companies have adopted remote work as a result of the pandemic, and we are one of them.

Designing an E-Commerce Site That Sells: How to Find Great Reference Examples

Designing an E-Commerce Site That Sells: How to Find Great Reference Examples

There is no single formula for e-commerce design that sells. Driving revenue requires a solid concept, and getting to that concept requires thorough research.

Productivity Tools We Recommend as a Production Company, Including Services That Work Well Solo

Productivity Tools We Recommend as a Production Company, Including Services That Work Well Solo

With remote work becoming the norm during the COVID-19 pandemic, our team now works from home most days of the week.

We Released Thought Recorder, a Figma Plugin for Keeping a Commit History of Your Designs

We Released Thought Recorder, a Figma Plugin for Keeping a Commit History of Your Designs

We hope this helps web designers who work in Figma. Read on for how to use it.

How to Build an E-Commerce Site, and Which Platforms We Recommend

How to Build an E-Commerce Site, and Which Platforms We Recommend

Shopping online for fashion, appliances, and even groceries is now routine. With the pandemic accelerating the shift, we receive a steady stream of questions about which platform to use and how much it costs.

Generating FastAPI Schema Classes from OpenAPI

Generating FastAPI Schema Classes from OpenAPI

We chose FastAPI, a relatively modern framework, for a Python API project. FastAPI can generate an OpenAPI definition from your backend code, but here we do the opposite: generating FastAPI schema classes from an OpenAPI definition prepared in advance.

View all articles

Contact us