7
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?

More than 5 years have passed since last update.

memcached-cli で Memcached の Slabs Reassign と LRU Crawler を試してみる

Last updated at Posted at 2016-03-30

この記事では、Gotanda.pm #8 でデモをする予定だった内容の手順と結果を紹介します。
勉強会では、発表時間が足りずデモが実施できませんでした。

何かの参考になれば幸いです。

はじめに

memcached-cli は筆者が開発した Perl 製の Memcached クライアントです。
テキストプロトコルでできる操作はすべて実行でき、TELNET よりもユーザーにやさしいインタフェースとなっております。
依存も少なく、Perl 5.8 以上であれば動作するように作ったつもりなので、Memcached をお使いの方はぜひ使ってみてください。

Memcached Slabs Reassign と LRU Crawler について

デモの手順に入る前に、今回触れる Memcached の機能について、かんたんに説明しておきます。

そもそもの話ですが、Memcached はデータをサイズに応じて異なる Slab Class に配置します。
各 Slab Class には 1MB のページ単位でメモリが割当てられます。一度ページが確保されると、通常はたとえ当該 Class のデータ量が減ったとしても、ページが解放されることはありません。1
Slabs Reassign はこの異なる Slab Class 間のページ割当てを変更できる機能です。

次に LRU Crawler ですが、これは Expire したデータをなめてメモリ領域を解放してくれるものです。
こちらも、Expire したデータを get したり、同じ Slab Class にデータを set するなりしなければ、通常は解放されません。

デモ手順と結果

環境は MacOSX で、Homebrew で Memcached 1.4.22 をインストールしています。

1. Memcached をメモリ少なめで起動

あふれるところが見たいので、Memcached の -m オプションを4MBとすごくメモリ少なめで起動します。
同時に、-o オプションで slab_reassignlru_crawler を有効にしておきます。
また、後で stats detail dump の結果を見たいので、 -D ":" でネームスペースごとの統計情報収集機能を有効にしておきます。

% memcached -m 4 -o slab_reassign,lru_crawler -D ":"

2. 2種類のデータサイズでデータを生成し、あふれさせる

まずは memcached-cli で接続します。
さっきの memcached の起動コマンドではフォアグラウンドで立ち上がるので、別窓で操作して下さい。

% memcached-cli localhost
Type '\h' or 'help' to show help.

memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM

サーバは起動したばかりなので、 display コマンドの結果は空です。
randomset コマンドでデータを生成して Memcached に set していきます。

// 500B のデータを "sample1" ネームスペース下に5000個生成
memcached@localhost:11211> randomset 5000 500 500 sample1
Random Generate. [....................]
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B         7s       3    5000     yes        0        0    0

// 1kB のデータを "sample2" ネームスペース下に1000個生成
memcached@localhost:11211> randomset 1000 1000 1000 sample2
Random Generate. [....................]
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B        29s       3    5000     yes        0        0    0
 12     1.2K         8s       1     885     yes      115        1    0

// 1kB のデータを "sample3" ネームスペース下に1000個生成
memcached@localhost:11211> randomset 1000 1000 1000 sample3
Random Generate. [....................]
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B        35s       3    5000     yes        0        0    0
 12     1.2K         2s       1     885     yes     1115        1    0

Slab Class #9 に3ページのメモリが確保されたので、 #12 には1ページしか確保できません。
#12 には 885 個以上データを set することができず、あふれて eviction してしまいました。

3. データを全て無効化し、LRU Crawler で掃除する

flush_all コマンドで全てのデータを期限切れにします。
ただし、これだけでは確保されたページが解放されるわけではないので、Slab Class #12 には 885 個以上データを set することができません。

memcached@localhost:11211> flush_all
OK
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B       466s       3    5000     yes        0        0    0
 12     1.2K       433s       1     885     yes     1115        1    0
memcached@localhost:11211> randomset 1000 1000 1000 sample3
Random Generate. [....................]
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B       486s       3    5000     yes        0        0    0
 12     1.2K         2s       1     885     yes     1230        1    0

そこで、Slabs Reassign の出番です。
データは無効化したので、このままページ割当てを #9 => #12 に変えて行っても特に問題は無いのですが、今回はその前に LRU Crawler で #9 のデータをクリアしておきます。

// LRU Crawler を Slab Class #9 に対して手動実行する
memcached@localhost:11211> call lru_crawler crawl 9
OK
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B         0s       3       0     yes        0        0    0
 12     1.2K        18s       1     885     yes     1230        1    0

// Slabs Reassign でページ割当てを #9 => #12 に移していく
memcached@localhost:11211> call slabs reassign 9 12
OK
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B         0s       2       0     yes        0        0    0
 12     1.2K        38s       2     885     yes     1230        1    0
memcached@localhost:11211> call slabs reassign 9 12
OK
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B         0s       1       0     yes        0        0    0
 12     1.2K        42s       3     885     yes     1230        1    0

以上、Pages の数が #9 => #12 に移動しているのがおわかりいただけるでしょうか。

これで、 #12 には 3MB 分データを set できるはずです。
やってみましょう。

// ネームスペースを変えながら、1000個ずつ計3000個のデータ set を試みる
memcached@localhost:11211> randomset 1000 1000 1000 sample3
Random Generate. [....................]
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B         0s       1       0     yes        0        0    0
 12     1.2K         4s       3    1000     yes     1230        1    0
memcached@localhost:11211> randomset 1000 1000 1000 sample4
Random Generate. [....................]
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B         0s       1       0     yes        0        0    0
 12     1.2K        17s       3    2000     yes     1230        1    0
memcached@localhost:11211> randomset 1000 1000 1000 sample5
Random Generate. [....................]
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
  9     600B         0s       1       0     yes        0        0    0
 12     1.2K        21s       3    2655     yes     1575       20    0

最後は少々あふれてしまいましたが、1ページしかなかった時と比べて、3倍のデータを格納することができました。

ネームスペースごとの統計を見てみる

今回のデモの主要なところは以上ですが、ついでに memcached/memcached-cli の機能をもう少し紹介していきます。

detaildump コマンドでは、ネームスペースごとの統計情報を見ることができます。

memcached@localhost:11211> detaildump
PREFIX sample4 get 0 hit 0 set 1000 del 0
PREFIX sample3 get 0 hit 0 set 3000 del 0
PREFIX sample5 get 0 hit 0 set 1000 del 0
PREFIX sample2 get 0 hit 0 set 1000 del 0
PREFIX sample1 get 0 hit 0 set 5000 del 0

もし、Memcached 起動時に統計情報の収集を有効にしていなかった場合、memcached-cli の detail on コマンドで有効化できます。
逆に、detail off コマンドで無効化もできます。

データを dump/restore してみる

memcached-cli では今のところ(〜v0.94)、dump をファイル保存する際は、バッチモードで動かす必要があります。
ので、一旦 \q で対話モードを終えて下さい。

memcached@localhost:11211> \q
// シェル上で memcached-cli の dump_all コマンドを実行し、出力をファイルにリダイレクト
% memcached-cli localhost dump_all > dump-memd.txt
Dumping memcache contents
  Number of buckets: 1
  Number of items  : 2655
Dumping bucket 12 - 2655 total items
% ll -h dump-memd.txt
-rw-r--r--  1 key-amb  1522739515   2.6M  3 31 01:19 dump-memd.txt
% wc -l dump-memd.txt
    5310 dump-memd.txt

dump が取れました。
では、別窓で動かしている Memcached を再起動します。

% memcached -m 4 -o slab_reassign,lru_crawler -D ":"
^CSignal handled: Interrupt: 2.
% memcached -m 4 -o slab_reassign,lru_crawler -D ":"

// 別窓で memcached-cli を立ち上げる
% memcached-cli localhost
Type '\h' or 'help' to show help.

memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM

再起動したので、データが空っぽになっています。
これに、先ほど取った dump データをリストアします。

memcached@localhost:11211> restore_dump dump-memd.txt
    ...loaded 200 lines
    ...loaded 400 lines
    ...loaded 600 lines
    ...loaded 800 lines
               :
    ...loaded 5000 lines
    ...loaded 5200 lines
Complete.
memcached@localhost:11211> display
  #  Item_Size  Max_age   Pages   Count   Full?  Evicted Evict_Time OOM
 12     1.2K         5s       3    2655     yes        0        0    0

無事にデータをリストアすることができました。

終わりに

以上、memcached-cliを用いて Memcached の Slabs Reassign と LRU Crawler の機能を体験してみました。

Memcached をお使いの方は、ぜひ memcached-cli をお試し下さい。

何かありましたら GitHub 上で Issue や Pull Request をお待ちしています。

それでは、Enjoy!

参考

脚注

  1. 余ったページを自動で開放する Slabs Automove というオプションもあります。

7
5
1

Register as a new user and use Qiita more conveniently

  1. You get articles that match your needs
  2. You can efficiently read back useful information
  3. You can use dark theme
What you can do with signing up
7
5

Delete article

Deleted articles cannot be recovered.

Draft of this article would be also deleted.

Are you sure you want to delete this article?