キャッシュ操作
リードキャッシュ
キャッシュは(キャッシュヒットを)打つ2例に分け、ミス(キャッシュミス)することができます読みます
キャッシュヒット
- まず、キャッシュからデータを取得
- キャッシュ内のデータが返されます
キャッシュミス
- まず、キャッシュからデータを取得
- この時、キャッシュミスは、データベースからデータを取得します
- キャッシュにデータを書き込みます
- 戻り値のデータ
でキャッシュ処理を読んで、そこにデータをキャッシュ?意思決定であり、キャッシュ内のデータがある場合、キャッシュヒットがそれがない場合は、キャッシュミス:
ライトキャッシュ
書き込みキャッシュを分割することができます更新缓存
と删除缓存
。
アップデートキャッシュ
二つの条件のキャッシュを更新する必要があります。
- 更新単純なデータ型(例えば、文字列)
- 更新複合データ型(例えば、ハッシュ)
以下のため简单数据类型
のデータ型である場合は、直接、キャッシュを更新するアップデートは、追加のオーバーヘッドを追加します。
- キャッシュからデータを取得
- コラムトランスにシーケンスデータオブジェクト
- 更新オブジェクトデータ
- キャッシュに更新されたデータのシーケンス
複雑なデータ・キャッシュを更新すると、4つのステップの最小値を必要とし、キャッシュには、データを書き込むたびに更新する必要なので、あまりシナリオをキャッシュ読むことを、データは7-8回の読み取りキャッシュを更新することができる唯一のあたりに加えて、それは支払っていないと思います一度起こります更新前のライトキャッシュデータが必要でないことは明らかであるとき、キャッシュデータ更新キャッシュに、キャッシュデータを算出する際には計算する必要がありますへの読み取りキャッシュ(キャッシュ・ミスを)延期、更新をキャッシュすることができます。
削除キャッシュ
呼ばれるキャッシュの削除キャッシュのアウト、削除キャッシュ操作は、それから、非常に単純な、直接キャッシュの削除キャッシュライブラリです。
キャッシュの動作シーケンス
キャッシュは、一般的に、データベースと組み合わせて使用するデータベースからデータを取得し、キャッシュを更新しています。なぜ我々は、キャッシュそれのための動作を議論する必要がありますか?操作の異なる順序が、いくつかのケースでは異なる結果を生成するので、操作の共通の配列を分けることができます。
- 最初のデータベース、およびキャッシュ
- まずキャッシュ、データベース
データベースを通過するどのような順序は、2段階の操作をキャッシュする、2つの操作がデータの不整合が生じる場合がアトミック操作ではありません。ここでは異なるため、それぞれ、一貫性のないデータ、並行性の問題を運ば説明します。
最初のデータベースキャッシュの後
図としてデータベースにデータを書き込み、その後、キャッシュを更新または削除するために行きます。故障が最初のステップは異常であることである場合、2つのステップ1と2は、失敗する可能性があり、今回は失敗した書き込みキャッシュ操作データベースとして理解されるべきではないので、ビジネス情報の処理によってスロービジネスの発信者キャッチ例外。
最初のステップは、(成功の書き込みデータベース)に成功し、再度の場合はキャッシュ操作が失敗した場合、2つのケースがあります。
- データベースのロールバック:ビジネスはデータベースキャッシュとの整合性を確保するための強い必要性がある場合は、呼び出し元にビジネス例外をスローすることができます。
- 対処するためではない:
数据库回滚
逆に、ビジネスリーチにキャッシュの有効期限の前に受け入れることができ、キャッシュとデータベースは、データの不整合を可能にします。
例えば、それが鍵となり、キャッシュデータの文字列データ型を想定name
し、データベースに今あると値がキャッシュされますarch-digest
。
String name = "arch-digest";
复制代码
現在までname
に更新された値juejin
に基づいて、最初のデータベースキャッシュ順:
//将name的值更新为juejin
public void update(String name){
db.insert(...); //更新数据库
cache.delete(name); //更新缓存
}
复制代码
通常の状況下ではdb.insert(...)
とcache.delete(name)
首尾異議を実行していません。それは他のいくつかの理由がされている場合はcache.delete(name)
失敗し、データベースが値を更新した値juejin
、およびキャッシュ内のデータやarch-digest
ので、次の時間は、読み取りキャッシュ値が取得しますarch-digest
。
public String getNameFromCache(String name){
String value = cache.get(name); //从缓存中获取数据
...
return value;
}
复制代码
場合は、読み取りキャッシュgetNameFromCache
方法、場合name
キャッシュの有効期限が切れていないと、それは常になりますarch-digest
ので、状況がデータを見るために一貫性のないユーザーになります。
最初のキャッシュ・データベースの後
最初のキャッシュ・データベースの後、それが中に来る前に最初のデータベースキャッシュ後の一貫性のないデータにつながる可能性以外にほとんどあり、それはまた、並行性の問題を持っています。
上記のデータが更新されるようになりましたとおり、それがある場合、更新数据库
障害が発生したときに何が?ここではキャッシュの操作に応じて2例は以下のとおりです。
- 更新キャッシュ:最新データへのキャッシュは、データベースは、次の読み取り古いデータである場合に、新しいデータ(データの矛盾)キャッシュを取得します、キャッシュデータを更新します。
- キャッシュを削除:あなたは(一貫性のあるデータ)を読んだときに、データベースから、キャッシュ内の次のフェッチされたデータを削除します。
更新缓存
そして、删除缓存
上記の動作は、説明するために行うことがあまりありませんが導入されています。明らかに更新缓存
し、删除缓存
この場合、最初の删除缓存
ない一貫性のないデータの問題、より適切であるが、使用中删除缓存
の時間べきでも注意を払っ原因並行性の問題:
- A成功したキャッシュされたスレッドを削除します
- スレッドBは、キャッシュミスを読み込み
- スレッドBは、データベースからデータを取得します
- スレッドBは、データベース内のキャッシュデータを書き込みます
- データベースに正常に書き込まれたスレッド
並行性の高いシナリオでは、一貫性のないデータ・キャッシュとデータベースの場合は、まだ起こります。そのデータベースとキャッシュデータの一貫性は何ソリューションを解決するには?
データの一貫性の最適化
ここではそれがある优化方案
分散環境での取引が問題となっているので、今は良い解決策がない、ああソリューションではありません。唯一の最適なビジネス最適化プログラム、業務内の一貫性のないデータの可能性を見つけるか、許容範囲にまで遅延させます。
いくつかの一般的な最適化方式には、があります。
- 扱っていません
- デュアルディレイを削除しました
- Binglogを購読
単純なものから複雑なものへの3つの方式は、サービスに応じて、最も適切な最適化方式を選択することができます。
扱っていません
扱っていない最も簡単な方法は、許可されたトラフィックの場合に扱われていないキャッシュ内のデータと矛盾しているデータベースです。少し不適切な、しかし非常に香りが、!
デュアルディレイを削除しました
遅延は、削除デュアル最適化するために使用することができる最初のキャッシュデータベースの後に並行性の問題を:
- A成功したキャッシュされたスレッドを削除します
- スレッドBは、キャッシュミスを読み込み
- スレッドBは、データベースからデータを取得します
- スレッドBは、データベース内のキャッシュデータを書き込みます
- データベースに正常に書き込まれたスレッド
- 睡眠1秒にして、キャッシュを削除スレッド
このプログラムは、ステップ6を追加し、他のスレッドがデータベースからデータを取得し、データが再度読み込まれるキャッシュを更新するために、キャッシュミスにつながるように、キャッシュされたデータを削除し、その後書き込みスレッド睡眠1秒の完了後にデータベースを作成し、そして。
どのくらいの期間、特定の睡眠を決定する方法この1秒?
このような状況のために、自分のプロジェクトのデータのビジネスロジックを読むために自分の時間がかかる上評価されるべきです。そして、睡眠時の書き込みデータは、ビジネス・ロジックの読み取りデータの基礎を消費し、あなたは数百ミリ秒を追加することができます。そうすることの目的は、書き込み要求がダーティデータによって引き起こされるキャッシュされた読み取り要求を削除することができます読み取り要求の終了ことを確認することです。
行うにはどのようにスループット減らすための戦略うち、この同期位相では?
第二には、非同期として除去します。自分スレッド、削除非同期。このように、書かれた要求は、一定期間後に眠れないだろうし、その後返します。スループット向上させるために、これを行うには。
BINLOGを購読
BINLOGサブスクリプションは、MySQLに新しい書き込み、更新、削除などを作成した後ので、あなたはRedisの、Redisのにプッシュビンログ関連ニュースを配置し、更新Redisの上のbinlogに応じて記録することができます使用。
MySQLのデータの整合性スタンバイバイナリログすることによって達成されるので、実際には、このメカニズムは、マスター・スレーブのMySQLバックアップ機構に非常に類似しています。
運河は、バックアップ要求スレーブmysqlデータベースの模倣である一方、データ更新のRedisは同じ効果に達したので、ここで運河(アリ、オープンソースのフレームワーク)を組み合わせることができ、あなたは、フレームを介してMySQLのバイナリログを購読することができます。
キャッシュを実装するためにカフカ、RabbitMQのプッシュの更新など:もちろん、ここでのメッセージのプッシュツール、あなたは他のサードパーティ製を使用することができます。
アーキテクチャの重い分野毎日のフロントラインのアプリケーションアーキテクチャ(高可用性、高性能、高い安定性)、ビッグデータ、機械学習、Javaのアーキテクチャの様々な人気のある分野に関与良いテキスト、インターネット企業。