This is a set of GitHub Actions to deploy microservices in a mono-repository (monorepo).
Our monorepo contains a set of microservices with application code and Kubernetes manifests. Here is the example of directory structure.
monorepo
├── backend
|   ├── sources...
|   └── kubernetes
|       ├── base
|       └── overlays
|           ├── develop
|           |   └── kustomization.yaml
|           └── staging
|               └── kustomization.yaml
├── frontend
|   ├── sources...
|   └── kubernetes
|       └── overlays
|           └── ...
└── ...
We adopt this strcuture for the following advantages:
- An owner of microservice (i.e. product team) has strong ownership for both application and manifest
 - We can change both application and manifest in a pull request
 
We deploy a set of services from a branch to a namespace. For example,
- When 
developbranch is pushed,- Build a Docker image from 
developbranch - Run kustomize build against 
developoverlay - Deploy to 
developnamespace 
 - Build a Docker image from 
 - When a pull request is created,
- Build a Docker image from head branch
 - Run kustomize build against 
stagingoverlay - Deploy to an ephemeral namespace like 
pr-12345 
 
Consequently, a structure of monorepo is like below.
monorepo
└── ${service}
    └── kubernetes
        └── overlays
            └── ${overlay}
                └── kustomization.yaml
Here are the definitions of words.
| Name | Description | Example | 
|---|---|---|
overlay | 
Name of the overlay to build with Kustomize | staging | 
namespace | 
Namespace to deploy into a cluster | pr-12345 | 
service | 
Name of a microservice | backend | 
We adopt App of Apps pattern of Argo CD for deployment hierarchy.
For a typical namespace such as develop or production, it is deployed with the below applications.
graph LR
  subgraph "generated-manifests"
    AppService[Application develop--SERVICE] --> Resources
  end
  App[Application monorepo--develop] --> AppService
    For a pull request namespace, it is deployed with the below applications and the pull request generator.
graph LR
  subgraph "generated-manifests"
    AppService[Application pr-NUMBER--SERVICE] --> Resources
  end
  AppSet[ApplicationSet monorepo--pr] --> AppPr[Application pr-NUMBER] --> AppService
    A namespace branch contains a set of generated manifest and Application manifest per a service.
destination-repository  (branch: ns/${source-repository}/${overlay}/${namespace})
├── applications
|   └── ${namespace}--${service}.yaml  (Application)
└── services
    └── ${service}
        └── generated.yaml
Node.js and pnpm is required.
brew install node@20
npm install -g pnpm@latest-10When a pull request is merged into main branch, a new minor release is created by GitHub Actions. See https://github.com/int128/release-typescript-action for details.
You can enable Renovate to update the dependencies. See https://github.com/int128/typescript-action-renovate-config for details.