diff options
author | Paul J. Davis <paul.joseph.davis@gmail.com> | 2020-06-04 15:54:01 -0500 |
---|---|---|
committer | Paul J. Davis <paul.joseph.davis@gmail.com> | 2020-06-25 11:31:26 -0500 |
commit | 596715783514a9edaa1295757e23f03c6f87e38f (patch) | |
tree | 9aeed904f8979e9b68c5a9992a2f1f518cd15cbe | |
parent | 49949de441e1bd458aa1fab326c8b6c3c626f829 (diff) | |
download | couchdb-596715783514a9edaa1295757e23f03c6f87e38f.tar.gz |
Condition cache storage/eviction on db_version
Now that db_version is comparable we can use that for cache control.
-rw-r--r-- | src/fabric/src/fabric2_server.erl | 10 | ||||
-rw-r--r-- | src/fabric/test/fabric2_db_misc_tests.erl | 23 |
2 files changed, 19 insertions, 14 deletions
diff --git a/src/fabric/src/fabric2_server.erl b/src/fabric/src/fabric2_server.erl index b557da8c7..067cf4949 100644 --- a/src/fabric/src/fabric2_server.erl +++ b/src/fabric/src/fabric2_server.erl @@ -94,12 +94,12 @@ store(#{name := DbName} = Db0) when is_binary(DbName) -> maybe_update(#{name := DbName} = Db0) when is_binary(DbName) -> #{ uuid := UUID, - md_version := MDVer + db_version := DBVer } = Db0, Db1 = sanitize(Db0), Head = {DbName, UUID, '$1', '_'}, - Guard = {'=<', '$1', MDVer}, - Body = {DbName, UUID, MDVer, {const, Db1}}, + Guard = {'=<', '$1', DBVer}, + Body = {DbName, UUID, DBVer, {const, Db1}}, try 1 =:= ets:select_replace(?MODULE, [{Head, [Guard], [{Body}]}]) catch @@ -116,10 +116,10 @@ remove(DbName) when is_binary(DbName) -> maybe_remove(#{name := DbName} = Db) when is_binary(DbName) -> #{ uuid := UUID, - md_version := MDVer + db_version := DBVer } = Db, Head = {DbName, UUID, '$1', '_'}, - Guard = {'=<', '$1', MDVer}, + Guard = {'=<', '$1', DBVer}, 1 =:= ets:select_delete(?MODULE, [{Head, [Guard], [true]}]). diff --git a/src/fabric/test/fabric2_db_misc_tests.erl b/src/fabric/test/fabric2_db_misc_tests.erl index a8a267763..cad91a530 100644 --- a/src/fabric/test/fabric2_db_misc_tests.erl +++ b/src/fabric/test/fabric2_db_misc_tests.erl @@ -340,13 +340,18 @@ metadata_bump({DbName, _, _}) -> % Perform a random operation which calls ensure_current {ok, _} = fabric2_db:get_db_info(Db), + % After previous operation, the cache should have been cleared + ?assertMatch(undefined, fabric2_server:fetch(DbName, undefined)), + + % Call open again and check that we have the latest db version + {ok, Db2} = fabric2_db:open(DbName, [{user_ctx, ?ADMIN_USER}]), + % Check that db handle in the cache got the new metadata version % and that check_current_ts was updated - CachedDb = fabric2_server:fetch(DbName, undefined), ?assertMatch(#{ md_version := NewMDVersion, check_current_ts := Ts - } when Ts >= TsBeforeEnsureCurrent, CachedDb). + } when Ts >= TsBeforeEnsureCurrent, Db2). db_version_bump({DbName, _, _}) -> @@ -358,12 +363,12 @@ db_version_bump({DbName, _, _}) -> % regular db open + update security doc or something like that to make sure % we don't touch the local cache #{db_prefix := DbPrefix} = Db, - DbVersionKey = erlfdb_tuple:pack({?DB_VERSION}, DbPrefix), {ok, Fdb} = application:get_env(fabric, db), - NewDbVersion = fabric2_util:uuid(), erlfdb:transactional(Fdb, fun(Tx) -> - erlfdb:set(Tx, DbVersionKey, NewDbVersion), - erlfdb:set_versionstamped_value(Tx, ?METADATA_VERSION_KEY, <<0:112>>) + DbVersionKey = erlfdb_tuple:pack({?DB_VERSION}, DbPrefix), + DbVersion = fabric2_fdb:new_versionstamp(Tx), + DbVersionVal = erlfdb_tuple:pack_vs({DbVersion}), + ok = erlfdb:set_versionstamped_value(Tx, DbVersionKey, DbVersionVal) end), % Perform a random operation which calls ensure_current @@ -375,15 +380,15 @@ db_version_bump({DbName, _, _}) -> % Call open again and check that we have the latest db version {ok, Db2} = fabric2_db:open(DbName, [{user_ctx, ?ADMIN_USER}]), - % Check that db handle in the cache got the new metadata version - ?assertMatch(#{db_version := NewDbVersion}, Db2). + % Check that db handle in the cache got a newer version + ?assert(maps:get(db_version, Db) < maps:get(db_version, Db2)). db_cache_doesnt_evict_newer_handles({DbName, _, _}) -> {ok, Db} = fabric2_db:open(DbName, [{user_ctx, ?ADMIN_USER}]), CachedDb = fabric2_server:fetch(DbName, undefined), - StaleDb = Db#{md_version := <<0>>}, + StaleDb = Db#{db_version := <<0>>}, ok = fabric2_server:store(StaleDb), ?assertEqual(CachedDb, fabric2_server:fetch(DbName, undefined)), |