SANDFISH FACTORY

技術ブログです。python・vuejsを愛でる日々について綴ります

Vue.jsとAWS Amplifyで開発するサーバレスなWebアプリ:環境構築

Vue Fes Japan 2019のCFPに申し込んでみた

Vue Fes Japan 2019 のプロポーザルの採択発表が7/8に行われました。
今回、Vue.jsで色々と経験できたことがあったので、得たものを整理して申し込んでみましたが、

結果は 未採択!

選んだネタはVueの話としてはちょっと弱そうだったので、難しいかなというのは頭の片隅にはありましたが、わずかな願いを込めてみました。
まぁ順当だったかな。
とは言っても、今回整理した内容はブログで書こうと思っていた内容なので、何回かに分けて書いてみようと思います。

内容は件名の通り「Vue.jsとAWS Amplifyで開発するサーバレスなWebアプリ」です。

AWS Amplify とは

AWS Amplify はホームページから引用すると以下の説明がされています。

  • AWS を使用したスケーラブルなモバイルアプリおよびウェブアプリの作成、設定、実装を容易にします。
  • Amplify はモバイルバックエンドをシームレスにプロビジョニングして管理し、バックエンドを iOSAndroid、ウェブ、React Native のフロントエンドと簡単に統合するためのシンプルなフレームワークを提供します。
  • また、Amplify は、フロントエンドとバックエンドの両方のアプリケーションリリースプロセスを自動化し、機能をより迅速に提供することができます。

AWS Amplify(アプリケーションの構築とデプロイ)| AWS

AWS Amplifyフロントエンド(モバイルアプリやWebアプリ)のフレームワークを提供し、AWSを用いたバッグエンドの仕組みを簡単に構築できる仕組みとなっています。 バッグエンドの仕組み(フレームワーク)についてはServerless Frameworkがありますが、AWS Amplifyも同じようなことができます。

環境

今回は以下の環境で試しました。

  • macOS Mojave
  • Node.js:v8.11.0
  • vue-cli:3.8.4
  • Yarn:1.17.0

サンプルプロジェクトを作る

まずはvue-cliを用いてプロジェクトの雛形を作成します。

vue create blog-vue-app
  • Manually select features
    • Babel
    • Router
    • Vuex
    • LInter / Formatter
    • Unit Testing
  • Use history mode for router?
    • Yes
  • Pick a linter / formatter config
    • ESLint with error prevention only
  • Pick additional lint features
    • Lint on save
  • Pick a unit testing solution
    • Jest
  • Where do you prefer placing config for Babel, PostCSS, ESLint, etc.?
    • In dedicated config files

UIライブラリを追加する

UIのライブラリとしてvuetifyを追加します。他のライブラリを使用している方はスキップして下さい。

vue add vuetify
  • Choose a preset(vuetifyのプリセットを選択します)
    • Default (recommended)

CLIインストール

Yarn経由でaws-ampilfy/cliをインストールします。 手順はドキュメントに詳しく書いてあるのでそちらを参考でも良いです。 すでにインストール済みの方はスキップして問題ないです。

yarn global add @aws-amplify/cli

次にAWS Amplifyの設定を行います。 すでに設定済みで新しくAWS Ampifyの設定を作る必要がない方はスキップして問題ないです。

amplify configure
  • AWSの管理者アカウントでログインが求められます。ブラウザが開くのでそちらでログインして下さい。
  • ターミナル上でEnterが求められるので、Enterするとリージョンの入力が求められます。必要なリージョンを選択して下さい
  • AWS Amplifyを用いるためのIAMユーザを作るので、IAMユーザ名を入力してEnterします。
  • 再度ブラウザが開かれます。IAMユーザに対する設定を行って下さい。(今回はデフォルトのまま進めます)
    • ユーザー名:入力したユーザー名
    • AWS アクセスの種類:プログラムによるアクセス - アクセスキーを使用
    • アクセス権限の境界:アクセス権限の境界が設定されていません
    • 管理ポリシー:AdministratorAccess
  • Accessキーがダウンロードできます。後ほど利用するので保存しておいて下さい。
  • ターミナルに戻ってEnterするとAccess Key ID、Secret Access Keyが求められますので入力します。(上でダウンロードしたもの)
  • これまで設定した内容をプロファイルとして保存します。プロファイル名が求められるので名前を入力して下さい。
  • ここまでで設定は完了です。

Amplifyインストール

Yarn経由でAmplifyをインストールします。

cd blog-vue-app
yarn add aws-amplify
yarn add aws-amplify-vue
  • 今回は以下のバージョンで進めます。
    • aws-amplify:1.1.30
    • aws-amplify-vue:0.2.13

AWSバックエンドを設定する

amplify-cliで初期化をし、AWSバックグラウンドの設定を行う。

amplify init
  • Enter a name for the project(プロジェクト名を入力する)
    • blog-vue-app
  • Enter a name for the environment(環境の名前を入力する)
    • dev
  • Choose your default editor(デフォルトで使っているテキストエディタを選ぶ)
  • Choose the type of app that you're building(アプリ開発する環境を選ぶ)
  • What javascript framework are you using(javascriptフレームワークを選ぶ)
    • vue
  • Source Directory Path(ソースディレクトリのパスを入力する)
    • src
  • Distribution Directory Path(配布ディレクトリのパスを入力する)
    • dist
  • Build Command(ビルドコマンドを入力する)
    • yarn build
  • Start Command(起動コマンドを入力する)
    • yarn serve
  • Do you want to use an AWS profile?(AWSプロファイルを利用するか)
    • Yes
  • Please choose the profile you want to use(amplify configureで作成したプロファイルの名前を入力する)

利用するAWSサービスを追加する

amplify-cliで利用する機能を追加します。今回は認証とストレージを利用するので、auth、storageを追加します。

amplify add auth
amplify add storage
amplify push

authを追加する

  • Do you want to use the default authentication and security configuration? (認証で用いるセキュリティ設定を指定する)
    • Default configuration
  • How do you want users to be able to sign in when using your Cognito User Pool? (Cognitoユーザープールでサインインする時に利用する要素を指定する)
    • Email
  • What attributes are required for signing up?(サインアップの必須要素を指定する)
    • Email

storageを追加する

  • Please select from one of the below mentioned services(利用するサービスを選択する)
    • Content (Images, audio, video, etc.)
  • Please provide a friendly name for your resource that will be used to label this category in the project(リソースにつけるラベル名を指定する)
  • Please provide bucket name(バケット名を指定する)
  • Who should have access(誰がアクセスするか指定する)
    • Auth users only
  • What kind of access do you want for Authenticated users? (認証されたユーザのアクセス制御を指定する)
    • create,update/read/delete

pushして環境を構築する

これまでに追加したサービスの設定内容を元にAWS上に環境を構築する。
amplify pushを実行することで内部で生成されたCloudFormationの設定ファイル経由で環境が作られます。

サンプルプログラムを書く

AWS Amplifyを組み込む

プロジェクフォルダ内のmain.jsにAWS Amplifyの設定を追加します。

import Vue from 'vue'
import App from './App.vue'
import router from './router'
import store from './store'
import Amplify, * as AmplifyModules from 'aws-amplify'
import { AmplifyPlugin } from 'aws-amplify-vue'
import awsconfig from './aws-exports'
Amplify.configure(awsconfig)

Vue.use(AmplifyPlugin, AmplifyModules)

Vue.config.productionTip = false

new Vue({
  router,
  store,
  render: h => h(App)
}).$mount('#app')

aws-amplifyからAmplify本体とモジュールを読み込みます。
aws-amplify-vueからvueコンポーネントが定義されているプラグインを読み込みます。
aws-exports.jsはamplify initで自動生成されます。aws-exportsはAWSへの接続情報が定義されています。自動生成しなくても手動で作成しても問題ないです。
Amplify本体に設定を登録し、Vueにプラグインとモジュールをインストールします。 ここまでで、VueでAWS AmplifyとVueコンポーネントを利用するための設定は終わりです。

サンプルコンポーネントを作る

今回のサンプルプログラムとしてログイン画面と写真一覧画面を作ります。
プロジェクト作成で作られたHelloWorld.vue、Home.vue、About.vueは削除して問題ないです。

// App.vue
<template>
  <v-app>
    <v-content>
      <router-view/>
    </v-content>
  </v-app>
</template>

<script>
export default {
  name: 'App'
}
</script>
// views/SignIn.vue
<template>
  <v-container fluid fill-height>
    <v-layout align-center justify-center>
      <div v-if="!signedIn">
        <amplify-authenticator :auth-config="authConfig" />
      </div>
      <div v-if="signedIn">
        <amplify-sign-out />
      </div>
    </v-layout>
  </v-container>
</template>

<script>
import { AmplifyEventBus } from 'aws-amplify-vue'
import Auth from '@aws-amplify/auth'

export default {
  props: [],
  data () {
    return {
      signedIn: false,
      authConfig: {
        // 通常のログイン
        signInConfig: {
          header: 'サインイン'
        },
        // 登録
        signUpConfig: {
          hideDefaults: true,
          signUpFields: [
            { label: 'ユーザーID', key: 'username', required: true, type: 'email', displayOrder: 0 },
            { label: 'パスワード', key: 'password', required: true, type: 'password', displayOrder: 1 },
          ]
        },
        confirmSignUpConfig: {},
        forgotPasswordConfig: {},
        confirmSignInConfig: {}
      }
    }
  },
  async beforeCreate () {
    try {
      await Auth.currentAuthenticatedUser()
      this.signedIn = true
    } catch (err) {
      console.log(err)
      this.signedIn = false
    }
    AmplifyEventBus.$on('authState', (info) => {
      if (info === 'signedIn') {
        this.signedIn = true
        this.$router.push('/photo')
      } else {
        this.signedIn = false
      }
    })
  }
}
</script>
// views/Photo.vue
<template>
<v-container fluid fill-height>
  <v-layout align-center justify-center>
    <div v-if="signedIn">
      <amplify-photo-picker :photo-picker-config="photoPickerConfig" />
      <amplify-s3-album path="upload/"></amplify-s3-album>
      <amplify-sign-out />
    </div>
    <div v-else>
      <amplify-sign-out />
    </div>
  </v-layout>
</v-container>
</template>

<script>
import { AmplifyEventBus } from 'aws-amplify-vue'
import Auth from '@aws-amplify/auth'

export default {
  props: [],
  data () {
    return {
      signedIn: false,
      imagePath: 'upload',
      photoPickerConfig: {
        header: 'Upload Photo',
        accept: 'image/*',
        path: 'upload/'
      }
    }
  },
  async beforeCreate () {
    try {
      await Auth.currentAuthenticatedUser()
      this.signedIn = true
    } catch (err) {
      this.signedIn = false
      console.log(err)
    }
    AmplifyEventBus.$on('authState', (info) => {
      if (info === 'signedIn') {
        this.signedIn = true
      } else if (info === 'signedOut') {
        this.signedIn = false
        console.log('signedOut OK')
        this.$router.push('/')
      } else {
        this.signedIn = false
      }
    })
  }
}
</script>

AWS Amplifyを動かす

ソースコードを保存して、yarn serveを実行すると問題がなければ開発用サーバーが起動します。 ブラウザからhttp://localhost:8080を入力すると下の画面が表示されるはずです。

サンプル画面(ログイン)
サンプル画面(ログイン)

ここまでが初めのサンプルプログラムの作成となります。
わずかな設定ではありますが、ここまでのコードだけでサインアップ、サインインとサイン後の画面までが出来上がりました。
次回以降で解説をしながら、カスタマイズしていこうと思います。