volatile_map 0.2.0 → 0.3.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: 741ca5ddadf8ec48692705ea3baa57ddaa9ec1b9ed5549ad6de8bce5118f0a08
4
- data.tar.gz: b199789a380616de7861d97401d05b49960b80bad32e1328a7bc06fe2965df0b
3
+ metadata.gz: 1a2771a72fbf86ca6d707d5e73d7ec3bc413f6f87b2c240a2dce1d89ccaf3a27
4
+ data.tar.gz: c03992f176a51f3aee3bac6a6fe31fbc4c9d35154451350c4706fc0d5f91955c
5
5
  SHA512:
6
- metadata.gz: 35b9afc7c775fc1db235ce0630fbffadf6749a3fa42c402e380dc3782d34a48695c3a0e02c70fe45508f62bdd728d4f1012728c4cf075a0e1400354016af68da
7
- data.tar.gz: 0f923260addb0b974b82437b6a63461302a43abdb18a133f7ba938fd143b1a8c0f5b64e33b08ae02fd808e3b30280929f322e666afc01a631d0b47a1811677fc
6
+ metadata.gz: 3b53c5a983029d81b43c7b61e03b978d9c12af401e187d9e41e041d84a2eabb0ea8198ab9c0d46615f7bf333d9e25108586be86e2ddfbfe00ec03354bb9630fe
7
+ data.tar.gz: f1235f6e0088e7ac8c4dca138741e32f65f07aaa8228d2ed1f266382bf4c14d6bbda0539d610d8dcea98c0d970ccea1728b457536d984ca886785e767747acb9
data/README.md CHANGED
@@ -26,7 +26,7 @@ gem install volatile_map
26
26
  require "volatile_map"
27
27
 
28
28
  # TTL is in seconds (Float or Integer)
29
- cache = VolatileMap.new(0.5)
29
+ cache = VolatileMap.new(ttl: 0.5)
30
30
 
31
31
  cache["session"] = { user_id: 42 }
32
32
  cache["session"] # => { user_id: 42 }
@@ -42,7 +42,10 @@ cache["session"] # => nil
42
42
 
43
43
  ### API
44
44
 
45
- - `VolatileMap.new(ttl)` — construct a map with the given TTL in seconds.
45
+ - `VolatileMap.new(ttl:, strict: false)` — construct a map with the given TTL
46
+ in seconds. The optional `strict:` keyword is stored on the instance and
47
+ exposed via `strict?`; when `true`, the keys will return `nil` when they
48
+ expire even if they are not claimed by the VM.
46
49
  - `map[key] = value` — store a value; resets the entry's timestamp.
47
50
  - `map[key]` — retrieve a value; returns `nil` if missing or expired.
48
51
  Refreshes the timestamp on a hit.
@@ -51,6 +54,7 @@ cache["session"] # => nil
51
54
  Also evicts and refreshes like `[]`.
52
55
  - `map.size` — number of entries currently stored.
53
56
  - `map.ttl` — the configured TTL in seconds.
57
+ - `map.strict?` — whether the map was constructed with `strict: true`.
54
58
 
55
59
  ### Semantics
56
60
 
@@ -18,6 +18,8 @@ static size_t vm_live_count = 0;
18
18
  static rb_postponed_job_handle_t vm_drain_job_handle;
19
19
  #endif
20
20
 
21
+ static ID ttl_id, strict_id;
22
+
21
23
  struct vm_drain_ctx {
22
24
  double now;
23
25
  double ttl;
@@ -128,6 +130,7 @@ VALUE alloc_volatile_map(VALUE klass) {
128
130
 
129
131
  vm->storage = rb_hash_new();
130
132
  vm->ttl = 0.0;
133
+ vm->is_strict = false;
131
134
  vm_live_count++;
132
135
 
133
136
  ensure_dirty_capacity();
@@ -142,13 +145,23 @@ static VolatileMap *vm_get(VALUE self) {
142
145
  return vm;
143
146
  }
144
147
 
145
- static VALUE vm_initialize(VALUE self, VALUE ttl) {
148
+ static VALUE vm_initialize(int argc, VALUE *argv, VALUE self) {
146
149
  VolatileMap *vm = vm_get(self);
147
- double ttl_value = NUM2DBL(ttl);
150
+ VALUE opts;
151
+ VALUE kwargs[2];
152
+ ID keys[2] = {ttl_id, strict_id};
153
+
154
+ rb_scan_args(argc, argv, ":", &opts);
155
+
156
+ rb_get_kwargs(opts, keys, 1, 1, kwargs);
157
+
158
+ double ttl_value = NUM2DBL(kwargs[0]);
159
+ VALUE is_strict = kwargs[1];
148
160
 
149
161
  if(ttl_value <= 0.0) rb_raise(rb_eArgError, "TTL must be positive");
150
162
 
151
163
  vm->ttl = ttl_value;
164
+ vm->is_strict = (is_strict != Qundef && RTEST(is_strict));
152
165
 
153
166
  return self;
154
167
  }
@@ -157,6 +170,10 @@ static VALUE vm_ttl(VALUE self) {
157
170
  return DBL2NUM(vm_get(self)->ttl);
158
171
  }
159
172
 
173
+ static VALUE vm_strict(VALUE self) {
174
+ return vm_get(self)->is_strict ? Qtrue : Qfalse;
175
+ }
176
+
160
177
  static VALUE vm_aset(VALUE self, VALUE key, VALUE value) {
161
178
  VolatileMap *vm = vm_get(self);
162
179
  VALUE entry = rb_ary_new_from_args(2, value, DBL2NUM(now_seconds()));
@@ -174,7 +191,7 @@ static VALUE vm_aref(VALUE self, VALUE key) {
174
191
 
175
192
  double now = now_seconds();
176
193
 
177
- if(is_stale(vm->ttl, entry, now)) {
194
+ if(vm->is_strict && is_stale(vm->ttl, entry, now)) {
178
195
  rb_hash_delete(vm->storage, key);
179
196
 
180
197
  return Qnil;
@@ -224,12 +241,16 @@ static VALUE vm_key(VALUE self, VALUE key) {
224
241
  void Init_volatile_map(void) {
225
242
  rb_require("volatile_map/version");
226
243
 
244
+ ttl_id = rb_intern("ttl");
245
+ strict_id = rb_intern("strict");
246
+
227
247
  VALUE volatile_map_class = rb_define_class("VolatileMap", rb_cObject);
228
248
 
229
249
  rb_define_alloc_func(volatile_map_class, alloc_volatile_map);
230
250
 
231
- rb_define_method(volatile_map_class, "initialize", vm_initialize, 1);
251
+ rb_define_method(volatile_map_class, "initialize", vm_initialize, -1);
232
252
  rb_define_method(volatile_map_class, "ttl", vm_ttl, 0);
253
+ rb_define_method(volatile_map_class, "strict?", vm_strict, 0);
233
254
  rb_define_method(volatile_map_class, "[]=", vm_aset, 2);
234
255
  rb_define_method(volatile_map_class, "[]", vm_aref, 1);
235
256
  rb_define_method(volatile_map_class, "delete", vm_delete, 1);
@@ -7,6 +7,7 @@
7
7
  typedef struct volatile_map_struct {
8
8
  VALUE storage;
9
9
  double ttl;
10
+ bool is_strict;
10
11
  } VolatileMap;
11
12
 
12
13
  VALUE alloc_volatile_map(VALUE klass);
@@ -1,5 +1,5 @@
1
1
  # frozen_string_literal: true
2
2
 
3
3
  class VolatileMap
4
- VERSION = "0.2.0"
4
+ VERSION = "0.3.0"
5
5
  end
metadata CHANGED
@@ -1,7 +1,7 @@
1
1
  --- !ruby/object:Gem::Specification
2
2
  name: volatile_map
3
3
  version: !ruby/object:Gem::Version
4
- version: 0.2.0
4
+ version: 0.3.0
5
5
  platform: ruby
6
6
  authors:
7
7
  - Mehmet Emin INAC