2016-08-02 18 views
2

X個のSQSキューがある場合、ApproximateNumberOfMessagesを1つのCloudWatchメトリックに集計するにはどうすればよいですか?AWS SQSを集計する方法ApproximateNumberOfMessages

キューにあるメッセージの数に基づいて、自動スケーリンググループスケールを設定したいと考えています。複数のCloudWatchアラーム(各キューに1つ)を使用すると、1つのキューが空になり、他のキューには「フル」があるため、問題が発生します。

答えて

5

私がこれを達成した方法は、Node.jsでAWS Lambdaを使用することです。毎分ラムダ関数を実行するCloudWatchイベントトリガを追加しました。これにより、sqsキューにクエリが実行され、カスタムのCloudWatchメトリックが作成されます。このメトリックを自動スケーリンググループに適用してスケーリングできます。

var AWS = require('aws-sdk'); 
var sqs = new AWS.SQS(); 
var cloudWatch = new AWS.CloudWatch(); 

var queueUrls = ['https://sqs.REGION.amazonaws.com/ACCOUNT-NUMBER/queueUrl1','https://sqs.REGION.amazonaws.com/ACCOUNT-NUMBER/queueUrl2']; 

exports.handler = (event, context, callback) => { 
    var fn = function (url) { 
     return new Promise(resolve => { 
      var sqsParams = { 
       AttributeNames: ['ApproximateNumberOfMessages'], 
       QueueUrl: url 
      }; 

      sqs.getQueueAttributes(sqsParams, function(err,data){ 
       if(err) 
       { 
        console.log(err,err.stack); 
        context.fail(err); 
       } 
       else 
       { 
        resolve({name: url.split('/').pop(), messageCount: parseInt(data.Attributes.ApproximateNumberOfMessages)}); 
       } 
      }); 
     }); 
    }; 

    var actions = queueUrls.map(fn); 
    Promise.all(actions).then(function(queues) { 
     var messageCount = queues.map(function(m){return m.messageCount;}); 
     var queueNames = queues.map(function(n){return n.name;}).join(); 

     var metricParams = { 
      MetricData:[{ 
       MetricName: 'ApproximateNumberOfMessages', 
       Dimensions:[{ 
        Name: 'QueueName', 
        Value: queueNames 
       }], 
       Unit: 'Count', 
       StatisticValues: { 
        Maximum: Math.max.apply(Math, messageCount), 
        Minimum: Math.min.apply(Math, messageCount), 
        SampleCount: queues.length, 
        Sum: messageCount.reduce((pv, cv) => pv+cv, 0) 
       } 
      }], 
      Namespace: 'AWS/SQS' 
     }; 
     cloudWatch.putMetricData(metricParams, function(err, metricData){ 
      if(err) console.log(err,err.stack); 
      else console.log(metricData); 
     }); 
    }); 
}; 

このコードは明らかに2つの以上のキューを処理するために最適化することができ、おそらく非同期滝の恩恵を受けることができます。

EDIT:promisesを使用するように更新されました。

EDIT2:CloudWatchメトリックのキュー名を連結

関連する問題