PLAID Engineer Blog

PLAID Engineer Blog


PLAID Engineer Blog

1年で4億UUを解析したKARTEを支えるAutoscaling 3パターン

NaohikoTakemuraNaohikoTakemura

みなさん、ごきげんよう。プレイドの@tik-sonと申します。

私たちはKARTEというリアルタイムでウェブ接客ができるサービスを提供しており、 KARTEの売りであるリアルタイム性を保てるように、日々インフラを磨きこんでいます。

このエントリーでは、そのインフラの仕組みについて一部を紹介していきます。
今回は「1年で4億UUを解析したKARTEを支えるAutoscaling 3パターン」です。
現在KARTEは主にAWS上で稼働しているので、このエントリーはAWSでのAutoScalingの紹介になります。

改めて説明は不要と思いますが、AutoScalingとは特定の条件をトリガーにリソースを自動的に増減させる仕組みのことです。

KARTEは

のでAutoScalingはとても重要な要素の1つになっています。

EC2でのAutoScaling

KARTEではサーバリソースとしてEC2を利用していて、その一部でAutoScalingを導入しています。
AutoScalingの構成パターンはざっくり言うと3種類あり、それぞれ紹介していきます。

1. Autoscaling+CloudWatch+ELB

一番標準的なパターンです。 AWSではAutoscalingという、サービス名の通りEC2の能力を自動的に縮小、拡張することができるサービスが存在するので、EC2でAutoscalingさせたい時はこのサービスを利用するのが標準です。
また、AutoScalingではサーバをScaleOutさせるだけでなく、ScaleOutしたサーバに対して処理を割り振らないといけないので、ロードバランサーと共に利用するのが一般的です。
このパターンではロードバランサーとしてAWSで提供されているElastic Load Balancing(ELB)を利用しています。ELBを使えばScaleOut時のロードバランサーへのインスタンスの紐付けも比較的に容易に実行できます。
AutoScalingのトリガーとしてはCloudWatchを利用しています。CloudWatchはAWSのモニタリングサービスでAWSの各サービスにおける基本的な監視ができ、AutoScalingのトリガーとして簡単に設定することが出来ます。
ちなみにCDP:Scale Outパターンが本パターンに該当すると思います。

image.png (70.2 kB)

2. Autoscaling+CloudWatch+CustomMetric+ELB

CloudWatchで用意されている標準のMetricだけだと、適切なタイミングでスケールアウト/インが実行されないことがあるので、独自のMetric(CustomMetric)を利用してスケールさせるパターンです。
CustomMeticを利用する以外は基本的には「1. Autoscaling+CloudWatch+ELB」と同じです。KARTEではこのパターンを解析サーバのAutoScalingで利用していて、解析状況をCustomMetricとして送付して利用しています。
AWSには色々な言語でのSDKが用意されているのでCustomMetricの送付はこれを利用すると便利です。
ちなみにNode.js(coffeescript)でMetricを送ろうとするとこんな感じになります。

AWS = require('aws-sdk')  
cloudwatch = new AWS.CloudWatch()  
params =  
  MetricData: [ {
    MetricName: 'YOUR_METRIC_NAME'
    Dimensions: [ {
      Name: 'YOUR_DIMENSIONS_NAME'
      Value: YOUR_DIMENSIONS_VALUES
    } ]
    Timestamp: new Date
    Unit: 'YOUR_UNIT'
    Value: YOUR_VALUE
  } ]
  Namespace: 'YOUR_NAMESPACE'
cloudwatch.putMetricData params, (err, data) ->  
  if err
    console.log err, err.stack
  else
    console.log data

まとめると以下の通りです。

image.png (82.4 kB)

3. Autoscaling+CloudWatch+ELB+Route53+NginxPlus

KARTEではSocket.IOを利用している部分があるのですが、Socket.IOはELBとは相性が悪く、
(HTTPモードの場合だとHTTPヘッダが書き換えられて、HTTPUpgradeができない、TCPモードだと接続ごとに別のサーバが応答するのでハンドシェイクが失敗する等) nginxをSocket.IOを利用するサーバのロードバランサーとして利用しています。
nginxはWebSocketProxyのサポートを1.3.13より開始しており、それによりSocket.IOもnginxで利用できるようになっているためです。
詳細な設定方法はnginxのブログに記載されているのでこちらをご覧いただければと思います。 ip_hashという方法で分散することがポイントで、これにより同じクライアントからのアクセスは一意になります。 ちなみにこのip_hash、IPv4の場合は初めの3オクテットがhashing keyとして利用されるので、注意が必要です。

Specifies that a group should use a load balancing method where requests are distributed between servers based on client IP addresses. The first three octets of the client IPv4 address, or the entire IPv6 address, are used as a hashing key. The method ensures that requests from the same client will always be passed to the same server except when this server is unavailable. In the latter case client requests will be passed to another server. Most probably, it will always be the same server as well.

nginxを利用することでSocket.IOの負荷分散ができるようになりましたが、最終的に実施したいことはAutoScalingです。
ELB利用時にはAutoscalingで新しく起動してくるインスタンスはAWS側でELBに紐付けてもらえますが、nginxを利用する場合はもちろんAWS側は何もしてくれないので、この仕組みを作る必要があります。
実現方法は色々とあると思いますが、この仕組みはRoute53とnginxPlusで実現可能です。

nginxのupstreamにはIPアドレスではなく名前であらかじめ利用予定のサーバ名を記載しておき、
インスタンスの起動時にインスタンス自身がRoute53に自分のIPアドレスをAレコードに登録するという方法です。

この方法では既存のレコードに影響をおよぼさないように

のような工夫が大切になります。

また、この仕組みには標準のnginxではなく、nginxPlusを利用します。 nginxPlusとはnginxのエンタープライズ向けのプロダクトで、nginxの機能に加え様々な機能が利用できます。
今回の仕組みの中でnginxPlusを利用するのは、サービスの再起動なしにupstream内のserverのAレコードの変更を追従してくれる機能があるためです。 https://www.nginx.com/resources/admin-guide/load-balancer/

NGINX Plus can monitor changes of IP addresses that correspond to a domain name of the server and automatically apply these changes to NGINX without its restart.

nginxPlusはAWSだとAmazonMarketPlaceでAMIとして購入できるので、EC2インスタンス同様に従量課金で利用することが可能です。

このパターンについてまとめます。

[以下、サーバ起動時の処理]

image.png (92.5 kB)

以下のようなことも諸々と考慮しないといけないのですが、今回のエントリーでは割愛させていただきます。

最後に

ウェブ接客プラットフォーム「KARTE」を運営するプレイドでは、 KARTEを支える技術に興味を持つエンジニア(インターンも!)を募集しています。

詳しくはこちら(Wantedly)募集一覧をご覧ください。 もしくはこちらのボタンよりお気軽に「話を聞きに行きたい」と押してください!

Comments