record-cache 0.1.4 → 0.1.5
Sign up to get free protection for your applications and to get access to all the features.
- 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
|