moneta 0.7.2 → 0.7.3
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.
- data/CHANGES +7 -1
- data/Gemfile +1 -0
- data/README.md +59 -5
- data/lib/moneta.rb +4 -2
- data/lib/moneta/adapters/cookie.rb +3 -1
- data/lib/moneta/adapters/couch.rb +5 -5
- data/lib/moneta/adapters/memory.rb +1 -0
- data/lib/moneta/adapters/null.rb +1 -0
- data/lib/moneta/adapters/restclient.rb +47 -0
- data/lib/moneta/builder.rb +2 -0
- data/lib/moneta/cache.rb +13 -12
- data/lib/moneta/expires.rb +4 -0
- data/lib/moneta/mixins.rb +18 -4
- data/lib/moneta/optionmerger.rb +2 -0
- data/lib/moneta/server.rb +7 -0
- data/lib/moneta/shared.rb +1 -0
- data/lib/moneta/stack.rb +7 -5
- data/lib/moneta/version.rb +1 -1
- data/lib/moneta/wrapper.rb +7 -0
- data/lib/rack/moneta_cookies.rb +1 -1
- data/lib/rack/moneta_rest.rb +31 -8
- data/lib/rack/moneta_store.rb +45 -0
- data/lib/rack/session/moneta.rb +1 -1
- data/spec/generate.rb +11 -0
- data/spec/helper.rb +30 -13
- data/spec/moneta/adapter_restclient_spec.rb +20 -0
- data/spec/moneta/simple_restclient_spec.rb +145 -0
- data/spec/rack/moneta_cookies_spec.rb +6 -5
- data/spec/rack/moneta_store_spec.rb +83 -0
- metadata +10 -2
data/CHANGES
CHANGED
data/Gemfile
CHANGED
data/README.md
CHANGED
@@ -12,7 +12,7 @@ Moneta provides a standard interface for interacting with various kinds of key/v
|
|
12
12
|
* Expiration for all stores (Added via proxy `Moneta::Expires` if not supported natively)
|
13
13
|
* Atomic incrementation and decrementation for most stores (Method `#increment` and `#decrement`)
|
14
14
|
* Includes a very simple key/value server (`Moneta::Server`) and client (`Moneta::Adapters::Client`)
|
15
|
-
* Integration with [Rails](http://rubyonrails.org/), [Rack](http://rack.github.com/)
|
15
|
+
* Integration with [Rails](http://rubyonrails.org/), [Rack](http://rack.github.com/), [Sinatra](http://sinatrarb.com/) and [Rack-Cache](https://github.com/rtomayko/rack-cache)
|
16
16
|
|
17
17
|
Moneta is tested thoroughly using [Travis-CI](http://travis-ci.org/minad/moneta).
|
18
18
|
|
@@ -56,8 +56,10 @@ Out of the box, it supports the following backends:
|
|
56
56
|
* Document databases:
|
57
57
|
* CouchDB (`:Couch`)
|
58
58
|
* MongoDB (`:Mongo`)
|
59
|
+
* Moneta network protocols:
|
60
|
+
* Moneta key/value client (`:Client` works with `Moneta::Server`)
|
61
|
+
* Moneta HTTP/REST client (`:RestClient` works with `Rack::MonetaRest`)
|
59
62
|
* Other
|
60
|
-
* Moneta key/value server client (`:Client` works with `Moneta::Server`)
|
61
63
|
* Fog cloud storage which supports Amazon S3, Rackspace, etc. (`:Fog`)
|
62
64
|
* Storage which doesn't store anything (`:Null`)
|
63
65
|
|
@@ -309,11 +311,21 @@ short_lived_store['key'] = 'value'
|
|
309
311
|
|
310
312
|
## Framework Integration
|
311
313
|
|
312
|
-
Inspired by [redis-store](https://github.com/jodosha/redis-store) there exist integration classes for [Rails](http://rubyonrails.org/), [Rack](http://rack.github.com/) and [Rack-Cache](https://github.com/rtomayko/rack-cache).
|
314
|
+
Inspired by [redis-store](https://github.com/jodosha/redis-store) there exist integration classes for [Rails](http://rubyonrails.org/), [Rack](http://rack.github.com/) and [Rack-Cache](https://github.com/rtomayko/rack-cache). You can also use all the Rack middlewares together with the [Sinatra](http://sinatrarb.com/) framework. There exist the following integration classes:
|
315
|
+
|
316
|
+
* Rack and Sinatra
|
317
|
+
* `Rack::Session::Moneta` is a Rack middleware to use Moneta for storing sessions
|
318
|
+
* `Rack::MonetaStore` is a Rack middleware which places a Moneta store in the environment and enables per-request caching
|
319
|
+
* `Rack::MonetaCookies` is a Rack middleware which uses Moneta to store cookies
|
320
|
+
* `Rack::MonetaRest` is a Rack application which exposes a Moneta store via REST/HTTP
|
321
|
+
* `Rack::Cache::Moneta` provides meta and entity stores for Rack-Cache
|
322
|
+
* Rails
|
323
|
+
* `ActionDispatch::Session::MonetaStore` is a Rails middleware to use Moneta for storing sessions
|
324
|
+
* `ActiveSupport::Cache::MonetaStore` is a Rails cache implementation which uses a Moneta store as backend
|
313
325
|
|
314
326
|
### Rack session store
|
315
327
|
|
316
|
-
|
328
|
+
You can use Moneta as a [Rack](http://rack.github.com/) session store. Use it in your `config.ru` like this:
|
317
329
|
|
318
330
|
~~~ ruby
|
319
331
|
require 'rack/session/moneta'
|
@@ -331,9 +343,51 @@ use Rack::Session::Moneta do
|
|
331
343
|
end
|
332
344
|
~~~
|
333
345
|
|
346
|
+
### Rack Moneta middleware
|
347
|
+
|
348
|
+
There is a simple middleware which places a Moneta store in the Rack environment at `env['rack.moneta_store']`. It supports per-request
|
349
|
+
caching if you add the option `:cache => true`. Use it in your `config.ru` like this:
|
350
|
+
|
351
|
+
~~~ ruby
|
352
|
+
# Add Rack::MonetaStore somewhere in your rack stack
|
353
|
+
use Rack::MonetaStore, :Memory, :cache => true
|
354
|
+
|
355
|
+
run lambda do |env|
|
356
|
+
env['rack.moneta_store'] # is a Moneta store with per-request caching
|
357
|
+
end
|
358
|
+
|
359
|
+
# Pass it a block like the one passed to Moneta.build
|
360
|
+
use Rack::MonetaStore do
|
361
|
+
use :Transformer, :value => :zlib
|
362
|
+
adapter :Cookie
|
363
|
+
end
|
364
|
+
|
365
|
+
run lambda do |env|
|
366
|
+
env['rack.moneta_store'] # is a Moneta store without caching
|
367
|
+
end
|
368
|
+
~~~
|
369
|
+
|
370
|
+
### Rack REST server
|
371
|
+
|
372
|
+
If you want to expose your Moneta key/value store via HTTP, you can use the Rack/Moneta REST service. Use it in your `config.ru` like this:
|
373
|
+
|
374
|
+
~~~ ruby
|
375
|
+
require 'rack/moneta_rest'
|
376
|
+
|
377
|
+
map '/moneta' do
|
378
|
+
run Rack::MonetaRest.new(:Memory)
|
379
|
+
end
|
380
|
+
|
381
|
+
# Or pass it a block like the one passed to Moneta.build
|
382
|
+
run Rack::MonetaRest.new do
|
383
|
+
use :Transformer, :value => :zlib
|
384
|
+
adapter :Memory
|
385
|
+
end
|
386
|
+
~~~
|
387
|
+
|
334
388
|
### Rack cache
|
335
389
|
|
336
|
-
|
390
|
+
You can use Moneta as a [Rack-Cache](https://github.com/rtomayko/rack-cache) store. Use it in your `config.ru` like this:
|
337
391
|
|
338
392
|
~~~ ruby
|
339
393
|
require 'rack/cache/moneta'
|
data/lib/moneta.rb
CHANGED
@@ -40,6 +40,7 @@ module Moneta
|
|
40
40
|
autoload :Null, 'moneta/adapters/null'
|
41
41
|
autoload :PStore, 'moneta/adapters/pstore'
|
42
42
|
autoload :Redis, 'moneta/adapters/redis'
|
43
|
+
autoload :RestClient, 'moneta/adapters/restclient'
|
43
44
|
autoload :Riak, 'moneta/adapters/riak'
|
44
45
|
autoload :SDBM, 'moneta/adapters/sdbm'
|
45
46
|
autoload :Sequel, 'moneta/adapters/sequel'
|
@@ -93,7 +94,7 @@ module Moneta
|
|
93
94
|
# FIXME: Couch should work only with :marshal but this raises an error on 1.9
|
94
95
|
transformer[:key] << :base64
|
95
96
|
transformer[:value] << :base64
|
96
|
-
when :Riak
|
97
|
+
when :Riak, :RestClient
|
97
98
|
# Riak accepts only utf-8 keys over the http interface
|
98
99
|
# We use base64 encoding therefore.
|
99
100
|
transformer[:key] << :base64
|
@@ -125,8 +126,9 @@ module Moneta
|
|
125
126
|
end
|
126
127
|
end
|
127
128
|
|
128
|
-
# Configure your own Moneta proxy stack
|
129
|
+
# Configure your own Moneta proxy stack
|
129
130
|
#
|
131
|
+
# @yieldparam Builder block
|
130
132
|
# @return [Moneta store] newly created Moneta store
|
131
133
|
#
|
132
134
|
# @example Moneta builder
|
@@ -1,6 +1,6 @@
|
|
1
1
|
module Moneta
|
2
2
|
module Adapters
|
3
|
-
# Cookie backend used by `Rack::MonetaCookies`
|
3
|
+
# Cookie backend used by the middleware `Rack::MonetaCookies`
|
4
4
|
# @api public
|
5
5
|
class Cookie < Memory
|
6
6
|
attr_reader :cookies
|
@@ -32,6 +32,8 @@ module Moneta
|
|
32
32
|
self
|
33
33
|
end
|
34
34
|
|
35
|
+
# Reset the cookie store
|
36
|
+
# This method is used by the middleware.
|
35
37
|
def reset(cookies)
|
36
38
|
@cookies, @hash = {}, cookies
|
37
39
|
end
|
@@ -17,14 +17,14 @@ module Moneta
|
|
17
17
|
# (see Proxy#key?)
|
18
18
|
def key?(key, options = {})
|
19
19
|
@db.get(key) != nil
|
20
|
-
rescue RestClient::ResourceNotFound
|
20
|
+
rescue ::RestClient::ResourceNotFound
|
21
21
|
false
|
22
22
|
end
|
23
23
|
|
24
24
|
# (see Proxy#load)
|
25
25
|
def load(key, options = {})
|
26
26
|
@db.get(key)['value']
|
27
|
-
rescue RestClient::ResourceNotFound
|
27
|
+
rescue ::RestClient::ResourceNotFound
|
28
28
|
nil
|
29
29
|
end
|
30
30
|
|
@@ -33,11 +33,11 @@ module Moneta
|
|
33
33
|
doc = {'_id' => key, 'value' => value}
|
34
34
|
begin
|
35
35
|
doc['_rev'] = @db.get(key)['_rev']
|
36
|
-
rescue RestClient::ResourceNotFound
|
36
|
+
rescue ::RestClient::ResourceNotFound
|
37
37
|
end
|
38
38
|
@db.save_doc(doc)
|
39
39
|
value
|
40
|
-
rescue RestClient::RequestFailed
|
40
|
+
rescue ::RestClient::RequestFailed
|
41
41
|
value
|
42
42
|
end
|
43
43
|
|
@@ -46,7 +46,7 @@ module Moneta
|
|
46
46
|
value = @db.get(key)
|
47
47
|
@db.delete_doc('_id' => value['_id'], '_rev' => value['_rev'])
|
48
48
|
value['value']
|
49
|
-
rescue RestClient::ResourceNotFound
|
49
|
+
rescue ::RestClient::ResourceNotFound
|
50
50
|
nil
|
51
51
|
end
|
52
52
|
|
data/lib/moneta/adapters/null.rb
CHANGED
@@ -0,0 +1,47 @@
|
|
1
|
+
require 'httpi'
|
2
|
+
|
3
|
+
module Moneta
|
4
|
+
module Adapters
|
5
|
+
# Moneta rest client backend which works together with `Rack::MonetaRest`
|
6
|
+
# @api public
|
7
|
+
class RestClient
|
8
|
+
include Defaults
|
9
|
+
|
10
|
+
# @param [Hash] options
|
11
|
+
# @option options [String] :url URL
|
12
|
+
def initialize(options = {})
|
13
|
+
raise ArgumentError, 'Option :url is required' unless @url = options[:url]
|
14
|
+
end
|
15
|
+
|
16
|
+
# (see Proxy#key?)
|
17
|
+
def key?(key, options = {})
|
18
|
+
response = HTTPI.head(@url + key)
|
19
|
+
response.code == 200
|
20
|
+
end
|
21
|
+
|
22
|
+
# (see Proxy#load)
|
23
|
+
def load(key, options = {})
|
24
|
+
response = HTTPI.get(@url + key)
|
25
|
+
response.code == 200 ? response.body : nil
|
26
|
+
end
|
27
|
+
|
28
|
+
# (see Proxy#store)
|
29
|
+
def store(key, value, options = {})
|
30
|
+
HTTPI.post(@url + key, value)
|
31
|
+
value
|
32
|
+
end
|
33
|
+
|
34
|
+
# (see Proxy#delete)
|
35
|
+
def delete(key, options = {})
|
36
|
+
response = HTTPI.delete(@url + key)
|
37
|
+
response.code == 200 ? response.body : nil
|
38
|
+
end
|
39
|
+
|
40
|
+
# (see Proxy#clear)
|
41
|
+
def clear(options = {})
|
42
|
+
HTTPI.delete(@url)
|
43
|
+
self
|
44
|
+
end
|
45
|
+
end
|
46
|
+
end
|
47
|
+
end
|
data/lib/moneta/builder.rb
CHANGED
@@ -2,6 +2,7 @@ module Moneta
|
|
2
2
|
# Builder implements the DSL to build a stack of Moneta store proxies
|
3
3
|
# @api private
|
4
4
|
class Builder
|
5
|
+
# @yieldparam Builder dsl code block
|
5
6
|
def initialize(&block)
|
6
7
|
raise ArgumentError, 'No block given' unless block_given?
|
7
8
|
@proxies = []
|
@@ -9,6 +10,7 @@ module Moneta
|
|
9
10
|
end
|
10
11
|
|
11
12
|
# Build proxy stack
|
13
|
+
#
|
12
14
|
# @return [Object] Generated Moneta proxy stack
|
13
15
|
# @api public
|
14
16
|
def build
|
data/lib/moneta/cache.rb
CHANGED
@@ -15,34 +15,35 @@ module Moneta
|
|
15
15
|
|
16
16
|
# @api private
|
17
17
|
class DSL
|
18
|
-
def initialize(
|
19
|
-
@
|
18
|
+
def initialize(store, &block)
|
19
|
+
@store = store
|
20
20
|
instance_eval(&block)
|
21
21
|
end
|
22
22
|
|
23
23
|
# @api public
|
24
24
|
def backend(store = nil, &block)
|
25
|
-
raise 'Backend already set' if @backend
|
25
|
+
raise 'Backend already set' if @store.backend
|
26
26
|
raise ArgumentError, 'Only argument or block allowed' if store && block
|
27
|
-
@backend = store || Moneta.build(&block)
|
27
|
+
@store.backend = store || Moneta.build(&block)
|
28
28
|
end
|
29
29
|
|
30
30
|
# @api public
|
31
31
|
def cache(store = nil, &block)
|
32
|
-
raise 'Cache already set' if @cache
|
32
|
+
raise 'Cache already set' if @store.cache
|
33
33
|
raise ArgumentError, 'Only argument or block allowed' if store && block
|
34
|
-
@cache = store || Moneta.build(&block)
|
35
|
-
end
|
36
|
-
|
37
|
-
def result
|
38
|
-
[@cache, @backend]
|
34
|
+
@store.cache = store || Moneta.build(&block)
|
39
35
|
end
|
40
36
|
end
|
41
37
|
|
42
|
-
|
38
|
+
attr_accessor :cache, :backend
|
43
39
|
|
40
|
+
# @param [Hash] options Options hash
|
41
|
+
# @option options [Moneta store] :cache Moneta store used as cache
|
42
|
+
# @option options [Moneta store] :backend Moneta store used as backend
|
43
|
+
# @yieldparam Builder block
|
44
44
|
def initialize(options = {}, &block)
|
45
|
-
@cache, @backend =
|
45
|
+
@cache, @backend = options[:cache], options[:backend]
|
46
|
+
DSL.new(self, &block) if block_given?
|
46
47
|
end
|
47
48
|
|
48
49
|
# (see Proxy#key?)
|
data/lib/moneta/expires.rb
CHANGED
@@ -14,6 +14,7 @@ module Moneta
|
|
14
14
|
@expires = options[:expires]
|
15
15
|
end
|
16
16
|
|
17
|
+
# (see Proxy#key?)
|
17
18
|
def key?(key, options = {})
|
18
19
|
# Transformer might raise exception
|
19
20
|
load_entry(key, options) != nil
|
@@ -22,12 +23,14 @@ module Moneta
|
|
22
23
|
super(key, options)
|
23
24
|
end
|
24
25
|
|
26
|
+
# (see Proxy#load)
|
25
27
|
def load(key, options = {})
|
26
28
|
return super if options.include?(:raw)
|
27
29
|
value, expires = load_entry(key, options)
|
28
30
|
value
|
29
31
|
end
|
30
32
|
|
33
|
+
# (see Proxy#store)
|
31
34
|
def store(key, value, options = {})
|
32
35
|
return super if options.include?(:raw)
|
33
36
|
expires = options.include?(:expires) && (options = options.dup; options.delete(:expires))
|
@@ -41,6 +44,7 @@ module Moneta
|
|
41
44
|
value
|
42
45
|
end
|
43
46
|
|
47
|
+
# (see Proxy#delete)
|
44
48
|
def delete(key, options = {})
|
45
49
|
return super if options.include?(:raw)
|
46
50
|
value, expires = super
|
data/lib/moneta/mixins.rb
CHANGED
@@ -1,11 +1,18 @@
|
|
1
1
|
module Moneta
|
2
2
|
# @api private
|
3
3
|
module OptionSupport
|
4
|
+
# Return Moneta store with default options
|
5
|
+
#
|
6
|
+
# @param [Hash] options Options to merge
|
7
|
+
# @return [OptionMerger]
|
4
8
|
# @api public
|
5
9
|
def with(options)
|
6
10
|
OptionMerger.new(self, options)
|
7
11
|
end
|
8
12
|
|
13
|
+
# Return Moneta store with default option :raw => true
|
14
|
+
#
|
15
|
+
# @return [OptionMerger]
|
9
16
|
# @api public
|
10
17
|
def raw
|
11
18
|
@raw_store ||=
|
@@ -16,11 +23,19 @@ module Moneta
|
|
16
23
|
end
|
17
24
|
end
|
18
25
|
|
26
|
+
# Return Moneta store with default prefix option
|
27
|
+
#
|
28
|
+
# @param [String] prefix Key prefix
|
29
|
+
# @return [OptionMerger]
|
19
30
|
# @api public
|
20
31
|
def prefix(prefix)
|
21
32
|
with(:prefix => prefix, :except => :clear)
|
22
33
|
end
|
23
34
|
|
35
|
+
# Return Moneta store with default expiration time
|
36
|
+
#
|
37
|
+
# @param [Integer] expires Default expiration time
|
38
|
+
# @return [OptionMerger]
|
24
39
|
# @api public
|
25
40
|
def expires(expires)
|
26
41
|
with(:expires => expires, :only => [:store, :increment])
|
@@ -35,8 +50,8 @@ module Moneta
|
|
35
50
|
# Exists the value with key
|
36
51
|
#
|
37
52
|
# @param [Object] key
|
38
|
-
# @return [Boolean]
|
39
53
|
# @param [Hash] options
|
54
|
+
# @return [Boolean]
|
40
55
|
# @api public
|
41
56
|
def key?(key, options = {})
|
42
57
|
load(key, options) != nil
|
@@ -44,11 +59,10 @@ module Moneta
|
|
44
59
|
|
45
60
|
# Atomically increment integer value with key
|
46
61
|
#
|
47
|
-
# Not every Moneta store implements this method,
|
48
|
-
# a NotImplementedError if it is not supported.
|
49
|
-
#
|
50
62
|
# This method also accepts negative amounts.
|
51
63
|
#
|
64
|
+
# @note Not every Moneta store implements this method,
|
65
|
+
# a NotImplementedError is raised if it is not supported.
|
52
66
|
# @param [Object] key
|
53
67
|
# @param [Integer] amount
|
54
68
|
# @param [Hash] options
|
data/lib/moneta/optionmerger.rb
CHANGED
data/lib/moneta/server.rb
CHANGED
@@ -19,10 +19,16 @@ module Moneta
|
|
19
19
|
@running = false
|
20
20
|
end
|
21
21
|
|
22
|
+
# Is the server running
|
23
|
+
#
|
24
|
+
# @return [Boolean] true if the server is running
|
22
25
|
def running?
|
23
26
|
@running
|
24
27
|
end
|
25
28
|
|
29
|
+
# Run the server
|
30
|
+
#
|
31
|
+
# @note This method blocks!
|
26
32
|
def run
|
27
33
|
raise 'Already running' if @running
|
28
34
|
@stop = false
|
@@ -36,6 +42,7 @@ module Moneta
|
|
36
42
|
end
|
37
43
|
end
|
38
44
|
|
45
|
+
# Stop the server
|
39
46
|
def stop
|
40
47
|
raise 'Not running' unless @running
|
41
48
|
@stop = true
|
data/lib/moneta/shared.rb
CHANGED
data/lib/moneta/stack.rb
CHANGED
@@ -17,10 +17,8 @@ module Moneta
|
|
17
17
|
|
18
18
|
# @api private
|
19
19
|
class DSL
|
20
|
-
|
21
|
-
|
22
|
-
def initialize(options, &block)
|
23
|
-
@stack = options[:stack].to_a
|
20
|
+
def initialize(stack, &block)
|
21
|
+
@stack = stack
|
24
22
|
instance_eval(&block)
|
25
23
|
end
|
26
24
|
|
@@ -34,8 +32,12 @@ module Moneta
|
|
34
32
|
|
35
33
|
attr_reader :stack
|
36
34
|
|
35
|
+
# @param [Hash] options Options hash
|
36
|
+
# @option options [Array] :stack Array of Moneta stores
|
37
|
+
# @yieldparam Builder block
|
37
38
|
def initialize(options = {}, &block)
|
38
|
-
@stack =
|
39
|
+
@stack = options[:stack].to_a
|
40
|
+
DSL.new(@stack, &block) if block_given?
|
39
41
|
end
|
40
42
|
|
41
43
|
# (see Proxy#key?)
|
data/lib/moneta/version.rb
CHANGED
data/lib/moneta/wrapper.rb
CHANGED
@@ -2,30 +2,37 @@ module Moneta
|
|
2
2
|
# Wraps the calls to the adapter
|
3
3
|
# @api public
|
4
4
|
class Wrapper < Proxy
|
5
|
+
# (see Proxy#key?)
|
5
6
|
def key?(key, options = {})
|
6
7
|
wrap(:key?, key, options) { super }
|
7
8
|
end
|
8
9
|
|
10
|
+
# (see Proxy#load)
|
9
11
|
def load(key, options = {})
|
10
12
|
wrap(:load, key, options) { super }
|
11
13
|
end
|
12
14
|
|
15
|
+
# (see Proxy#store)
|
13
16
|
def store(key, value, options = {})
|
14
17
|
wrap(:store, key, value, options) { super }
|
15
18
|
end
|
16
19
|
|
20
|
+
# (see Proxy#delete)
|
17
21
|
def delete(key, options = {})
|
18
22
|
wrap(:delete, key, options) { super }
|
19
23
|
end
|
20
24
|
|
25
|
+
# (see Proxy#increment)
|
21
26
|
def increment(key, amount = 1, options = {})
|
22
27
|
wrap(:increment, key, amount, options) { super }
|
23
28
|
end
|
24
29
|
|
30
|
+
# (see Proxy#clear)
|
25
31
|
def clear(options = {})
|
26
32
|
wrap(:clear, options) { super }
|
27
33
|
end
|
28
34
|
|
35
|
+
# (see Proxy#close)
|
29
36
|
def close
|
30
37
|
wrap(:close) { super }
|
31
38
|
end
|
data/lib/rack/moneta_cookies.rb
CHANGED
@@ -47,7 +47,7 @@ module Rack
|
|
47
47
|
|
48
48
|
def call(env)
|
49
49
|
stores = @pool.pop || @builder.build
|
50
|
-
env['rack.request.cookie_hash'] = stores.last
|
50
|
+
env['rack.moneta_cookies'] = env['rack.request.cookie_hash'] = stores.last
|
51
51
|
env['rack.request.cookie_string'] = env['HTTP_COOKIE']
|
52
52
|
stores.first.reset(Rack::Utils.parse_query(env['HTTP_COOKIE']))
|
53
53
|
status, headers, body = @app.call(env)
|
data/lib/rack/moneta_rest.rb
CHANGED
@@ -1,13 +1,28 @@
|
|
1
1
|
require 'moneta'
|
2
2
|
|
3
3
|
module Rack
|
4
|
+
# A Rack application which provides a REST interface to a Moneta store.
|
5
|
+
#
|
6
|
+
# @example config.ru
|
7
|
+
# map '/moneta' do
|
8
|
+
# run Rack::MonetaRest.new(:Memory)
|
9
|
+
# end
|
10
|
+
#
|
11
|
+
# @example config.ru
|
12
|
+
# # Pass it a block like the one passed to Moneta.build
|
13
|
+
# run Rack::MonetaRest.new do
|
14
|
+
# use :Transformer, :value => :zlib
|
15
|
+
# adapter :Memory
|
16
|
+
# end
|
17
|
+
#
|
18
|
+
# @api public
|
4
19
|
class MonetaRest
|
5
20
|
def initialize(store = nil, options = {}, &block)
|
6
21
|
if block
|
7
|
-
raise ArgumentError, 'Use either block or options' unless options.
|
22
|
+
raise ArgumentError, 'Use either block or options' unless options.empty?
|
8
23
|
@store = ::Moneta.build(&block)
|
9
24
|
else
|
10
|
-
raise ArgumentError, '
|
25
|
+
raise ArgumentError, 'Block or argument store is required' unless @store = store
|
11
26
|
@store = ::Moneta.new(@store, options) if Symbol === @store
|
12
27
|
end
|
13
28
|
end
|
@@ -16,19 +31,27 @@ module Rack
|
|
16
31
|
key = env['PATH_INFO'][1..-1]
|
17
32
|
case env['REQUEST_METHOD']
|
18
33
|
when 'HEAD'
|
19
|
-
if
|
20
|
-
respond(
|
34
|
+
if key.empty?
|
35
|
+
respond(400, 'Empty key')
|
36
|
+
elsif @store.key?(key)
|
37
|
+
empty(200)
|
21
38
|
else
|
22
39
|
empty(404)
|
23
40
|
end
|
24
41
|
when 'GET'
|
25
|
-
if
|
42
|
+
if key.empty?
|
43
|
+
respond(400, 'Empty key')
|
44
|
+
elsif value = @store[key]
|
26
45
|
respond(200, value)
|
27
46
|
else
|
28
47
|
empty(404)
|
29
48
|
end
|
30
49
|
when 'POST', 'PUT'
|
31
|
-
|
50
|
+
if key.empty?
|
51
|
+
respond(400, 'Empty key')
|
52
|
+
else
|
53
|
+
respond(200, @store[key] = env['rack.input'].read)
|
54
|
+
end
|
32
55
|
when 'DELETE'
|
33
56
|
if key.empty?
|
34
57
|
@store.clear
|
@@ -37,10 +60,10 @@ module Rack
|
|
37
60
|
respond(200, @store.delete(key))
|
38
61
|
end
|
39
62
|
else
|
40
|
-
|
63
|
+
respond(400, 'Bad method')
|
41
64
|
end
|
42
65
|
rescue => ex
|
43
|
-
respond(500, ex.message)
|
66
|
+
respond(500, "Exception: #{ex.message}")
|
44
67
|
end
|
45
68
|
|
46
69
|
private
|
@@ -0,0 +1,45 @@
|
|
1
|
+
require 'moneta'
|
2
|
+
|
3
|
+
module Rack
|
4
|
+
# A Rack middleware that inserts a Moneta store in the environment
|
5
|
+
# and supports per-request caching via the the option `:cache => true`.
|
6
|
+
#
|
7
|
+
# @example config.ru
|
8
|
+
# # Add Rack::MonetaStore somewhere in your rack stack
|
9
|
+
# use Rack::MonetaStore, :Memory, :cache => true
|
10
|
+
#
|
11
|
+
# run lambda do |env|
|
12
|
+
# env['rack.moneta_store'] # is a Moneta store with per-request caching
|
13
|
+
# end
|
14
|
+
#
|
15
|
+
# @example config.ru
|
16
|
+
# # Pass it a block like the one passed to Moneta.build
|
17
|
+
# use Rack::MonetaStore do
|
18
|
+
# use :Transformer, :value => :zlib
|
19
|
+
# adapter :Cookie
|
20
|
+
# end
|
21
|
+
#
|
22
|
+
# run lambda do |env|
|
23
|
+
# env['rack.moneta_store'] # is a Moneta store without caching
|
24
|
+
# end
|
25
|
+
#
|
26
|
+
# @api public
|
27
|
+
class MonetaStore
|
28
|
+
def initialize(app, store = nil, options = {}, &block)
|
29
|
+
@app = app
|
30
|
+
@cache = options.delete(:cache)
|
31
|
+
if block
|
32
|
+
raise ArgumentError, 'Use either block or options' unless options.empty?
|
33
|
+
@store = ::Moneta.build(&block)
|
34
|
+
else
|
35
|
+
raise ArgumentError, 'Block or argument store is required' unless @store = store
|
36
|
+
@store = ::Moneta.new(@store, options) if Symbol === @store
|
37
|
+
end
|
38
|
+
end
|
39
|
+
|
40
|
+
def call(env)
|
41
|
+
env['rack.moneta_store'] = @cache ? ::Moneta::Cache.new(:cache => ::Moneta::Adapters::Memory.new, :backend => @store) : @store
|
42
|
+
@app.call(env)
|
43
|
+
end
|
44
|
+
end
|
45
|
+
end
|
data/lib/rack/session/moneta.rb
CHANGED
@@ -14,7 +14,7 @@ module Rack
|
|
14
14
|
raise ArgumentError, 'Use either block or option :store' if options[:store]
|
15
15
|
@pool = ::Moneta.build(&block)
|
16
16
|
else
|
17
|
-
raise ArgumentError, '
|
17
|
+
raise ArgumentError, 'Block or option :store is required' unless @pool = options[:store]
|
18
18
|
@pool = ::Moneta.new(@pool, :expires => true) if Symbol === @pool
|
19
19
|
end
|
20
20
|
@mutex = Mutex.new
|
data/spec/generate.rb
CHANGED
@@ -129,6 +129,12 @@ end
|
|
129
129
|
:options => ":file => File.join(make_tempdir, 'simple_client_unix')",
|
130
130
|
:specs => STANDARD_SPECS
|
131
131
|
},
|
132
|
+
'simple_restclient' => {
|
133
|
+
:preamble => "start_restserver\n",
|
134
|
+
:store => :RestClient,
|
135
|
+
:options => ":url => 'http://localhost:8808/moneta/'",
|
136
|
+
:specs => STANDARD_SPECS.without_increment
|
137
|
+
},
|
132
138
|
'simple_memory' => {
|
133
139
|
:store => :Memory,
|
134
140
|
:specs => STANDARD_SPECS.without_persist
|
@@ -844,6 +850,11 @@ end
|
|
844
850
|
:build => "Moneta::Adapters::Client.new",
|
845
851
|
:specs => ADAPTER_SPECS
|
846
852
|
},
|
853
|
+
'adapter_restclient' => {
|
854
|
+
:preamble => "start_restserver\n",
|
855
|
+
:build => "Moneta::Adapters::RestClient.new(:url => 'http://localhost:8808/moneta/')",
|
856
|
+
:specs => ADAPTER_SPECS.without_increment
|
857
|
+
},
|
847
858
|
'adapter_cassandra' => {
|
848
859
|
:build => "Moneta::Adapters::Cassandra.new(:keyspace => 'adapter_cassandra')",
|
849
860
|
:specs => ADAPTER_SPECS.without_increment.with_expires,
|
data/spec/helper.rb
CHANGED
@@ -9,19 +9,6 @@ RSpec::Core::Formatters::ProgressFormatter.class_eval do
|
|
9
9
|
end
|
10
10
|
end
|
11
11
|
|
12
|
-
module Moneta
|
13
|
-
class Transformer < Proxy
|
14
|
-
class << self
|
15
|
-
alias_method :verbose_new, :new
|
16
|
-
|
17
|
-
def new(adapter, options = {})
|
18
|
-
options[:quiet] = true
|
19
|
-
verbose_new(adapter, options)
|
20
|
-
end
|
21
|
-
end
|
22
|
-
end
|
23
|
-
end
|
24
|
-
|
25
12
|
class Value
|
26
13
|
attr_accessor :x
|
27
14
|
def initialize(x)
|
@@ -41,6 +28,36 @@ class Value
|
|
41
28
|
end
|
42
29
|
end
|
43
30
|
|
31
|
+
def start_restserver
|
32
|
+
require 'rack'
|
33
|
+
require 'webrick'
|
34
|
+
require 'httpi'
|
35
|
+
require 'rack/moneta_rest'
|
36
|
+
|
37
|
+
HTTPI.log = false
|
38
|
+
|
39
|
+
# Keep webrick quiet
|
40
|
+
::WEBrick::HTTPServer.class_eval do
|
41
|
+
def access_log(config, req, res); end
|
42
|
+
end
|
43
|
+
::WEBrick::BasicLog.class_eval do
|
44
|
+
def log(level, data); end
|
45
|
+
end
|
46
|
+
|
47
|
+
Thread.start do
|
48
|
+
Rack::Server.start(:app => Rack::Builder.app do
|
49
|
+
use Rack::Lint
|
50
|
+
map '/moneta' do
|
51
|
+
run Rack::MonetaRest.new(:store => :Memory)
|
52
|
+
end
|
53
|
+
end,
|
54
|
+
:environment => :none,
|
55
|
+
:server => :webrick,
|
56
|
+
:Port => 8808)
|
57
|
+
end
|
58
|
+
sleep 1
|
59
|
+
end
|
60
|
+
|
44
61
|
def start_server(*args)
|
45
62
|
server = Moneta::Server.new(*args)
|
46
63
|
Thread.new { server.run }
|
@@ -0,0 +1,20 @@
|
|
1
|
+
# Generated by generate.rb
|
2
|
+
require 'helper'
|
3
|
+
|
4
|
+
describe_moneta "adapter_restclient" do
|
5
|
+
start_restserver
|
6
|
+
def new_store
|
7
|
+
Moneta::Adapters::RestClient.new(:url => 'http://localhost:8808/moneta/')
|
8
|
+
end
|
9
|
+
|
10
|
+
def load_value(value)
|
11
|
+
Marshal.load(value)
|
12
|
+
end
|
13
|
+
|
14
|
+
include_context 'setup_store'
|
15
|
+
it_should_behave_like 'not_increment'
|
16
|
+
it_should_behave_like 'null_stringkey_stringvalue'
|
17
|
+
it_should_behave_like 'persist_stringkey_stringvalue'
|
18
|
+
it_should_behave_like 'returndifferent_stringkey_stringvalue'
|
19
|
+
it_should_behave_like 'store_stringkey_stringvalue'
|
20
|
+
end
|
@@ -0,0 +1,145 @@
|
|
1
|
+
# Generated by generate.rb
|
2
|
+
require 'helper'
|
3
|
+
|
4
|
+
describe_moneta "simple_restclient" do
|
5
|
+
start_restserver
|
6
|
+
def new_store
|
7
|
+
Moneta.new(:RestClient, :url => 'http://localhost:8808/moneta/', :logger => {:out => File.open(File.join(make_tempdir, 'simple_restclient.log'), 'a')})
|
8
|
+
end
|
9
|
+
|
10
|
+
def load_value(value)
|
11
|
+
Marshal.load(value)
|
12
|
+
end
|
13
|
+
|
14
|
+
include_context 'setup_store'
|
15
|
+
it_should_behave_like 'marshallable_key'
|
16
|
+
it_should_behave_like 'marshallable_value'
|
17
|
+
it_should_behave_like 'not_increment'
|
18
|
+
it_should_behave_like 'null_objectkey_objectvalue'
|
19
|
+
it_should_behave_like 'null_objectkey_stringvalue'
|
20
|
+
it_should_behave_like 'null_objectkey_hashvalue'
|
21
|
+
it_should_behave_like 'null_objectkey_booleanvalue'
|
22
|
+
it_should_behave_like 'null_objectkey_nilvalue'
|
23
|
+
it_should_behave_like 'null_objectkey_integervalue'
|
24
|
+
it_should_behave_like 'null_stringkey_objectvalue'
|
25
|
+
it_should_behave_like 'null_stringkey_stringvalue'
|
26
|
+
it_should_behave_like 'null_stringkey_hashvalue'
|
27
|
+
it_should_behave_like 'null_stringkey_booleanvalue'
|
28
|
+
it_should_behave_like 'null_stringkey_nilvalue'
|
29
|
+
it_should_behave_like 'null_stringkey_integervalue'
|
30
|
+
it_should_behave_like 'null_hashkey_objectvalue'
|
31
|
+
it_should_behave_like 'null_hashkey_stringvalue'
|
32
|
+
it_should_behave_like 'null_hashkey_hashvalue'
|
33
|
+
it_should_behave_like 'null_hashkey_booleanvalue'
|
34
|
+
it_should_behave_like 'null_hashkey_nilvalue'
|
35
|
+
it_should_behave_like 'null_hashkey_integervalue'
|
36
|
+
it_should_behave_like 'null_booleankey_objectvalue'
|
37
|
+
it_should_behave_like 'null_booleankey_stringvalue'
|
38
|
+
it_should_behave_like 'null_booleankey_hashvalue'
|
39
|
+
it_should_behave_like 'null_booleankey_booleanvalue'
|
40
|
+
it_should_behave_like 'null_booleankey_nilvalue'
|
41
|
+
it_should_behave_like 'null_booleankey_integervalue'
|
42
|
+
it_should_behave_like 'null_nilkey_objectvalue'
|
43
|
+
it_should_behave_like 'null_nilkey_stringvalue'
|
44
|
+
it_should_behave_like 'null_nilkey_hashvalue'
|
45
|
+
it_should_behave_like 'null_nilkey_booleanvalue'
|
46
|
+
it_should_behave_like 'null_nilkey_nilvalue'
|
47
|
+
it_should_behave_like 'null_nilkey_integervalue'
|
48
|
+
it_should_behave_like 'null_integerkey_objectvalue'
|
49
|
+
it_should_behave_like 'null_integerkey_stringvalue'
|
50
|
+
it_should_behave_like 'null_integerkey_hashvalue'
|
51
|
+
it_should_behave_like 'null_integerkey_booleanvalue'
|
52
|
+
it_should_behave_like 'null_integerkey_nilvalue'
|
53
|
+
it_should_behave_like 'null_integerkey_integervalue'
|
54
|
+
it_should_behave_like 'persist_objectkey_objectvalue'
|
55
|
+
it_should_behave_like 'persist_objectkey_stringvalue'
|
56
|
+
it_should_behave_like 'persist_objectkey_hashvalue'
|
57
|
+
it_should_behave_like 'persist_objectkey_booleanvalue'
|
58
|
+
it_should_behave_like 'persist_objectkey_nilvalue'
|
59
|
+
it_should_behave_like 'persist_objectkey_integervalue'
|
60
|
+
it_should_behave_like 'persist_stringkey_objectvalue'
|
61
|
+
it_should_behave_like 'persist_stringkey_stringvalue'
|
62
|
+
it_should_behave_like 'persist_stringkey_hashvalue'
|
63
|
+
it_should_behave_like 'persist_stringkey_booleanvalue'
|
64
|
+
it_should_behave_like 'persist_stringkey_nilvalue'
|
65
|
+
it_should_behave_like 'persist_stringkey_integervalue'
|
66
|
+
it_should_behave_like 'persist_hashkey_objectvalue'
|
67
|
+
it_should_behave_like 'persist_hashkey_stringvalue'
|
68
|
+
it_should_behave_like 'persist_hashkey_hashvalue'
|
69
|
+
it_should_behave_like 'persist_hashkey_booleanvalue'
|
70
|
+
it_should_behave_like 'persist_hashkey_nilvalue'
|
71
|
+
it_should_behave_like 'persist_hashkey_integervalue'
|
72
|
+
it_should_behave_like 'persist_booleankey_objectvalue'
|
73
|
+
it_should_behave_like 'persist_booleankey_stringvalue'
|
74
|
+
it_should_behave_like 'persist_booleankey_hashvalue'
|
75
|
+
it_should_behave_like 'persist_booleankey_booleanvalue'
|
76
|
+
it_should_behave_like 'persist_booleankey_nilvalue'
|
77
|
+
it_should_behave_like 'persist_booleankey_integervalue'
|
78
|
+
it_should_behave_like 'persist_nilkey_objectvalue'
|
79
|
+
it_should_behave_like 'persist_nilkey_stringvalue'
|
80
|
+
it_should_behave_like 'persist_nilkey_hashvalue'
|
81
|
+
it_should_behave_like 'persist_nilkey_booleanvalue'
|
82
|
+
it_should_behave_like 'persist_nilkey_nilvalue'
|
83
|
+
it_should_behave_like 'persist_nilkey_integervalue'
|
84
|
+
it_should_behave_like 'persist_integerkey_objectvalue'
|
85
|
+
it_should_behave_like 'persist_integerkey_stringvalue'
|
86
|
+
it_should_behave_like 'persist_integerkey_hashvalue'
|
87
|
+
it_should_behave_like 'persist_integerkey_booleanvalue'
|
88
|
+
it_should_behave_like 'persist_integerkey_nilvalue'
|
89
|
+
it_should_behave_like 'persist_integerkey_integervalue'
|
90
|
+
it_should_behave_like 'returndifferent_objectkey_objectvalue'
|
91
|
+
it_should_behave_like 'returndifferent_objectkey_stringvalue'
|
92
|
+
it_should_behave_like 'returndifferent_objectkey_hashvalue'
|
93
|
+
it_should_behave_like 'returndifferent_stringkey_objectvalue'
|
94
|
+
it_should_behave_like 'returndifferent_stringkey_stringvalue'
|
95
|
+
it_should_behave_like 'returndifferent_stringkey_hashvalue'
|
96
|
+
it_should_behave_like 'returndifferent_hashkey_objectvalue'
|
97
|
+
it_should_behave_like 'returndifferent_hashkey_stringvalue'
|
98
|
+
it_should_behave_like 'returndifferent_hashkey_hashvalue'
|
99
|
+
it_should_behave_like 'returndifferent_booleankey_objectvalue'
|
100
|
+
it_should_behave_like 'returndifferent_booleankey_stringvalue'
|
101
|
+
it_should_behave_like 'returndifferent_booleankey_hashvalue'
|
102
|
+
it_should_behave_like 'returndifferent_nilkey_objectvalue'
|
103
|
+
it_should_behave_like 'returndifferent_nilkey_stringvalue'
|
104
|
+
it_should_behave_like 'returndifferent_nilkey_hashvalue'
|
105
|
+
it_should_behave_like 'returndifferent_integerkey_objectvalue'
|
106
|
+
it_should_behave_like 'returndifferent_integerkey_stringvalue'
|
107
|
+
it_should_behave_like 'returndifferent_integerkey_hashvalue'
|
108
|
+
it_should_behave_like 'store_objectkey_objectvalue'
|
109
|
+
it_should_behave_like 'store_objectkey_stringvalue'
|
110
|
+
it_should_behave_like 'store_objectkey_hashvalue'
|
111
|
+
it_should_behave_like 'store_objectkey_booleanvalue'
|
112
|
+
it_should_behave_like 'store_objectkey_nilvalue'
|
113
|
+
it_should_behave_like 'store_objectkey_integervalue'
|
114
|
+
it_should_behave_like 'store_stringkey_objectvalue'
|
115
|
+
it_should_behave_like 'store_stringkey_stringvalue'
|
116
|
+
it_should_behave_like 'store_stringkey_hashvalue'
|
117
|
+
it_should_behave_like 'store_stringkey_booleanvalue'
|
118
|
+
it_should_behave_like 'store_stringkey_nilvalue'
|
119
|
+
it_should_behave_like 'store_stringkey_integervalue'
|
120
|
+
it_should_behave_like 'store_hashkey_objectvalue'
|
121
|
+
it_should_behave_like 'store_hashkey_stringvalue'
|
122
|
+
it_should_behave_like 'store_hashkey_hashvalue'
|
123
|
+
it_should_behave_like 'store_hashkey_booleanvalue'
|
124
|
+
it_should_behave_like 'store_hashkey_nilvalue'
|
125
|
+
it_should_behave_like 'store_hashkey_integervalue'
|
126
|
+
it_should_behave_like 'store_booleankey_objectvalue'
|
127
|
+
it_should_behave_like 'store_booleankey_stringvalue'
|
128
|
+
it_should_behave_like 'store_booleankey_hashvalue'
|
129
|
+
it_should_behave_like 'store_booleankey_booleanvalue'
|
130
|
+
it_should_behave_like 'store_booleankey_nilvalue'
|
131
|
+
it_should_behave_like 'store_booleankey_integervalue'
|
132
|
+
it_should_behave_like 'store_nilkey_objectvalue'
|
133
|
+
it_should_behave_like 'store_nilkey_stringvalue'
|
134
|
+
it_should_behave_like 'store_nilkey_hashvalue'
|
135
|
+
it_should_behave_like 'store_nilkey_booleanvalue'
|
136
|
+
it_should_behave_like 'store_nilkey_nilvalue'
|
137
|
+
it_should_behave_like 'store_nilkey_integervalue'
|
138
|
+
it_should_behave_like 'store_integerkey_objectvalue'
|
139
|
+
it_should_behave_like 'store_integerkey_stringvalue'
|
140
|
+
it_should_behave_like 'store_integerkey_hashvalue'
|
141
|
+
it_should_behave_like 'store_integerkey_booleanvalue'
|
142
|
+
it_should_behave_like 'store_integerkey_nilvalue'
|
143
|
+
it_should_behave_like 'store_integerkey_integervalue'
|
144
|
+
it_should_behave_like 'transform_value'
|
145
|
+
end
|
@@ -13,11 +13,12 @@ describe Rack::MonetaCookies do
|
|
13
13
|
end
|
14
14
|
|
15
15
|
def backend
|
16
|
-
Rack::MockRequest.new(Rack::MonetaCookies.new(lambda
|
16
|
+
Rack::MockRequest.new(Rack::MonetaCookies.new(lambda do |env|
|
17
17
|
@store = env['rack.request.cookie_hash']
|
18
|
+
expect(@store).to equal(env['rack.moneta_cookies'])
|
18
19
|
app.call(env) if app
|
19
20
|
[200,{},[]]
|
20
|
-
|
21
|
+
end, @options || {}, &@block))
|
21
22
|
end
|
22
23
|
|
23
24
|
def get(cookies = {}, &block)
|
@@ -25,20 +26,20 @@ describe Rack::MonetaCookies do
|
|
25
26
|
@response = backend.get('/','HTTP_COOKIE' => Rack::Utils.build_query(cookies))
|
26
27
|
end
|
27
28
|
|
28
|
-
it 'should be able to read a
|
29
|
+
it 'should be able to read a key' do
|
29
30
|
get 'key' => 'value' do
|
30
31
|
expect( @store['key'] ).to eql('value')
|
31
32
|
end
|
32
33
|
end
|
33
34
|
|
34
|
-
it 'should be able to set a
|
35
|
+
it 'should be able to set a key' do
|
35
36
|
get do
|
36
37
|
@store['key'] = 'value'
|
37
38
|
end
|
38
39
|
expect( @response['Set-Cookie'] ).to eql('key=value')
|
39
40
|
end
|
40
41
|
|
41
|
-
it 'should be able to remove a
|
42
|
+
it 'should be able to remove a key' do
|
42
43
|
get 'key' => 'value' do
|
43
44
|
@store.delete('key')
|
44
45
|
end
|
@@ -0,0 +1,83 @@
|
|
1
|
+
require 'helper'
|
2
|
+
require 'rack/mock'
|
3
|
+
require 'rack/moneta_store'
|
4
|
+
|
5
|
+
describe Rack::MonetaStore do
|
6
|
+
def config(store_arg = nil, options = nil, &block)
|
7
|
+
@store_arg = store_arg
|
8
|
+
@options = options
|
9
|
+
@block = block
|
10
|
+
end
|
11
|
+
|
12
|
+
def app(&block)
|
13
|
+
@app_block ||= block
|
14
|
+
end
|
15
|
+
|
16
|
+
def middleware
|
17
|
+
@middleware ||= Rack::MonetaStore.new(lambda do |env|
|
18
|
+
@store = env['rack.moneta_store']
|
19
|
+
app.call(env) if app
|
20
|
+
[200,{},[]]
|
21
|
+
end, @store_arg, @options || {}, &@block)
|
22
|
+
end
|
23
|
+
|
24
|
+
def backend
|
25
|
+
@backend ||= Rack::MockRequest.new(middleware)
|
26
|
+
end
|
27
|
+
|
28
|
+
def get(&block)
|
29
|
+
app(&block)
|
30
|
+
@response = backend.get('/')
|
31
|
+
end
|
32
|
+
|
33
|
+
def uncached_store
|
34
|
+
middleware.instance_variable_get(:@store)
|
35
|
+
end
|
36
|
+
|
37
|
+
it 'should be able to get a key without caching' do
|
38
|
+
config :Memory
|
39
|
+
uncached_store['key'] = 'value'
|
40
|
+
get do
|
41
|
+
expect(@store['key']).to eql('value')
|
42
|
+
end
|
43
|
+
end
|
44
|
+
|
45
|
+
it 'should be able to get a key with caching' do
|
46
|
+
config :Memory, :cache => true
|
47
|
+
uncached_store['key'] = 'value'
|
48
|
+
get do
|
49
|
+
expect(@store['key']).to eql('value')
|
50
|
+
expect(@store.backend).to equal(uncached_store)
|
51
|
+
expect(@store.cache['key']).to eql('value')
|
52
|
+
end
|
53
|
+
end
|
54
|
+
|
55
|
+
it 'should be able to set a key' do
|
56
|
+
config :Memory
|
57
|
+
get do
|
58
|
+
@store['key'] = 'value'
|
59
|
+
end
|
60
|
+
expect( @store['key'] ).to eql('value')
|
61
|
+
expect(uncached_store['key']).to eql('value')
|
62
|
+
end
|
63
|
+
|
64
|
+
it 'should be able to get a remove a key' do
|
65
|
+
config :Memory
|
66
|
+
uncached_store['key'] = 'value'
|
67
|
+
get do
|
68
|
+
expect(@store.delete('key')).to eql('value')
|
69
|
+
end
|
70
|
+
expect(uncached_store.key?('key')).to be_false
|
71
|
+
end
|
72
|
+
|
73
|
+
it 'should accept a config block' do
|
74
|
+
config do
|
75
|
+
use :Transformer, :key => :prefix, :prefix => 'moneta.'
|
76
|
+
adapter :Memory
|
77
|
+
end
|
78
|
+
uncached_store['key'] = 'value'
|
79
|
+
get do
|
80
|
+
expect(@store['key']).to eql('value')
|
81
|
+
end
|
82
|
+
end
|
83
|
+
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: moneta
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.7.
|
4
|
+
version: 0.7.3
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -11,7 +11,7 @@ authors:
|
|
11
11
|
autorequire:
|
12
12
|
bindir: bin
|
13
13
|
cert_chain: []
|
14
|
-
date: 2012-12-
|
14
|
+
date: 2012-12-31 00:00:00.000000000 Z
|
15
15
|
dependencies: []
|
16
16
|
description: A unified interface to key/value stores
|
17
17
|
email:
|
@@ -60,6 +60,7 @@ files:
|
|
60
60
|
- lib/moneta/adapters/null.rb
|
61
61
|
- lib/moneta/adapters/pstore.rb
|
62
62
|
- lib/moneta/adapters/redis.rb
|
63
|
+
- lib/moneta/adapters/restclient.rb
|
63
64
|
- lib/moneta/adapters/riak.rb
|
64
65
|
- lib/moneta/adapters/sdbm.rb
|
65
66
|
- lib/moneta/adapters/sequel.rb
|
@@ -85,6 +86,7 @@ files:
|
|
85
86
|
- lib/rack/cache/moneta.rb
|
86
87
|
- lib/rack/moneta_cookies.rb
|
87
88
|
- lib/rack/moneta_rest.rb
|
89
|
+
- lib/rack/moneta_store.rb
|
88
90
|
- lib/rack/session/moneta.rb
|
89
91
|
- moneta.gemspec
|
90
92
|
- spec/action_dispatch/fixtures/session_autoload_test/foo.rb
|
@@ -113,6 +115,7 @@ files:
|
|
113
115
|
- spec/moneta/adapter_mongo_spec.rb
|
114
116
|
- spec/moneta/adapter_pstore_spec.rb
|
115
117
|
- spec/moneta/adapter_redis_spec.rb
|
118
|
+
- spec/moneta/adapter_restclient_spec.rb
|
116
119
|
- spec/moneta/adapter_riak_spec.rb
|
117
120
|
- spec/moneta/adapter_sdbm_spec.rb
|
118
121
|
- spec/moneta/adapter_sequel_spec.rb
|
@@ -175,6 +178,7 @@ files:
|
|
175
178
|
- spec/moneta/simple_pstore_spec.rb
|
176
179
|
- spec/moneta/simple_pstore_with_expires_spec.rb
|
177
180
|
- spec/moneta/simple_redis_spec.rb
|
181
|
+
- spec/moneta/simple_restclient_spec.rb
|
178
182
|
- spec/moneta/simple_riak_spec.rb
|
179
183
|
- spec/moneta/simple_riak_with_expires_spec.rb
|
180
184
|
- spec/moneta/simple_sdbm_spec.rb
|
@@ -224,6 +228,7 @@ files:
|
|
224
228
|
- spec/monetaspecs.rb
|
225
229
|
- spec/rack/cache_moneta_spec.rb
|
226
230
|
- spec/rack/moneta_cookies_spec.rb
|
231
|
+
- spec/rack/moneta_store_spec.rb
|
227
232
|
- spec/rack/session_moneta_spec.rb
|
228
233
|
homepage: http://github.com/minad/moneta
|
229
234
|
licenses: []
|
@@ -277,6 +282,7 @@ test_files:
|
|
277
282
|
- spec/moneta/adapter_mongo_spec.rb
|
278
283
|
- spec/moneta/adapter_pstore_spec.rb
|
279
284
|
- spec/moneta/adapter_redis_spec.rb
|
285
|
+
- spec/moneta/adapter_restclient_spec.rb
|
280
286
|
- spec/moneta/adapter_riak_spec.rb
|
281
287
|
- spec/moneta/adapter_sdbm_spec.rb
|
282
288
|
- spec/moneta/adapter_sequel_spec.rb
|
@@ -339,6 +345,7 @@ test_files:
|
|
339
345
|
- spec/moneta/simple_pstore_spec.rb
|
340
346
|
- spec/moneta/simple_pstore_with_expires_spec.rb
|
341
347
|
- spec/moneta/simple_redis_spec.rb
|
348
|
+
- spec/moneta/simple_restclient_spec.rb
|
342
349
|
- spec/moneta/simple_riak_spec.rb
|
343
350
|
- spec/moneta/simple_riak_with_expires_spec.rb
|
344
351
|
- spec/moneta/simple_sdbm_spec.rb
|
@@ -388,5 +395,6 @@ test_files:
|
|
388
395
|
- spec/monetaspecs.rb
|
389
396
|
- spec/rack/cache_moneta_spec.rb
|
390
397
|
- spec/rack/moneta_cookies_spec.rb
|
398
|
+
- spec/rack/moneta_store_spec.rb
|
391
399
|
- spec/rack/session_moneta_spec.rb
|
392
400
|
has_rdoc:
|