AWS Amplify Consoleを連携させてテスト結果ページを自動生成・管理する

本記事は、[Qiita Advent Calendar 2019 - AWS Amplify](https://qiita.com/advent-calendar/2019/aws-amplify)の10日目の記事です。

タイトルでは表現しづらい内容ですが、やりたいことは下図の通りです。

![スクリーンショット 2019-12-10 23.47.01.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/102769/a2e7adfe-76b6-ddc9-d311-3c28d75fe469.png)



Amplify Consoleを利用してテスト／ビルドできるようにしていたら、テスト結果も自動的に蓄積されて参照可能な形にできないか、、、と思い始めて手を動かした結果です。

# やりたいことの流れ
1. 以前開発した[Cognito管理Web画面](https://github.com/kojiisd/cognito-user-manager/tree/master)のビルドをAmplify Consoleで行う。
 1. https://github.com/kojiisd/cognito-user-manager/tree/master
 2. そのAmplify Consoleのビルドの中でKarateやunittestによるE2Eテスト、単体テストが実施される。
2. E2Eテスト、単体テストの結果を別の試験結果保存用WebサイトのGithubリポジトリにPushする。
 1. https://github.com/kojiisd/hugo-test-result-management  
（Hugo製のWebサイト）
 2. 試験結果を新規ページとして保持する構成となっている。
3. hug-test-result-managementがAmplify Consoleにより自動デプロイされ、試験結果が追加される更新処理が走る

こうできれば、ビルドをするたびに自動的にビルド結果をリアルタイムに確認することができます。（またそのビルド結果の履歴を保持することもできる）

# 実現までの流れ
以下が実現までに必要な流れと考えてます。

1. 対象アプリケーション（cognito-user-manager）のAmplify Consoleによるビルド設定
2. 試験結果を表示するWebページの準備とAmplify Console設定
3. No.1のアプリケーションのビルドの中で、試験実施が完了したらその結果をNo.2のリポジトリにPushするためのスクリプト準備

# 1. 対象アプリケーション（cognito-user-manager）のAmplify Consoleによるビルド設定
以前こちらで書いた内容がほぼ全てになります。なので省略。

AWS Amplify ConsoleでCIを頑張った話
https://qiita.com/kojiisd/items/50a394c365d9c98543f9
※今はAmplify ConsoleでのベースのPythonがバージョンアップしていることもあり、いくつかビルドスクリプトは異なりますが、大枠の流れは同じです。

# 2. 試験結果を表示するWebページの準備とAmplify Console設定
Hugoでページのベースを作ることで、Markdownのテキストを追加するだけでページの追加が可能になります。Hugoに着いては以下のページから参照可能。

https://gohugo.io/

このHugoベースで作成したWebページ（試験結果表示ページ）に追記していく流れを作りたいと思います。ちなみにベースとなるWebページは以下。シンプルにKarateとunittestで実施した内容を日付降順で並べて一覧表示をしています。

https://github.com/kojiisd/hugo-test-result-management

![スクリーンショット 2019-12-10 16.18.38.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/102769/ba5eb2d9-3adf-e7c2-19c4-9c66d00450bf.png)

それぞれのページは別タブで表示されるような仕組みです。ページを表示させると、それぞれのテスト結果が確認できます。
![スクリーンショット 2019-12-10 16.20.06.png](https://qiita-image-store.s3.ap-northeast-1.amazonaws.com/0/102769/1f79c187-0226-f1ec-c705-16b32a7cb283.png)


このページをAmplify Consoleでビルドできるように設定します。これが自動で更新（テスト結果が自動で増えていく）されるようになったら素晴らしいです。

この設定自体は全てHugoでデフォルトの設定になります。（そもそもリポジトリを読み込ませれば勝手にHugoベースと判断されて以下の設定が適用される）

```yml
version: 0.1
frontend:
  phases:
    build:
      commands:
        - hugo
  artifacts:
    baseDirectory: public
    files:
      - '**/*'
  cache:
    paths: []
```

# 3. No.1のアプリケーションのビルドの中で、試験実施が完了したらその結果をNo.2のリポジトリにPushするためのスクリプト準備

アプリケーションをビルドする際に以下の流れを実装します。これをbuild.ymlに実装するのが本記事の最終的な目標になります。

1. unittestとKarateのテストを実行する。
2. No.2をGithubからダウンロードする。
3. 新しいページをhugoコマンドで追加し、Karateとunittestの結果を追記する。
4. GithubにコードをCommit/Pushする。
5. No.2のビルドが開始される。
6. 自動的にテスト結果ページがPushされる。


という感じです。それぞれ実施します。

## 3-1. unittestとKarateのテストを実行する。
これはすでに元々[cognito-user-manager](https://github.com/kojiisd/cognito-user-manager/tree/master)に対してAmplify Consoleで設定をしているので、自動的にテストが実施されるようになっています。

この辺。

```yml
        - python3 tests/test_user_handler.py
：
：
        - cd cognito-manager-client/
        - npm install -g forever
        - forever start node_modules/@angular/cli/bin/ng serve
        - yum install -y java-1.8.0-openjdk-devel.x86_64
        - java -version
        - yum install -y apache-maven
        - mvn --version
        - cd e2e_karate/manager
        - mvn clean test
```


## 3-2. No.2をGithubからダウンロードする。
上記のテスト実施後、テスト結果を保持するため、対象となるコードをクローンします。Githubからダウンロードする際に指定するユーザID、パスワードはAWS Systems ManagerのParameter Storeに格納するようにしています。

```yml
        - yum -y install git

        - git clone ${GIT_URL}
        - cd ${REPO_NAME}
```

これで、Githubから、テスト結果保持用のコードをダウンロードできるようになります。

## 3-3. 新しいページをhugoコマンドで追加し、Karateとunittestの結果を追記する。
Amplify ConsoleはHugoコマンドをすでにインストールしているので、インストール不要で利用できます。実行日時をファイル名として新しいページを追加します。

試験結果をHugoで新しく作成したページに追記することで、ページ追加を行います。今回、Markdownの中にHTMLコードを書くことで中身を表示できる仕組みを用いるため、こちらのサイトを参考にしてすでにテスト結果ページの方に細工をしています。YAMLファイル中にHTMLタグを埋め込もうとすると問題が発生するので、これらの処理は```predict.sh```というシェルスクリプトにまとめることにしました。

【HUGO】マークダウンの中にHTMLコードを書いて表示する方法
https://srbrnote.work/archives/2772

```sh
# for karate
hugo new karate/`cat now.txt`.md
echo "{{<rawhtml>}}" >> content/karate/`cat now.txt`.md
echo "`cat ../result_karate.html`" >> content/karate/`cat now.txt`.md
echo "{{</rawhtml>}}" >> content/karate/`cat now.txt`.md

# for unittest
hugo new unittest/`cat now.txt`.md
echo "{{<rawhtml>}}" >> content/unittest/`cat now.txt`.md
echo "`cat ../result_unittest.html`" >> content/unittest/`cat now.txt`.md
echo "{{</rawhtml>}}" >> content/unittest/`cat now.txt`.md
```


## 3-4. GithubにコードをCommit/Pushする。
上記までできたら、あとはGithubに対象コードをCommit/Pushします。

## 3-5. No.2のビルドが開始される。
GithubのPushを検知して、テスト結果ページに設定したAmplify Consoleが起動、追加したページをデプロイするようになります。

## 3-6. 自動的にテスト結果ページがPushされる。
結果として、試験結果が追加されたページが表示されるようになります。

トータルでYAMLファイルは以下のような設定になりました。

```yml
version: 0.1
frontend:
  phases:
    preBuild:
      commands:
        - mkdir  -p ~/.aws
        - echo "[${SLS_AWS_ACCOUNT_ID}]" > ~/.aws/credentials
        - echo "aws_access_key_id = ${ACCESS_KEY}" >>  ~/.aws/credentials
        - echo "aws_secret_access_key = ${SECRET_KEY}" >>  ~/.aws/credentials
        - npm install -g serverless
        - cd cognito-manager-server/
        - sed -i -e "s@COGNITO_IDP_ARN@${COGNITO_IDP_ARN}@g" serverless.yml
        - sed -i -e "s@USER_POOL_ID@${USER_POOL_ID}@g" serverless.yml
        - yum update python37 -y
        - yum -y install python37
        - curl https://bootstrap.pypa.io/get-pip.py | python3
        - pip3 install -r requirements_test.txt -t libs
        - if [ -d reports ]; then rm -rf reports; fi
        - python3 tests/test_user_handler.py
        - ls reports/html_report/ > file_path.txt
        - cp -p reports/html_report/`cat file_path.txt` ../result_unittest.html

        - npm install
        - sls deploy --profile ${SLS_AWS_ACCOUNT_ID}
        - cd ../
        - cd cognito-manager-client/
        - npm install -g forever
        - forever start node_modules/@angular/cli/bin/ng serve
        - yum install -y java-1.8.0-openjdk-devel.x86_64
        - java -version
        - yum install -y maven

        - cd e2e_karate/manager
        - mvn clean test
        - ls target/
        - cd target/surefire-reports/
        - ls *.html > unittest_path.txt
        - cp -p `cat unittest_path.txt` ../../../../../result_karate.html
        - cd ../../../../

        - sed -i -e "s/REGION/${REGION}/g" src/environments/environment.ts
        - sed -i -e "s/USER_POOL_ID/${USER_POOL_ID}/g" src/environments/environment.ts
        - sed -i -e "s/USER_POOL_WEB_CLIENT_ID/${USER_POOL_WEB_CLIENT_ID}/g" src/environments/environment.ts
        - sed -i -e "s/IDENTITY_POOL_ID/${IDENTITY_POOL_ID}/g" src/environments/environment.ts
        - sed -i -e "s#API_BASE_URL#${API_BASE_URL}#g" src/environments/environment.ts
        - sed -i -e "s/LOCAL_STORAGE_BASE_KEY/${LOCAL_STORAGE_BASE_KEY}/g" src/environments/environment.ts

        - cd ../
        - yum -y install git
        - yum -y install jq
        - touch ~/.netrc
        - echo "machine github.com" >> ~/.netrc
        - echo "login `aws ssm get-parameters --names ${SSM_USER_KEY} --region us-east-1  --profile ${SLS_AWS_ACCOUNT_ID} | jq -r '.Parameters[].Value'`" >> ~/.netrc
        - echo "password `aws ssm get-parameters --names ${SSM_PASS_KEY} --with-decryption --region us-east-1  --profile ${SLS_AWS_ACCOUNT_ID} | jq -r '.Parameters[].Value'`" >> ~/.netrc

        - git clone ${GIT_URL}
        - cd ${REPO_NAME}
        - date "+%Y%m%d%H%M%S" > ../now.txt

        - sh ../prebuild.sh
        - cd ../cognito-manager-client
        - rm -rf ${REPO_NAME}

    build:
      commands:
        - npm run build
  artifacts:
    baseDirectory: cognito-manager-client/dist/cognito-manager-client
    files:
      - '**/*'
  cache:
    paths:
      - cognito-manager-client/node_modules/**/*

```

```predict.sh``` の中身はこんな感じになりました。

```sh
#!/bin/sh

# for karate
hugo new karate/`cat ../now.txt`.md
echo "{{<rawhtml>}}" >> content/karate/`cat ../now.txt`.md
echo "`cat ../result_karate.html`" >> content/karate/`cat ../now.txt`.md
echo "{{</rawhtml>}}" >> content/karate/`cat ../now.txt`.md

# for unittest
hugo new unittest/`cat ../now.txt`.md
echo "{{<rawhtml>}}" >> content/unittest/`cat ../now.txt`.md
echo "`cat ../result_unittest.html`" >> content/unittest/`cat ../now.txt`.md
echo "{{</rawhtml>}}" >> content/unittest/`cat ../now.txt`.md

git config --global user.email ${GIT_EMAIL}
git config --global user.name ${GIT_NAME}
git add *
git commit -a -m "`cat ../now.txt` commit."
git push origin master
```

# まとめ
以前、ビルド結果を表示できるように色々と工夫してみましたが、Amplify Consoleを連携させることで、ビルド結果を蓄積しつつ、履歴／一覧表示ができるくらいまでにはなりました。まだまだAmplify Consoleの便利な利用方法はありそうです。