dynamoid 0.1.2 → 0.2.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.
- data/Dynamoid.gemspec +5 -3
- data/README.markdown +13 -4
- data/VERSION +1 -1
- data/lib/dynamoid/adapter.rb +6 -4
- data/lib/dynamoid/adapter/aws_sdk.rb +29 -8
- data/lib/dynamoid/adapter/local.rb +37 -12
- data/lib/dynamoid/associations/has_one.rb +10 -2
- data/lib/dynamoid/criteria.rb +1 -1
- data/lib/dynamoid/criteria/chain.rb +42 -6
- data/lib/dynamoid/errors.rb +1 -1
- data/lib/dynamoid/indexes.rb +18 -30
- data/lib/dynamoid/indexes/index.rb +62 -0
- data/lib/dynamoid/persistence.rb +7 -3
- data/spec/app/models/user.rb +4 -0
- data/spec/dynamoid/adapter/aws_sdk_spec.rb +63 -8
- data/spec/dynamoid/adapter/local_spec.rb +89 -5
- data/spec/dynamoid/adapter_spec.rb +29 -1
- data/spec/dynamoid/criteria/chain_spec.rb +31 -8
- data/spec/dynamoid/criteria_spec.rb +1 -1
- data/spec/dynamoid/indexes/index_spec.rb +84 -0
- data/spec/dynamoid/indexes_spec.rb +9 -37
- metadata +69 -22
@@ -0,0 +1,84 @@
|
|
1
|
+
require File.expand_path(File.dirname(__FILE__) + '/../../spec_helper')
|
2
|
+
|
3
|
+
describe "Dynamoid::Indexes::Index" do
|
4
|
+
|
5
|
+
before do
|
6
|
+
@time = DateTime.now
|
7
|
+
@index = Dynamoid::Indexes::Index.new(User, [:password, :name], :range_key => :created_at)
|
8
|
+
end
|
9
|
+
|
10
|
+
it 'reorders keys alphabetically' do
|
11
|
+
@index.sort([:password, :name, :created_at]).should == [:created_at, :name, :password]
|
12
|
+
end
|
13
|
+
|
14
|
+
it 'assigns itself hash keys' do
|
15
|
+
@index.hash_keys.should == [:name, :password]
|
16
|
+
end
|
17
|
+
|
18
|
+
it 'assigns itself range keys' do
|
19
|
+
@index.range_keys.should == [:created_at]
|
20
|
+
end
|
21
|
+
|
22
|
+
it 'reorders its name automatically' do
|
23
|
+
@index.name.should == [:created_at, :name, :password]
|
24
|
+
end
|
25
|
+
|
26
|
+
it 'determines its own table name' do
|
27
|
+
@index.table_name.should == 'dynamoid_tests_index_user_created_ats_and_names_and_passwords'
|
28
|
+
end
|
29
|
+
|
30
|
+
it 'raises an error if a field does not exist' do
|
31
|
+
lambda {@index = Dynamoid::Indexes::Index.new(User, [:password, :text])}.should raise_error(Dynamoid::Errors::InvalidField)
|
32
|
+
end
|
33
|
+
|
34
|
+
it 'returns values for indexes' do
|
35
|
+
@index.values(:name => 'Josh', :password => 'test123', :created_at => @time).should == {:hash_value => 'Josh.test123', :range_value => @time.to_f}
|
36
|
+
end
|
37
|
+
|
38
|
+
it 'ignores values for fields that do not exist' do
|
39
|
+
@index.values(:name => 'Josh', :password => 'test123', :created_at => @time, :email => 'josh@joshsymonds.com').should == {:hash_value => 'Josh.test123', :range_value => @time.to_f}
|
40
|
+
end
|
41
|
+
|
42
|
+
it 'substitutes a blank string for a hash value that does not exist' do
|
43
|
+
@index.values(:name => 'Josh', :created_at => @time).should == {:hash_value => 'Josh.', :range_value => @time.to_f}
|
44
|
+
end
|
45
|
+
|
46
|
+
it 'substitutes a blank string if both hash values do not exist' do
|
47
|
+
@index.values(:created_at => @time).should == {:hash_value => '.', :range_value => @time.to_f}
|
48
|
+
end
|
49
|
+
|
50
|
+
it 'accepts values from an object instead of a hash' do
|
51
|
+
@user = User.new(:name => 'Josh', :password => 'test123', :created_at => @time)
|
52
|
+
|
53
|
+
@index.values(@user).should == {:hash_value => 'Josh.test123', :range_value => @time.to_f}
|
54
|
+
end
|
55
|
+
|
56
|
+
it 'saves an object to the index it is associated with' do
|
57
|
+
@index = Dynamoid::Indexes::Index.new(User, :name)
|
58
|
+
@user = User.new(:name => 'Josh', :password => 'test123', :created_at => @time, :id => 'test123')
|
59
|
+
|
60
|
+
@index.save(@user)
|
61
|
+
|
62
|
+
Dynamoid::Adapter.read("dynamoid_tests_index_user_names", 'Josh')[:ids].should == Set['test123']
|
63
|
+
end
|
64
|
+
|
65
|
+
it 'saves an object to the index it is associated with with a range' do
|
66
|
+
@index = Dynamoid::Indexes::Index.new(User, :name, :range_key => :last_logged_in_at)
|
67
|
+
@user = User.create(:name => 'Josh', :last_logged_in_at => @time)
|
68
|
+
|
69
|
+
@index.save(@user)
|
70
|
+
|
71
|
+
Dynamoid::Adapter.read("dynamoid_tests_index_user_last_logged_in_ats_and_names", 'Josh', @time.to_f)[:ids].should == Set[@user.id]
|
72
|
+
end
|
73
|
+
|
74
|
+
it 'deletes an object from the index it is associated with' do
|
75
|
+
@index = Dynamoid::Indexes::Index.new(User, :name)
|
76
|
+
@user = User.create(:name => 'Josh', :password => 'test123', :last_logged_in_at => @time, :id => 'test123')
|
77
|
+
|
78
|
+
@index.save(@user)
|
79
|
+
@index.delete(@user)
|
80
|
+
|
81
|
+
Dynamoid::Adapter.read("dynamoid_tests_index_user_names", 'Josh')[:ids].should be_nil
|
82
|
+
end
|
83
|
+
|
84
|
+
end
|
@@ -2,52 +2,24 @@ require File.expand_path(File.dirname(__FILE__) + '/../spec_helper')
|
|
2
2
|
|
3
3
|
describe "Dynamoid::Indexes" do
|
4
4
|
|
5
|
-
before(:all) do
|
6
|
-
User.create_indexes
|
7
|
-
end
|
8
|
-
|
9
|
-
it 'raises an error if a field does not exist' do
|
10
|
-
lambda {User.send(:index, :test)}.should raise_error(Dynamoid::Errors::InvalidField)
|
11
|
-
end
|
12
|
-
|
13
5
|
it 'adds indexes to the index array' do
|
14
|
-
User.indexes.should
|
15
|
-
end
|
16
|
-
|
17
|
-
it 'reorders index names alphabetically' do
|
18
|
-
User.indexes.last.should == [:email, :name]
|
19
|
-
end
|
20
|
-
|
21
|
-
it 'creates a name for a table index' do
|
22
|
-
User.index_table_name([:email, :name]).should == 'dynamoid_tests_index_user_emails_and_names'
|
23
|
-
end
|
24
|
-
|
25
|
-
it 'assembles a hashed value for the key of an index' do
|
26
|
-
@user = User.create(:name => 'Josh', :email => 'josh@joshsymonds.com')
|
27
|
-
|
28
|
-
@user.key_for_index([:email, :name]).should == "Josh.josh@joshsymonds.com"
|
6
|
+
User.indexes.keys.should =~ [[:created_at], [:created_at, :name], [:email], [:email, :name], [:last_logged_in_at, :name], [:name]]
|
29
7
|
end
|
30
8
|
|
31
9
|
it 'saves indexes to their tables' do
|
32
|
-
@user = User.
|
10
|
+
@user = User.new(:name => 'Josh')
|
33
11
|
|
34
|
-
|
35
|
-
Dynamoid::Adapter.read("dynamoid_tests_index_user_names", @user.key_for_index([:name]))[:ids].should == Set[@user.id]
|
36
|
-
end
|
37
|
-
|
38
|
-
it 'saves multiple indexes with the same value as an array' do
|
39
|
-
@user1 = User.create(:name => 'Josh')
|
40
|
-
@user2 = User.create(:name => 'Josh')
|
12
|
+
User.indexes.each {|k, v| v.expects(:save).with(@user).once.returns(true)}
|
41
13
|
|
42
|
-
|
43
|
-
Dynamoid::Adapter.read("dynamoid_tests_index_user_names", @user1.key_for_index([:name]))[:ids].should == Set[@user2.id, @user1.id]
|
14
|
+
@user.save
|
44
15
|
end
|
45
|
-
|
16
|
+
|
46
17
|
it 'deletes indexes when the object is destroyed' do
|
47
18
|
@user = User.create(:name => 'Josh')
|
48
|
-
@user.destroy
|
49
19
|
|
50
|
-
|
51
|
-
end
|
20
|
+
User.indexes.each {|k, v| v.expects(:delete).with(@user).once.returns(true)}
|
52
21
|
|
22
|
+
@user.destroy
|
23
|
+
end
|
24
|
+
|
53
25
|
end
|
metadata
CHANGED
@@ -1,7 +1,7 @@
|
|
1
1
|
--- !ruby/object:Gem::Specification
|
2
2
|
name: dynamoid
|
3
3
|
version: !ruby/object:Gem::Version
|
4
|
-
version: 0.
|
4
|
+
version: 0.2.0
|
5
5
|
prerelease:
|
6
6
|
platform: ruby
|
7
7
|
authors:
|
@@ -9,11 +9,11 @@ authors:
|
|
9
9
|
autorequire:
|
10
10
|
bindir: bin
|
11
11
|
cert_chain: []
|
12
|
-
date: 2012-03-
|
12
|
+
date: 2012-03-15 00:00:00.000000000 Z
|
13
13
|
dependencies:
|
14
14
|
- !ruby/object:Gem::Dependency
|
15
15
|
name: activemodel
|
16
|
-
requirement:
|
16
|
+
requirement: !ruby/object:Gem::Requirement
|
17
17
|
none: false
|
18
18
|
requirements:
|
19
19
|
- - ! '>='
|
@@ -21,10 +21,15 @@ dependencies:
|
|
21
21
|
version: '0'
|
22
22
|
type: :runtime
|
23
23
|
prerelease: false
|
24
|
-
version_requirements:
|
24
|
+
version_requirements: !ruby/object:Gem::Requirement
|
25
|
+
none: false
|
26
|
+
requirements:
|
27
|
+
- - ! '>='
|
28
|
+
- !ruby/object:Gem::Version
|
29
|
+
version: '0'
|
25
30
|
- !ruby/object:Gem::Dependency
|
26
31
|
name: tzinfo
|
27
|
-
requirement:
|
32
|
+
requirement: !ruby/object:Gem::Requirement
|
28
33
|
none: false
|
29
34
|
requirements:
|
30
35
|
- - ! '>='
|
@@ -32,10 +37,15 @@ dependencies:
|
|
32
37
|
version: '0'
|
33
38
|
type: :runtime
|
34
39
|
prerelease: false
|
35
|
-
version_requirements:
|
40
|
+
version_requirements: !ruby/object:Gem::Requirement
|
41
|
+
none: false
|
42
|
+
requirements:
|
43
|
+
- - ! '>='
|
44
|
+
- !ruby/object:Gem::Version
|
45
|
+
version: '0'
|
36
46
|
- !ruby/object:Gem::Dependency
|
37
47
|
name: aws-sdk
|
38
|
-
requirement:
|
48
|
+
requirement: !ruby/object:Gem::Requirement
|
39
49
|
none: false
|
40
50
|
requirements:
|
41
51
|
- - ! '>='
|
@@ -43,10 +53,15 @@ dependencies:
|
|
43
53
|
version: '0'
|
44
54
|
type: :runtime
|
45
55
|
prerelease: false
|
46
|
-
version_requirements:
|
56
|
+
version_requirements: !ruby/object:Gem::Requirement
|
57
|
+
none: false
|
58
|
+
requirements:
|
59
|
+
- - ! '>='
|
60
|
+
- !ruby/object:Gem::Version
|
61
|
+
version: '0'
|
47
62
|
- !ruby/object:Gem::Dependency
|
48
63
|
name: mocha
|
49
|
-
requirement:
|
64
|
+
requirement: !ruby/object:Gem::Requirement
|
50
65
|
none: false
|
51
66
|
requirements:
|
52
67
|
- - ! '>='
|
@@ -54,10 +69,15 @@ dependencies:
|
|
54
69
|
version: '0'
|
55
70
|
type: :development
|
56
71
|
prerelease: false
|
57
|
-
version_requirements:
|
72
|
+
version_requirements: !ruby/object:Gem::Requirement
|
73
|
+
none: false
|
74
|
+
requirements:
|
75
|
+
- - ! '>='
|
76
|
+
- !ruby/object:Gem::Version
|
77
|
+
version: '0'
|
58
78
|
- !ruby/object:Gem::Dependency
|
59
79
|
name: rake
|
60
|
-
requirement:
|
80
|
+
requirement: !ruby/object:Gem::Requirement
|
61
81
|
none: false
|
62
82
|
requirements:
|
63
83
|
- - ! '>='
|
@@ -65,10 +85,15 @@ dependencies:
|
|
65
85
|
version: '0'
|
66
86
|
type: :development
|
67
87
|
prerelease: false
|
68
|
-
version_requirements:
|
88
|
+
version_requirements: !ruby/object:Gem::Requirement
|
89
|
+
none: false
|
90
|
+
requirements:
|
91
|
+
- - ! '>='
|
92
|
+
- !ruby/object:Gem::Version
|
93
|
+
version: '0'
|
69
94
|
- !ruby/object:Gem::Dependency
|
70
95
|
name: rspec
|
71
|
-
requirement:
|
96
|
+
requirement: !ruby/object:Gem::Requirement
|
72
97
|
none: false
|
73
98
|
requirements:
|
74
99
|
- - ! '>='
|
@@ -76,10 +101,15 @@ dependencies:
|
|
76
101
|
version: '0'
|
77
102
|
type: :development
|
78
103
|
prerelease: false
|
79
|
-
version_requirements:
|
104
|
+
version_requirements: !ruby/object:Gem::Requirement
|
105
|
+
none: false
|
106
|
+
requirements:
|
107
|
+
- - ! '>='
|
108
|
+
- !ruby/object:Gem::Version
|
109
|
+
version: '0'
|
80
110
|
- !ruby/object:Gem::Dependency
|
81
111
|
name: bundler
|
82
|
-
requirement:
|
112
|
+
requirement: !ruby/object:Gem::Requirement
|
83
113
|
none: false
|
84
114
|
requirements:
|
85
115
|
- - ! '>='
|
@@ -87,10 +117,15 @@ dependencies:
|
|
87
117
|
version: '0'
|
88
118
|
type: :development
|
89
119
|
prerelease: false
|
90
|
-
version_requirements:
|
120
|
+
version_requirements: !ruby/object:Gem::Requirement
|
121
|
+
none: false
|
122
|
+
requirements:
|
123
|
+
- - ! '>='
|
124
|
+
- !ruby/object:Gem::Version
|
125
|
+
version: '0'
|
91
126
|
- !ruby/object:Gem::Dependency
|
92
127
|
name: jeweler
|
93
|
-
requirement:
|
128
|
+
requirement: !ruby/object:Gem::Requirement
|
94
129
|
none: false
|
95
130
|
requirements:
|
96
131
|
- - ! '>='
|
@@ -98,10 +133,15 @@ dependencies:
|
|
98
133
|
version: '0'
|
99
134
|
type: :development
|
100
135
|
prerelease: false
|
101
|
-
version_requirements:
|
136
|
+
version_requirements: !ruby/object:Gem::Requirement
|
137
|
+
none: false
|
138
|
+
requirements:
|
139
|
+
- - ! '>='
|
140
|
+
- !ruby/object:Gem::Version
|
141
|
+
version: '0'
|
102
142
|
- !ruby/object:Gem::Dependency
|
103
143
|
name: rcov
|
104
|
-
requirement:
|
144
|
+
requirement: !ruby/object:Gem::Requirement
|
105
145
|
none: false
|
106
146
|
requirements:
|
107
147
|
- - ! '>='
|
@@ -109,7 +149,12 @@ dependencies:
|
|
109
149
|
version: '0'
|
110
150
|
type: :development
|
111
151
|
prerelease: false
|
112
|
-
version_requirements:
|
152
|
+
version_requirements: !ruby/object:Gem::Requirement
|
153
|
+
none: false
|
154
|
+
requirements:
|
155
|
+
- - ! '>='
|
156
|
+
- !ruby/object:Gem::Version
|
157
|
+
version: '0'
|
113
158
|
description: Dynamoid is an ORM for Amazon's DynamoDB that supports offline development,
|
114
159
|
associations, querying, and everything else you'd expect from an ActiveRecord-style
|
115
160
|
replacement.
|
@@ -149,6 +194,7 @@ files:
|
|
149
194
|
- lib/dynamoid/fields.rb
|
150
195
|
- lib/dynamoid/finders.rb
|
151
196
|
- lib/dynamoid/indexes.rb
|
197
|
+
- lib/dynamoid/indexes/index.rb
|
152
198
|
- lib/dynamoid/persistence.rb
|
153
199
|
- spec/app/models/address.rb
|
154
200
|
- spec/app/models/magazine.rb
|
@@ -170,6 +216,7 @@ files:
|
|
170
216
|
- spec/dynamoid/document_spec.rb
|
171
217
|
- spec/dynamoid/fields_spec.rb
|
172
218
|
- spec/dynamoid/finders_spec.rb
|
219
|
+
- spec/dynamoid/indexes/index_spec.rb
|
173
220
|
- spec/dynamoid/indexes_spec.rb
|
174
221
|
- spec/dynamoid/persistence_spec.rb
|
175
222
|
- spec/dynamoid_spec.rb
|
@@ -189,7 +236,7 @@ required_ruby_version: !ruby/object:Gem::Requirement
|
|
189
236
|
version: '0'
|
190
237
|
segments:
|
191
238
|
- 0
|
192
|
-
hash:
|
239
|
+
hash: -1313456439157708017
|
193
240
|
required_rubygems_version: !ruby/object:Gem::Requirement
|
194
241
|
none: false
|
195
242
|
requirements:
|
@@ -198,7 +245,7 @@ required_rubygems_version: !ruby/object:Gem::Requirement
|
|
198
245
|
version: '0'
|
199
246
|
requirements: []
|
200
247
|
rubyforge_project:
|
201
|
-
rubygems_version: 1.8.
|
248
|
+
rubygems_version: 1.8.18
|
202
249
|
signing_key:
|
203
250
|
specification_version: 3
|
204
251
|
summary: Dynamoid is an ORM for Amazon's DynamoDB
|