[JAWS-UG CLI] SQS:#3 メッセージの受信 (処理側)

AWS CLIを利用して、SQSのキューに滞留しているメッセージを取り出してみましょう。
ジョブ処理側の立場で、ジョブの依頼を取得するイメージになります。



前提条件
========

## SQSへの権限

* 操作するキューに対してRead/Write権限があること。

## AWS CLIのバージョン

以下のバージョンで動作確認済

* AWS CLI 1.10.6
* AWS CLI 1.6.10


0. 事前作業
===========


0.1. リージョンの指定
---------------------

対象のキューが存在するリージョンを指定します。

```bash:コマンド:
export AWS_DEFAULT_REGION='ap-northeast-1'
```

0.2. 変数の確認
---------------

プロファイルが想定のものになっていることを確認します。

```bash:コマンド:
aws configure list
```

```text:結果(例)
            Name                    Value             Type    Location
            ----                    -----             ----    --------
         profile         sqs-prjz-mbp13        env    AWS_DEFAULT_PROFILE
      access_key     ****************XXXX shared-credentials-file
      secret_key     ****************XXXX shared-credentials-file
          region                         ap-northeast-1  env    AWS_DEFAULT_REGION
```

0.3. キューの指定
-----------------

取り出したいメッセージの存在するキューのURLを確認します。

ここでは、http://qiita.com/tcsh/items/a41ac99e41430c1d758c で作成したキューを指定します。

```bash:コマンド:
SQS_QUEUE_NAME='example-queue'
```

```bash:コマンド:
SQS_QUEUE_URL=$( \
  aws sqs get-queue-url \
    --queue-name ${SQS_QUEUE_NAME} \
    --output text\
  ) \
     && echo ${SQS_QUEUE_URL}
```

```text:結果:
   https://ap-northeast-1.queue.amazonaws.com/XXXXXXXXXXXX/example-queue
```


1. メッセージ数の確認
===========================

メッセージ受信前に、キューにいくつのメッセージが処理待ちになっているか確認します。

```bash:コマンド:
aws sqs get-queue-attributes \
    --queue-url ${SQS_QUEUE_URL} \
    --attribute-names ApproximateNumberOfMessages
```

```json:結果
{
    "Attributes": {
        "ApproximateNumberOfMessages": "1"
    }
}
```

同じキューのメッセージを誰も受信していなければ1のはずです。


2. メッセージの受信
===================

SQSのキューは、受信操作をするとVisibilityTimeoutの時間だけ見えなくなります。

シェルで処理する場合は、出力結果を一旦ファイルに保存するのがよいでしょう。

```bash:コマンド:
FILE_SQS_MSG="${SQS_QUEUE_NAME}-msg".json
```

```bash:コマンド:
aws sqs receive-message \
  --queue-url "${SQS_QUEUE_URL}" > ${FILE_SQS_MSG} \
     && cat ${FILE_SQS_MSG}
```

```json:結果
   {
       "Messages": [
           {
               "Body": "Hello Worls!", 
               "ReceiptHandle": "AQEBUo4y+XVuRSe4jMv0QM6Ob1viUnPbZ64WI01+Kmj6erhv192m80m+wgyob+zBgL4OMT+bps4KR/q5WK+W3tnno6cCFuwKGRM4OQGM9omMkK1F+ZwBC49hbl7UlzqAqcSrHfxyDo5x+xEyrEyL+sFK2MxNV6d0mF+7WxXTboyAu7JxIiKLG6cUlkhWfk3W4/Kghagy5erwRhwTaKtmF+7hw3Y99b55JLFTrZjW+/Jrq9awLCedce0kBQ3d2+7pnlpEcoY42+7T1dRI2s7um+nj5TIUpx2oSd9BWBHCjd8UQjmyye645asrWMAl1VCvHZrHRIG/v3vgq776e1mmi9pGxN96IW1aDZCQ1CSeqTFASe4=", 
               "MD5OfBody": "6699d5711c044a109a6aff9fc193aada", 
               "MessageId": "xxxxxxxx-xxxx-xxxx-xxxx-xxxxxxxxxxxx"
           }
       ]
   }
```


3. メッセージ数の確認
===========================

メッセージ受信後に、キューにいくつのメッセージが処理待ちになっているか確認します。

3.1. ApproximateNumberOfMessagesの確認
----------------------------------------

受信によりメッセージがVisibilityTimeout待ちになったので、値が0になっているはずです。

```bash:コマンド:
aws sqs get-queue-attributes \
    --queue-url ${SQS_QUEUE_URL} \
    --attribute-names ApproximateNumberOfMessages
```

```json:結果
{
    "Attributes": {
        "ApproximateNumberOfMessages": "0"
    }
}
```

VisibilityTimeout後、メッセージがエンキューされると値が1になります。

3.2. ApproximateNumberOfMessagesNotVisibleの確認
----------------------------------------

受信によりメッセージがNotVisibleになったので、VisibilityTimeout前であれば値が1になっているはずです。

```bash:コマンド:
aws sqs get-queue-attributes \
    --queue-url ${SQS_QUEUE_URL} \
    --attribute-names ApproximateNumberOfMessagesNotVisible
```

```json:結果
{
    "Attributes": {
        "ApproximateNumberOfMessages": "1"
    }
}
```

VisibilityTimeout後、メッセージがエンキューされると値が0になります。



4. ReceiptHandleの取得
======================

保存した実行結果(JSON形式)からReceiptHandleの値を取り出します。

このReceiptHandleの値は、そのメッセージを操作するときに必要になります。

```bash:コマンド:
SQS_RECEIPT_HANDLE=$( \
  cat ${FILE_SQS_MSG} | jq -r '.Messages[].ReceiptHandle' \
) \
     && echo ${SQS_RECEIPT_HANDLE}
```

```text:結果:
AQEBUo4y+XVuRSe4jMv0QM6Ob1viUnPbZ64WI01+Kmj6erhv192m80m+wgyob+zBgL4OMT+bps4KR/q5WK+W3tnno6cCFuwKGRM4OQGM9omMkK1F+ZwBC49hbl7UlzqAqcSrHfxyDo5x+xEyrEyL+sFK2MxNV6d0mF+7WxXTboyAu7JxIiKLG6cUlkhWfk3W4/Kghagy5erwRhwTaKtmF+7hw3Y99b55JLFTrZjW+/Jrq9awLCedce0kBQ3d2+7pnlpEcoY42+7T1dRI2s7um+nj5TIUpx2oSd9BWBHCjd8UQjmyye645asrWMAl1VCvHZrHRIG/v3vgq776e1mmi9pGxN96IW1aDZCQ1CSeqTFASe4=
```


5. メッセージの削除
===================

誰かが取得したメッセージは、「処理済み」としてキューから削除しておく必要があります。

ReceiptHandleの値でメッセージを特定して、delete-messageコマンドで削除します。

```bash:コマンド:
aws sqs delete-message \
     --queue-url "${SQS_QUEUE_URL}" \
     --receipt-handle ${SQS_RECEIPT_HANDLE}
```

```text:結果:
   (戻り値なし)
```


6. メッセージ数の確認
===========================

メッセージ送信後に、キューにいくつのメッセージが処理待ちになっているか確認します。

```bash:コマンド:
aws sqs get-queue-attributes \
    --queue-url ${SQS_QUEUE_URL} \
    --attribute-names ApproximateNumberOfMessagesNotVisible
```

```json:結果
{
    "Attributes": {
        "ApproximateNumberOfMessagesNotVisible": "0"
    }
}
```

```bash:コマンド:
aws sqs get-queue-attributes \
       --queue-url ${SQS_QUEUE_URL} \
       --attribute-names ApproximateNumberOfMessages
```

```json:結果
   {
       "Attributes": {
           "ApproximateNumberOfMessages": "0"
       }
   }
```

両方とも値がゼロになっていれば、処理待ちのメッセージが無いことになります。



完了
====