nest 0.0.7 → 1.0.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.
@@ -1,32 +1,31 @@
1
1
  Nest
2
2
  ====
3
3
 
4
- Generate nested namespaced keys for key-value databases.
4
+ Object Oriented Keys for Redis.
5
5
 
6
6
  Description
7
7
  -----------
8
8
 
9
- If you are familiar with databases like
10
- [Redis](http://code.google.com/p/redis) and
11
- libraries like [Ohm](http://ohm.keyvalue.org) or
12
- [redis-namespace](http://github.com/defunkt/redis-namespace), you
13
- already know how important it is to craft the keys that will hold the
14
- data.
9
+ If you are familiar with databases like [Redis](http://code.google.com/p/redis)
10
+ and libraries like [Ohm](http://ohm.keyvalue.org) you already know how
11
+ important it is to craft the keys that will hold the data.
15
12
 
16
- >> @redis.set "event:3:name", "Redis Meetup"
17
- >> @redis.get "event:3:name"
18
- => "Redis Meetup"
13
+ >> redis = Redis.new
14
+ >> redis.sadd("event:3:attendees", "Albert")
15
+ >> redis.smembers("event:3:attendees")
16
+ => ["Albert"]
19
17
 
20
18
  It is a design pattern in key-value databases to use the key to simulate
21
19
  structure, and you can read more about this in the [case study for a
22
20
  Twitter clone](http://code.google.com/p/redis/wiki/TwitterAlikeExample).
23
21
 
24
- Nest helps you generate those keys by providing chainable namespaces:
22
+ Nest helps you generate those keys by providing chainable namespaces that are
23
+ already connected to Redis:
25
24
 
26
25
  >> event = Nest.new("event")
27
- >> @redis.set event[3][:name], "Redis Meetup"
28
- >> @redis.get event[3][:name]
29
- => "Redis Meetup"
26
+ >> event[3][:attendees].sadd("Albert")
27
+ >> event[3][:attendees].smembers
28
+ => ["Albert"]
30
29
 
31
30
  Usage
32
31
  -----
@@ -53,34 +52,41 @@ dealing with events:
53
52
  >> events = Nest.new("events")
54
53
  => "events"
55
54
 
56
- >> redis = Redis.new
57
- => #<Redis::Client...>
58
-
59
- >> id = redis.incr(event)
55
+ >> id = events[:id].incr
60
56
  => 1
61
57
 
62
- >> redis.set events[id][:name], "Redis Meetup"
58
+ >> events[id][:attendees].sadd("Albert")
63
59
  => "OK"
64
60
 
65
- >> redis.get events[id][:name]
66
- => "Redis Meetup"
67
-
68
61
  >> meetup = events[id]
69
62
  => "events:1"
70
63
 
71
- >> redis.get meetup[:name]
72
- => "Redis Meetup"
64
+ >> meetup[:attendees].smembers
65
+ => ["Albert"]
73
66
 
74
- Using Nest as an object oriented Redis key
75
- ------------------------------------------
67
+ Supplying your existing Redis instance
68
+ --------------------------------------
76
69
 
77
- If you supply a Redis client as a second parameter, you can operate with
78
- Redis directly:
70
+ You can supply a `Redis` instance as a second parameter. If you don't, a default
71
+ instance is created for you:
79
72
 
80
73
  >> redis = Redis.new
81
74
  => #<Redis::Client...>
82
75
 
83
- >> events = Nest.new("events", redis)
76
+ >> users = Nest.new("users", redis)
77
+ => "users"
78
+
79
+ >> id = users[:id].incr
80
+ => 1
81
+
82
+ >> users[id].hset(:name, "Albert")
83
+ => "OK"
84
+
85
+ `Nest` objects respond to `redis` and return a `Redis` instance. It is
86
+ automatically reused when you create a new namespace, and you can reuse it when
87
+ creating a new instance of Nest:
88
+
89
+ >> events = Nest.new("events", meetup.redis)
84
90
  => "events"
85
91
 
86
92
  >> events.sadd(meetup)
@@ -95,8 +101,9 @@ Redis directly:
95
101
  >> events.del
96
102
  >> true
97
103
 
98
- It allows you to execute all the Redis commands that expect a key as the
99
- first parameter. Think of it as a curried Redis client.
104
+ Nest allows you to execute all the Redis commands that expect a key as the
105
+ first parameter. Think of it as a
106
+ [curried](http://en.wikipedia.org/wiki/Currying) Redis client.
100
107
 
101
108
  Differences with redis-namespace
102
109
  --------------------------------
@@ -109,6 +116,10 @@ different scope.
109
116
 
110
117
  Use Nest when you want to use the keys to represent structure.
111
118
 
119
+ Tip: instead of using redis-namespace, it is recommended that you run a
120
+ different instance of `redis-server`. Translating keys back and forth is not
121
+ only delicate, but unnecessary and counterproductive.
122
+
112
123
  Differences with Ohm
113
124
  --------------------
114
125
 
@@ -119,12 +130,15 @@ between objects.
119
130
 
120
131
  Use Ohm when you want to use Redis as your database.
121
132
 
122
- Use Nest when mapping objects with Ohm is not possible.
133
+ Use Nest when mapping objects with Ohm is not possible or overkill.
134
+
135
+ Tip: Ohm uses Nest internally to deal with keys. Having a good knowledge
136
+ of Nest will let you extend Ohm to suit your needs.
123
137
 
124
138
  Installation
125
139
  ------------
126
140
 
127
- $ sudo gem install nest
141
+ $ gem install nest
128
142
 
129
143
  License
130
144
  -------
data/Rakefile CHANGED
@@ -1,5 +1,6 @@
1
1
  task :test do
2
- system "cd test && ruby nest_test.rb"
2
+ require "cutest"
3
+ Cutest.run(Dir["test/nest*"])
3
4
  end
4
5
 
5
6
  task :default => :test
@@ -1,5 +1,7 @@
1
+ require "redis"
2
+
1
3
  class Nest < String
2
- VERSION = "0.0.7"
4
+ VERSION = "1.0.0"
3
5
 
4
6
  METHODS = [:append, :blpop, :brpop, :decr, :decrby, :del, :exists,
5
7
  :expire, :expireat, :get, :getset, :hdel, :hexists, :hget, :hgetall,
@@ -15,7 +17,9 @@ class Nest < String
15
17
  :zrem, :zremrangebyrank, :zremrangebyscore, :zrevrange, :zrevrank,
16
18
  :zscore, :zunionstore]
17
19
 
18
- def initialize(key, redis = nil)
20
+ attr :redis
21
+
22
+ def initialize(key, redis = Redis.connect)
19
23
  super(key.to_s)
20
24
  @redis = redis
21
25
  end
@@ -29,10 +33,4 @@ class Nest < String
29
33
  redis.send(meth, self, *args, &block)
30
34
  end
31
35
  end
32
-
33
- private
34
-
35
- def redis
36
- @redis
37
- end
38
36
  end
@@ -1,10 +1,12 @@
1
1
  Gem::Specification.new do |s|
2
2
  s.name = "nest"
3
- s.version = "0.0.7"
4
- s.summary = "Generate nested namespaced keys for key-value databases."
3
+ s.version = "1.0.0"
4
+ s.summary = "Object Oriented Keys for Redis."
5
5
  s.description = "It is a design pattern in key-value databases to use the key to simulate structure, and Nest can take care of that."
6
6
  s.authors = ["Michel Martens"]
7
7
  s.email = ["michel@soveran.com"]
8
8
  s.homepage = "http://github.com/soveran/nest"
9
9
  s.files = ["LICENSE", "README.markdown", "Rakefile", "lib/nest.rb", "nest.gemspec", "test/nest_test.rb", "test/test_helper.rb"]
10
+ s.add_dependency "redis", "~> 2.0.0"
11
+ s.add_development_dependency "cutest", "~> 0.1"
10
12
  end
@@ -1,91 +1,86 @@
1
1
  require File.expand_path("test_helper", File.dirname(__FILE__))
2
2
 
3
- class TestNest < Test::Unit::TestCase
4
- context "creating namespaces" do
5
- should "return the namespace" do
6
- n1 = Nest.new("foo")
7
- assert_equal "foo", n1
8
- end
9
-
10
- should "prepend the namespace" do
11
- n1 = Nest.new("foo")
12
- assert_equal "foo:bar", n1["bar"]
13
- end
14
-
15
- should "work in more than one level" do
16
- n1 = Nest.new("foo")
17
- n2 = Nest.new(n1["bar"])
18
- assert_equal "foo:bar:baz", n2["baz"]
19
- end
3
+ # Creating namespaces.
4
+ scope do
5
+ test "return the namespace" do
6
+ n1 = Nest.new("foo")
7
+ assert "foo" == n1
8
+ end
20
9
 
21
- should "be chainable" do
22
- n1 = Nest.new("foo")
23
- assert_equal "foo:bar:baz", n1["bar"]["baz"]
24
- end
10
+ test "prepend the namespace" do
11
+ n1 = Nest.new("foo")
12
+ assert "foo:bar" == n1["bar"]
13
+ end
25
14
 
26
- should "accept symbols" do
27
- n1 = Nest.new(:foo)
28
- assert_equal "foo:bar", n1[:bar]
29
- end
15
+ test "work in more than one level" do
16
+ n1 = Nest.new("foo")
17
+ n2 = Nest.new(n1["bar"])
18
+ assert "foo:bar:baz" == n2["baz"]
19
+ end
30
20
 
31
- should "accept numbers" do
32
- n1 = Nest.new("foo")
33
- assert_equal "foo:3", n1[3]
34
- end
21
+ test "be chainable" do
22
+ n1 = Nest.new("foo")
23
+ assert "foo:bar:baz" == n1["bar"]["baz"]
35
24
  end
36
25
 
37
- context "operating with redis" do
38
- require "redis"
26
+ test "accept symbols" do
27
+ n1 = Nest.new(:foo)
28
+ assert "foo:bar" == n1[:bar]
29
+ end
39
30
 
40
- setup do
41
- @redis = Redis.new :db => 15
42
- @redis.flushdb
43
- end
31
+ test "accept numbers" do
32
+ n1 = Nest.new("foo")
33
+ assert "foo:3" == n1[3]
34
+ end
35
+ end
44
36
 
45
- should "raise if no redis instance was passed" do
46
- n1 = Nest.new("foo")
37
+ # Operating with redis.
38
+ scope do
39
+ prepare do
40
+ @redis = Redis.new
41
+ @redis.flushdb
42
+ end
47
43
 
48
- assert_raises NoMethodError do
49
- n1.set("s1")
50
- end
51
- end
44
+ test "work if no redis instance was passed" do
45
+ n1 = Nest.new("foo")
46
+ n1.set("s1")
52
47
 
53
- should "work if a redis instance is supplied" do
54
- n1 = Nest.new("foo", @redis)
55
- n1.set("s1")
48
+ assert "s1" == n1.get
49
+ end
56
50
 
57
- assert_equal "s1", n1.get
58
- end
51
+ test "work if a redis instance is supplied" do
52
+ n1 = Nest.new("foo", @redis)
53
+ n1.set("s1")
59
54
 
60
- should "pass the redis instance to new keys" do
61
- n1 = Nest.new("foo", @redis)
62
- n1["bar"].set("s2")
55
+ assert "s1" == n1.get
56
+ end
63
57
 
64
- assert_equal nil, n1.get
65
- assert_equal "s2", n1["bar"].get
66
- end
58
+ test "pass the redis instance to new keys" do
59
+ n1 = Nest.new("foo", @redis)
67
60
 
68
- should "PubSub" do
69
- foo = Nest.new("foo", @redis)
70
- listening = false
71
- message_received = false
61
+ assert @redis.id == n1["bar"].redis.id
62
+ end
72
63
 
73
- Thread.new do
74
- while !listening; end
75
- Nest.new("foo", Redis.new(:db => 15)).publish("")
76
- end
64
+ test "PubSub" do
65
+ foo = Nest.new("foo", @redis)
66
+ listening = false
67
+ message_received = false
77
68
 
78
- foo.subscribe do |on|
79
- on.message do
80
- message_received = true
69
+ Thread.new do
70
+ while !listening; end
71
+ Nest.new("foo", Redis.new(:db => 15)).publish("")
72
+ end
81
73
 
82
- foo.unsubscribe
83
- end
74
+ foo.subscribe do |on|
75
+ on.message do
76
+ message_received = true
84
77
 
85
- listening = true
78
+ foo.unsubscribe
86
79
  end
87
80
 
88
- assert message_received
81
+ listening = true
89
82
  end
83
+
84
+ assert message_received
90
85
  end
91
86
  end
@@ -1,3 +1,3 @@
1
1
  require "rubygems"
2
- require "contest"
2
+ require "cutest"
3
3
  require File.join(File.dirname(__FILE__), "..", "lib", "nest")
metadata CHANGED
@@ -3,10 +3,10 @@ name: nest
3
3
  version: !ruby/object:Gem::Version
4
4
  prerelease: false
5
5
  segments:
6
+ - 1
6
7
  - 0
7
8
  - 0
8
- - 7
9
- version: 0.0.7
9
+ version: 1.0.0
10
10
  platform: ruby
11
11
  authors:
12
12
  - Michel Martens
@@ -14,10 +14,38 @@ autorequire:
14
14
  bindir: bin
15
15
  cert_chain: []
16
16
 
17
- date: 2010-08-05 00:00:00 -03:00
17
+ date: 2010-10-22 00:00:00 -03:00
18
18
  default_executable:
19
- dependencies: []
20
-
19
+ dependencies:
20
+ - !ruby/object:Gem::Dependency
21
+ name: redis
22
+ prerelease: false
23
+ requirement: &id001 !ruby/object:Gem::Requirement
24
+ none: false
25
+ requirements:
26
+ - - ~>
27
+ - !ruby/object:Gem::Version
28
+ segments:
29
+ - 2
30
+ - 0
31
+ - 0
32
+ version: 2.0.0
33
+ type: :runtime
34
+ version_requirements: *id001
35
+ - !ruby/object:Gem::Dependency
36
+ name: cutest
37
+ prerelease: false
38
+ requirement: &id002 !ruby/object:Gem::Requirement
39
+ none: false
40
+ requirements:
41
+ - - ~>
42
+ - !ruby/object:Gem::Version
43
+ segments:
44
+ - 0
45
+ - 1
46
+ version: "0.1"
47
+ type: :development
48
+ version_requirements: *id002
21
49
  description: It is a design pattern in key-value databases to use the key to simulate structure, and Nest can take care of that.
22
50
  email:
23
51
  - michel@soveran.com
@@ -66,6 +94,6 @@ rubyforge_project:
66
94
  rubygems_version: 1.3.7
67
95
  signing_key:
68
96
  specification_version: 3
69
- summary: Generate nested namespaced keys for key-value databases.
97
+ summary: Object Oriented Keys for Redis.
70
98
  test_files: []
71
99