Skip to content

Commit

Permalink
Merge pull request #49 from RyosukeDTomita/feature/env-change
Browse files Browse the repository at this point in the history
Feature/env change
  • Loading branch information
RyosukeDTomita authored Aug 4, 2024
2 parents 0b4f2e8 + 25bb9de commit d3b08d1
Show file tree
Hide file tree
Showing 32 changed files with 262 additions and 373 deletions.
4 changes: 2 additions & 2 deletions .dockerignore
Original file line number Diff line number Diff line change
@@ -1,4 +1,3 @@
docker_test.sh
README.md
.gitignore
CODEOWNERS
Expand All @@ -10,4 +9,5 @@ LICENSE
src/__tests__/*
copilot/*
Dockerfile
docker-compose.yml
compose.yaml
run_local.sh
32 changes: 30 additions & 2 deletions .github/workflows/react-jest.yaml
Original file line number Diff line number Diff line change
@@ -1,3 +1,4 @@
# node_version: 20, 22とenvironment_type: development, staging, productionの計6パターンでテストを実行
name: run-jest
on:
push:
Expand All @@ -22,6 +23,9 @@ jobs:
strategy:
matrix:
node_version: [20, 22]
environment_type: ["development", "staging", "production"]
environment:
name: ${{ matrix.environment_type }}

steps:
# checkout repository to runner
Expand All @@ -40,5 +44,29 @@ jobs:
- name: install dependencies
run: github-comment exec --token ${{ secrets.token }} -- npm install

- name: run npm test
run: github-comment exec --token ${{ secrets.token }} -- npm test -- --watchall=false
# 3環境まとめてテスト
- name: run npm run test
env:
GH_TOKEN: ${{ secrets.token }} # gh用
run: |
if [ ${{ matrix.environment_type }} = "development" ]; then
npm_type="dev"
elif [ ${{ matrix.environment_type }} = "staging" ]; then
npm_type="stg"
elif [ ${{ matrix.environment_type }} = "production" ]; then
npm_type="prod"
else
echo "invalid environment_type"
exit 1
fi
# environmentにあった名称でenv_fileを作成し,github actions environment variableを書き込み
# NOTE: env_fileはgitで管理したくないため,workflow実行時に作成している。
env_file=".env.${{ matrix.environment_type }}"
touch $env_file
cat <<EOF >> $env_file
$(gh variable list --env ${{ matrix.environment_type }} | awk '{print $1"="$2}')
EOF
echo ----[DEBUG]: CHECK $env_file----
cat .env.${{ matrix.environment_type }}
echo ----[DEBUG]: END----
github-comment exec --token ${{ secrets.token }} -- npm run test-$npm_type -- --watchall=false
7 changes: 4 additions & 3 deletions .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -13,10 +13,11 @@

# misc
.DS_Store
.env.local
.env.development.local
.env
.env.development
.env.test.local
.env.production.local
.env.production
.env.staging

npm-debug.log*
yarn-debug.log*
Expand Down
35 changes: 29 additions & 6 deletions Dockerfile
Original file line number Diff line number Diff line change
@@ -1,24 +1,47 @@
# Build Image
FROM node:20 AS build
WORKDIR /app

# defaultをdevelopmentにし,引数でproductionにも切り替えられるようにする
ARG BUILD_ENV=development

COPY . .
RUN npm install && npm run build

# npm startは.env.developmentが優先されるがnpm run buildでは.env.productoinが優先されるので注意。
RUN <<EOF
npm install
if [ "$BUILD_ENV" = "development" ]; then
echo "build mode = development"
npm run build
elif [ "$BUILD_ENV" = "staging" ]; then
echo "build mode = staging"
elif [ "$BUILD_ENV" = "productoin" ]; then
echo "build mode = production"
npm run build-dev
else
echo "build mode = unknown"
exit 1
fi

rm -rf node_modules/.cache
EOF


# Product Image
FROM public.ecr.aws/eks-distro-build-tooling/eks-distro-minimal-base-nginx:latest-al23

# Change owner to allow non-root users to start the service
USER root
RUN mkdir -p /var/log/nginx \
&& chown -R nginx:nginx /var/log/nginx \
&& touch /run/nginx.pid \
&& chown -R nginx:nginx /run/nginx.pid
RUN <<EOF
mkdir -p /var/log/nginx
chown -R nginx:nginx /var/log/nginx
touch /run/nginx.pid
chown -R nginx:nginx /run/nginx.pid
EOF

COPY --from=build /app/build /usr/share/nginx/html
COPY nginx.conf /etc/nginx/nginx.conf

# Use 8080 instead of 80 to avoid the `nginx: [emerg] bind() to 0.0.0.0:80 failed (13: Permission denied)` when using ECS.
EXPOSE 8080
USER nginx
CMD ["nginx", "-g", "daemon off;"]
128 changes: 53 additions & 75 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -20,11 +20,14 @@

Sample React application for Trying to Use DevSecOps tools.

> [!WARNING]
> Since it costs money to maintain the AWS environment created with copilot-cli for the demo environment, I plan to use `GitHub-Pages` for future demos. I have archived [this branch](https://github.com/RyosukeDTomita/devsecops-demo-aws-ecs).
> デモ環境に対して`copilot-cli`で作ったAWS環境を維持するのにお金がかかるのはもったいないので,以降は`github-pages`を使ってデモを動かそうと思います。[このブランチ](https://github.com/RyosukeDTomita/devsecops-demo-aws-ecs)をアーカイブを残してあります。
1. [PREPARING](#preparing)の設定を先にやる。
2. commit時にはpre-commitとgit-secretが作動。
3. push時にはGitHub ActionsによりSAST(semgrep),UnitTest(jest),Dependency Check(trivy)が実行される。
4. masterブランチにマージしたりmasterにpushした時にCodePipelineによってAWSへリポジトリがクローンされ,ビルド(image scanを含む),developmentへのデプロイが始まる。
5. developmentで問題がなければCodePipeline上で承認し,productionへデプロイ
4. github-pagesにデプロイされる。 # TODO: more info

## ENVIRONMENT

Expand All @@ -37,7 +40,7 @@ Sample React application for Trying to Use DevSecOps tools.
- [ghalint](./doc/tools_doc/ghalint.md): GitHub Actionsで実行されるworkflows用のlinter
- [github-comment](./doc/tools_doc/github-comment.md): GitHub Actionsで実行されるCIが失敗したときにコメントとしてエラーを出力する。
- [semgrep](./doc/tools_doc/semgrep.md): GitHub Actionsで実行するSASTツール
- [trivy](./doc/tools_doc/trivy.md): イメージのスキャンやdependency checkができる。dependency checkはGitHub Actionsで実行,イメージスキャンはAWS Code Pipelineで実行。
- [trivy](./doc/tools_doc/trivy.md): イメージのスキャンやdependency checkができる。dependency checkはGitHub Actionsで実行,イメージスキャンは#TODO

- [aqua](./doc/tools_doc/aqua.md): GitHub Actionsで使用するCLIツールのバージョン管理ができる。
- [pinact](./doc/tools_doc/pinact.md): GitHub Actionsで使うactionsのバージョンをフルコミットハッシュに変換。
Expand All @@ -63,107 +66,82 @@ Sample React application for Trying to Use DevSecOps tools.

---

### AWSの構成

AWS: ECS on FargateにCode Pipeline経由でデプロイする。サンプルではdevとprod環境を用意し、dev環境で動作確認後に承認ボタンを押すとprod環境のデプロイが進む形になっている。

- app-infrastructure-roles
![app-infrastructure-roles](./doc/fig/cfn/app-infrastructure-roles.png)
- app-infrastructure
![app-infrastructure](./doc/fig/cfn/app-infrastructure.png)
- environment
![env](./doc/fig/cfn/env.png)
- service
![svc](./doc/fig/cfn/svc.png)
- pipeline
![pipeline](./doc/fig/cfn/pipeline.png)

---

## PREPARING

### AWSの設定
### 始めにやること

[initialsettings_aws](./initialsettings_aws.md)を参照
- Reopsitoryをforkする

---
### ローカルにインストールするツール

## HOW TO USE
- `pre-commit`
- `git secret`
- `gh`コマンドのインストール
- VSCodeのExtensionsもお好みでインストール。TODO: Devcontainer化する。

- [PREPARING](#preparing)をやる。
- ローカルでのセットアップが必用なのは git-secretsのセットアップ。
### GitHub Actionsでghコマンドを使うための設定

```shell
cd devsecops-demo-aws-ecs
pre-commit install
- [Personal access tokens](https://github.com/settings/tokens)を作り,repository secretsに登録する。
TODO: 一旦これくらいで作成。もっと権限しぼれるかも
![personal acccess token例](./doc/fig/pat.png)
- repository secretsに登録する。
![Actions secrets and variables](./doc/fig/actions-secrets-set.png)

git secrets --install
git secrets --register-aws # awsのクレデンシャル検知ルールを登録
```
### GitHub Actions Variablesの設定

- pre-commitのセットアップ
- Repositoryに[Environment](https://github.com/RyosukeDTomita/devsecops-demo-aws-ecs/settings/environments)を作る。
![Environment例](./doc/fig/github-environment.png)
- ローカルに3環境分の.envファイルをを作成する。

```shell
pip install pre-commit
pre-commit install
# 作成
for environment in development staging production;
do
touch .env.${environment}
echo $REACT_APP_MESSAGE=${environment} > .env.${environment}
done
```

- VSCodeのExtensionsもお好みでインストール。
- GitHub Actionsがスキャン結果のファイルをアップロードできるように権限をつける。詳細は[semgrepのyaml](./.github/workflows/react-semgrep.yaml)を参照。

---

## ERROR LOG

<details>
<summary>今まで詰まったエラー一覧</summary><div>

### Code Build のエラー

以下コマンドでログが見られる。ブラウザのAWS Code Deploy
- github actions enrironment variablesに登録/更新する。

```shell
copilot svc logs --previous
source ./update_github_actions_variables.sh
```

#### nginx: [emerg] bind() to 0.0.0.0:80 failed (13: Permission denied)
### GitHub Actionsで実行したスキャン結果をアップロードできるようにGitHubリポジトリの設定を変更する

- [ECS の仕様で非特権ユーザを使用したコンテナでは 80 番ポートが使えないっぽい](https://repost.aws/questions/QU1bCV9wT4T5iBrrP1c2ISfg/container-cannot-bind-to-port-80-running-as-non-root-user-on-ecs-fargate) --> つまり,localのdockerで80でサービスが起動できてもECSだと権限エラーになる。このため,コンテナで開放するportは8080としている(ALBに対して8080がマッピングされているためブラウザからは80でアクセスできる)
- GitHub Actionsがスキャン結果のファイルをアップロードできるようにGitHubリポジトリの設定を変更。詳細は[semgrepのyaml](./.github/workflows/react-semgrep.yaml)を参照

#### toomanyrequests: You have reached your pull rate limit. You may increase the limit by authenticating and upgrading: <https://www.docker.com/increase-rate-limit>
---

- Docker Hubに短期間にアクセスしすぎているだけなので放置でOK
## HOW TO USE

#### Error response from daemon: dockerfile parse error
### コミット時の検査セットアップ

- DockerfileのRUNをヒアドキュメントで書いていたら怒られた(ローカルでは動いてたのに...)
- git-secretsのセットアップ。

```dockerfile
# 修正前Dockerfile
RUN <<EOF
mkdir -p /var/log/nginx
chown -R nginx:nginx /var/log/nginx
touch /run/nginx.pid
chown -R nginx:nginx /run/nginx.pid
EOF
```shell
cd devsecops-demo-aws-ecs
pre-commit install

# 修正後
RUN mkdir -p /var/log/nginx \
&& chown -R nginx:nginx /var/log/nginx \
&& touch /run/nginx.pid \
&& chown -R nginx:nginx /run/nginx.pid
git secrets --install
git secrets --register-aws # awsのクレデンシャル検知ルールを登録
```

#### Resource handler returned message: "Error occurred during operation 'ECS Deployment Circuit Breaker was triggered'

コンテナが正常に起動していない。amd64を指定したら動いた。
- pre-commitのセットアップ

```shell
DOCKER_DEFAULT_PLATFORM=linux/amd64 copilot deploy
pip install pre-commit
pre-commit install
```

#### copilot app show で CFn スタックを消したはずのアプリが表示されてしまう
---

- `copilot app show`はParameter Storeを見ているのでそこを消す。
## ERROR LOG

</div></details>
<details>
<summary>今まで詰まったエラー一覧</summary>
<div>
TODO
</div>
</details>
1 change: 0 additions & 1 deletion copilot/.workspace

This file was deleted.

47 changes: 0 additions & 47 deletions copilot/dev-svc/manifest.yml

This file was deleted.

21 changes: 0 additions & 21 deletions copilot/environments/dev-env/manifest.yml

This file was deleted.

Loading

0 comments on commit d3b08d1

Please sign in to comment.