mongous 0.2.0 → 0.4.2
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/.rubocop.yml +73 -0
- data/README.adoc +191 -38
- data/README.ja.adoc +192 -39
- data/Rakefile +8 -8
- data/lib/mongous/base.rb +52 -8
- data/lib/mongous/document.rb +36 -13
- data/lib/mongous/extention.rb +51 -39
- data/lib/mongous/filter.rb +316 -227
- data/lib/mongous/version.rb +1 -1
- data/mongous.gemspec +4 -4
- data/sample/connect_auto_0.rb +9 -0
- data/sample/declare_compact_1.rb +6 -8
- data/sample/declare_compact_2.rb +38 -0
- data/sample/declare_label_1.rb +9 -7
- data/sample/declare_ndex_1.rb +8 -6
- data/sample/declare_ndex_2.rb +9 -7
- data/sample/declare_strict_1.rb +9 -9
- data/sample/declare_strict_2.rb +4 -5
- data/sample/multi_collection_1.rb +0 -2
- data/sample/multi_collection_2.rb +5 -5
- data/sample/multi_collection_3.rb +24 -0
- data/sample/query_basic_1.rb +8 -2
- data/sample/query_basic_2.rb +8 -2
- data/sample/query_basic_3.rb +0 -2
- data/sample/query_basic_4.rb +3 -5
- data/sample/query_basic_5.rb +0 -2
- data/sample/query_basic_6.rb +56 -0
- data/sample/query_detail_1.rb +3 -3
- data/sample/query_detail_2.rb +3 -3
- data/sample/query_detail_3.rb +4 -5
- data/sample/query_filter_1.rb +1 -3
- data/sample/query_filter_2.rb +2 -4
- data/sample/query_find_1.rb +6 -5
- data/sample/query_select_1.rb +54 -0
- data/sample/query_skip_limit_1.rb +25 -14
- data/sample/query_skip_limit_2.rb +20 -11
- data/sample/query_sort_1.rb +43 -0
- data/sample/save_basic_1.rb +2 -6
- data/sample/save_basic_2.rb +2 -6
- data/sample/save_basic_3.rb +2 -6
- data/sample/save_detail_1.rb +3 -3
- data/sample/save_detail_2.rb +3 -3
- data/sample/save_detail_3.rb +10 -10
- data/sample/save_verify_1.rb +6 -6
- data/sample/save_verify_2.rb +0 -2
- data/sample/save_verify_3.rb +0 -2
- data/sample/save_verify_4.rb +0 -2
- data/sample/save_verify_5.rb +3 -5
- data/sample/save_verify_6.rb +3 -5
- data/sample/save_verify_7.rb +21 -0
- data/sample/update_basic_1.rb +9 -0
- data/sample/zap_basic_1.rb +1 -5
- data/sample/zap_basic_2.rb +2 -6
- data/sample/zap_basic_3.rb +2 -6
- data/sample/zbenchmark_search_1.rb +114 -0
- data/sample/zbenchmark_search_2.rb +114 -0
- data/sample/zbenchmark_search_3.rb +88 -0
- metadata +31 -21
- data/sample/query_projection_1.rb +0 -41
- data/sample/query_sort_order_1.rb +0 -46
data/lib/mongous/document.rb
CHANGED
@@ -15,7 +15,7 @@ module Mongous
|
|
15
15
|
end
|
16
16
|
end
|
17
17
|
|
18
|
-
def method_missing( sym, *args, **
|
18
|
+
def method_missing( sym, *args, **_opts, &_block )
|
19
19
|
m = /\A(\w+)([=])?\Z/.match( sym.to_s )
|
20
20
|
if args.size == 0 && m[2].nil?
|
21
21
|
self[ m[1] ]
|
@@ -52,17 +52,25 @@ module Mongous
|
|
52
52
|
else
|
53
53
|
savemode = :update
|
54
54
|
end
|
55
|
+
|
55
56
|
self.class.fields.each do |label, field|
|
56
|
-
|
57
|
+
default_value = getvalue_or_callproc( field[:default] )
|
58
|
+
must = field[:_attrs].include?(:must)
|
57
59
|
if @doc.has_key?(label)
|
58
|
-
if
|
59
|
-
|
60
|
+
if !having?( @doc[label] )
|
61
|
+
if default_value
|
62
|
+
self[label] = default_value
|
63
|
+
elsif must
|
64
|
+
raise Mongous::Error, "must but unassigned field. : #{ label }"
|
65
|
+
elsif self.class.symbols[:strict]
|
66
|
+
self[label] = nil
|
67
|
+
end
|
60
68
|
end
|
61
69
|
else
|
62
|
-
if default_value
|
70
|
+
if default_value
|
63
71
|
self[label] = default_value
|
64
|
-
elsif
|
65
|
-
raise Mongous::Error, "must
|
72
|
+
elsif must
|
73
|
+
raise Mongous::Error, "must but unassigned field. : #{ label }"
|
66
74
|
elsif self.class.symbols[:strict]
|
67
75
|
self[label] = nil
|
68
76
|
end
|
@@ -70,11 +78,11 @@ module Mongous
|
|
70
78
|
|
71
79
|
case savemode
|
72
80
|
when :create
|
73
|
-
if
|
81
|
+
if ( create_value = getvalue_or_callproc( field[:create] ) )
|
74
82
|
self[label] = create_value
|
75
83
|
end
|
76
84
|
when :update
|
77
|
-
if
|
85
|
+
if ( update_value = getvalue_or_callproc( field[:update] ) )
|
78
86
|
self[label] = update_value
|
79
87
|
end
|
80
88
|
end
|
@@ -92,15 +100,23 @@ module Mongous
|
|
92
100
|
when :update
|
93
101
|
self.class.collection.update_one( { "_id"=> @doc["_id"] }, { '$set' => @doc } )
|
94
102
|
end
|
95
|
-
|
96
103
|
self
|
97
104
|
end
|
98
105
|
|
106
|
+
def to_hash
|
107
|
+
@doc.dup
|
108
|
+
end
|
109
|
+
|
110
|
+
def to_json( **opts )
|
111
|
+
::JSON.generate( @doc, **opts )
|
112
|
+
end
|
113
|
+
|
99
114
|
def []( label )
|
100
115
|
label = label.to_s
|
101
116
|
|
102
117
|
if self.class.symbols[:strict]
|
103
|
-
|
118
|
+
labels = ["_id"] + self.class.fields.keys
|
119
|
+
if !labels.include?( label )
|
104
120
|
raise Mongous::Error, "undefined field. : #{ label }"
|
105
121
|
end
|
106
122
|
end
|
@@ -128,10 +144,13 @@ module Mongous
|
|
128
144
|
end
|
129
145
|
|
130
146
|
field = self.class.fields[label]
|
131
|
-
|
147
|
+
if field.nil?
|
148
|
+
@doc[label] = value
|
149
|
+
return
|
150
|
+
end
|
132
151
|
|
133
152
|
types = []
|
134
|
-
if
|
153
|
+
if ( attrs = field[:_attrs] || [] )
|
135
154
|
attrs.each do |attr|
|
136
155
|
if attr.class == Class
|
137
156
|
types << attr
|
@@ -175,6 +194,10 @@ module Mongous
|
|
175
194
|
if !attr.cover?( value )
|
176
195
|
raise Mongous::Error, "out of range. : #{ label } : #{ value }"
|
177
196
|
end
|
197
|
+
when Regexp
|
198
|
+
if !attr.match( value )
|
199
|
+
raise Mongous::Error, "unmatch regexp. : #{ label } : #{ value }"
|
200
|
+
end
|
178
201
|
end
|
179
202
|
end
|
180
203
|
end
|
data/lib/mongous/extention.rb
CHANGED
@@ -5,87 +5,93 @@ module Mongous
|
|
5
5
|
if self.class_variable_defined?( :@@client )
|
6
6
|
self.class_variable_get( :@@client )
|
7
7
|
else
|
8
|
-
|
9
|
-
self.class_variable_set( :@@client,
|
8
|
+
new_client = Mongous.client
|
9
|
+
self.class_variable_set( :@@client, new_client )
|
10
10
|
end
|
11
11
|
end
|
12
12
|
|
13
|
-
def client=(
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
raise Mongous::Error, "type invalid. : #{
|
13
|
+
def client=( new_client )
|
14
|
+
if !new_client.is_a?( Mongo::Client )
|
15
|
+
m = /(.*?):(\d+)/.match( caller()[0] )
|
16
|
+
call_from = [ m[1], m[2] ].join(":")
|
17
|
+
raise Mongous::Error, "type invalid. : #{ new_client } at #{ call_from }"
|
18
18
|
end
|
19
|
-
self.class_variable_set( :@@client,
|
19
|
+
self.class_variable_set( :@@client, new_client )
|
20
20
|
end
|
21
21
|
|
22
22
|
def collection_name
|
23
23
|
if self.class_variable_defined?( :@@collection_name )
|
24
|
-
self.class_variable_get( :@@collection_name )
|
25
|
-
|
26
|
-
_client_name = self.name
|
27
|
-
self.class_variable_set( :@@collection_name, _client_name )
|
24
|
+
value = self.class_variable_get( :@@collection_name )
|
25
|
+
return value if value
|
28
26
|
end
|
27
|
+
|
28
|
+
self.class_variable_set( :@@collection_name, self.name )
|
29
29
|
end
|
30
30
|
|
31
|
-
def collection_name=(
|
32
|
-
self.class_variable_set( :@@collection_name,
|
31
|
+
def collection_name=( new_collection_name )
|
32
|
+
self.class_variable_set( :@@collection_name, new_collection_name )
|
33
33
|
if self.class_variable_defined?( :@@collection )
|
34
34
|
self.remove_class_variable( :@@collection )
|
35
35
|
end
|
36
36
|
end
|
37
37
|
|
38
|
-
def collection
|
39
|
-
if
|
40
|
-
if
|
41
|
-
|
38
|
+
def collection( temp_collection_name = nil )
|
39
|
+
if temp_collection_name.nil?
|
40
|
+
if self.class_variable_defined?( :@@collection )
|
41
|
+
if ( new_collection = self.class_variable_get( :@@collection ) )
|
42
|
+
return new_collection
|
43
|
+
end
|
42
44
|
end
|
45
|
+
new_collection_name = collection_name
|
46
|
+
else
|
47
|
+
new_collection_name = temp_collection_name
|
43
48
|
end
|
49
|
+
new_client = client
|
44
50
|
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
if _client.database.collection_names.include?( _collection_name )
|
49
|
-
_collection = _client[ _collection_name ]
|
51
|
+
if new_client.database.collection_names.include?( new_collection_name )
|
52
|
+
new_collection = new_client[ new_collection_name ]
|
50
53
|
else
|
51
|
-
|
52
|
-
|
54
|
+
new_collection = new_client[ new_collection_name ]
|
55
|
+
new_collection.create
|
53
56
|
end
|
54
57
|
|
55
58
|
indexes.each do |keys, opts|
|
56
|
-
|
59
|
+
new_collection.indexes.create_one( keys, opts ) rescue nil
|
57
60
|
end
|
58
61
|
|
59
|
-
self.class_variable_set( :@@collection,
|
62
|
+
self.class_variable_set( :@@collection, new_collection ) if temp_collection_name.nil?
|
63
|
+
new_collection
|
60
64
|
end
|
61
65
|
|
62
66
|
def fields
|
63
|
-
|
67
|
+
setup_class_variable( :@@fields, {} )
|
64
68
|
end
|
65
69
|
|
66
70
|
def symbols
|
67
|
-
|
71
|
+
setup_class_variable( :@@symbols, {} )
|
68
72
|
end
|
69
73
|
|
70
74
|
def blocks
|
71
|
-
|
75
|
+
setup_class_variable( :@@blocks, {} )
|
72
76
|
end
|
73
77
|
|
74
78
|
def indexes
|
75
|
-
|
79
|
+
setup_class_variable( :@@indexes, [] )
|
76
80
|
end
|
77
81
|
|
78
82
|
def filters
|
79
|
-
|
83
|
+
setup_class_variable( :@@filters, {} )
|
80
84
|
end
|
81
85
|
|
82
86
|
def defaults
|
83
|
-
|
87
|
+
setup_class_variable( :@@defaults, {} )
|
84
88
|
end
|
85
89
|
|
86
|
-
def
|
90
|
+
def setup_class_variable( symbol, default = {}, &block )
|
87
91
|
if self.class_variable_defined?( symbol )
|
88
92
|
self.class_variable_get( symbol )
|
93
|
+
elsif block_given?
|
94
|
+
self.class_variable_set( symbol, block.call )
|
89
95
|
else
|
90
96
|
self.class_variable_set( symbol, default )
|
91
97
|
end
|
@@ -95,6 +101,10 @@ module Mongous
|
|
95
101
|
self.new( **doc ).save
|
96
102
|
end
|
97
103
|
|
104
|
+
def drop
|
105
|
+
self.collection.drop
|
106
|
+
end
|
107
|
+
|
98
108
|
def find( conditios = {}, options = {} )
|
99
109
|
self.collection.find( conditios, options )
|
100
110
|
end
|
@@ -104,9 +114,9 @@ module Mongous
|
|
104
114
|
call_from = [ m[1], m[2] ].join(":")
|
105
115
|
|
106
116
|
attrs.each do |attr|
|
107
|
-
if klass = attr.class
|
108
|
-
if ![Class, Range, Array, Proc, Symbol].include?(klass)
|
109
|
-
raise Mongous::Error, "field
|
117
|
+
if ( klass = attr.class )
|
118
|
+
if ![Class, Range, Array, Regexp, Proc, Symbol].include?(klass)
|
119
|
+
raise Mongous::Error, "'field' arguments error. : #{ attr } on #{ symbol } at #{ call_from }"
|
110
120
|
end
|
111
121
|
end
|
112
122
|
end
|
@@ -114,7 +124,7 @@ module Mongous
|
|
114
124
|
items.each do |key, value|
|
115
125
|
next if [:default, :create, :update].include?(key) && [Proc, String, Numeric].include?(value.class)
|
116
126
|
|
117
|
-
raise Mongous::Error, "field
|
127
|
+
raise Mongous::Error, "'field' options error. : #{key} on #{ symbol } at #{ call_from }"
|
118
128
|
end
|
119
129
|
|
120
130
|
items[:_attrs] = attrs
|
@@ -130,6 +140,8 @@ module Mongous
|
|
130
140
|
m = /(.*?):(\d+)/.match( caller()[0] )
|
131
141
|
call_from = [ m[1], m[2] ].join(":")
|
132
142
|
blocks[call_from] = block
|
143
|
+
else
|
144
|
+
raise Mongous::Error, "'verify' arguments error. need directives or block."
|
133
145
|
end
|
134
146
|
end
|
135
147
|
|
@@ -151,7 +163,7 @@ module Mongous
|
|
151
163
|
else
|
152
164
|
m = /(.*?):(\d+)/.match( caller()[0] )
|
153
165
|
call_from = [ m[1], m[2] ].join(":")
|
154
|
-
raise Mongous::Error, "filter error. : #{symbol}, #{filter_or_condition} at #{ call_from }"
|
166
|
+
raise Mongous::Error, "'filter' arguments error. : #{symbol}, #{filter_or_condition} at #{ call_from }"
|
155
167
|
end
|
156
168
|
end
|
157
169
|
end
|
data/lib/mongous/filter.rb
CHANGED
@@ -1,227 +1,316 @@
|
|
1
|
-
|
2
|
-
module Mongous
|
3
|
-
module Extention
|
4
|
-
def count
|
5
|
-
self.collection.
|
6
|
-
end
|
7
|
-
|
8
|
-
def
|
9
|
-
|
10
|
-
|
11
|
-
|
12
|
-
|
13
|
-
|
14
|
-
|
15
|
-
|
16
|
-
|
17
|
-
|
18
|
-
|
19
|
-
|
20
|
-
|
21
|
-
|
22
|
-
|
23
|
-
|
24
|
-
|
25
|
-
|
26
|
-
|
27
|
-
|
28
|
-
|
29
|
-
|
30
|
-
|
31
|
-
|
32
|
-
|
33
|
-
|
34
|
-
|
35
|
-
|
36
|
-
|
37
|
-
|
38
|
-
|
39
|
-
|
40
|
-
|
41
|
-
|
42
|
-
|
43
|
-
|
44
|
-
|
45
|
-
|
46
|
-
|
47
|
-
|
48
|
-
|
49
|
-
|
50
|
-
|
51
|
-
|
52
|
-
|
53
|
-
|
54
|
-
|
55
|
-
|
56
|
-
|
57
|
-
|
58
|
-
condition =
|
59
|
-
|
60
|
-
|
61
|
-
|
62
|
-
|
63
|
-
|
64
|
-
|
65
|
-
|
66
|
-
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
71
|
-
|
72
|
-
|
73
|
-
|
74
|
-
|
75
|
-
|
76
|
-
end
|
77
|
-
|
78
|
-
|
79
|
-
|
80
|
-
def
|
81
|
-
|
82
|
-
|
83
|
-
|
84
|
-
|
85
|
-
|
86
|
-
|
87
|
-
|
88
|
-
|
89
|
-
|
90
|
-
|
91
|
-
|
92
|
-
|
93
|
-
|
94
|
-
|
95
|
-
|
96
|
-
|
97
|
-
|
98
|
-
|
99
|
-
|
100
|
-
|
101
|
-
|
102
|
-
|
103
|
-
|
104
|
-
|
105
|
-
|
106
|
-
|
107
|
-
|
108
|
-
|
109
|
-
|
110
|
-
|
111
|
-
|
112
|
-
|
113
|
-
|
114
|
-
|
115
|
-
|
116
|
-
|
117
|
-
|
118
|
-
|
119
|
-
|
120
|
-
|
121
|
-
|
122
|
-
|
123
|
-
|
124
|
-
|
125
|
-
|
126
|
-
|
127
|
-
|
128
|
-
|
129
|
-
|
130
|
-
|
131
|
-
|
132
|
-
|
133
|
-
|
134
|
-
|
135
|
-
|
136
|
-
|
137
|
-
|
138
|
-
|
139
|
-
|
140
|
-
|
141
|
-
|
142
|
-
|
143
|
-
|
144
|
-
|
145
|
-
|
146
|
-
|
147
|
-
|
148
|
-
|
149
|
-
|
150
|
-
|
151
|
-
|
152
|
-
|
153
|
-
|
154
|
-
|
155
|
-
|
156
|
-
|
157
|
-
|
158
|
-
|
159
|
-
|
160
|
-
|
161
|
-
|
162
|
-
|
163
|
-
|
164
|
-
|
165
|
-
|
166
|
-
|
167
|
-
|
168
|
-
|
169
|
-
|
170
|
-
|
171
|
-
|
172
|
-
|
173
|
-
self.dup
|
174
|
-
|
175
|
-
|
176
|
-
|
177
|
-
|
178
|
-
|
179
|
-
|
180
|
-
|
181
|
-
|
182
|
-
|
183
|
-
|
184
|
-
|
185
|
-
|
186
|
-
|
187
|
-
|
188
|
-
|
189
|
-
|
190
|
-
|
191
|
-
|
192
|
-
|
193
|
-
|
194
|
-
|
195
|
-
|
196
|
-
|
197
|
-
|
198
|
-
|
199
|
-
|
200
|
-
|
201
|
-
|
202
|
-
|
203
|
-
|
204
|
-
|
205
|
-
|
206
|
-
|
207
|
-
|
208
|
-
|
209
|
-
|
210
|
-
|
211
|
-
|
212
|
-
|
213
|
-
|
214
|
-
|
215
|
-
|
216
|
-
|
217
|
-
|
218
|
-
|
219
|
-
|
220
|
-
|
221
|
-
|
222
|
-
|
223
|
-
|
224
|
-
|
225
|
-
|
226
|
-
|
227
|
-
|
1
|
+
|
2
|
+
module Mongous
|
3
|
+
module Extention
|
4
|
+
def count
|
5
|
+
self.collection.estimated_document_count
|
6
|
+
end
|
7
|
+
|
8
|
+
def all
|
9
|
+
self.collection.find.map do |doc|
|
10
|
+
self.new( **doc )
|
11
|
+
end
|
12
|
+
end
|
13
|
+
|
14
|
+
def each( &block )
|
15
|
+
all.each( &block )
|
16
|
+
end
|
17
|
+
|
18
|
+
def map( &block )
|
19
|
+
all.map( &block )
|
20
|
+
end
|
21
|
+
|
22
|
+
def delete
|
23
|
+
self.collection.delete_many({})
|
24
|
+
end
|
25
|
+
|
26
|
+
def attach( collection_name )
|
27
|
+
Filter.new( self ).attach( collection_name )
|
28
|
+
end
|
29
|
+
|
30
|
+
def []( nth_or_range, len = nil )
|
31
|
+
Filter.new( self )[ nth_or_range, len ]
|
32
|
+
end
|
33
|
+
|
34
|
+
def first
|
35
|
+
Filter.new( self ).first
|
36
|
+
end
|
37
|
+
|
38
|
+
def last
|
39
|
+
Filter.new( self ).last
|
40
|
+
end
|
41
|
+
|
42
|
+
def sort( *keys, **hash )
|
43
|
+
Filter.new( self ).sort( *keys, **hash )
|
44
|
+
end
|
45
|
+
|
46
|
+
def select( *keys, **hash )
|
47
|
+
Filter.new( self ).select( *keys, **hash )
|
48
|
+
end
|
49
|
+
|
50
|
+
def where( filter = nil, **conditions )
|
51
|
+
condition = normalize( filter, conditions )
|
52
|
+
Filter.new( self ).where( condition )
|
53
|
+
end
|
54
|
+
|
55
|
+
def not( filter = nil, **conditions )
|
56
|
+
raise Mongous::Error, "Unset args for #{self}.not." if filter.nil? && conditions.empty?
|
57
|
+
|
58
|
+
condition = normalize( filter, conditions )
|
59
|
+
Filter.new( self ).not( condition )
|
60
|
+
end
|
61
|
+
|
62
|
+
def and( *filters )
|
63
|
+
raise Mongous::Error, "Unset args for #{self}.and." if filters.empty?
|
64
|
+
|
65
|
+
conditions = filters.map do |filter|
|
66
|
+
normalize( filter, {} )
|
67
|
+
end
|
68
|
+
Filter.new( self ).where({"$and" => conditions})
|
69
|
+
end
|
70
|
+
|
71
|
+
def or( *filters )
|
72
|
+
raise Mongous::Error, "Unset args for #{self}.or." if filters.empty?
|
73
|
+
|
74
|
+
conditions = filters.map do |filter|
|
75
|
+
normalize( filter, {} )
|
76
|
+
end
|
77
|
+
Filter.new( self ).where({"$or" => conditions})
|
78
|
+
end
|
79
|
+
|
80
|
+
def normalize( filter, conditions )
|
81
|
+
case filter
|
82
|
+
when Filter
|
83
|
+
filter.to_condition
|
84
|
+
when Symbol
|
85
|
+
case ( new_filter = filters[filter] )
|
86
|
+
when Filter
|
87
|
+
new_filter.to_condition
|
88
|
+
when Hash
|
89
|
+
new_filter
|
90
|
+
end
|
91
|
+
when NilClass
|
92
|
+
Filter.new( self ).where( conditions ).to_condition
|
93
|
+
else
|
94
|
+
caller_method = /`(.*?)'/.match( caller()[0] )[1]
|
95
|
+
raise Mongous::Error, "Invalid args for #{self}.#{ caller_method }. : #{filter}, #{conditions}"
|
96
|
+
end
|
97
|
+
end
|
98
|
+
end
|
99
|
+
end
|
100
|
+
|
101
|
+
module Mongous
|
102
|
+
class Filter
|
103
|
+
def initialize( klass )
|
104
|
+
@klass = klass
|
105
|
+
@filter = {}
|
106
|
+
@option = {}
|
107
|
+
end
|
108
|
+
|
109
|
+
def attach( collection_name )
|
110
|
+
w = self.dup
|
111
|
+
w.instance_variable_set( :@collection_name, collection_name.to_s )
|
112
|
+
w
|
113
|
+
end
|
114
|
+
|
115
|
+
def build_condition( conditions )
|
116
|
+
hash = {}
|
117
|
+
conditions.each do |key, item|
|
118
|
+
case key
|
119
|
+
when /\$(and|or|nor)/
|
120
|
+
hash[key] = item
|
121
|
+
|
122
|
+
else
|
123
|
+
case item
|
124
|
+
when Array
|
125
|
+
hash[key] = {"$in"=>item}
|
126
|
+
|
127
|
+
when Range
|
128
|
+
begin_oper = "$gte"
|
129
|
+
end_oper = item.exclude_end? ? "$lt" : "$lte"
|
130
|
+
|
131
|
+
if item.begin && item.end
|
132
|
+
hash[key] = { begin_oper => item.begin, end_oper => item.end }
|
133
|
+
|
134
|
+
elsif !item.begin && item.end
|
135
|
+
hash[key] = { end_oper => item.end }
|
136
|
+
|
137
|
+
elsif item.begin && !item.end
|
138
|
+
hash[key] = { begin_oper => item.begin }
|
139
|
+
|
140
|
+
else
|
141
|
+
raise Mongous::Error, "invalid range. : #{ item }"
|
142
|
+
|
143
|
+
end
|
144
|
+
|
145
|
+
else
|
146
|
+
hash[key] = item
|
147
|
+
|
148
|
+
end
|
149
|
+
end
|
150
|
+
end
|
151
|
+
hash
|
152
|
+
end
|
153
|
+
|
154
|
+
def where( conditions = {} )
|
155
|
+
hash = build_condition( conditions )
|
156
|
+
w = self.dup
|
157
|
+
w.instance_variable_set( :@filter, @filter.merge( hash ) )
|
158
|
+
w
|
159
|
+
end
|
160
|
+
|
161
|
+
def not( conditions = {} )
|
162
|
+
hash = build_condition( conditions )
|
163
|
+
w = self.dup
|
164
|
+
w.instance_variable_set( :@filter, @filter.merge( {"$nor" => [hash]} ) )
|
165
|
+
w
|
166
|
+
end
|
167
|
+
|
168
|
+
def to_condition
|
169
|
+
@filter.dup
|
170
|
+
end
|
171
|
+
|
172
|
+
def option( new_option )
|
173
|
+
w = self.dup
|
174
|
+
w.instance_variable_set( :@option, @option.merge( new_option ) )
|
175
|
+
w
|
176
|
+
end
|
177
|
+
|
178
|
+
def select( *keys, **hash )
|
179
|
+
if not keys.empty?
|
180
|
+
new_projection = Hash[ keys.zip( Array.new(keys.length, 1) ) ]
|
181
|
+
elsif not hash.empty?
|
182
|
+
new_projection = hash
|
183
|
+
else
|
184
|
+
new_projection = nil
|
185
|
+
end
|
186
|
+
w = self.dup
|
187
|
+
w.instance_variable_set( :@projection, new_projection )
|
188
|
+
w
|
189
|
+
end
|
190
|
+
|
191
|
+
def sort( *keys, **hash )
|
192
|
+
if not keys.empty?
|
193
|
+
new_sort = Hash[ keys.zip( Array.new( keys.length, 1 ) ) ]
|
194
|
+
elsif not hash.empty?
|
195
|
+
new_sort = hash
|
196
|
+
else
|
197
|
+
new_sort = nil
|
198
|
+
end
|
199
|
+
w = self.dup
|
200
|
+
w.instance_variable_set( :@sort, new_sort )
|
201
|
+
w
|
202
|
+
end
|
203
|
+
|
204
|
+
def []( nth_or_range, len = nil )
|
205
|
+
case nth_or_range
|
206
|
+
when Integer
|
207
|
+
new_skip = nth_or_range
|
208
|
+
|
209
|
+
if len.is_a?(NilClass)
|
210
|
+
new_limit = 1
|
211
|
+
elsif len.is_a?(Integer) && len == 0
|
212
|
+
new_limit = nil
|
213
|
+
elsif len.is_a?(Integer) && len > 0
|
214
|
+
new_limit = len
|
215
|
+
else
|
216
|
+
raise Mongous::Error, "invalid len. : #{ len }"
|
217
|
+
end
|
218
|
+
|
219
|
+
when Range
|
220
|
+
from = nth_or_range.begin
|
221
|
+
raise Mongous::Error, "invalid range. : #{ nth_or_range }" unless from.is_a? Integer
|
222
|
+
|
223
|
+
to = nth_or_range.end
|
224
|
+
raise Mongous::Error, "invalid range. : #{ nth_or_range }" unless to.is_a? Integer
|
225
|
+
|
226
|
+
to -= 1 if nth_or_range.exclude_end?
|
227
|
+
new_skip = from
|
228
|
+
new_limit = to - from + 1
|
229
|
+
|
230
|
+
else
|
231
|
+
raise Mongous::Error, "invalid class. : #{ nth_or_range }"
|
232
|
+
|
233
|
+
end
|
234
|
+
|
235
|
+
w = self.dup
|
236
|
+
w.instance_variable_set( :@skip, new_skip )
|
237
|
+
w.instance_variable_set( :@limit, new_limit )
|
238
|
+
w
|
239
|
+
end
|
240
|
+
|
241
|
+
def exec_query
|
242
|
+
new_filter = @filter
|
243
|
+
new_option = @option.dup
|
244
|
+
new_option[:projection] = @projection if @projection
|
245
|
+
found = @klass.collection( @collection_name ).find( new_filter, new_option )
|
246
|
+
found = found.sort( @sort ) if @sort
|
247
|
+
found = found.skip( @skip ) if @skip
|
248
|
+
found = found.limit( @limit ) if @limit
|
249
|
+
found
|
250
|
+
end
|
251
|
+
|
252
|
+
def count
|
253
|
+
found = @klass.collection.find( @filter )
|
254
|
+
found = found.skip( @skip ) if @skip
|
255
|
+
found = found.limit( @limit ) if @limit
|
256
|
+
new_count = found.count_documents
|
257
|
+
if @skip
|
258
|
+
if @skip > new_count
|
259
|
+
0
|
260
|
+
elsif @limit
|
261
|
+
[new_count - @skip, @limit].min
|
262
|
+
else
|
263
|
+
new_count - @skip
|
264
|
+
end
|
265
|
+
else
|
266
|
+
if @limit
|
267
|
+
[new_count, @limit].min
|
268
|
+
else
|
269
|
+
new_count
|
270
|
+
end
|
271
|
+
end
|
272
|
+
end
|
273
|
+
|
274
|
+
def first
|
275
|
+
new_filter = @filter
|
276
|
+
new_option = @option.dup
|
277
|
+
new_option[:projection] = @projection if @projection
|
278
|
+
found = @klass.collection( @collection_name ).find( new_filter, new_option )
|
279
|
+
new_order = @sort || { _id: 1 }
|
280
|
+
doc = found.sort( new_order ).first
|
281
|
+
@klass.new( **doc ) if doc
|
282
|
+
end
|
283
|
+
|
284
|
+
def last
|
285
|
+
new_filter = @filter
|
286
|
+
new_option = @option.dup
|
287
|
+
new_option[:projection] = @projection if @projection
|
288
|
+
found = @klass.collection( @collection_name ).find( new_filter, new_option )
|
289
|
+
new_order = {}
|
290
|
+
( @sort || {_id: 1} ).each do |k,v|
|
291
|
+
new_order[k] = - v
|
292
|
+
end
|
293
|
+
doc = found.sort( new_order ).first
|
294
|
+
@klass.new( **doc ) if doc
|
295
|
+
end
|
296
|
+
|
297
|
+
def all
|
298
|
+
exec_query.map do |doc|
|
299
|
+
@klass.new( **doc )
|
300
|
+
end
|
301
|
+
end
|
302
|
+
|
303
|
+
def each( &block )
|
304
|
+
all.each( &block )
|
305
|
+
end
|
306
|
+
|
307
|
+
def map( &block )
|
308
|
+
all.map( &block )
|
309
|
+
end
|
310
|
+
|
311
|
+
def delete
|
312
|
+
@klass.collection.delete_many( @filter )
|
313
|
+
end
|
314
|
+
end
|
315
|
+
end
|
316
|
+
|