riak-record 0.0.4 → 0.1.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 +4 -4
- data/Gemfile +3 -0
- data/Gemfile.lock +37 -0
- data/Guardfile +11 -0
- data/README.md +70 -14
- data/TODO.md +8 -0
- data/VERSION +1 -1
- data/lib/riak_record/associations.rb +49 -0
- data/lib/riak_record/base.rb +146 -0
- data/lib/riak_record/finder.rb +125 -0
- data/lib/riak_record.rb +6 -0
- data/riak-record.gemspec +22 -5
- data/spec/riak_record/associations_spec.rb +93 -0
- data/spec/riak_record/base_spec.rb +204 -0
- data/spec/riak_record/finder_spec.rb +163 -0
- data/spec/riak_record_spec.rb +4 -0
- data/spec/spec_helper.rb +9 -3
- metadata +54 -4
- data/lib/riak-record.rb +0 -77
- data/spec/riak-record_spec.rb +0 -102
checksums.yaml
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
---
|
2
2
|
SHA1:
|
3
|
-
metadata.gz:
|
4
|
-
data.tar.gz:
|
3
|
+
metadata.gz: f9cefbb009666dc6e1e326b9e0f27add25fde982
|
4
|
+
data.tar.gz: 16df6690a2751083ba1bfa157158dd648aeee2e8
|
5
5
|
SHA512:
|
6
|
-
metadata.gz:
|
7
|
-
data.tar.gz:
|
6
|
+
metadata.gz: 9dda40575f7149e095a93ff445ac05870d906f4c364faf899fa0ab59fa27e79faf90367f8e8ec1e83989c3f01803ec928b052e791260d65ffa14d089560de061
|
7
|
+
data.tar.gz: 90d8f57ddc8e236431c472f68d9468ea5f8b91317f9751a9cf22dc5b53dad363606716addd548772e834f8b7a40b4fa131cbccba13b9e8a3777f5a74983b5a99
|
data/Gemfile
CHANGED
data/Gemfile.lock
CHANGED
@@ -4,13 +4,18 @@ GEM
|
|
4
4
|
addressable (2.3.6)
|
5
5
|
beefcake (1.0.0)
|
6
6
|
builder (3.2.2)
|
7
|
+
celluloid (0.15.2)
|
8
|
+
timers (~> 1.1.0)
|
7
9
|
cert_validator (0.0.1)
|
10
|
+
coderay (1.1.0)
|
8
11
|
descendants_tracker (0.0.4)
|
9
12
|
thread_safe (~> 0.3, >= 0.3.1)
|
10
13
|
diff-lcs (1.2.5)
|
11
14
|
docile (1.1.5)
|
12
15
|
faraday (0.9.0)
|
13
16
|
multipart-post (>= 1.2, < 3)
|
17
|
+
ffi (1.9.3)
|
18
|
+
formatador (0.2.5)
|
14
19
|
git (1.2.8)
|
15
20
|
github_api (0.12.1)
|
16
21
|
addressable (~> 2.3)
|
@@ -20,6 +25,18 @@ GEM
|
|
20
25
|
multi_json (>= 1.7.5, < 2.0)
|
21
26
|
nokogiri (~> 1.6.3)
|
22
27
|
oauth2
|
28
|
+
guard (2.6.1)
|
29
|
+
formatador (>= 0.2.4)
|
30
|
+
listen (~> 2.7)
|
31
|
+
lumberjack (~> 1.0)
|
32
|
+
pry (>= 0.9.12)
|
33
|
+
thor (>= 0.18.1)
|
34
|
+
guard-bundler (2.0.0)
|
35
|
+
bundler (~> 1.0)
|
36
|
+
guard (~> 2.2)
|
37
|
+
guard-rspec (4.3.1)
|
38
|
+
guard (~> 2.1)
|
39
|
+
rspec (>= 2.14, < 4.0)
|
23
40
|
hashie (3.3.1)
|
24
41
|
highline (1.6.21)
|
25
42
|
i18n (0.6.11)
|
@@ -35,6 +52,12 @@ GEM
|
|
35
52
|
rdoc
|
36
53
|
json (1.8.1)
|
37
54
|
jwt (1.0.0)
|
55
|
+
listen (2.7.8)
|
56
|
+
celluloid (>= 0.15.2)
|
57
|
+
rb-fsevent (>= 0.9.3)
|
58
|
+
rb-inotify (>= 0.9)
|
59
|
+
lumberjack (1.0.6)
|
60
|
+
method_source (0.8.2)
|
38
61
|
mini_portile (0.6.0)
|
39
62
|
multi_json (1.10.1)
|
40
63
|
multi_xml (0.5.5)
|
@@ -47,8 +70,15 @@ GEM
|
|
47
70
|
multi_json (~> 1.3)
|
48
71
|
multi_xml (~> 0.5)
|
49
72
|
rack (~> 1.2)
|
73
|
+
pry (0.10.0)
|
74
|
+
coderay (~> 1.1.0)
|
75
|
+
method_source (~> 0.8.1)
|
76
|
+
slop (~> 3.4)
|
50
77
|
rack (1.5.2)
|
51
78
|
rake (10.3.2)
|
79
|
+
rb-fsevent (0.9.4)
|
80
|
+
rb-inotify (0.9.5)
|
81
|
+
ffi (>= 0.5.0)
|
52
82
|
rdoc (3.12.2)
|
53
83
|
json (~> 1.4)
|
54
84
|
riak-client (2.0.0)
|
@@ -74,15 +104,22 @@ GEM
|
|
74
104
|
multi_json
|
75
105
|
simplecov-html (~> 0.8.0)
|
76
106
|
simplecov-html (0.8.0)
|
107
|
+
slop (3.5.0)
|
108
|
+
terminal-notifier-guard (1.5.3)
|
109
|
+
thor (0.19.1)
|
77
110
|
thread_safe (0.3.4)
|
111
|
+
timers (1.1.0)
|
78
112
|
|
79
113
|
PLATFORMS
|
80
114
|
ruby
|
81
115
|
|
82
116
|
DEPENDENCIES
|
83
117
|
bundler (~> 1.0)
|
118
|
+
guard-bundler
|
119
|
+
guard-rspec (~> 4.3.1)
|
84
120
|
jeweler (~> 2.0.1)
|
85
121
|
rdoc (~> 3.12)
|
86
122
|
riak-client (~> 2.0.0)
|
87
123
|
rspec (~> 3.1.0)
|
88
124
|
simplecov
|
125
|
+
terminal-notifier-guard
|
data/Guardfile
ADDED
@@ -0,0 +1,11 @@
|
|
1
|
+
guard :bundler do
|
2
|
+
watch('Gemfile')
|
3
|
+
# Uncomment next line if your Gemfile contains the `gemspec' command.
|
4
|
+
# watch(/^.+\.gemspec/)
|
5
|
+
end
|
6
|
+
|
7
|
+
guard :rspec, cmd: 'bundle exec rspec' do
|
8
|
+
watch(%r{^spec/.+_spec\.rb$})
|
9
|
+
watch(%r{^lib/(.+)\.rb$}) { |m| "spec/#{m[1]}_spec.rb" }
|
10
|
+
watch('spec/spec_helper.rb') { "spec" }
|
11
|
+
end
|
data/README.md
CHANGED
@@ -1,33 +1,89 @@
|
|
1
1
|
# riak-record
|
2
2
|
|
3
3
|
RiakRecord is a thin and immature wrapper around riak-ruby-client. It creates a bucket for
|
4
|
-
each class, provides a simple finder, and creates attribute reader.
|
4
|
+
each class, provides a simple finder, and creates attribute reader. It adds a layer over
|
5
|
+
the Riak::Client to make interacting with Riak more ActiveRecord-like while
|
6
|
+
still giving you all the access to Riak's underlying client's capabilities.
|
5
7
|
|
6
8
|
## Usage
|
7
9
|
|
8
10
|
```ruby
|
9
11
|
require 'riak-record'
|
10
12
|
|
11
|
-
RiakRecord.client = Riak::Client.new
|
12
|
-
RiakRecord.namespace = 'staging' # optional. Namespaces buckets
|
13
|
+
RiakRecord::Base.client = Riak::Client.new
|
14
|
+
RiakRecord::Base.namespace = 'staging' # optional. Namespaces buckets
|
13
15
|
|
14
|
-
class
|
15
|
-
bucket_name
|
16
|
-
|
16
|
+
class Post < RiakRecord::Base
|
17
|
+
bucket_name :posts
|
18
|
+
data_attributes :title, :body, :category
|
19
|
+
belongs_to :author
|
20
|
+
has_many :comments
|
21
|
+
|
22
|
+
index_int_attributes :author_id # author_id_int
|
23
|
+
index_bin_attributes :category # catgory_bin
|
24
|
+
end
|
25
|
+
|
26
|
+
class Author < RiakRecord::Base
|
27
|
+
bucket_name :authors
|
28
|
+
data_attributes :name
|
29
|
+
has_many :posts
|
17
30
|
end
|
18
31
|
|
19
|
-
|
20
|
-
|
32
|
+
class Comment < RiakRecord::Base
|
33
|
+
bucket_name :comments
|
34
|
+
data_attribute :comment
|
35
|
+
belongs_to :post
|
36
|
+
|
37
|
+
index_int_attributes :post_id
|
38
|
+
end
|
39
|
+
|
40
|
+
Author.client #> instance of Riak::Client
|
41
|
+
Author.bucket #> instance of Riak::Bucket
|
42
|
+
|
43
|
+
author = Author.new(99) # create a new record with id/key 99
|
44
|
+
author.name = 'Robert' # set an attribute
|
45
|
+
author.save # store in riak
|
46
|
+
|
47
|
+
Post.find(["my-first-post","a-farewell-to-blogging"]) #> Array of ExampleRecords returned
|
48
|
+
|
49
|
+
post = Post.find("my-first-post") #> Instance of ExampleRecord
|
50
|
+
post.riak_object #> directly access Riak::RObject
|
51
|
+
post.data #> same as record.riak_object.data
|
21
52
|
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
53
|
+
post.title = 'My First Post' #> record.riak_object.data['title']=
|
54
|
+
post.title #> record.riak_object.data['title']
|
55
|
+
|
56
|
+
post.author = 99 #> record.riak_object.indexes["author_id_int"] = [99]
|
57
|
+
post.category = 'ruby' #> record.riak_object.indexes["category_bin"] = ["ruby"]
|
58
|
+
post.save #> record.riak_object.store
|
59
|
+
post.reload #> reload the underlying riak_object from the db discarding changes
|
60
|
+
|
61
|
+
Author.find(99).posts #> [post]
|
62
|
+
|
63
|
+
finder = Post.where(:category => 'ruby') #> Instance of RiakRecord::Finder
|
64
|
+
finder.count #> 1
|
65
|
+
finder.any? #> true
|
66
|
+
finder.any?{|o| o.category == 'php'} #> false
|
67
|
+
finder.none? #> false
|
68
|
+
finder.each{|e| ... } #> supports all enumerable methods
|
69
|
+
finder.count_by(:author_id) #> {"1" => 1}
|
28
70
|
```
|
29
71
|
|
72
|
+
## Using RiakRecord::Associations in other classes
|
30
73
|
|
74
|
+
If you're using another data store with Riak, it might be helpful to include Riak's associations in the other class.
|
75
|
+
|
76
|
+
```ruby
|
77
|
+
class User < ActiveRecord::Base
|
78
|
+
include RiakRecord::Assocations
|
79
|
+
|
80
|
+
has_many_riak :posts, :class_name => "Post", :foreign_key => :user_id
|
81
|
+
belongs_to_riak :author, :class_name => "Author", :foreign_key => :author_id
|
82
|
+
end
|
83
|
+
|
84
|
+
User.find(1).posts #> create RiakRecord::Finder(Post, :user_id => 1)
|
85
|
+
User.find(1).author #> Author.find(self.author_id)
|
86
|
+
```
|
31
87
|
|
32
88
|
## Contributing to riak-record
|
33
89
|
|
data/TODO.md
ADDED
data/VERSION
CHANGED
@@ -1 +1 @@
|
|
1
|
-
0.0
|
1
|
+
0.1.0
|
@@ -0,0 +1,49 @@
|
|
1
|
+
module RiakRecord
|
2
|
+
module Associations
|
3
|
+
|
4
|
+
module ClassMethods
|
5
|
+
def belongs_to_riak(association_name, options = {})
|
6
|
+
class_name = options[:class_name] ||= association_name.to_s.split("_").collect(&:capitalize).join
|
7
|
+
foreign_key = options[:foreign_key] || "#{association_name}_id"
|
8
|
+
method_def = <<-END_OF_RUBY
|
9
|
+
|
10
|
+
def #{association_name}
|
11
|
+
@belongs_to_riak_#{association_name} = nil if @belongs_to_riak_#{association_name} && @belongs_to_riak_#{association_name}.id.to_s != Array(#{foreign_key}).first.to_s
|
12
|
+
@belongs_to_riak_#{association_name} ||= #{class_name}.find(#{foreign_key})
|
13
|
+
end
|
14
|
+
|
15
|
+
def #{association_name}=(obj)
|
16
|
+
raise ArgumentError, "not an instance of RiakRecord" unless obj.kind_of?(RiakRecord::Base)
|
17
|
+
@belongs_to_riak_#{association_name} = obj
|
18
|
+
self.#{foreign_key} = obj.id
|
19
|
+
end
|
20
|
+
|
21
|
+
END_OF_RUBY
|
22
|
+
|
23
|
+
class_eval method_def
|
24
|
+
end
|
25
|
+
|
26
|
+
def has_many_riak(association_name, options = {})
|
27
|
+
class_name = options[:class_name]
|
28
|
+
foreign_key = options[:foreign_key]
|
29
|
+
class_name && foreign_key or raise ArgumentError, "has_many_riak requires class_name and foreign_key options"
|
30
|
+
|
31
|
+
method_def = <<-END_OF_RUBY
|
32
|
+
|
33
|
+
def #{association_name}
|
34
|
+
@has_many_riak_#{association_name} ||= #{class_name}.where(:#{foreign_key} => self.id.to_s)
|
35
|
+
end
|
36
|
+
|
37
|
+
END_OF_RUBY
|
38
|
+
|
39
|
+
class_eval method_def
|
40
|
+
end
|
41
|
+
|
42
|
+
end
|
43
|
+
|
44
|
+
def self.included(base)
|
45
|
+
base.extend(ClassMethods)
|
46
|
+
end
|
47
|
+
|
48
|
+
end
|
49
|
+
end
|
@@ -0,0 +1,146 @@
|
|
1
|
+
require 'riak'
|
2
|
+
|
3
|
+
module RiakRecord
|
4
|
+
class Base
|
5
|
+
attr_reader :riak_object
|
6
|
+
include Associations
|
7
|
+
class << self
|
8
|
+
alias :has_many :has_many_riak
|
9
|
+
alias :belongs_to :belongs_to_riak
|
10
|
+
end
|
11
|
+
|
12
|
+
def initialize(r = nil)
|
13
|
+
unless r.is_a? Riak::RObject
|
14
|
+
r = self.class.bucket.new(r.to_s)
|
15
|
+
r.data = {}
|
16
|
+
end
|
17
|
+
@riak_object = r
|
18
|
+
end
|
19
|
+
|
20
|
+
def data
|
21
|
+
riak_object.data
|
22
|
+
end
|
23
|
+
|
24
|
+
def indexes
|
25
|
+
riak_object.indexes
|
26
|
+
end
|
27
|
+
|
28
|
+
def save
|
29
|
+
riak_object.store(:returnbody => false)
|
30
|
+
self
|
31
|
+
end
|
32
|
+
|
33
|
+
def id
|
34
|
+
riak_object.key
|
35
|
+
end
|
36
|
+
|
37
|
+
def reload
|
38
|
+
@riak_object = self.class.bucket.get(id)
|
39
|
+
@riak_object.data = {} if @riak_object.data.nil?
|
40
|
+
self
|
41
|
+
end
|
42
|
+
|
43
|
+
def self.bucket_name(name = :not_a_name)
|
44
|
+
@bucket_name = name.to_s unless name == :not_a_name
|
45
|
+
namespace.present? ? namespace_prefixed+@bucket_name : @bucket_name
|
46
|
+
end
|
47
|
+
|
48
|
+
def self.bucket
|
49
|
+
@bucket ||= client.bucket(bucket_name)
|
50
|
+
end
|
51
|
+
|
52
|
+
def self.data_attributes(*attributes)
|
53
|
+
attributes.map(&:to_sym).each do |method_name|
|
54
|
+
define_method(method_name) do
|
55
|
+
data[method_name.to_s]
|
56
|
+
end
|
57
|
+
|
58
|
+
define_method("#{method_name}=".to_sym) do |value|
|
59
|
+
data[method_name.to_s] = value
|
60
|
+
end
|
61
|
+
end
|
62
|
+
end
|
63
|
+
|
64
|
+
def self.index_int_attributes(*attributes)
|
65
|
+
attributes.map(&:to_sym).each do |method_name|
|
66
|
+
index_names[method_name.to_sym] = "#{method_name}_int"
|
67
|
+
|
68
|
+
define_method(method_name) do
|
69
|
+
indexes["#{method_name}_int"]
|
70
|
+
end
|
71
|
+
|
72
|
+
define_method("#{method_name}=".to_sym) do |value|
|
73
|
+
indexes["#{method_name}_int"] = Array(value).map(&:to_i)
|
74
|
+
end
|
75
|
+
end
|
76
|
+
end
|
77
|
+
|
78
|
+
def self.index_bin_attributes(*attributes)
|
79
|
+
attributes.map(&:to_sym).each do |method_name|
|
80
|
+
index_names[method_name.to_sym] = "#{method_name}_bin"
|
81
|
+
|
82
|
+
define_method(method_name) do
|
83
|
+
indexes["#{method_name}_bin"]
|
84
|
+
end
|
85
|
+
|
86
|
+
define_method("#{method_name}=".to_sym) do |value|
|
87
|
+
indexes["#{method_name}_bin"] = Array(value).map(&:to_s)
|
88
|
+
end
|
89
|
+
end
|
90
|
+
end
|
91
|
+
|
92
|
+
def self.index_names
|
93
|
+
@index_names ||= {}
|
94
|
+
end
|
95
|
+
|
96
|
+
def self.where(options)
|
97
|
+
RiakRecord::Finder.new(self, options)
|
98
|
+
end
|
99
|
+
|
100
|
+
def self.find(key_or_keys)
|
101
|
+
return find_many(key_or_keys) if key_or_keys.is_a?(Array)
|
102
|
+
|
103
|
+
begin
|
104
|
+
self.new(bucket.get(key_or_keys.to_s))
|
105
|
+
rescue Riak::FailedRequest => e
|
106
|
+
if e.not_found?
|
107
|
+
nil
|
108
|
+
else
|
109
|
+
raise e
|
110
|
+
end
|
111
|
+
end
|
112
|
+
end
|
113
|
+
|
114
|
+
def self.find_many(keys)
|
115
|
+
hash = bucket.get_many(keys.map(&:to_s))
|
116
|
+
keys.map{ |k| hash[k] }
|
117
|
+
end
|
118
|
+
|
119
|
+
@@namespace = nil
|
120
|
+
def self.namespace=(namespace)
|
121
|
+
@@namespace = namespace
|
122
|
+
end
|
123
|
+
|
124
|
+
def self.namespace
|
125
|
+
@@namespace
|
126
|
+
end
|
127
|
+
|
128
|
+
def self.namespace_prefixed
|
129
|
+
self.namespace + ":-:"
|
130
|
+
end
|
131
|
+
|
132
|
+
def self.all_buckets_in_namespace
|
133
|
+
raise "namespace not set" unless self.namespace
|
134
|
+
client.list_buckets.select{|b| b.name.match(/^#{ Regexp.escape(self.namespace_prefixed) }/) }
|
135
|
+
end
|
136
|
+
|
137
|
+
def self.client=(client)
|
138
|
+
@@client = client
|
139
|
+
end
|
140
|
+
|
141
|
+
def self.client
|
142
|
+
@@client
|
143
|
+
end
|
144
|
+
|
145
|
+
end
|
146
|
+
end
|
@@ -0,0 +1,125 @@
|
|
1
|
+
module RiakRecord
|
2
|
+
class Finder
|
3
|
+
include Enumerable
|
4
|
+
|
5
|
+
def initialize(finder_class, conditions)
|
6
|
+
unless finder_class <= RiakRecord::Base
|
7
|
+
raise ArgumentError, "RiakRecord::Finder requires a RiakRecord::Base class"
|
8
|
+
end
|
9
|
+
unless conditions.is_a?(Hash) && conditions.size == 1
|
10
|
+
raise ArgumentError, "RiakRecord::Finder requires exactly one condition specified as a hash"
|
11
|
+
end
|
12
|
+
@finder_class = finder_class
|
13
|
+
@bucket = finder_class.bucket
|
14
|
+
@index = finder_class.index_names[conditions.keys.first.to_sym]
|
15
|
+
@value = conditions.values.first
|
16
|
+
@load_complete = false
|
17
|
+
@page_size = 100
|
18
|
+
@loaded_objects = []
|
19
|
+
end
|
20
|
+
|
21
|
+
def all
|
22
|
+
until @load_complete do
|
23
|
+
load_next_page
|
24
|
+
end
|
25
|
+
@loaded_objects
|
26
|
+
end
|
27
|
+
alias :to_a :all
|
28
|
+
|
29
|
+
def each
|
30
|
+
@loaded_objects.each{|o| yield o}
|
31
|
+
end
|
32
|
+
|
33
|
+
def count
|
34
|
+
@load_complete ? @loaded_objects.count : count_map_reduce
|
35
|
+
end
|
36
|
+
|
37
|
+
def first(n=nil)
|
38
|
+
if n
|
39
|
+
until @load_complete || n <= @loaded_objects.count
|
40
|
+
load_next_page
|
41
|
+
end
|
42
|
+
@loaded_objects.first(n)
|
43
|
+
else
|
44
|
+
load_next_page unless load_started?
|
45
|
+
@loaded_objects.first
|
46
|
+
end
|
47
|
+
end
|
48
|
+
|
49
|
+
def find(ifnone = nil, &block)
|
50
|
+
found = @loaded_objects.find(&block)
|
51
|
+
until found || @load_complete
|
52
|
+
found = load_next_page.find(&block)
|
53
|
+
end
|
54
|
+
return found if found
|
55
|
+
return ifnone.call if ifnone
|
56
|
+
nil
|
57
|
+
end
|
58
|
+
alias :detect :find
|
59
|
+
|
60
|
+
def empty?(&block)
|
61
|
+
if block_given?
|
62
|
+
!any?(&block)
|
63
|
+
else
|
64
|
+
load_next_page unless load_started?
|
65
|
+
@loaded_objects.count.zero?
|
66
|
+
end
|
67
|
+
end
|
68
|
+
alias :none? :empty?
|
69
|
+
|
70
|
+
def any?(&block)
|
71
|
+
if block_given?
|
72
|
+
return true if @loaded_objects.any? &block
|
73
|
+
until @load_complete
|
74
|
+
load_next_page.any? &block
|
75
|
+
end
|
76
|
+
false
|
77
|
+
else
|
78
|
+
!empty?
|
79
|
+
end
|
80
|
+
end
|
81
|
+
|
82
|
+
def count_by(attribute)
|
83
|
+
return count_by_map_reduce(attribute) unless @load_complete
|
84
|
+
results = {}
|
85
|
+
@loaded_objects.each{|o| k = o.send(attribute).to_s; results[k] ||= 0; results[k] += 1 }
|
86
|
+
results
|
87
|
+
end
|
88
|
+
|
89
|
+
private
|
90
|
+
|
91
|
+
def load_started?
|
92
|
+
@load_complete || @loaded_objects.count > 0
|
93
|
+
end
|
94
|
+
|
95
|
+
def count_by_map_reduce(attribute)
|
96
|
+
count_by_index = @finder_class.index_names[attribute.to_sym].present?
|
97
|
+
parsed_attribute = count_by_index ? "v.values[0].metadata.index.#{@finder_class.index_names[attribute.to_sym]}" : "JSON.parse(v.values[0].data).#{attribute}"
|
98
|
+
Riak::MapReduce.new(@finder_class.client).
|
99
|
+
index(@bucket, @index, @value).
|
100
|
+
map("function(v){ var h = {}; h[#{parsed_attribute}] = 1; return [h] }", :keep => false).
|
101
|
+
reduce("function(values) { var result = {}; for (var value in values) { for (var key in values[value]) { if (key in result) { result[key] += values[value][key]; } else { result[key] = values[value][key]; }}} return [result]; }", :keep => true).run.first
|
102
|
+
end
|
103
|
+
|
104
|
+
def count_map_reduce
|
105
|
+
Riak::MapReduce.new(@finder_class.client).
|
106
|
+
index(@bucket, @index, @value).
|
107
|
+
map("function(v){ return [1] }", :keep => false).
|
108
|
+
reduce("Riak.reduceSum", :keep => true).run.first
|
109
|
+
end
|
110
|
+
|
111
|
+
def load_next_page
|
112
|
+
return if @load_complete
|
113
|
+
if @querier
|
114
|
+
@querier = @querier.next_page
|
115
|
+
else
|
116
|
+
@querier = Riak::SecondaryIndex.new(@bucket, @index, @value, :max_results => @page_size)
|
117
|
+
end
|
118
|
+
@load_complete = !@querier.has_next_page?
|
119
|
+
new_objects = @querier.values.map{ |robject| @finder_class.new(robject) }
|
120
|
+
@loaded_objects.concat(new_objects)
|
121
|
+
new_objects
|
122
|
+
end
|
123
|
+
|
124
|
+
end
|
125
|
+
end
|
data/lib/riak_record.rb
ADDED
data/riak-record.gemspec
CHANGED
@@ -2,16 +2,16 @@
|
|
2
2
|
# DO NOT EDIT THIS FILE DIRECTLY
|
3
3
|
# Instead, edit Jeweler::Tasks in Rakefile, and run 'rake gemspec'
|
4
4
|
# -*- encoding: utf-8 -*-
|
5
|
-
# stub: riak-record 0.0
|
5
|
+
# stub: riak-record 0.1.0 ruby lib
|
6
6
|
|
7
7
|
Gem::Specification.new do |s|
|
8
8
|
s.name = "riak-record"
|
9
|
-
s.version = "0.0
|
9
|
+
s.version = "0.1.0"
|
10
10
|
|
11
11
|
s.required_rubygems_version = Gem::Requirement.new(">= 0") if s.respond_to? :required_rubygems_version=
|
12
12
|
s.require_paths = ["lib"]
|
13
13
|
s.authors = ["Robert Graff"]
|
14
|
-
s.date = "2014-09-
|
14
|
+
s.date = "2014-09-23"
|
15
15
|
s.description = "RiakRecord is a thin and immature wrapper around riak-ruby-client. It creates a bucket for\n each class, provides a simple finder, and creates attribute reader."
|
16
16
|
s.email = "robert_graff@yahoo.com"
|
17
17
|
s.extra_rdoc_files = [
|
@@ -23,13 +23,21 @@ Gem::Specification.new do |s|
|
|
23
23
|
".rspec",
|
24
24
|
"Gemfile",
|
25
25
|
"Gemfile.lock",
|
26
|
+
"Guardfile",
|
26
27
|
"LICENSE.txt",
|
27
28
|
"README.md",
|
28
29
|
"Rakefile",
|
30
|
+
"TODO.md",
|
29
31
|
"VERSION",
|
30
|
-
"lib/
|
32
|
+
"lib/riak_record.rb",
|
33
|
+
"lib/riak_record/associations.rb",
|
34
|
+
"lib/riak_record/base.rb",
|
35
|
+
"lib/riak_record/finder.rb",
|
31
36
|
"riak-record.gemspec",
|
32
|
-
"spec/
|
37
|
+
"spec/riak_record/associations_spec.rb",
|
38
|
+
"spec/riak_record/base_spec.rb",
|
39
|
+
"spec/riak_record/finder_spec.rb",
|
40
|
+
"spec/riak_record_spec.rb",
|
33
41
|
"spec/spec_helper.rb"
|
34
42
|
]
|
35
43
|
s.homepage = "http://github.com/rgraff/riak-record"
|
@@ -47,6 +55,9 @@ Gem::Specification.new do |s|
|
|
47
55
|
s.add_development_dependency(%q<bundler>, ["~> 1.0"])
|
48
56
|
s.add_development_dependency(%q<jeweler>, ["~> 2.0.1"])
|
49
57
|
s.add_development_dependency(%q<simplecov>, [">= 0"])
|
58
|
+
s.add_development_dependency(%q<guard-rspec>, ["~> 4.3.1"])
|
59
|
+
s.add_development_dependency(%q<guard-bundler>, [">= 0"])
|
60
|
+
s.add_development_dependency(%q<terminal-notifier-guard>, [">= 0"])
|
50
61
|
else
|
51
62
|
s.add_dependency(%q<riak-client>, ["~> 2.0.0"])
|
52
63
|
s.add_dependency(%q<rspec>, ["~> 3.1.0"])
|
@@ -54,6 +65,9 @@ Gem::Specification.new do |s|
|
|
54
65
|
s.add_dependency(%q<bundler>, ["~> 1.0"])
|
55
66
|
s.add_dependency(%q<jeweler>, ["~> 2.0.1"])
|
56
67
|
s.add_dependency(%q<simplecov>, [">= 0"])
|
68
|
+
s.add_dependency(%q<guard-rspec>, ["~> 4.3.1"])
|
69
|
+
s.add_dependency(%q<guard-bundler>, [">= 0"])
|
70
|
+
s.add_dependency(%q<terminal-notifier-guard>, [">= 0"])
|
57
71
|
end
|
58
72
|
else
|
59
73
|
s.add_dependency(%q<riak-client>, ["~> 2.0.0"])
|
@@ -62,6 +76,9 @@ Gem::Specification.new do |s|
|
|
62
76
|
s.add_dependency(%q<bundler>, ["~> 1.0"])
|
63
77
|
s.add_dependency(%q<jeweler>, ["~> 2.0.1"])
|
64
78
|
s.add_dependency(%q<simplecov>, [">= 0"])
|
79
|
+
s.add_dependency(%q<guard-rspec>, ["~> 4.3.1"])
|
80
|
+
s.add_dependency(%q<guard-bundler>, [">= 0"])
|
81
|
+
s.add_dependency(%q<terminal-notifier-guard>, [">= 0"])
|
65
82
|
end
|
66
83
|
end
|
67
84
|
|