キャッシュのデータをロードするメソッドが一括呼び出しであるユース ケースがありますが、getAll を使用してキャッシュからデータを取得することは決してありません。単一の loadAll で複数の同時 get all ブロックを実行する方法はありますか? 個々のキーが異なるキーを取得して、データ ソースへの複数の呼び出しが発生することは望ましくありません。
cache.get(key1); // missing entry, starts refresh
cache.get(key2); // separate thread, already getting reloaded due to key1 miss
LocalCache を調べた後、データ アクセサーのローカル キャッシュのようなものを使用して独自の同期を実装する必要があると思います。呼び出しが成功したら、単一の割り当てステートメントでローカル コピーを更新します。
Guava のキャッシュ ライブラリに何か不足していますか?
編集:
以下のようなものを検討しています。loadAll
ただし、終了中に古いデータを返し続ける可能性があります。すべてが でブロックされload
、最初のリクエストのみがloadAll
続行されることを望みます。
public class DataCacheLoader extends CacheLoader<String, Double>
{
private final Cache<String, Double> cache;
private ConcurrentMap<String, Double> currentData;
private final AtomicBoolean isloading;
public DataCacheLoader( final Cache<String, Double> cache )
{
this.cache = cache;
isLoading = new AtomicBoolean( false );
}
@Override
public Double load( final String key ) throws Exception
{
if ( isLoading.compareAndSet( false, true ) )
{
cache.putAll( loadAll( Lists.newArrayList( key ) ) ) );
}
return currentData.get( key );
}
@Override
public Map<String, Double> loadAll(Iterable<? extends String> keys) throws Exception
{
currentData = source.getAllData();
return currentData;
}
}