Generating unique id numbers in Azure

29
Generating unique ID numbers in Microsoft Azure kyrt Takekazu Omi [email protected] @takekazuomi 2014/3/29 1.0.1

description

Global Windows Azure Boot Camp 2014 Japan の資料です。

Transcript of Generating unique id numbers in Azure

Page 1: Generating unique id numbers in Azure

Generating unique ID numbers

in Microsoft Azure

kyrt Takekazu Omi

[email protected]

@takekazuomi

2014/3/29 1.0.1

Page 2: Generating unique id numbers in Azure

Generating unique ID numbers

in Microsoft Azureスケーラブルな ID 生成手法の比較と、 twitter snowflake に見る工夫

2014/2/26 kyrt @takekazuomi 2

Page 3: Generating unique id numbers in Azure

Agenda

• Challenge• スケーラブルなサービスとスケーラブルな採番

• twitter snowflake• スケーラブルな分散採番サービスの例

• Cloud Design Patterns• 応用例

kyrt @takekazuomi 32014/2/26

Page 4: Generating unique id numbers in Azure

Challengeスケーラブルなサービスには、スケーラブルな採番が必須課題と背景的な話「またの名を Challenge を課題と訳さないで」

2014/2/26 kyrt @takekazuomi 4

Page 5: Generating unique id numbers in Azure

ID 生成の要件

1. ユニークである重複が無い。これは ID をキーにしたいので当然ですね。

2. 時系列で増えていく(または減っていく)ID が生成される度に増加していくのは連番での重要な性質の一つ

3. 秒間の発行数採番を一箇所で行わずに分散してするとスケールする

4. 連続性連続した欠落の無い番号の生成

kyrt @takekazuomi 52014/2/26

Page 6: Generating unique id numbers in Azure

ID 生成のパターン

1. SQL Database の自動連番を使う• スケールしない、耐障害性を考慮すると複数台必要

2. ID Provider が完全に独立して存在する• GUID 等、 128bit 16 byte

3. 擬似 ID Provider が、擬似 ID を生成し、 UNIQUE 性は別システムで担保される

4. ID Provider の Network Service を使う• Azure Cache, memcached, redis の increment 等

5. ID Provider の Cluster Service が実装されていて Cluster 内で合意をとって ID を生成する• snowflake

kyrt @takekazuomi 6

Page 7: Generating unique id numbers in Azure

最初の2つ

• SQL Database の利用• 秒間の発番数、同時接続数に問題なければ、従来どおり利用可能• 上記の問題があるなら、複数の DB を使う (sharding) という方法も

ある• しかし、仕組みとしてはちょっと重い。コストも高い。• 秒間 100 程度まで

• GUID の利用• クライアントで完結するので、速くてスケールするしかし• 128bit あって長い( 16 byte)• 時系列で並ばない→ 時間由来のデータを prefix にすることで解決

kyrt @takekazuomi 7

Page 8: Generating unique id numbers in Azure

時系列のキーの例

.Net なら、 Tikcs などを使う

こんな感じvar id =

string.Format("{0:D19}{1:N}",DateTime.UtcNow.Ticks, Guid.NewGuid());

var reverseId =

string.Format("{0:D19}{1:N}“,long.MaxValue-DateTime.UtcNow.Ticks, Guid.NewGuid());

結果0635317467093215594d1931d619d7041c69ececd37383ca4ae85880545697615502266d18953688dc4fbdb84da60f4d8e25c8

しかし長い・・・・・ 19+32 で 51 文字。(工夫の余地はあるけど)kyrt @takekazuomi 8

Page 9: Generating unique id numbers in Azure

擬似 ID Provider パターン

• Client で擬似的に ID を生成して、 UNIQUE 性は、永続化レイヤーで担保• retry の発生頻度にパフォー

マンスが依存• 性能が永続化レイヤーに依存• スケールのためには永続化レ

イヤーの分散が必要• SQL Database  < Storage

Table ( 分散の容易度 )

kyrt @takekazuomi 9

SQL Database (Windows Azure)

Storage Table

or

④ retry

Client 永続化レイヤー

① 擬似 ID で Insert

② 重複無しで成功

③ 重複有りで失敗

Page 10: Generating unique id numbers in Azure

Cache などの Network Service を利用

• RBD の自動連番より小さなレイテンシー (1-2ms)• ID は時系列で増える• 耐障害性に課題

• HA 構成、永続化オプションを考慮

• 工夫• 起動時の時間+ incremental

number• 障害後にかぶらないように

kyrt @takekazuomi 10

Client Cache

ID を取得

Windows Azure Cache

memcached

or

redis

or

Page 11: Generating unique id numbers in Azure

課題整理

1. latency (レイテンシー)HA のために、 Node 間通信、永続化に時間がかかる。 retry が発生すると時間がかかる

2. reliability (信頼性)採番系が一箇所なのは、 UNIQUE の担保には有利だが、障害に弱くなる。→分散すれば Ok

3. scalability (スケーラビリティ)分散が必要。 ID 生成が分散して Node 間通信が少なければ、スケーラビリティが上がる

4. data size (データサイズ)data size を大きくして冗長性を増せば、 retry の頻度は下がる

kyrt @takekazuomi 11

Page 12: Generating unique id numbers in Azure

特性の比較

kyrt @takekazuomi 12

latency reliability scalability data size

SQL 自動連番 ◯ × × ◯

GUID 等 ◯ ◯ ◯ ×

Pseudo ID and Retry △※ 1 ◯ ◯ △

Cache ◯ × △ ◯

Snowflake ◯ ◯ ◯ ◯

※ 1 Data Size を小さくすると、衝突が起きやすくなるのでレイテンシーが上がる

Page 13: Generating unique id numbers in Azure

ここまでのまとめ

• 永続化ストレージ• latency (↓)、 reliability (↑)、 scalability (↓)、 data size (↑)• scalability 改善には、パーティショニングが必要 → パーテーションを跨い

だ UNIQUE 性に制限、 data size (↓)

• On Memory• latency (↑)、 reliability (↓)、 scalability (↓)、 data size (↓)• reliability 改善

• 複数 Node で HA 構成にすれば良い。しかし、更新の度に、 Node 間で通信して合意をとると latency が悪化

• scalability 改善• シングル Node だと Node の性能上限=スケールの上限になってしまうので、複数

Node 構成にしたい。しかし、

kyrt @takekazuomi 13

↑ :良↓ :悪

Page 14: Generating unique id numbers in Azure

こんなのがあったら

•GUID のように速く•SQL の自動採番のように並んで•簡単に使える•そんなに長くない (longぐらいで入ると嬉しい)

kyrt @takekazuomi 14

Page 15: Generating unique id numbers in Azure

twitter snowflakehttps://github.com/twitter/snowflake/

kyrt @takekazuomi 15

Page 16: Generating unique id numbers in Azure

snowflake の短い説明

• snowflake は、 Twitter 社が作成した、 UNIQUE な ID 生成のネットワークサービス。いくつかの簡単な保証で高いスケーラビリティを実現

• Twitter 社が、 MySQL から Cassandra に移行するにあたって、 Cassandra には シーケンシャルな id 生成の仕組みが無かったことから作成• 参考: Twitter IDs, JSON and Snowflake

https://dev.twitter.com/docs/twitter-ids-json-and-snowflake• ソースは https://github.com/twitter/snowflake/ に公開• ライセンス、 Apache License, Version 2.0

kyrt @takekazuomi 162014/2/26

Page 17: Generating unique id numbers in Azure

基本的なアイディア

• Clock Skew (クロックスキュー)に上手く対応することで、オンメモリの計算だけで UNIQ な ID を生成する

• 永続化レイヤーの支援無しに UNIQ な ID が生成できる、 ID 生成はオンメモリなので速い( 10k ids per second per process Snowflake https://github.com/twitter/snowflake/ )というのが特徴

• GUID v1 と似ているが、半分のデータ量 64bit(long) で、おおよそ時系列で増えていく「 (Roughly) Time Ordered 」

kyrt @takekazuomi 17

Page 18: Generating unique id numbers in Azure

データ構造

• snowflake では、 64bit を上記のように分割して使います• time が時間由来の数字でミリ秒単位• machine id は、 datacenter id と、 worker id で構成されていて、

Cluster 内の Node固有の値• sequence number は、同一時間の連番

kyrt @takekazuomi 18

Page 19: Generating unique id numbers in Azure

ポイント

• 時間由来のデータが先頭 41bit なので発番の時間順に並びます• ms で 41bit だと  (2^41)*(10^-3)/60/60/24/365 で約 69年

•各インスタンスは、 クラスター内で UNIQUE な、 machine id を持ちます• machine id が重複しない限りは ID は重複しない

• 同時間内の発番では、 sequence number がインクリメントされます• ms 内の発番は、 2^12 = 4096 まで

採番情報は on memory のみで処理kyrt @takekazuomi 19

Page 21: Generating unique id numbers in Azure

time skew対策

• 最後に発番してから timestamp が戻っていないか確認 L63• 巻き戻っていればエラーで帰る(呼び出し側が再試行する)

kyrt @takekazuomi 21

Page 22: Generating unique id numbers in Azure

time 41bit の有効利用

•開始時間を採番の開始時間と合わせて bit を有効利用• TwEpoch は、 2010/11/04 。 2010/11/01 + 69年

kyrt @takekazuomi 22

Page 23: Generating unique id numbers in Azure

sequence

• 同一 timestamp なら、 _sequence をインクリメントして採番 `L72 <https://gist.github.com/takekazuomi/9571376#file-idworker-cs-L72>`_• timestamp が進んでいれば、 _sequence = 0 で採番 `L82

<https://gist.github.com/takekazuomi/9571376#file-idworker-cs-L82>`_• 同一 timestamp 内で、 _sequence がオーバーフローした場

合は、 timestamp が変わるまで待つ `L75 <https://gist.github.com/takekazuomi/9571376#file-idworker-cs-L75>`_

kyrt @takekazuomi 23

Page 24: Generating unique id numbers in Azure

起動時にWorker Id の重複を確認

構成

• snowflake の Worker は複数の Node で構成• Node の起動時に Worker Id

の重複を zookeeper を使って担保

• GUID では、 MAC Address 48bit が、 machine Id相当

kyrt @takekazuomi 24

Client

snowflake cluster

ID 要求

zookeeper cluster

Page 25: Generating unique id numbers in Azure

machine id を重複させない仕組

• snowflake では、 machine id の下位 5bit の Worker Id をzookeeper で管理しています• 起動時に Worker Id で、 Ephemeral Nodes を作成

kyrt @takekazuomi 25

/workerIdZkPath

/

/0 /1 /2 /n

worker id の ephemeral node

1. 同じ Node 名では1つのみ2. session が切れると node は消える

Page 26: Generating unique id numbers in Azure

kyrt @takekazuomi 26

Micorosoft Azure でどうするか

• Azure Blob のリースを使うとほぼ同じことができます• Worker Id の path の lease が取れば、重複なしで起動 Ok• インスタンスが生きてる間は、 Lease を更新• 参考: Cloud Design Patterns

• patterns & practices• Leader Election Pattern 、 BlobDistributedMutex

/workerIdZkPath

/

/0 /2 /n/1

Blob Lease でBlobDistributedMutex 利用

Page 27: Generating unique id numbers in Azure

まとめ

• snowflake は、 on memory で時間情報を元に高速に ID を生成する• ID の一部には machine   id が含まれていて、 node の起動

時に zookeeper を使って重複を確認する• 起動後は、 node-zookeeper 間の通信は ephemeral nodes

の keep alive のみ• 時間の巻き戻り対策がされている( time service対策)• zookeeper の ephemeral nodes 相当の機能は Azure Blob

で実装できる

kyrt @takekazuomi 27

Page 28: Generating unique id numbers in Azure

Appendix

2014/2/26 kyrt @takekazuomi 28

Page 29: Generating unique id numbers in Azure

リファレンス• Twitter IDs, JSON and Snowflake

• https://dev.twitter.com/docs/twitter-ids-json-and-snowflake

• snowflake source code• https://github.com/twitter/snowflake/

• Cloud Design Patterns / patterns & practices• Leader Election Pattern http://msdn.microsoft.com/en-us/library/dn568104.aspx• BlobDistributedMutex Code http://aka.ms/cloud-design-patterns-sample

• Apache ZooKeeper• http://zookeeper.apache.org/• http://zookeeper.apache.org/doc/r3.2.1/zookeeperProgrammers.html#Ephemeral+Nodes

• Twitter の snowflake について(お勧め)• http://www.slideshare.net/moaikids/20130901-snowflake

• 全ての情報は 2014/3/29 時点のものです。2014/2/12 kyrt @takekazuomi 29