AWS Cognito(2)JavaScriptによるクライアントの実装

前回のCognitoのAWS側の設定に続いて、今回はWebコンテンツ側でCognito認証を利用する際のJavascript SDKを用いた実装方法について確認する。AWS Javascript SDKを用いたCognitoの認証はサーバ側にスクリプトを用意する必要がなく、S3などを用いて安価にWebサーバを構築することが可能である。

なお、AWSの認証情報とパブリックログインプロバイダから取得したトークンは、一定期間後に認証切れとなる。Cognitoはトークンの再取得についての機能は提供していないが、多くのパブリックログインプロバイダはリフレッシュトークンを用いたトークンの再取得をサポートしている。

Javascriptによる実装

AWS Javascript SDKを用いたCognitoの認証とデータ同期の実装は以下の通り。

  • AWS Javascript SDK のインポート
  • Amazon Cognito Sync Manager for JavaScript の取得とインポート
    • Cognito Sync(データセットの同期)処理をライブラリで提供している
    • Github からライブラリファイルを取得し、配置する
<script src="https://sdk.amazonaws.com/js/aws-sdk-2.2.6.min.js"></script>
    <script src="amazon-cognito.min.js"></script>
  • Credentials Objectを初期化する
    • AWS.CognitoIdentityCredentialsクラス を利用する
    • オブジェクト初期化には、Cognito Identity Pool IDとパブリックログインプロバイダのトークンを用いる
// Cognito認証を行う
    // 
    // @param {String} provider provider name
    // @param {String} token token
    // @param {Object} data data
    function getIdentityId(provider, token, data){

    		var logins = {};
    		// insert key of associative array in a variable
    		logins[provider] = token;
    		log("You have SUCCESSFULLY logged in. provider: " + provider + " token:" + token);
    		// region (tokyo)
    		AWS.config.region = 'ap-northeast-1';
    		// authentication providers
    		if(provider!=null && token!=null){
    			AWS.config.credentials = new AWS.CognitoIdentityCredentials({
        				// identity pool id
        				IdentityPoolId: 'ap-northeast-1:**********',
        				// provider name and token
        				Logins: logins // object (associative array)
    			});
    		// unauthenticated identities
    		}else{	
    			AWS.config.credentials = new AWS.CognitoIdentityCredentials({
        				IdentityPoolId: 'ap-northeast-1:**********',
    			});
    		}
    		//
    		// 以下に続く
    		//
    	}
  • 作成したCredentials Objectを用いて、Cognito IDを取得する
    • AWS.config.credentials.get()
    • Cognito IDは、 AWS.config.credentials.identityIdで取得できる
		AWS.config.credentials.get(function(err) {
            		if (!err) {
                			//
                			// データセット処理
                			//
            		}else{
                			log("Error Occurred: " + err);
            		}
    		});
  • データの保管と同期を行う( Amazon Cognito Sync Manager
    • syncClient.openOrCreateDataset()
    • dataset.put()
    • dataset.synchronize()
	AWS.config.credentials.get(function(err) {
            		if (!err) {
                			log("Cognito Identity Id: " + AWS.config.credentials.identityId);
    				var syncClient = new AWS.CognitoSyncManager();
    				if(data != null){
    					// open or create dataset
    					syncClient.openOrCreateDataset(provider, function(err, dataset) {
    						$.each(data, function (key, val) {
    							dataset.put(key, val, function(err, record){
                    						log("Put Dataset: { " + key + ": " + val + " }");
    							});
    						});
    						// synchronize dataset
    						dataset.synchronize({
    							onSuccess: function(data, newRecords) {	
                    						log("Syncronize Dataset: { " + provider + " }");
    							},
    							onFailure: function(err) {
                    						log("Error Occurred: " + err);
    							}
    						});
    					});
    				}else{
    					log("NOT Syncronize Dataset: no data");
    				}
    			}else{
    				log("Error Occurred: " + err);
    			}
    		});

Cognitoには各ユーザごとに保存領域が用意されており、各ユーザごとに複数のデータセット(テーブル)を持つことができる。ユーザデータは一旦ローカル上に保管されるため、通信状況には影響しない。ローカルに保存されたデータセットは、明示的に同期メソッドを実行した際にAWSと同期される。同期の際にデータが衝突した場合は、ローカルを優先するかAWSを優先するか選択することができる。詳細は、Amazon Cognito Sync Manager for JavaScriptに記述されている。