AWS AmplifyでReactアプリケーション (TypeScript & GraphQL)

AWS Amplifyを利用してServerlessなReactアプリケーションの構築を行います。TypeScriptの利用を前提とし、APIはGraphQLを導入します。

Amplify CLIのインストール

npm i -g @aws-amplify/cli

Amplify設定

以下のコマンドを実行するとブラウザが開き、AWSコンソールへのログインを求められます。

amplify configure

ログインができたら、ターミナルに戻りEnterを押すと、Regionの選択とIAMユーザを入力します。今回は新たにIAMユーザを作成するのでサジェストされた名前もしくは任意の名前を入力しEnterを押します。

Follow these steps to set up access to your AWS account:

Sign in to your AWS administrator account:
https://console.aws.amazon.com/
Press Enter to continue

Specify the AWS Region
? region:  
  eu-west-1 
  eu-west-2 
  eu-central-1 
❯ ap-northeast-1 
  ap-northeast-2 
  ap-southeast-1 
  ap-southeast-2 
(Move up and down to reveal more choices)

Specify the username of the new IAM user:
? user name:  (amplify-AAAA)  

再びブラウザに戻り、上記ユーザの作成画面に遷移するので、画面に沿って作成します。

  • Select AWS access type: Programmatic accessにチェック
  • Set permissions: AdministratorAccessにチェック
  • Add tags (optional): 未入力のまま次へ
  • Create userボタンを押下しユーザの作成が完了

ユーザ作成が完了すると以下のようなCredential情報のページが表示されます。ここでのKeyは後ほどAmplify設定で使用するのでこのまま開いた状態にするかCSVダウンロードしておきます。

再びターミナルに戻りEnterを押すと上記のAccess key ID, Secret access keyとprofileを利用する場合にはその名の入力が求められます。今回は未入力(default)とします。

Enter the access key of the newly created user:
? accessKeyId:  ********************
? secretAccessKey:  ****************************************
This would update/create the AWS Profile in your local machine
? Profile Name:  default

Successfully set up the new user.

これで設定完了。

Reactプロジェクトの作成

create-react-appのインストールを前提として以下を実行

npx create-react-app react-ts-app --typescript

React appでのAmplify初期設定

ReactプロジェクトにてAmplifyの設定を行います。

amplify init
Note: It is recommended to run this command from the root of your app directory
? Enter a name for the project amplifydrill
? Enter a name for the environment dev
? Choose your default editor: Visual Studio Code
? Choose the type of app that you're building javascript
Please tell us about your project
? What javascript framework are you using react
? Source Directory Path:  src
? Distribution Directory Path: build
? Build Command:  npm run-script build
? Start Command: npm run-script start
Using default provider  awscloudformation

For more information on AWS Profiles, see:
https://docs.aws.amazon.com/cli/latest/userguide/cli-multiple-profiles.html

? Do you want to use an AWS profile? Yes
? Please choose the profile you want to use default

Adding backend environment dev to AWS Amplify Console app: du9humgj6xxxxx
⠦ Initializing project in the cloud...

CREATE_IN_PROGRESS AuthRole                        AWS::IAM::Role             Sat May 16 2020 23:39:36 GMT+0900 (Japan Standard Time) Resource creation Initiated
CREATE_IN_PROGRESS UnauthRole                      AWS::IAM::Role             Sat May 16 2020 23:39:36 GMT+0900 (Japan Standard Time) Resource creation Initiated
CREATE_IN_PROGRESS AuthRole                        AWS::IAM::Role             Sat May 16 2020 23:39:35 GMT+0900 (Japan Standard Time)                            
CREATE_IN_PROGRESS UnauthRole                      AWS::IAM::Role             Sat May 16 2020 23:39:35 GMT+0900 (Japan Standard Time)                            
CREATE_IN_PROGRESS DeploymentBucket                AWS::S3::Bucket            Sat May 16 2020 23:39:35 GMT+0900 (Japan Standard Time)                            
CREATE_IN_PROGRESS amplify-amplifydrill-dev-233929 AWS::CloudFormation::Stack Sat May 16 2020 23:39:31 GMT+0900 (Japan Standard Time) User Initiated             
⠧ Initializing project in the cloud...

CREATE_IN_PROGRESS DeploymentBucket AWS::S3::Bucket Sat May 16 2020 23:39:36 GMT+0900 (Japan Standard Time) Resource creation Initiated
⠧ Initializing project in the cloud...

CREATE_COMPLETE AuthRole   AWS::IAM::Role Sat May 16 2020 23:39:52 GMT+0900 (Japan Standard Time) 
CREATE_COMPLETE UnauthRole AWS::IAM::Role Sat May 16 2020 23:39:52 GMT+0900 (Japan Standard Time) 
⠇ Initializing project in the cloud...

CREATE_COMPLETE amplify-amplifydrill-dev-233929 AWS::CloudFormation::Stack Sat May 16 2020 23:40:00 GMT+0900 (Japan Standard Time) 
CREATE_COMPLETE DeploymentBucket                AWS::S3::Bucket            Sat May 16 2020 23:39:58 GMT+0900 (Japan Standard Time) 
✔ Successfully created initial AWS cloud resources for deployments.
✔ Initialized provider successfully.
Initialized your environment successfully.

Your project has been successfully initialized and connected to the cloud!

Some next steps:
"amplify status" will show you what you've added already and if it's locally configured or deployed
"amplify add " will allow you to add features like user login or a backend API
"amplify push" will build all your local backend resources and provision it in the cloud
"amplify console" to open the Amplify Console and view your project status
"amplify publish" will build all your local backend and frontend resources (if you have hosting category added) and provision it in the cloud

Pro tip:
Try "amplify add api" to create a backend API and then "amplify publish" to deploy everything

こんな感じで設定が完了します。`amplify` フォルダがプロジェクトに作成されているのを確認します。
AWS CloundFormationとはAWSインフラをcode化していわばテンプレート化してくれるサービスで、これによりインフラの移設などが自動化できるというとても便利なものです。

API作成

amplify add api
? Please select from one of the below mentioned services: GraphQL
? Provide API name: amplifydrill
? Choose the default authorization type for the API Amazon Cognito User Pool
Using service: Cognito, provided by: awscloudformation

 The current configured provider is Amazon Cognito. 

 Do you want to use the default authentication and security configuration? Default configuration
 Warning: you will not be able to edit these selections. 
 How do you want users to be able to sign in? Email
 Do you want to configure advanced settings? No, I am done.
Successfully added auth resource
? Do you want to configure advanced settings for the GraphQL API Yes, I want to make some additional changes.
? Configure additional auth types? No
? Configure conflict detection? No
? Do you have an annotated GraphQL schema? No
? Do you want a guided schema creation? Yes
? What best describes your project: One-to-many relationship (e.g., “Blogs” with “Posts” and “Comments”)
? Do you want to edit the schema now? Yes
Please edit the file in your editor: /Users/*****/Documents/projects/amplify_sample/amplify/backend/api/amplifydrill/schema.graphql
? Press enter to continue 

schema.graphql

必要に応じて編集します。

type Blog @model {
  id: ID!
  name: String!
  posts: [Post] @connection(keyName: "byBlog", fields: ["id"])
}

type Post @model @key(name: "byBlog", fields: ["blogID"]) {
  id: ID!
  title: String!
  blogID: ID!
  blog: Blog @connection(fields: ["blogID"])
  comments: [Comment] @connection(keyName: "byPost", fields: ["id"])
}

type Comment @model @key(name: "byPost", fields: ["postID", "content"]) {
  id: ID!
  postID: ID!
  post: Post @connection(fields: ["postID"])
  content: String!
}

Save後にEnter押下でgraphqlコンパイルが完了するので、このローカルの状態をcloudにも反映させます。

amplify push
✔ Successfully pulled backend environment dev from the cloud.

Current Environment: dev

| Category | Resource name        | Operation | Provider plugin   |
| -------- | -------------------- | --------- | ----------------- |
| Auth     | amplifysampled5b6xxxx | Create    | awscloudformation |
| Api      | amplifysample         | Create    | awscloudformation |
? Are you sure you want to continue? Yes

The following types do not have '@auth' enabled. Consider using @auth with @model
         - Blog
         - Post
         - Comment
Learn more about @auth here: https://docs.amplify.aws/cli/graphql-transformer/directives#auth

GraphQL schema compiled successfully.

Edit your schema at /Users/yosukesato/Documents/projects/personal/amplify_drill/amplify/backend/api/amplifydrill/schema.graphql or place .graphql files in a directory at /Users/yosukesato/Documents/projects/personal/amplify_drill/amplify/backend/api/amplifydrill/schema
? Do you want to generate code for your newly created GraphQL API Yes
? Choose the code generation language target typescript
? Enter the file name pattern of graphql queries, mutations and subscriptions src/graphql/**/*.ts
? Do you want to generate/update all possible GraphQL operations - queries, mutations and subscriptions Yes
? Enter maximum statement depth [increase from default if your schema is deeply nested] 2
? Enter the file name for the generated code src/API.ts
⠸ Updating resources in the cloud. This may take a few minutes...

aws-amplify, aws-amplify-reactのインストール

Amplifyを利用する際のapiモジュールなどが利用できるパッケージをインストールします。

yarn add -D aws-amplify aws-amplify-react

index.tsxの編集

最後にAmplifyをReactで利用できるようにします。
src/index.tsx に以下を追加します。

import Amplify from 'aws-amplify';
import aws_exports from './aws-exports';

Amplify.configure(aws_exports);

これで準備完了。