kasket 4.1.0 → 4.2.0
Sign up to get free protection for your applications and to get access to all the features.
- checksums.yaml +4 -4
- data/README.md +143 -0
- data/lib/kasket.rb +2 -1
- data/lib/kasket/version.rb +1 -1
- data/lib/kasket/write_mixin.rb +20 -5
- metadata +7 -8
- data/README.rdoc +0 -123
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: 70892c6d927d66172bfa651364fb0d83ab575b68
|
4
|
+
data.tar.gz: 16fc178ed0ba3aee24b4547ab87337f5d28260bb
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 16844a7cdf3e9c8cdcd8612c33248372c3dcf30fde06607e06c9d021649e6a97810ab22bac1f8246f97015900b26992bf496fa5312c960e2988ea27d39358bbc
|
7
|
+
data.tar.gz: 541bb732c0356a8425637619fb097699a130a003e71a8068c36c592e212763bc08db3ac1fdac7f31aec2b15702cc9b1901ab4356f60eec894589685c611c3eb8
|
data/README.md
ADDED
@@ -0,0 +1,143 @@
|
|
1
|
+
# Kasket [![Build Status](https://secure.travis-ci.org/zendesk/kasket.svg)](http://travis-ci.org/zendesk/kasket)
|
2
|
+
|
3
|
+
### Puts a cap on your queries
|
4
|
+
A caching layer for ActiveRecord (3.x and 4.x)
|
5
|
+
|
6
|
+
Developed and used by [Zendesk](http://zendesk.com).
|
7
|
+
|
8
|
+
## Sponsored by Zendesk - Enlightened Customer Support
|
9
|
+
|
10
|
+
## Description
|
11
|
+
|
12
|
+
Kasket is a safe way to cache your database queries in memcached.
|
13
|
+
Designed to be as small and simple as possible, and to get out of the way when it is not safe to cache.
|
14
|
+
|
15
|
+
You can configure exactly what models to cache and what type of queries to cache.
|
16
|
+
|
17
|
+
### Features
|
18
|
+
|
19
|
+
* Declarative configuration
|
20
|
+
* Collection caching as well as caching of single instances
|
21
|
+
* Automatic cache expiry on database migration
|
22
|
+
* Automatic cache expiry in Kasket udates
|
23
|
+
* Very small code base
|
24
|
+
|
25
|
+
## Setting up Kasket
|
26
|
+
|
27
|
+
Kasket is set up by simply calling `Kasket.setup` in an initializer script.
|
28
|
+
This will include the required modules into ActiveRecord.
|
29
|
+
|
30
|
+
### Options
|
31
|
+
|
32
|
+
#### Max Collection Size
|
33
|
+
|
34
|
+
By default, Kasket will cache each instance collection with a maximum length of 100.
|
35
|
+
You can override this by passing the `:max_collection_size` option to the `Kasket.setup` call:
|
36
|
+
|
37
|
+
```
|
38
|
+
Kasket.setup(:max_collection_size => 50)
|
39
|
+
```
|
40
|
+
|
41
|
+
#### Write-Through Caching
|
42
|
+
|
43
|
+
By default, when a model is saved, Kasket will invalidate cache entries by deleting them.
|
44
|
+
You can pass ':write_through => true' to the `Kasket.setup` call to get write-through cache
|
45
|
+
semantics instead. In this mode, the model will be updated in the cache as well as the database.
|
46
|
+
|
47
|
+
```
|
48
|
+
Kasket.setup(:write_through => true)
|
49
|
+
```
|
50
|
+
|
51
|
+
## Configuring caching of your models
|
52
|
+
|
53
|
+
You can configure Kasket for any ActiveRecord model, and subclasses will automatically inherit the caching
|
54
|
+
configuration.
|
55
|
+
|
56
|
+
If you have an `Account` model, you can can do the simplest caching configuration like:
|
57
|
+
|
58
|
+
```
|
59
|
+
Account.has_kasket
|
60
|
+
```
|
61
|
+
|
62
|
+
This will add a caching index on the id attribute of the Account model,
|
63
|
+
and will make sure that all your calls like `Account.find(1)` and `Account.find_by_id(1)` will be cached.
|
64
|
+
All other calls (say, `Account.find_by_subdomain('zendesk')`) are untouched.
|
65
|
+
|
66
|
+
If you wanted to configure a caching index on the subdomain attribute of the Account model, you would simply write
|
67
|
+
|
68
|
+
```
|
69
|
+
Account.has_kasket_on :subdomain
|
70
|
+
```
|
71
|
+
|
72
|
+
This would add caching to calls like:
|
73
|
+
* `Account.find_by_subdomain('zendesk')`
|
74
|
+
* `Account.find_all_by_subdomain('zendesk')`
|
75
|
+
|
76
|
+
and all other ways of expressing lookups on subdomain.
|
77
|
+
|
78
|
+
## Cache expiry
|
79
|
+
|
80
|
+
The goal of Kasket is to be as safe as possible to use, so the cache is expired in a number of situations:
|
81
|
+
* When you save a model instance
|
82
|
+
* When your database schema changes
|
83
|
+
* When you install a new version of Kasket
|
84
|
+
* When you ask it to
|
85
|
+
|
86
|
+
### Cache expiry on instance save
|
87
|
+
|
88
|
+
When you save a model instance, Kasket will calculate the cache entries to expire.
|
89
|
+
|
90
|
+
### Cache expiry on database schema changes
|
91
|
+
|
92
|
+
All Kasket cache keys contain a hash of the column names of the table associated with the model.
|
93
|
+
If you somehow change your table schema, all cache entries for that table will automatically expire.
|
94
|
+
|
95
|
+
### Cache expiry on Kasket upgrades
|
96
|
+
|
97
|
+
All Kasket cache keys contain the Kasket version number, so upgrading Kasket will expire all Kasket cache entries.
|
98
|
+
|
99
|
+
### Manually expiring caches
|
100
|
+
|
101
|
+
If you have model methods that update the database behind the back of ActiveRecord, you need to mark these methods
|
102
|
+
as being dirty.
|
103
|
+
|
104
|
+
```
|
105
|
+
Account.kasket_dirty_methods :update_last_action
|
106
|
+
```
|
107
|
+
|
108
|
+
This will make sure the clear the cache entries for the current instance when you call `update_last_action`.
|
109
|
+
|
110
|
+
## How does this work?
|
111
|
+
|
112
|
+
## Known issues
|
113
|
+
|
114
|
+
We have only used and tested Kasket with MySQL.
|
115
|
+
|
116
|
+
Let us know if you find any.
|
117
|
+
|
118
|
+
## Isn't this what [Cache Money](https://github.com/nkallen/cache-money) does?
|
119
|
+
|
120
|
+
Absolutely, but Cache Money does so much more.
|
121
|
+
* Cache Money has way more features than what we need.
|
122
|
+
* The Cache Money code is overly complex.
|
123
|
+
* Cache Money seems abandoned.
|
124
|
+
|
125
|
+
## Note on Patches/Pull Requests
|
126
|
+
|
127
|
+
* Fork the project.
|
128
|
+
* Make your feature addition or bug fix.
|
129
|
+
* Add tests for it. This is important so I don't break it in a future version unintentionally.
|
130
|
+
* Commit, do not mess with Rakefile, version, or history.
|
131
|
+
(If you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull.)
|
132
|
+
* Send me a pull request. Bonus points for topic branches.
|
133
|
+
|
134
|
+
## Copyright and license
|
135
|
+
|
136
|
+
Copyright 2013 Zendesk
|
137
|
+
|
138
|
+
Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License.
|
139
|
+
You may obtain a copy of the License at
|
140
|
+
|
141
|
+
http://www.apache.org/licenses/LICENSE-2.0
|
142
|
+
|
143
|
+
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.
|
data/lib/kasket.rb
CHANGED
@@ -14,7 +14,7 @@ module Kasket
|
|
14
14
|
autoload :SelectManagerMixin, 'kasket/select_manager_mixin'
|
15
15
|
autoload :RelationMixin, 'kasket/relation_mixin'
|
16
16
|
|
17
|
-
CONFIGURATION = {:max_collection_size => 100}
|
17
|
+
CONFIGURATION = {:max_collection_size => 100, :write_through => false}
|
18
18
|
|
19
19
|
module_function
|
20
20
|
|
@@ -22,6 +22,7 @@ module Kasket
|
|
22
22
|
return if ActiveRecord::Base.respond_to?(:has_kasket)
|
23
23
|
|
24
24
|
CONFIGURATION[:max_collection_size] = options[:max_collection_size] if options[:max_collection_size]
|
25
|
+
CONFIGURATION[:write_through] = options[:write_through] if options[:write_through]
|
25
26
|
|
26
27
|
ActiveRecord::Base.extend(Kasket::ConfigurationMixin)
|
27
28
|
|
data/lib/kasket/version.rb
CHANGED
data/lib/kasket/write_mixin.rb
CHANGED
@@ -40,8 +40,8 @@ module Kasket
|
|
40
40
|
def kasket_keys
|
41
41
|
attribute_sets = [attributes.symbolize_keys]
|
42
42
|
|
43
|
-
if
|
44
|
-
old_attributes = Hash[*
|
43
|
+
if previous_changes.present?
|
44
|
+
old_attributes = Hash[*previous_changes.map {|attribute, values| [attribute, values[0]]}.flatten].symbolize_keys
|
45
45
|
attribute_sets << old_attributes.reverse_merge(attribute_sets[0])
|
46
46
|
end
|
47
47
|
|
@@ -58,6 +58,19 @@ module Kasket
|
|
58
58
|
keys
|
59
59
|
end
|
60
60
|
|
61
|
+
def kasket_after_commit
|
62
|
+
keys = kasket_keys
|
63
|
+
|
64
|
+
if persisted? && Kasket::CONFIGURATION[:write_through]
|
65
|
+
key = store_in_kasket
|
66
|
+
keys.delete(key)
|
67
|
+
end
|
68
|
+
|
69
|
+
keys.each do |key|
|
70
|
+
Kasket.cache.delete(key)
|
71
|
+
end
|
72
|
+
end
|
73
|
+
|
61
74
|
def clear_kasket_indices
|
62
75
|
kasket_keys.each do |key|
|
63
76
|
Kasket.cache.delete(key)
|
@@ -84,9 +97,11 @@ module Kasket
|
|
84
97
|
model_class.send(:alias_method, :kasket_cacheable?, :default_kasket_cacheable?)
|
85
98
|
end
|
86
99
|
|
87
|
-
model_class.
|
88
|
-
|
89
|
-
|
100
|
+
model_class.after_commit :kasket_after_commit
|
101
|
+
|
102
|
+
if ActiveRecord::VERSION::MAJOR == 3 || (ActiveRecord::VERSION::MAJOR == 4 && ActiveRecord::VERSION::MINOR == 0)
|
103
|
+
model_class.after_touch :kasket_after_commit
|
104
|
+
end
|
90
105
|
|
91
106
|
class << model_class
|
92
107
|
alias_method_chain :transaction, :kasket_disabled
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: kasket
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 4.
|
4
|
+
version: 4.2.0
|
5
5
|
platform: ruby
|
6
6
|
authors:
|
7
7
|
- Mick Staugaard
|
@@ -9,7 +9,7 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date:
|
12
|
+
date: 2016-01-02 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: activerecord
|
@@ -88,7 +88,7 @@ dependencies:
|
|
88
88
|
- !ruby/object:Gem::Version
|
89
89
|
version: '0'
|
90
90
|
- !ruby/object:Gem::Dependency
|
91
|
-
name:
|
91
|
+
name: minitest
|
92
92
|
requirement: !ruby/object:Gem::Requirement
|
93
93
|
requirements:
|
94
94
|
- - ">="
|
@@ -102,7 +102,7 @@ dependencies:
|
|
102
102
|
- !ruby/object:Gem::Version
|
103
103
|
version: '0'
|
104
104
|
- !ruby/object:Gem::Dependency
|
105
|
-
name: minitest
|
105
|
+
name: minitest-rg
|
106
106
|
requirement: !ruby/object:Gem::Requirement
|
107
107
|
requirements:
|
108
108
|
- - ">="
|
@@ -116,7 +116,7 @@ dependencies:
|
|
116
116
|
- !ruby/object:Gem::Version
|
117
117
|
version: '0'
|
118
118
|
- !ruby/object:Gem::Dependency
|
119
|
-
name:
|
119
|
+
name: timecop
|
120
120
|
requirement: !ruby/object:Gem::Requirement
|
121
121
|
requirements:
|
122
122
|
- - ">="
|
@@ -130,7 +130,7 @@ dependencies:
|
|
130
130
|
- !ruby/object:Gem::Version
|
131
131
|
version: '0'
|
132
132
|
- !ruby/object:Gem::Dependency
|
133
|
-
name:
|
133
|
+
name: test_after_commit
|
134
134
|
requirement: !ruby/object:Gem::Requirement
|
135
135
|
requirements:
|
136
136
|
- - ">="
|
@@ -146,12 +146,11 @@ dependencies:
|
|
146
146
|
description: puts a cap on your queries
|
147
147
|
email:
|
148
148
|
- mick@zendesk.com
|
149
|
-
- eac@zendesk.com
|
150
149
|
executables: []
|
151
150
|
extensions: []
|
152
151
|
extra_rdoc_files: []
|
153
152
|
files:
|
154
|
-
- README.
|
153
|
+
- README.md
|
155
154
|
- lib/kasket.rb
|
156
155
|
- lib/kasket/configuration_mixin.rb
|
157
156
|
- lib/kasket/dirty_mixin.rb
|
data/README.rdoc
DELETED
@@ -1,123 +0,0 @@
|
|
1
|
-
= Kasket {<img src="https://secure.travis-ci.org/zendesk/kasket.png" />}[http://travis-ci.org/zendesk/kasket]
|
2
|
-
=== Puts a cap on your queries
|
3
|
-
A caching layer for ActiveRecord (2.3.x and 3.1.x)
|
4
|
-
|
5
|
-
Developed and used on http://zendesk.com.
|
6
|
-
|
7
|
-
== Sponsored by Zendesk - Enlightened Customer Support
|
8
|
-
|
9
|
-
== Description
|
10
|
-
|
11
|
-
Kasket is a safe way to cache your database queries in memcached.
|
12
|
-
Designed to be as small and simple as possible, and to get out of the way when it is not safe to cache.
|
13
|
-
|
14
|
-
You can configure exactly what models to cache and what type of queries to cache.
|
15
|
-
|
16
|
-
=== Features
|
17
|
-
|
18
|
-
* Declarative configuration
|
19
|
-
* Collection caching as well as caching of single instances
|
20
|
-
* Automatic cache expiry on database migration
|
21
|
-
* Automatic cache expiry in Kasket udates
|
22
|
-
* Very small code base
|
23
|
-
|
24
|
-
== Setting up Kasket
|
25
|
-
|
26
|
-
Kasket is set up by simply calling Kasket.setup in an initializer script.
|
27
|
-
This will include the required modules into the ActiveRecord
|
28
|
-
|
29
|
-
=== Options
|
30
|
-
|
31
|
-
By default, Kasket will cache instance collection with a maximum length of 100.
|
32
|
-
You can everride this by passing the :max_collection_size option to the Kasket.setup call:
|
33
|
-
|
34
|
-
Kasket.setup(:max_collection_size => 50)
|
35
|
-
|
36
|
-
== Configuring caching of your models
|
37
|
-
|
38
|
-
You can configure Kasket for any ActiveRecord model, and subclasses will automatically inherit the caching
|
39
|
-
configuration.
|
40
|
-
|
41
|
-
If you have an Account model, you can can do the simplest caching configuration like:
|
42
|
-
|
43
|
-
Account.has_kasket
|
44
|
-
|
45
|
-
This will add a caching index on the id attribute of the Account model,
|
46
|
-
and will make sure that all your calls like Account.find(1) and Account.find_by_id(1) will be cached.
|
47
|
-
All other calls ( say Account.find_by_subdomain('zendesk') ) are untouched.
|
48
|
-
|
49
|
-
If you wanted to configure a caching index on the subdomain attribute of the Account model, you would simply write
|
50
|
-
|
51
|
-
Account.has_kasket_on :subdomain
|
52
|
-
|
53
|
-
This would add caching to calls like:
|
54
|
-
* Account.find_by_subdomain('zendesk')
|
55
|
-
* Account.find_all_by_subdomain('zendesk')
|
56
|
-
|
57
|
-
and all other ways of expressing lookups on subdomain.
|
58
|
-
|
59
|
-
== Cache expiry
|
60
|
-
|
61
|
-
The goal of Kasket is to be as safe as possible to use, so the cache is expired in a number of situations
|
62
|
-
* When you save a model instance
|
63
|
-
* When your database schema changes
|
64
|
-
* When you install a new version of Kasket
|
65
|
-
* When you ask it to
|
66
|
-
|
67
|
-
=== Cahce expiry on instance save
|
68
|
-
|
69
|
-
When you save a model instance, Kasket will calculate the cache entries to expire.
|
70
|
-
|
71
|
-
=== Cache expiry on database schema changes
|
72
|
-
|
73
|
-
All Kasket cache keys contain a hash of the column names of the table associated with the model.
|
74
|
-
If you somehow change your table schema, all cache entries for that table will automatically expire
|
75
|
-
|
76
|
-
=== Cache expiry on Kasket upgrades
|
77
|
-
|
78
|
-
All Kasket cache keys contain the Kasket version number, so upgrading Kasket will expire all Kasket cache entries.
|
79
|
-
|
80
|
-
=== Manually expiring caches
|
81
|
-
|
82
|
-
If you have model methods that update the database behind the back of ActiveRecord, you need to mark these methods
|
83
|
-
as beeing dirty.
|
84
|
-
|
85
|
-
Account.kasket_dirty_methods :update_last_action
|
86
|
-
|
87
|
-
This will make sure the clear the cache entries for the current instance when you call update_last_action
|
88
|
-
|
89
|
-
== How does this work?
|
90
|
-
|
91
|
-
== Known issues
|
92
|
-
|
93
|
-
We have only used and tested Kasket on MySql.
|
94
|
-
|
95
|
-
Let us know if you find any.
|
96
|
-
|
97
|
-
== Isn't this what Cache Money does?
|
98
|
-
|
99
|
-
Absolutely, but cache money does so much more.
|
100
|
-
|
101
|
-
* Cache Money has way more features than what we need
|
102
|
-
* The Cache Money code is overly complex
|
103
|
-
* Cache Money seems abandoned
|
104
|
-
|
105
|
-
== Note on Patches/Pull Requests
|
106
|
-
|
107
|
-
* Fork the project.
|
108
|
-
* Make your feature addition or bug fix.
|
109
|
-
* Add tests for it. This is important so I don't break it in a future version unintentionally.
|
110
|
-
* Commit, do not mess with rakefile, version, or history.
|
111
|
-
(if you want to have your own version, that is fine but bump version in a commit by itself I can ignore when I pull)
|
112
|
-
* Send me a pull request. Bonus points for topic branches.
|
113
|
-
|
114
|
-
== Copyright and license
|
115
|
-
|
116
|
-
Copyright 2013 Zendesk
|
117
|
-
|
118
|
-
Licensed under the Apache License, Version 2.0 (the "License"); you may not use this file except in compliance with the License.
|
119
|
-
You may obtain a copy of the License at
|
120
|
-
|
121
|
-
http://www.apache.org/licenses/LICENSE-2.0
|
122
|
-
|
123
|
-
Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.
|