record-cache 0.1.4 → 0.1.5
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- checksums.yaml +8 -8
- data/lib/record_cache/datastore/active_record_40.rb +1 -0
- data/lib/record_cache/strategy/full_table_cache.rb +1 -1
- data/lib/record_cache/strategy/index_cache.rb +1 -1
- data/lib/record_cache/strategy/unique_index_cache.rb +1 -1
- data/lib/record_cache/strategy/util.rb +1 -1
- data/lib/record_cache/test/resettable_version_store.rb +2 -2
- data/lib/record_cache/version.rb +1 -1
- data/lib/record_cache/version_store.rb +13 -3
- data/spec/lib/version_store_spec.rb +39 -1
- metadata +3 -3
checksums.yaml
CHANGED
@@ -1,15 +1,15 @@
|
|
1
1
|
---
|
2
2
|
!binary "U0hBMQ==":
|
3
3
|
metadata.gz: !binary |-
|
4
|
-
|
4
|
+
MDI2NWVjM2RkZjhjMmFkMmU2M2VhMTFlN2VmZTgwZDM5YmJhYWRjMA==
|
5
5
|
data.tar.gz: !binary |-
|
6
|
-
|
6
|
+
ZmI3NDhhNzE0ZTcwZmZjNzZiNDhhMzg1Mjk2MDlkMjc1Njc0Zjg1NA==
|
7
7
|
SHA512:
|
8
8
|
metadata.gz: !binary |-
|
9
|
-
|
10
|
-
|
11
|
-
|
9
|
+
OTdiNmIzNWMwMTk5ODQ3ZDUyNWJiYTc5NGM2NDI0OWI0YzdkYTZkM2UzYmNk
|
10
|
+
ZjIxYTBkNzBlYWI1M2EwYTU2YTlkYTA0ZTNjZTEwMmY3YmQ0YmFkMWU4MjMz
|
11
|
+
MDUyYjE1OWYxNDM3YzQ3ZGRlZjZhMjBkODUzZjNmNzUyNzRmNjA=
|
12
12
|
data.tar.gz: !binary |-
|
13
|
-
|
14
|
-
|
15
|
-
|
13
|
+
MGRkZjIwZGVhNTgzNjU0NmFlMWQyOGRiMzZkZTY5MmU4MDlhM2VlZWYwNTQ3
|
14
|
+
NmY3NzliYjM1ZWE1NjI1Yzg1YTc2ZjVkNzY5OGE2MjFlZmNiODMxNDBiNWVk
|
15
|
+
YjYxYTU2YWFlZDQ3MjhlMGFjZTdlYjM5NjBkY2YyNjEzMjY1ZGE=
|
@@ -399,6 +399,7 @@ module RecordCache
|
|
399
399
|
|
400
400
|
module InstanceMethods
|
401
401
|
def delete_records_with_record_cache(records, method)
|
402
|
+
records = load_target if records == :all
|
402
403
|
# invalidate :id cache for all records
|
403
404
|
records.each{ |record| record.class.record_cache.invalidate(record.id) if record.class.record_cache? unless record.new_record? }
|
404
405
|
# invalidate the referenced class for the attribute/value pair on the index cache
|
@@ -36,7 +36,7 @@ module RecordCache
|
|
36
36
|
# no records found?
|
37
37
|
unless records
|
38
38
|
# renew the version in case the version was not known
|
39
|
-
current_version ||= version_store.
|
39
|
+
current_version ||= version_store.renew_for_read(key, version_opts)
|
40
40
|
# retrieve all records from the DB
|
41
41
|
records = from_db(key, current_version)
|
42
42
|
end
|
@@ -54,7 +54,7 @@ module RecordCache
|
|
54
54
|
# retrieve the current version of the ids list
|
55
55
|
current_version = version_store.current(key)
|
56
56
|
# create the versioned key, renew the version in case it was missing in the version store
|
57
|
-
versioned_key = versioned_key(key, current_version || version_store.
|
57
|
+
versioned_key = versioned_key(key, current_version || version_store.renew_for_read(key, version_opts))
|
58
58
|
# retrieve the ids from the local cache based on the current version from the version store
|
59
59
|
ids = current_version ? fetch_ids_from_cache(versioned_key) : nil
|
60
60
|
# logging (only in debug mode!) and statistics
|
@@ -104,7 +104,7 @@ module RecordCache
|
|
104
104
|
unless versioned_key
|
105
105
|
# renew the key in the version store in case it was missing
|
106
106
|
key = id_to_key_map[record.send(@attribute)]
|
107
|
-
versioned_key = versioned_key(key, version_store.
|
107
|
+
versioned_key = versioned_key(key, version_store.renew_for_read(key, version_opts))
|
108
108
|
end
|
109
109
|
# store the record based on the versioned key
|
110
110
|
record_store.write(versioned_key, Util.serialize(record))
|
@@ -17,7 +17,7 @@ module RecordCache
|
|
17
17
|
# deserialize a cached record
|
18
18
|
def deserialize(serialized)
|
19
19
|
record = serialized[CLASS_KEY].constantize.allocate
|
20
|
-
attributes = serialized[ATTRIBUTES_KEY]
|
20
|
+
attributes = serialized[ATTRIBUTES_KEY].clone
|
21
21
|
record.class.serialized_attributes.keys.each do |attribute|
|
22
22
|
if attributes[attribute].respond_to?(:unserialize)
|
23
23
|
if attributes[attribute].method(:unserialize).arity > 0
|
@@ -20,9 +20,9 @@ module RecordCache
|
|
20
20
|
|
21
21
|
module InstanceMethods
|
22
22
|
|
23
|
-
def renew_with_reset(key, opts = {})
|
23
|
+
def renew_with_reset(key, write = true, opts = {})
|
24
24
|
updated_version_keys << key
|
25
|
-
renew_without_reset(key, opts)
|
25
|
+
renew_without_reset(key, write, opts)
|
26
26
|
end
|
27
27
|
|
28
28
|
def reset!
|
data/lib/record_cache/version.rb
CHANGED
@@ -9,6 +9,10 @@ module RecordCache
|
|
9
9
|
@store = store
|
10
10
|
end
|
11
11
|
|
12
|
+
def on_write_failure(&blk)
|
13
|
+
@on_write_failure = blk
|
14
|
+
end
|
15
|
+
|
12
16
|
# Retrieve the current versions for the given key
|
13
17
|
# @return nil in case the key is not known in the version store
|
14
18
|
def current(key)
|
@@ -24,11 +28,16 @@ module RecordCache
|
|
24
28
|
Hash[id_key_map.map{ |id, key| [id, current_versions[key]] }]
|
25
29
|
end
|
26
30
|
|
31
|
+
def renew_for_read(key, options = {})
|
32
|
+
renew(key, false, options)
|
33
|
+
end
|
34
|
+
|
27
35
|
# Call this method to reset the key to a new (unique) version
|
28
|
-
def renew(key, options = {})
|
36
|
+
def renew(key, write = true, options = {})
|
29
37
|
new_version = (Time.current.to_f * 10000).to_i
|
30
38
|
seconds = options[:ttl] ? options[:ttl] + (rand(options[:ttl] / 2) * [1, -1].sample) : nil
|
31
|
-
@store.write(key, new_version, {:expires_in => seconds})
|
39
|
+
written = @store.write(key, new_version, {:expires_in => seconds})
|
40
|
+
@on_write_failure.call(key) if !written && write && @on_write_failure
|
32
41
|
RecordCache::Base.logger.debug{ "Version Store: renew #{key}: nil => #{new_version}" }
|
33
42
|
new_version
|
34
43
|
end
|
@@ -47,12 +56,13 @@ module RecordCache
|
|
47
56
|
# @deprecated: use renew instead
|
48
57
|
def increment(key)
|
49
58
|
RecordCache::Base.logger.debug{ "increment is deprecated, use renew instead. Called from: #{caller[0]}" }
|
50
|
-
renew(key)
|
59
|
+
renew(key, true)
|
51
60
|
end
|
52
61
|
|
53
62
|
# Delete key from the version store (records cached in the Record Store belonging to this key will become unreachable)
|
54
63
|
def delete(key)
|
55
64
|
deleted = @store.delete(key)
|
65
|
+
@on_write_failure.call(key) if !deleted && @on_write_failure
|
56
66
|
RecordCache::Base.logger.debug{ "Version Store: deleted #{key}" }
|
57
67
|
deleted
|
58
68
|
end
|
@@ -49,7 +49,30 @@ RSpec.describe RecordCache::VersionStore do
|
|
49
49
|
@version_store.renew("unknown_key")
|
50
50
|
expect(@version_store.current("unknown_key")).to_not be_nil
|
51
51
|
end
|
52
|
-
|
52
|
+
|
53
|
+
it "should call on_write_failure hook when renew fails" do
|
54
|
+
allow(@version_store.store).to receive(:write) { false }
|
55
|
+
failed = nil
|
56
|
+
@version_store.on_write_failure{ |key| failed = key }
|
57
|
+
@version_store.renew("key1")
|
58
|
+
expect(failed).to eq("key1")
|
59
|
+
end
|
60
|
+
|
61
|
+
it "should not call on_write_failure hook when renew_for_read fails" do
|
62
|
+
allow(@version_store.store).to receive(:write) { false }
|
63
|
+
failed = "nothing failed"
|
64
|
+
@version_store.on_write_failure{ |key| failed = key }
|
65
|
+
@version_store.renew_for_read("key1")
|
66
|
+
expect(failed).to eq("nothing failed")
|
67
|
+
end
|
68
|
+
|
69
|
+
it "should not call on_write_failure hook when renew succeeds" do
|
70
|
+
failed = "nothing failed"
|
71
|
+
@version_store.on_write_failure{ |key| failed = key }
|
72
|
+
@version_store.renew("key1")
|
73
|
+
expect(failed).to eq("nothing failed")
|
74
|
+
end
|
75
|
+
|
53
76
|
it "should write to the debug log" do
|
54
77
|
expect{ @version_store.renew("key1") }.to log(:debug, /Version Store: renew key1: nil => \d+/)
|
55
78
|
end
|
@@ -77,6 +100,21 @@ RSpec.describe RecordCache::VersionStore do
|
|
77
100
|
expect(@version_store.current("unknown_key")).to be_nil
|
78
101
|
end
|
79
102
|
|
103
|
+
it "should call on_write_failure hook when delete fails" do
|
104
|
+
allow(@version_store.store).to receive(:delete) { false }
|
105
|
+
failed = nil
|
106
|
+
@version_store.on_write_failure{ |key| failed = key }
|
107
|
+
@version_store.delete("key1")
|
108
|
+
expect(failed).to eq("key1")
|
109
|
+
end
|
110
|
+
|
111
|
+
it "should not call on_write_failure hook when delete succeeds" do
|
112
|
+
failed = "nothing failed"
|
113
|
+
@version_store.on_write_failure{ |key| failed = key }
|
114
|
+
@version_store.delete("key1")
|
115
|
+
expect(failed).to eq("nothing failed")
|
116
|
+
end
|
117
|
+
|
80
118
|
it "should write to the debug log" do
|
81
119
|
expect{ @version_store.delete("key1") }.to log(:debug, %(Version Store: deleted key1))
|
82
120
|
end
|
metadata
CHANGED
@@ -1,14 +1,14 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: record-cache
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.1.
|
4
|
+
version: 0.1.5
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Orslumen
|
8
8
|
autorequire:
|
9
9
|
bindir: bin
|
10
10
|
cert_chain: []
|
11
|
-
date: 2015-
|
11
|
+
date: 2015-11-06 00:00:00.000000000 Z
|
12
12
|
dependencies:
|
13
13
|
- !ruby/object:Gem::Dependency
|
14
14
|
name: rails
|
@@ -260,7 +260,7 @@ rubyforge_project:
|
|
260
260
|
rubygems_version: 2.1.11
|
261
261
|
signing_key:
|
262
262
|
specification_version: 4
|
263
|
-
summary: Record Cache v0.1.
|
263
|
+
summary: Record Cache v0.1.5 transparantly stores Records in a Cache Store and retrieve
|
264
264
|
those Records from the store when queried using Active Model.
|
265
265
|
test_files:
|
266
266
|
- spec/db/create-record-cache-db_and_user.sql
|