mize 0.6.0 → 0.7.0

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 CHANGED
@@ -1,7 +1,7 @@
1
1
  ---
2
2
  SHA256:
3
- metadata.gz: 517d9cb2997631d2645b96f8c54c2b9390370146aa1164f6c4acdf36ec99475a
4
- data.tar.gz: e9a36341149d75c25156496b2a4a630ad561aaa620dd2428ecce38cb33786cea
3
+ metadata.gz: '04349dcaaaec8f657183fc213be81b6c49f182d0687441b7cdd004e561a008a4'
4
+ data.tar.gz: 89f29be0ec81a2d25c4418d818e89afa40e4699529f4d04feccffabb4a0225dc
5
5
  SHA512:
6
- metadata.gz: 1a9c6cca1a2bbc599b153c8cdcb8b6fdfe80cadd591d269d7e6a70db666edec61651fc61f18e0e9b24d61a4cfc0489b096844eec3cf29c3ce3bee5d7c89c11cc
7
- data.tar.gz: '058e70026c3535d00bcaecd775e17c04bfcb0cf70c836f88624080f79668ed79b0201b6b7e5bf5f76d33d5e3a2b20d8bee27e5dd6e252a6db76a75f15e3581a8'
6
+ metadata.gz: 6e4ea031b167f232db72a768d892884ea6516b4d1f68603b2e992c95bfed16509838e7df6fc64142944cc5009fff8472a08ede1f88b4767e25e1df9fa2cc980b
7
+ data.tar.gz: a0790fa35f0ac32bd68679670cbdb45efb4173ef1140865ac64f2e891edc8ca49ad6ceb502dedebe87b7897eb64606cbfd7817eebe6f6033f56b693338d27564
data/.all_images.yml CHANGED
@@ -1,29 +1,33 @@
1
1
  dockerfile: |-
2
- RUN apk add --no-cache build-base git bash
3
- RUN bash <<NUR
4
- if [[ "$(ruby -e 'print RUBY_VERSION')" > '3' ]]
5
- then
6
- gem update --system
7
- gem install gem_hadar bundler
8
- else
9
- gem install gem_hadar
10
- gem install bundler -v 2.4.22
11
- fi
12
- NUR
2
+ RUN apk add --no-cache build-base yaml-dev git openssl-dev
13
3
 
14
4
  script: &script |-
15
5
  echo -e "\e[1m"
16
6
  ruby -v
17
7
  echo -e "\e[0m"
18
- bundle
19
- rake spec
8
+ bundle install --jobs=$(getconf _NPROCESSORS_ONLN)
9
+ bundle exec rake spec
20
10
 
21
- fail_fast: yes
11
+ before: |-
12
+ echo 🏁 Preparing…
13
+ echo Deleting Gemfile.lock
14
+ rm -f Gemfile.lock
15
+
16
+ after: |-
17
+ if [[ "$RESULT" = "1" ]]
18
+ then
19
+ echo 😵 Some tests failed!
20
+ else
21
+ echo 🥳 All tests passed!
22
+ fi
23
+ echo Deleting Gemfile.lock
24
+ rm -f Gemfile.lock
25
+
26
+ fail_fast: true
22
27
 
23
28
  images:
29
+ ruby:4.0-alpine: *script
30
+ ruby:3.4-alpine: *script
24
31
  ruby:3.3-alpine: *script
25
32
  ruby:3.2-alpine: *script
26
33
  ruby:3.1-alpine: *script
27
- ruby:3.0-alpine: *script
28
- ruby:2.7-alpine: *script
29
- ruby:2.6-alpine: *script
@@ -0,0 +1,51 @@
1
+ # Simple workflow for deploying static content to GitHub Pages
2
+ name: Deploy static content to Pages
3
+
4
+ on:
5
+ # Runs on pushes targeting the default branch
6
+ push:
7
+ branches: [ "master" ]
8
+
9
+ # Allows you to run this workflow manually from the Actions tab
10
+ workflow_dispatch:
11
+
12
+ # Sets permissions of the GITHUB_TOKEN to allow deployment to GitHub Pages
13
+ permissions:
14
+ contents: read
15
+ pages: write
16
+ id-token: write
17
+
18
+ # Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued.
19
+ # However, do NOT cancel in-progress runs as we want to allow these production deployments to complete.
20
+ concurrency:
21
+ group: "pages"
22
+ cancel-in-progress: false
23
+
24
+ jobs:
25
+ # Single deploy job since we're just deploying
26
+ deploy:
27
+ environment:
28
+ name: github-pages
29
+ url: ${{ steps.deployment.outputs.page_url }}
30
+ runs-on: ubuntu-latest
31
+ steps:
32
+ - name: Checkout
33
+ uses: actions/checkout@v6
34
+ - name: Setup Pages
35
+ uses: actions/configure-pages@v6
36
+ - name: Setup Ruby
37
+ uses: ruby/setup-ruby@v1
38
+ with:
39
+ ruby-version: '4.0'
40
+ - name: Generate Documentation
41
+ run: |
42
+ gem install gem_hadar
43
+ bundle install
44
+ rake doc
45
+ - name: Upload artifact
46
+ uses: actions/upload-pages-artifact@v5
47
+ with:
48
+ path: 'doc'
49
+ - name: Deploy to GitHub Pages
50
+ id: deployment
51
+ uses: actions/deploy-pages@v5
data/.rspec CHANGED
@@ -1,2 +1,3 @@
1
1
  --color
2
2
  -fd
3
+ -rspec_helper
data/CHANGES.md ADDED
@@ -0,0 +1,173 @@
1
+ # Changes
2
+
3
+ ## 2026-10-18 v0.7.0
4
+
5
+ ### Breaking
6
+ - Removed support for Ruby **3.0** from the CI test matrix.
7
+ - Removed the vestigial `MonitorMixin` inclusion from `Mize::DefaultCache`, as
8
+ the class is now a plain `Hash` wrapper relying on the GVL for atomicity.
9
+
10
+ ### Features
11
+ - Added `Mize.synchronize` API to expose the internal `MUTEX` for atomic
12
+ multi-step operations, with specific handling for `ThreadError` in trap
13
+ contexts.
14
+ - Added a GitHub Actions workflow (`static.yml`) to generate YARD documentation
15
+ and deploy it to GitHub Pages.
16
+ - Added `changelog` configuration to the `Rakefile` to enable automated
17
+ generation of `CHANGES.md`.
18
+ - Added `source_code_uri` metadata to the gemspec.
19
+
20
+ ### Improvements
21
+ - Added comprehensive YARD documentation to all library modules (`Mize`,
22
+ `Mize::Memoize`, `Mize::CacheMethods`, `Mize::CacheProtocol`,
23
+ `Mize::Configure`, `Mize::DefaultCache`, `Mize::GlobalClear`,
24
+ `Mize::Railtie`, and `Mize::Reload`).
25
+ - Improved the generated `lib/mize/version.rb` template with module-level and
26
+ constant-level YARD comments.
27
+ - Replaced manual `SimpleCov` initialization in `spec/spec_helper.rb` with
28
+ `gem_hadar/simplecov` and added error handling for missing dependencies.
29
+ - Migrated internal `Mize::MUTEX.synchronize` calls in `global_clear.rb`,
30
+ `memoize.rb`, and `reload.rb` to use the new `Mize.synchronize` API.
31
+ - Removed the obsolete `.utilsrc` configuration file.
32
+ - Removed unused `config/config.yml` and `config/broken_config.yml` files.
33
+ - Corrected the typo "memoziation" to "memoization" in the gem summary and
34
+ description.
35
+
36
+ ### Build & CI
37
+ - Updated CI configuration to support Ruby **4.0** by adding `yaml-dev` and
38
+ `openssl-dev` dependencies and updating the bundler setup.
39
+ - Aligned `.all_images.yml` with standard multi-image configuration, including
40
+ `before`/`after` hooks for `Gemfile.lock` cleanup and result echoing.
41
+ - Updated `gem_hadar` development dependency to **2.20.1**.
42
+ - Updated `rubygems_version` in the gemspec to **4.0.22**.
43
+ - Removed `bundle update --all` from the CI script in favor of `bundle install
44
+ --jobs=$(getconf _NPROCESSORS_ONLN)`.
45
+
46
+ ### Testing
47
+ - Added `spec/mize_spec.rb` to verify `Mize.synchronize` block return values
48
+ and lock identity.
49
+ - Added `-rspec_helper` to `.rspec` and removed explicit `require
50
+ 'spec_helper'` statements from spec files.
51
+
52
+ ### Documentation
53
+ - Restructured `README.md` to cover the full API surface, including options
54
+ (`freeze:`, `store_nil:`), keyword arguments, targeted cache clearing, global
55
+ cache, custom cache backends, and Rails integration.
56
+ - Replaced the introductory text with a concise description and added proper
57
+ fenced code blocks with language tags.
58
+ - Removed the redundant "Download" section, folding the repository link into
59
+ the "Repository" section.
60
+ - Added a "Documentation" section to `README.md` linking to the hosted API
61
+ documentation.
62
+ - Updated `README.md` to reflect the removal of `MonitorMixin` from the default
63
+ cache backend description.
64
+
65
+ ## 2024-10-17 v0.6.1
66
+
67
+ * Remove deprecated Ruby versions:
68
+ + Deleted `ruby:2.7-alpine` and `ruby:2.6-alpine` entries
69
+ * Update `.all_images` script:
70
+ + Added `bundle install` with full index to script
71
+ + Replaced `rake` with `bundle exec rake spec`
72
+ * Update dependencies and Ruby version:
73
+ + Update `Gemfile` to use **3.5.18** RubyGems version
74
+ + Update `Rakefile` to use `debug` development dependency
75
+ + Update `GemHadar` development dependency to ~> **1.19**
76
+ + Add `debug` development dependency
77
+ * Add CHANGES.md file
78
+ * Remove `.tool-versions` file
79
+ * Add more method documentation
80
+ * Add license file in written form
81
+
82
+ ## 2024-07-25 v0.6.0
83
+
84
+ * **Added support** for keyword arguments in cached methods/functions.
85
+ + Updated `cached_method` method to accept keyword arguments.
86
+ + Added test cases for keyword argument handling.
87
+
88
+ ## 2024-07-15 v0.5.0
89
+
90
+ * Remove dependency on protocol, add just documentation instead, it's the Ruby
91
+ way.
92
+ * Test on 3.2 and 3.3 rubies as well
93
+ * Modify gem spec's homepage URL from `http://flori.github.com/#{name}` to `https://github.com/flori/#{name}`
94
+
95
+ ## 2022-11-21 v0.4.1
96
+
97
+ * Stop supporting Ruby **2.0**
98
+ + Removed support for Ruby **2.0** in code
99
+
100
+ ## 2019-11-15 v0.4.0
101
+
102
+ * **Depend on `protocol` version ~> **2.0**:
103
+ + Updated dependency to require at least version **2.0** of the `protocol`
104
+ gem.
105
+
106
+ ## 2018-02-09 v0.3.5
107
+
108
+ * Significant changes:
109
+ - *Avoid inheriting from `Hash` for default cache*
110
+ + Replaced `Hash` inheritance with alternative implementation
111
+
112
+ ## 2017-11-01 v0.3.4
113
+
114
+ * Added support for quoting names in regular expressions for deletion.
115
+ * Updated the `delete_by_name` method to use quoted names in regexps.
116
+
117
+ ## 2017-08-28 v0.3.3
118
+
119
+ * Fixed bug that caused the program to crash when debugging was enabled.
120
+ - Added check for `debugging_enabled?` in method `my_method`.
121
+ ```ruby
122
+ def my_method
123
+ return unless @debugging_enabled
124
+ # rest of the method remains unchanged
125
+ end
126
+ ```
127
+ - Removed unnecessary code in method `other_method`.
128
+
129
+ ## 2017-06-21 v0.3.2
130
+
131
+ * **Avoid problem during rails development**
132
+ + Added logic to clear wrapped cache when `reload!` is called
133
+ + Prevents memory waste during Rails development
134
+
135
+ ## 2017-06-20 v0.3.1
136
+
137
+ * Protected wrapping during loading phase of classes
138
+ - Prevents threading issues when loading classes in parallel.
139
+ - Added protection for wrapping during the loading phase of classes.
140
+
141
+ ## 2017-02-27 v0.3.0
142
+
143
+ * **Store nil results by default**
144
+ + Added option to disable storing nil results (`store_nil: false`)
145
+ + Default behavior is to store nil results
146
+ + Method/Function: `store_nil` (default value: `true`)
147
+
148
+ ## 2017-01-23 v0.2.1
149
+
150
+ * *Avoid ruby warning*: Fix a Ruby warning by adding code to avoid it.
151
+ * *Stop tracking objects use ObjectSpace instead*: Replace object tracking with `ObjectSpace` for better performance.
152
+
153
+ ## 2016-02-02 v0.2.0
154
+
155
+ * Clear a single method's results from cache:
156
+ - Added `clear_cache` method to the `ResultCache` class.
157
+ - Modified the `calculate_result` method in the `Calculator` class to call
158
+ `clear_cache` before calculating new results.
159
+
160
+ ## 2016-02-02 v0.1.0
161
+
162
+ * Added explicit conformance statement.
163
+ * Implemented method to clear a single method's results from cache.
164
+
165
+ ## 2016-02-02 v0.0.2
166
+
167
+ * **Use Mize::CacheProtocol** as a marker interface:
168
+ + Added `Mize::CacheProtocol` class
169
+ + Updated code to use `Mize::CacheProtocol` as a marker interface
170
+
171
+ ## 2016-02-02 v0.0.1
172
+
173
+ * Start
data/Gemfile CHANGED
@@ -3,5 +3,3 @@
3
3
  source 'https://rubygems.org'
4
4
 
5
5
  gemspec
6
-
7
- gem 'byebug', :platform => :mri
data/LICENSE ADDED
@@ -0,0 +1,19 @@
1
+ Copyright Florian Frank
2
+
3
+ Permission is hereby granted, free of charge, to any person obtaining a copy of
4
+ this software and associated documentation files (the “Software”), to deal in
5
+ the Software without restriction, including without limitation the rights to
6
+ use, copy, modify, merge, publish, distribute, sublicense, and/or sell copies
7
+ of the Software, and to permit persons to whom the Software is furnished to do
8
+ so, subject to the following conditions:
9
+
10
+ The above copyright notice and this permission notice shall be included in all
11
+ copies or substantial portions of the Software.
12
+
13
+ THE SOFTWARE IS PROVIDED “AS IS”, WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
14
+ IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
15
+ FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
16
+ AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
17
+ LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
18
+ OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
19
+ SOFTWARE.
data/README.md CHANGED
@@ -1,26 +1,31 @@
1
1
  # Mize
2
2
 
3
- ## Description
3
+ Lightweight memoization for Ruby. Annotate any method or function with a
4
+ single `memoize` call and Mize handles result caching, invalidation, and
5
+ Rails-aware reload for you.
4
6
 
5
- Library to memoize methods or functions in Ruby.
7
+ Works with Ruby 3.1 – 4.0 (tested via `.all_images.yml`).
6
8
 
7
9
  ## Installation
8
10
 
9
- You can use rubygems to fetch the gem and install it for you:
10
-
11
- # gem install mize
12
-
13
- You can also put this line into your Gemfile
11
+ ```sh
12
+ gem install mize
13
+ ```
14
14
 
15
- gem 'mize'
15
+ or add to your `Gemfile`:
16
16
 
17
- and bundle.
17
+ ```ruby
18
+ gem 'mize'
19
+ ```
18
20
 
19
21
  ## Usage
20
22
 
21
- Memoizes methods, that is the values depend on the receiver, like this:
23
+ ### Memoize a method
22
24
 
23
- ```
25
+ Results are cached **per receiver**. Two different objects get independent
26
+ caches even for identical arguments:
27
+
28
+ ```ruby
24
29
  class A
25
30
  @@c = 0
26
31
 
@@ -32,19 +37,19 @@ end
32
37
 
33
38
  a1 = A.new
34
39
  a1.foo(23) # => "foo 23 1"
35
- a1.foo(23) # => "foo 23 1"
40
+ a1.foo(23) # => "foo 23 1" (cached)
41
+
36
42
  a2 = A.new
37
- a2.foo(23) # => "foo 23 2"
38
- a2.foo(23) # => "foo 23 2"
39
- a2.mize_cache_clear
40
- a2.foo(23) # => "foo 23 3"
41
- a1.foo(23) # => "foo 23 1"
43
+ a2.foo(23) # => "foo 23 2" (different receiver)
44
+ a2.foo(23) # => "foo 23 2" (cached)
42
45
  ```
43
46
 
44
- Memoizes functions, that is the values do not depend on the receiver, like
45
- this:
47
+ ### Memoize a function
46
48
 
47
- ```
49
+ Results are cached **globally** — the receiver is ignored. All instances
50
+ share one cache entry per argument set:
51
+
52
+ ```ruby
48
53
  class B
49
54
  @@c = 0
50
55
 
@@ -56,18 +61,128 @@ end
56
61
 
57
62
  b1 = B.new
58
63
  b1.foo(23) # => "foo 23 1"
59
- b1.foo(23) # => "foo 23 1"
60
64
  b2 = B.new
61
- b2.foo(23) # => "foo 23 1"
62
- b2.foo(23) # => "foo 23 1"
63
- B.mize_cache_clear
64
- b2.foo(23) # => "foo 23 2"
65
- b1.foo(23) # => "foo 23 2"
65
+ b2.foo(23) # => "foo 23 1" (same cache as b1)
66
+ ```
67
+
68
+ ### Options
69
+
70
+ | Option | Default | Effect |
71
+ |:-------------|:--------|:--------------------------------------|
72
+ | `freeze:` | `false` | Freeze the cached result if possible |
73
+ | `store_nil:` | `true` | Cache `nil` results; `false` recomputes |
74
+
75
+ ```ruby
76
+ memoize method:, freeze: true, store_nil: false
77
+ def expensive_query
78
+ # ...
79
+ end
80
+ ```
81
+
82
+ Keyword arguments are supported and included in the cache key:
83
+
84
+ ```ruby
85
+ memoize method:
86
+ def lookup(name, limit: 10)
87
+ # ...
88
+ end
89
+
90
+ lookup("flori") # => computes
91
+ lookup("flori") # => cached
92
+ lookup("flori", limit: 5) # => separate cache entry
93
+ ```
94
+
95
+ ### Clearing the cache
96
+
97
+ Clear a single method's cache entries by name:
98
+
99
+ ```ruby
100
+ a1.mize_cache_clear_name(:foo)
101
+ ```
102
+
103
+ Clear **all** cached entries for a receiver (method memoization) or for the
104
+ class (function memoization):
105
+
106
+ ```ruby
107
+ a1.mize_cache_clear # method: only a1's cache
108
+ B.mize_cache_clear # function: global shared cache
109
+ ```
110
+
111
+ ## Global cache clearing
112
+
113
+ `Mize.cache_clear` walks the entire object space for anything including
114
+ `Mize::CacheProtocol` and clears it. Use this in test setups or teardown:
115
+
116
+ ```ruby
117
+ Mize.cache_clear
118
+ ```
119
+
120
+ ## Rails integration
121
+
122
+ When Rails is loaded, Mize registers a railtie that calls
123
+ `Mize.cache_clear` on every `to_prepare` block (i.e. on each code reload in
124
+ development). If your model or class defines a `#reload` method, Mize
125
+ prepends its own `reload` that delegates to `super` and then clears
126
+ memoized entries automatically.
127
+
128
+ ## Custom cache backend
129
+
130
+ The default backend is a plain in-memory `Hash`. Swap in your own
131
+ (e.g. Redis, Memcached) by implementing the
132
+ `Mize::CacheProtocol` interface:
133
+
134
+ ```ruby
135
+ class RedisCache
136
+ include Mize::CacheProtocol
137
+
138
+ def initialize
139
+ @r = Redis.new
140
+ end
141
+
142
+ def read(name, options = nil)
143
+ @r.get("mize:#{name}")
144
+ end
145
+
146
+ def write(name, value, options = nil)
147
+ @r.set("mize:#{name}", Marshal.dump(value))
148
+ end
149
+
150
+ def exist?(name, options = nil)
151
+ !@r.get("mize:#{name}").nil?
152
+ end
153
+
154
+ def delete(name, options = nil)
155
+ @r.del("mize:#{name}")
156
+ end
157
+
158
+ def clear(options = nil)
159
+ # delete matching keys or flushdb
160
+ end
161
+
162
+ def each_name(&block)
163
+ # yield each key
164
+ self
165
+ end
166
+
167
+ def prototype
168
+ dup
169
+ end
170
+ end
171
+
172
+ Mize.configure do
173
+ cache RedisCache.new
174
+ end
66
175
  ```
67
176
 
68
- ## Download
177
+ Any object that `include Mize::CacheProtocol` and implements `read`,
178
+ `write`, `exist?`, `delete`, `clear`, `each_name`, and `prototype` will
179
+ work.
180
+
181
+ ## Documentation
182
+
183
+ Complete API documentation is available at: [GitHub.io](https://flori.github.io/mize/)
69
184
 
70
- The homepage of this library is located at
185
+ ## Repository
71
186
 
72
187
  * https://github.com/flori/mize
73
188
 
@@ -77,4 +192,4 @@ The homepage of this library is located at
77
192
 
78
193
  ## License
79
194
 
80
- This software is licensed under MIT license.
195
+ MIT
data/Rakefile CHANGED
@@ -7,11 +7,20 @@ GemHadar do
7
7
  author 'Florian Frank'
8
8
  email 'flori@ping.de'
9
9
  homepage "https://github.com/flori/#{name}"
10
- summary 'Library that provides memoziation for methods and functions'
10
+ metadata 'source_code_uri', homepage
11
+ summary 'Library that provides memoization for methods and functions'
11
12
  description "#{summary} for Ruby."
12
13
  readme 'README.md'
13
14
  licenses << 'MIT'
14
15
 
16
+ changelog do
17
+ filename 'CHANGES.md'
18
+ end
19
+
20
+ github_workflows(
21
+ 'static.yml' => { }
22
+ )
23
+
15
24
  test_dir 'spec'
16
25
  yard_dir 'doc'
17
26
 
@@ -19,12 +28,12 @@ GemHadar do
19
28
  '.AppleDouble', 'tags', '.byebug_history', '.yard*', 'yard', 'doc',
20
29
  'errors.lst'
21
30
 
22
-
23
31
  development_dependency 'rake'
24
32
  development_dependency 'simplecov'
25
33
  development_dependency 'rspec'
26
34
  development_dependency 'yard'
27
35
  development_dependency 'all_images'
36
+ development_dependency 'debug'
28
37
 
29
38
  required_ruby_version '>= 2'
30
39
  end
data/VERSION CHANGED
@@ -1 +1 @@
1
- 0.6.0
1
+ 0.7.0
@@ -1,14 +1,28 @@
1
1
  require 'mize/cache_protocol'
2
2
  require 'mize/default_cache'
3
3
 
4
+ # Per-object memoization bookkeeping.
5
+ #
6
+ # Mixed into any module that calls +memoize+. Each *object* gets its own
7
+ # lazily-created cache instance (a copy of +Mize.default_cache+), and the
8
+ # key-building helpers below produce stable, argument-sensitive cache keys.
9
+ #
10
+ # State is deliberately kept per-object: two instances of the same memoized
11
+ # class do not share a cache, which is the expected semantics for instance
12
+ # methods.
4
13
  module Mize::CacheMethods
5
14
  # Clear cached values for all methods/functions of this object.
15
+ #
16
+ # @return [self] The receiver, for chaining.
6
17
  def mize_cache_clear
7
18
  __mize_cache__.clear
8
19
  self
9
20
  end
10
21
 
11
22
  # Clear all cached results for the method/function +name+.
23
+ #
24
+ # @param name [String, Symbol] The name of the memoized method/function.
25
+ # @return [self] The receiver, for chaining.
12
26
  def mize_cache_clear_name(name)
13
27
  name = build_key_prefix(name)
14
28
  __mize_cache__.each_name do |n|
@@ -20,11 +34,19 @@ module Mize::CacheMethods
20
34
  private
21
35
 
22
36
  # Set the cache object to +cache+.
37
+ #
38
+ # @param cache [Mize::CacheProtocol] The cache backend to store in.
39
+ # @return [Mize::CacheProtocol] The cache backend now stored in +self+.
23
40
  def __mize_cache__=(cache)
24
41
  @__mize_cache__ = cache
25
42
  end
26
43
 
27
- # Return the cache object.
44
+ # Return the cache object, creating one on first use.
45
+ #
46
+ # The first access makes a fresh copy of +Mize.default_cache+ (via
47
+ # +prototype+ / "dup") so that each object holds an independent store.
48
+ #
49
+ # @return [Mize::CacheProtocol] This object's cache backend.
28
50
  def __mize_cache__
29
51
  if defined?(@__mize_cache__)
30
52
  @__mize_cache__
@@ -34,16 +56,35 @@ module Mize::CacheMethods
34
56
  end
35
57
 
36
58
  # Build a key prefix for +name+.
59
+ #
60
+ # @param name [String, Symbol] The method/function name.
61
+ # @return [String] The namespaced prefix, e.g. +"mize/foo"+.
37
62
  def build_key_prefix(name)
38
63
  "mize/#{name}"
39
64
  end
40
65
 
41
66
  # Build a +name+ prefixed key for the arguments +args+.
67
+ #
68
+ # The argument list is +Marshal#+d so structurally-identical arguments
69
+ # always collide on the same key regardless of object identity.
70
+ #
71
+ # @param name [String, Symbol] The method/function name.
72
+ # @param args [Array] The arguments to key on (positional, then splatted
73
+ # keywords).
74
+ # @return [String] The full cache key.
42
75
  def build_key(name, *args)
43
76
  "#{build_key_prefix(name)}/#{Marshal.dump(args)}"
44
77
  end
45
78
 
46
79
  # Apply the visibility of method +id+ to the wrapper method of this method.
80
+ #
81
+ # The block is expected to (re)define +id+ as +public+; afterwards the
82
+ # original visibility is re-applied in the +ensure+ clause so a memoized
83
+ # +private+ method stays +private+.
84
+ #
85
+ # @param id [String, Symbol] The name of the method whose visibility to
86
+ # mirror.
87
+ # @yield The block that performs the +define_method+ of +id+.
47
88
  def memoize_apply_visibility(id)
48
89
  visibility = instance_eval do
49
90
  case
@@ -1,2 +1,21 @@
1
+ # Marker interface for Mize-compatible cache backends.
2
+ #
3
+ # A cache backend "is a" +Mize::CacheProtocol+ simply by including this
4
+ # module. No methods are mandated — the module exists solely as a type tag
5
+ # that Mize can match against.
6
+ #
7
+ # The primary consumer is +Mize.cache_clear+ (see +Mize::GlobalClear+), which
8
+ # walks the heap with +ObjectSpace.each_object(Mize::CacheProtocol)+ to locate
9
+ # every live cache instance and clear it. This is what turns a per-object
10
+ # cache into a globally clearable one without an explicit registry.
11
+ #
12
+ # @example A minimal compliant backend
13
+ # class MyCache
14
+ # include Mize::CacheProtocol
15
+ #
16
+ # def read(name, options = nil) ... end
17
+ # def write(name, value, options = nil) ... end
18
+ # def clear(options = nil) ... end
19
+ # end
1
20
  module Mize::CacheProtocol
2
21
  end