Memcachedとタグ。 Kohanaフレームワークの実装

すべてにご挨拶。



かなり長い間、私たちはCohanでプロジェクトを開発しており、効率的なデータキャッシングの必要性が生じました。 現時点でパフォーマンスの問題が非常に深刻であることではありませんが、事前に準備し、訪問者の波の夜にキャッシュシステムを作成したくないです。 はい、そして出席者は絶えず増加しており、ある時点で通常の1日と比較して最大3倍の急増があります。



実際、キャッシュシステムの選択に特別な質問はありませんでした-有名なmemcachedがすぐに思い浮かびます。



少なくともmemcachedを少し見たなら、おおむね2つの操作しかサポートしていないことに注意してください:値の取得、値の書き込み。 特定の属性またはパターンに従ってすべてのキーを拡張する方法はありません。 これは、できる限り簡単に、したがってできるだけ速くするために、意図的に行われました。



そのため、ブログエントリのデータをpost_キーの下にキャッシュする状況を想像してください。 ある時点で、キャッシュを完全にクリアせずに、投稿を含むすべてのレコードをリセットする必要があります(他のデータはそこに保存できますが、その値はまだ関連しています)。 状況は絶望的です。 投稿キーのリストはわかりません;それらを取得する方法はありません;パターンによってキーをリセットすることも不可能です。 どうする?





memcachedがレコードにタグ付けシステムを実装する方法についての理論的な説明には触れません。このテーマに関する記事は多数あります。 たとえば、Andrei Smirnovのブログ: www.smira.ru/2008/10/29/web-caching-memcached-5 私のサイトでキャッシュシステムを作成するときに使用したのは、この方法でした。



私たちが話していることを理解できるように、キャッシュのデータを次の形式の配列に保存します。



array (

'tags' => array (

'tag1' => <......>,

'tag2' => <......>

),

'data' => <.... ...>,

);



* This source code was highlighted with Source Code Highlighter .






また、各ラベルはキーtag_ <タグ名>とともにmemcachedに保存されます。 値に特定の数を格納します。 この場合、信頼性のために、ミリ秒の精度でタグを作成/更新する時間を保存します。

キャッシュに新しい要素を追加するとき、この数値を読み取り、上記の配列に格納します。 キー値を読み取るとき、ラベル値がキー値に保存された値に対して変化しているかどうかを確認します。 それらが異なる場合-キーがリセットされると考えます。 したがって、ラベルによるキーのリセットは、ラベルキ​​ーの値を変更することによって行われます。



例:

// post_1:

array (

'tags' => array (

'posts' => 1

),

'data' => 'post content'

)

// tag_posts:

array (

'data' => 1

)




* This source code was highlighted with Source Code Highlighter .








post_1キーを読み取る場合、アルゴリズムはtag_posts値も読み取り、post_1キーの['tags'] ['posts']に格納されている値と比較します。 それらが等しい場合-すべてが正常で、post_1は有効です。 値が異なる場合、post_1は無効であると考え、NULLを返します。 したがって、「ラベル」に保存されている値を変更するだけで、キーを無効としてマークできます。



私が説明した場合、それはあまり明確ではありません-それは問題ではありません。 上記で、私が使用する技術がより詳細に説明されている記事へのリンクを提供しました。



Kohanaのmemcachedドライバーは、デフォルトではmemcachedタグをサポートしていません。 より正確には、数バージョン前に実装されましたが、最終的に著者がラベルを完全に放棄することを決定するように機能しました。 つまり、memcachedに1つのキーが作成され、<key name> => <list of labels>という形式の配列が格納されました。 多かれ少なかれ大規模なサイトで、このアレイがどのサイズであったか想像できます。



ドライバーバージョンは、 github.com / Kolger / kohana-memcacheimpからダウンロードできます。

これは通常のcohanaモジュールです。 コードをダウンロードし、プロジェクトのapplication / modulesフォルダーにmemcachedimpディレクトリを作成します。 config.phpでモジュールを接続することを忘れないでください:



$config[ 'modules' ] = array

(

//.....

MODPATH. 'memcacheimp' , // Memcacheimp driver

//.....

);

// , cache.php:



$config[ 'default' ] = array

(

'driver' => 'memcacheimp' ,

'lifetime' => 3600,

'requests' => 1000,

);




* This source code was highlighted with Source Code Highlighter .








これで、Cacheクラスは新しいドライバーで動作します。

使用法は、ドキュメントに記載されている方法と違いはありません: docs.kohanaphp.com/libraries/cache

$cache = new Cache();

// :

$cache-> set ( 'post_1' , 'post content' , array( 'posts' ));

$cache-> set ( 'post_2' , 'post content' , array( 'posts' ));

//

$ value = $cache-> get ( 'post_1' );

// $value == post content

// "" . , , tag_posts, post_1 post_2 -

$cache->delete_tag( 'posts' );

// post_1

$ value = $cache-> get ( 'post_1' );

// $value === NULL, . post_1 , , .. .



* This source code was highlighted with Source Code Highlighter .








クラスを少し変更すると、Cohanだけでなく、他のPHPプロジェクトでも使用できると思います。 クラスを改善または最適化する方法についてアイデアがある場合は、 github.com / Kolger / kohana - memcacheimp githubにようこそ:)



改善すべき点:

-memcachedへのリクエストを生成しないように、getMultiを使用してgetメソッドでタグを取得します。

-ラベルが変更された場合のキーの削除。



All Articles