cuprum-collections 0.4.0 → 0.5.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/CHANGELOG.md +73 -0
- data/README.md +5 -5
- data/lib/cuprum/collections/association.rb +9 -28
- data/lib/cuprum/collections/associations/belongs_to.rb +1 -8
- data/lib/cuprum/collections/associations/has_many.rb +1 -10
- data/lib/cuprum/collections/associations/has_one.rb +1 -10
- data/lib/cuprum/collections/basic/collection.rb +56 -49
- data/lib/cuprum/collections/basic/command.rb +22 -88
- data/lib/cuprum/collections/basic/commands/assign_one.rb +2 -6
- data/lib/cuprum/collections/basic/commands/build_one.rb +1 -4
- data/lib/cuprum/collections/basic/commands/destroy_one.rb +4 -8
- data/lib/cuprum/collections/basic/commands/find_many.rb +4 -24
- data/lib/cuprum/collections/basic/commands/find_matching.rb +5 -21
- data/lib/cuprum/collections/basic/commands/find_one.rb +3 -20
- data/lib/cuprum/collections/basic/commands/insert_one.rb +3 -6
- data/lib/cuprum/collections/basic/commands/update_one.rb +3 -6
- data/lib/cuprum/collections/basic/commands/validate_one.rb +13 -18
- data/lib/cuprum/collections/basic/query.rb +26 -40
- data/lib/cuprum/collections/basic/repository.rb +4 -3
- data/lib/cuprum/collections/basic/scopes/all_scope.rb +25 -0
- data/lib/cuprum/collections/basic/scopes/base.rb +32 -0
- data/lib/cuprum/collections/basic/scopes/builder.rb +39 -0
- data/lib/cuprum/collections/basic/scopes/conjunction_scope.rb +20 -0
- data/lib/cuprum/collections/basic/scopes/criteria_scope.rb +62 -0
- data/lib/cuprum/collections/basic/scopes/disjunction_scope.rb +20 -0
- data/lib/cuprum/collections/basic/scopes/none_scope.rb +33 -0
- data/lib/cuprum/collections/basic/scopes.rb +23 -0
- data/lib/cuprum/collections/basic.rb +1 -0
- data/lib/cuprum/collections/collection.rb +24 -82
- data/lib/cuprum/collections/collection_command.rb +116 -0
- data/lib/cuprum/collections/commands/abstract_find_many.rb +11 -21
- data/lib/cuprum/collections/commands/abstract_find_matching.rb +43 -24
- data/lib/cuprum/collections/commands/abstract_find_one.rb +7 -10
- data/lib/cuprum/collections/commands/associations/find_many.rb +3 -8
- data/lib/cuprum/collections/commands/associations/require_many.rb +5 -5
- data/lib/cuprum/collections/commands/create.rb +3 -3
- data/lib/cuprum/collections/commands/find_one_matching.rb +6 -6
- data/lib/cuprum/collections/commands/query_command.rb +19 -0
- data/lib/cuprum/collections/commands/update.rb +3 -3
- data/lib/cuprum/collections/commands/upsert.rb +10 -10
- data/lib/cuprum/collections/commands.rb +1 -0
- data/lib/cuprum/collections/constraints/ordering.rb +2 -2
- data/lib/cuprum/collections/errors/abstract_find_error.rb +25 -42
- data/lib/cuprum/collections/errors/extra_attributes.rb +3 -3
- data/lib/cuprum/collections/errors/failed_validation.rb +2 -2
- data/lib/cuprum/collections/errors/invalid_parameters.rb +2 -2
- data/lib/cuprum/collections/errors/invalid_query.rb +10 -16
- data/lib/cuprum/collections/errors/missing_default_contract.rb +1 -1
- data/lib/cuprum/collections/errors/unknown_operator.rb +1 -1
- data/lib/cuprum/collections/queries.rb +31 -0
- data/lib/cuprum/collections/query.rb +50 -62
- data/lib/cuprum/collections/relation.rb +5 -383
- data/lib/cuprum/collections/relations/cardinality.rb +66 -0
- data/lib/cuprum/collections/relations/options.rb +18 -0
- data/lib/cuprum/collections/relations/parameters.rb +217 -0
- data/lib/cuprum/collections/relations/primary_keys.rb +23 -0
- data/lib/cuprum/collections/relations/scope.rb +65 -0
- data/lib/cuprum/collections/relations.rb +14 -0
- data/lib/cuprum/collections/repository.rb +5 -5
- data/lib/cuprum/collections/resource.rb +10 -41
- data/lib/cuprum/collections/rspec/contracts/association_contracts.rb +80 -90
- data/lib/cuprum/collections/rspec/contracts/collection_contracts.rb +69 -111
- data/lib/cuprum/collections/rspec/contracts/command_contracts.rb +42 -1335
- data/lib/cuprum/collections/rspec/contracts/query_contracts.rb +352 -531
- data/lib/cuprum/collections/rspec/contracts/relation_contracts.rb +74 -191
- data/lib/cuprum/collections/rspec/contracts/repository_contracts.rb +13 -13
- data/lib/cuprum/collections/rspec/contracts/scope_contracts.rb +1029 -0
- data/lib/cuprum/collections/rspec/contracts/scopes/builder_contracts.rb +856 -0
- data/lib/cuprum/collections/rspec/contracts/scopes/composition_contracts.rb +1430 -0
- data/lib/cuprum/collections/rspec/contracts/scopes/criteria_contracts.rb +2217 -0
- data/lib/cuprum/collections/rspec/contracts/scopes/logical_contracts.rb +297 -0
- data/lib/cuprum/collections/rspec/contracts/scopes.rb +13 -0
- data/lib/cuprum/collections/rspec/contracts.rb +2 -0
- data/lib/cuprum/collections/rspec/deferred/association_examples.rb +2098 -0
- data/lib/cuprum/collections/rspec/deferred/collection_examples.rb +338 -0
- data/lib/cuprum/collections/rspec/deferred/command_examples.rb +160 -0
- data/lib/cuprum/collections/rspec/deferred/commands/assign_one_examples.rb +178 -0
- data/lib/cuprum/collections/rspec/deferred/commands/build_one_examples.rb +94 -0
- data/lib/cuprum/collections/rspec/deferred/commands/destroy_one_examples.rb +118 -0
- data/lib/cuprum/collections/rspec/deferred/commands/find_many_examples.rb +307 -0
- data/lib/cuprum/collections/rspec/deferred/commands/find_matching_examples.rb +143 -0
- data/lib/cuprum/collections/rspec/deferred/commands/find_one_examples.rb +116 -0
- data/lib/cuprum/collections/rspec/deferred/commands/insert_one_examples.rb +103 -0
- data/lib/cuprum/collections/rspec/deferred/commands/update_one_examples.rb +99 -0
- data/lib/cuprum/collections/rspec/deferred/commands/validate_one_examples.rb +117 -0
- data/lib/cuprum/collections/rspec/deferred/commands.rb +8 -0
- data/lib/cuprum/collections/rspec/deferred/relation_examples.rb +1437 -0
- data/lib/cuprum/collections/rspec/deferred/resource_examples.rb +26 -0
- data/lib/cuprum/collections/rspec/deferred.rb +8 -0
- data/lib/cuprum/collections/scope.rb +29 -0
- data/lib/cuprum/collections/scopes/all.rb +51 -0
- data/lib/cuprum/collections/scopes/all_scope.rb +18 -0
- data/lib/cuprum/collections/scopes/base.rb +79 -0
- data/lib/cuprum/collections/scopes/builder.rb +39 -0
- data/lib/cuprum/collections/scopes/building.rb +221 -0
- data/lib/cuprum/collections/scopes/composition.rb +162 -0
- data/lib/cuprum/collections/scopes/conjunction.rb +44 -0
- data/lib/cuprum/collections/scopes/conjunction_scope.rb +12 -0
- data/lib/cuprum/collections/scopes/container.rb +65 -0
- data/lib/cuprum/collections/scopes/criteria/parser.rb +241 -0
- data/lib/cuprum/collections/scopes/criteria.rb +206 -0
- data/lib/cuprum/collections/scopes/criteria_scope.rb +12 -0
- data/lib/cuprum/collections/scopes/disjunction.rb +45 -0
- data/lib/cuprum/collections/scopes/disjunction_scope.rb +12 -0
- data/lib/cuprum/collections/scopes/none.rb +62 -0
- data/lib/cuprum/collections/scopes/none_scope.rb +18 -0
- data/lib/cuprum/collections/scopes.rb +23 -0
- data/lib/cuprum/collections/version.rb +2 -2
- data/lib/cuprum/collections.rb +14 -9
- metadata +61 -15
- data/lib/cuprum/collections/basic/query_builder.rb +0 -69
- data/lib/cuprum/collections/command.rb +0 -26
- data/lib/cuprum/collections/queries/parse.rb +0 -22
- data/lib/cuprum/collections/queries/parse_block.rb +0 -206
- data/lib/cuprum/collections/queries/parse_strategy.rb +0 -91
- data/lib/cuprum/collections/query_builder.rb +0 -61
- data/lib/cuprum/collections/rspec/contracts/basic/command_contracts.rb +0 -484
@@ -100,22 +100,22 @@ module Cuprum::Collections::Commands
|
|
100
100
|
|
101
101
|
def create_entity(attributes:)
|
102
102
|
Cuprum::Collections::Commands::Create
|
103
|
-
.new(collection
|
104
|
-
.call(attributes:
|
103
|
+
.new(collection:, contract:)
|
104
|
+
.call(attributes:)
|
105
105
|
end
|
106
106
|
|
107
107
|
def filter_attributes(attributes:)
|
108
108
|
tools
|
109
109
|
.hash_tools
|
110
110
|
.convert_keys_to_strings(attributes)
|
111
|
-
.
|
111
|
+
.slice(*attribute_names)
|
112
112
|
end
|
113
113
|
|
114
114
|
def find_entity(attributes:)
|
115
|
-
filtered = filter_attributes(attributes:
|
115
|
+
filtered = filter_attributes(attributes:)
|
116
116
|
result =
|
117
117
|
Cuprum::Collections::Commands::FindOneMatching
|
118
|
-
.new(collection:
|
118
|
+
.new(collection:)
|
119
119
|
.call(attributes: filtered)
|
120
120
|
|
121
121
|
return if result.error.is_a?(Cuprum::Collections::Errors::NotFound)
|
@@ -140,12 +140,12 @@ module Cuprum::Collections::Commands
|
|
140
140
|
end
|
141
141
|
|
142
142
|
def process(attributes:)
|
143
|
-
entity = step { find_entity(attributes:
|
143
|
+
entity = step { find_entity(attributes:) }
|
144
144
|
|
145
145
|
if entity
|
146
|
-
update_entity(attributes
|
146
|
+
update_entity(attributes:, entity:)
|
147
147
|
else
|
148
|
-
create_entity(attributes:
|
148
|
+
create_entity(attributes:)
|
149
149
|
end
|
150
150
|
end
|
151
151
|
|
@@ -155,8 +155,8 @@ module Cuprum::Collections::Commands
|
|
155
155
|
|
156
156
|
def update_entity(attributes:, entity:)
|
157
157
|
Cuprum::Collections::Commands::Update
|
158
|
-
.new(collection
|
159
|
-
.call(attributes
|
158
|
+
.new(collection:, contract:)
|
159
|
+
.call(attributes:, entity:)
|
160
160
|
end
|
161
161
|
end
|
162
162
|
end
|
@@ -8,6 +8,7 @@ module Cuprum::Collections
|
|
8
8
|
autoload :Associations, 'cuprum/collections/commands/associations'
|
9
9
|
autoload :Create, 'cuprum/collections/commands/create'
|
10
10
|
autoload :FindOneMatching, 'cuprum/collections/commands/find_one_matching'
|
11
|
+
autoload :QueryCommand, 'cuprum/collections/commands/query_command'
|
11
12
|
autoload :Update, 'cuprum/collections/commands/update'
|
12
13
|
autoload :Upsert, 'cuprum/collections/commands/upsert'
|
13
14
|
end
|
@@ -35,12 +35,12 @@ module Cuprum::Collections::Errors
|
|
35
35
|
resolve_options(**options)
|
36
36
|
|
37
37
|
super(
|
38
|
-
attribute_name
|
39
|
-
attribute_value
|
40
|
-
attributes
|
41
|
-
collection_name
|
38
|
+
attribute_name:,
|
39
|
+
attribute_value:,
|
40
|
+
attributes:,
|
41
|
+
collection_name:,
|
42
42
|
message: generate_message,
|
43
|
-
|
43
|
+
scope:
|
44
44
|
)
|
45
45
|
end
|
46
46
|
|
@@ -56,18 +56,23 @@ module Cuprum::Collections::Errors
|
|
56
56
|
# @return [String] the name of the collection.
|
57
57
|
attr_reader :collection_name
|
58
58
|
|
59
|
-
# @return [Cuprum::Collections::
|
60
|
-
attr_reader :
|
59
|
+
# @return [Cuprum::Collections::Scopes::Base] the query scope, if any.
|
60
|
+
attr_reader :scope
|
61
61
|
|
62
|
-
# @return [Array<Array>] the details of the query, in
|
63
|
-
def details
|
62
|
+
# @return [Array<Array>] the details of the query, in scope format.
|
63
|
+
def details # rubocop:disable Metrics/MethodLength
|
64
64
|
if attribute_name
|
65
|
-
[[attribute_name, :equal, attribute_value]]
|
65
|
+
criteria = [[attribute_name, :equal, attribute_value]]
|
66
|
+
|
67
|
+
{ 'type' => :criteria, 'criteria' => criteria }
|
66
68
|
elsif attributes
|
67
|
-
|
68
|
-
|
69
|
-
|
70
|
-
|
69
|
+
criteria =
|
70
|
+
attributes
|
71
|
+
.map { |attr_name, attr_value| [attr_name, :equal, attr_value] }
|
72
|
+
|
73
|
+
{ 'type' => :criteria, 'criteria' => criteria }
|
74
|
+
elsif scope
|
75
|
+
scope
|
71
76
|
end
|
72
77
|
end
|
73
78
|
|
@@ -112,10 +117,10 @@ module Cuprum::Collections::Errors
|
|
112
117
|
if attribute_name
|
113
118
|
"#{core_message} with #{attribute_name.inspect} " \
|
114
119
|
"#{attribute_value.inspect}" \
|
115
|
-
"#{
|
120
|
+
"#{' (primary key)' if primary_key?}"
|
116
121
|
elsif attributes
|
117
122
|
"#{core_message} with attributes #{attributes.inspect}"
|
118
|
-
elsif
|
123
|
+
elsif scope
|
119
124
|
"#{core_message} matching the query"
|
120
125
|
end
|
121
126
|
end
|
@@ -142,15 +147,13 @@ module Cuprum::Collections::Errors
|
|
142
147
|
|
143
148
|
def resolve_query_options(**options)
|
144
149
|
options = options.dup
|
145
|
-
@
|
150
|
+
@scope = options.delete(:query)&.scope
|
146
151
|
|
147
152
|
validate_keywords(extra_keywords: options.keys)
|
148
153
|
end
|
149
154
|
|
150
155
|
def resolve_options(**options) # rubocop:disable Metrics/MethodLength
|
151
|
-
if options[:
|
152
|
-
resolve_primary_key_options(**options)
|
153
|
-
elsif options[:attribute_name] && options.key?(:attribute_value)
|
156
|
+
if options[:attribute_name] && options.key?(:attribute_value)
|
154
157
|
resolve_attribute_options(**options)
|
155
158
|
elsif options[:attributes]
|
156
159
|
resolve_attributes_options(**options)
|
@@ -163,26 +166,6 @@ module Cuprum::Collections::Errors
|
|
163
166
|
end
|
164
167
|
end
|
165
168
|
|
166
|
-
def resolve_primary_key_options(**options) # rubocop:disable Metrics/MethodLength
|
167
|
-
values = Array(options[:primary_key_values])
|
168
|
-
|
169
|
-
unless values.size == 1
|
170
|
-
raise ArgumentError,
|
171
|
-
'deprecated mode does not support empty or multiple attribute values'
|
172
|
-
end
|
173
|
-
|
174
|
-
SleepingKingStudios::Tools::CoreTools
|
175
|
-
.instance
|
176
|
-
.deprecate(
|
177
|
-
'NotFound.new(primary_key_name:, primary_key_values:)',
|
178
|
-
message: 'use NotFound.new(attribute_name:, attribute_value:)'
|
179
|
-
)
|
180
|
-
|
181
|
-
@attribute_name = options[:primary_key_name]
|
182
|
-
@attribute_value = values.first
|
183
|
-
@primary_key = true
|
184
|
-
end
|
185
|
-
|
186
169
|
def titleize(string)
|
187
170
|
tools.str.underscore(string).split('_').map(&:capitalize).join(' ')
|
188
171
|
end
|
@@ -198,11 +181,11 @@ module Cuprum::Collections::Errors
|
|
198
181
|
|
199
182
|
if ambiguous_keywords.empty?
|
200
183
|
raise ArgumentError,
|
201
|
-
"unknown keyword#{extra_keywords.size == 1
|
184
|
+
"unknown keyword#{'s' unless extra_keywords.size == 1} " \
|
202
185
|
"#{extra_keywords.map(&:inspect).join(', ')}"
|
203
186
|
else
|
204
187
|
raise ArgumentError,
|
205
|
-
"ambiguous keyword#{extra_keywords.size == 1
|
188
|
+
"ambiguous keyword#{'s' unless extra_keywords.size == 1} " \
|
206
189
|
"#{ambiguous_keywords.map(&:inspect).join(', ')}"
|
207
190
|
end
|
208
191
|
end
|
@@ -21,10 +21,10 @@ module Cuprum::Collections::Errors
|
|
21
21
|
@valid_attributes = valid_attributes
|
22
22
|
|
23
23
|
super(
|
24
|
-
entity_class
|
25
|
-
extra_attributes
|
24
|
+
entity_class:,
|
25
|
+
extra_attributes:,
|
26
26
|
message: default_message,
|
27
|
-
valid_attributes:
|
27
|
+
valid_attributes:
|
28
28
|
)
|
29
29
|
end
|
30
30
|
|
@@ -10,36 +10,30 @@ module Cuprum::Collections::Errors
|
|
10
10
|
# Short string used to identify the type of error.
|
11
11
|
TYPE = 'cuprum.collections.errors.invalid_query'
|
12
12
|
|
13
|
-
# @param
|
14
|
-
# @param
|
15
|
-
def initialize(
|
16
|
-
@
|
17
|
-
@strategy = strategy
|
13
|
+
# @param query [Object] the given filter parameters, if any.
|
14
|
+
# @param message [String] the message to display.
|
15
|
+
def initialize(query:, message: nil)
|
16
|
+
@query = query
|
18
17
|
|
19
18
|
super(
|
20
|
-
|
21
|
-
|
22
|
-
strategy: strategy
|
19
|
+
message: message || default_message,
|
20
|
+
query:
|
23
21
|
)
|
24
22
|
end
|
25
23
|
|
26
|
-
# @return [
|
27
|
-
attr_reader :
|
28
|
-
|
29
|
-
# @return [Symbol] the strategy used to construct the query.
|
30
|
-
attr_reader :strategy
|
24
|
+
# @return [Object] the given filter parameters, if any.
|
25
|
+
attr_reader :query
|
31
26
|
|
32
27
|
private
|
33
28
|
|
34
29
|
def as_json_data
|
35
30
|
{
|
36
|
-
'
|
37
|
-
'strategy' => strategy
|
31
|
+
'query' => (query.respond_to?(:as_json) ? query.as_json : query.inspect)
|
38
32
|
}
|
39
33
|
end
|
40
34
|
|
41
35
|
def default_message
|
42
|
-
|
36
|
+
'unable to parse query'
|
43
37
|
end
|
44
38
|
end
|
45
39
|
end
|
@@ -19,6 +19,37 @@ module Cuprum::Collections
|
|
19
19
|
ONE_OF: :one_of
|
20
20
|
).freeze
|
21
21
|
|
22
|
+
# Exception raised when trying to invert an operator with no inverse.
|
23
|
+
class UninvertibleOperatorException < StandardError; end
|
24
|
+
|
25
|
+
# Exception raised when an invalid operator is referenced.
|
26
|
+
class UnknownOperatorException < StandardError
|
27
|
+
# @param msg [String] the exception message.
|
28
|
+
# @param name [String] the name of the invalid operator.
|
29
|
+
def initialize(msg = nil, name = nil)
|
30
|
+
super(msg)
|
31
|
+
|
32
|
+
@name = name
|
33
|
+
end
|
34
|
+
|
35
|
+
# @return [String] the name of the invalid operator.
|
36
|
+
def name
|
37
|
+
@name || cause&.name
|
38
|
+
end
|
39
|
+
end
|
40
|
+
|
41
|
+
# Defines the negated operator corresponding to each operator.
|
42
|
+
INVERTIBLE_OPERATORS = {
|
43
|
+
Operators::EQUAL => Operators::NOT_EQUAL,
|
44
|
+
Operators::GREATER_THAN => Operators::LESS_THAN_OR_EQUAL_TO,
|
45
|
+
Operators::GREATER_THAN_OR_EQUAL_TO => Operators::LESS_THAN,
|
46
|
+
Operators::LESS_THAN => Operators::GREATER_THAN_OR_EQUAL_TO, # rubocop:disable Layout/LineLength
|
47
|
+
Operators::LESS_THAN_OR_EQUAL_TO => Operators::GREATER_THAN,
|
48
|
+
Operators::NOT_EQUAL => Operators::EQUAL,
|
49
|
+
Operators::NOT_ONE_OF => Operators::ONE_OF,
|
50
|
+
Operators::ONE_OF => Operators::NOT_ONE_OF
|
51
|
+
}.freeze
|
52
|
+
|
22
53
|
# Enumerates the valid operators as a Set for performant lookup.
|
23
54
|
VALID_OPERATORS = Set.new(Operators.values).freeze
|
24
55
|
end
|
@@ -2,38 +2,36 @@
|
|
2
2
|
|
3
3
|
require 'cuprum/collections'
|
4
4
|
require 'cuprum/collections/queries/ordering'
|
5
|
+
require 'cuprum/collections/scopes/all_scope'
|
5
6
|
|
6
7
|
module Cuprum::Collections
|
7
8
|
# Abstract base class for collection Query implementations.
|
8
9
|
class Query
|
10
|
+
include Enumerable
|
11
|
+
|
9
12
|
UNDEFINED = Object.new.freeze
|
10
13
|
private_constant :UNDEFINED
|
11
14
|
|
12
|
-
|
13
|
-
|
15
|
+
# @param scope [Cuprum::Collections::Scopes::Base] the base scope for the
|
16
|
+
# query. Defaults to nil.
|
17
|
+
def initialize(scope: nil)
|
18
|
+
@limit = nil
|
19
|
+
@offset = nil
|
20
|
+
@order = {}
|
21
|
+
@scope = scope ? default_scope.and(scope) : default_scope
|
14
22
|
end
|
15
23
|
|
16
|
-
# Returns
|
17
|
-
#
|
18
|
-
# The query criteria define which data from the collection matches the
|
19
|
-
# query. Specifically, an item in the collection matches the query if and
|
20
|
-
# only if it matches each criterion. If the query has no criteria, then it
|
21
|
-
# will match all items in the collection.
|
22
|
-
#
|
23
|
-
# Each criterion is represented as an Array with three elements:
|
24
|
-
# - The name of the property or column to select by.
|
25
|
-
# - The operation to filter, such as :eq (an equality operation).
|
26
|
-
# - The expected value.
|
24
|
+
# Returns the current scope for the query.
|
27
25
|
#
|
28
|
-
#
|
29
|
-
#
|
30
|
-
#
|
26
|
+
# Composition methods should not be called on the scope directly, as they
|
27
|
+
# will not change the scope object bound to the query. Call the
|
28
|
+
# corresponding methods on the query itself, i.e. call query.where() instead
|
29
|
+
# of query.scope.where().
|
31
30
|
#
|
32
|
-
# @return [
|
33
|
-
#
|
34
|
-
|
35
|
-
|
36
|
-
@criteria.dup
|
31
|
+
# @return [Cuprum::Collections::Scopes::Base] the current scope for the
|
32
|
+
# query.
|
33
|
+
def scope
|
34
|
+
@scope ||= default_scope
|
37
35
|
end
|
38
36
|
|
39
37
|
# Sets or returns the maximum number of items returned by the query.
|
@@ -151,49 +149,35 @@ module Cuprum::Collections
|
|
151
149
|
dup.reset!
|
152
150
|
end
|
153
151
|
|
154
|
-
#
|
152
|
+
# @overload where(hash)
|
153
|
+
# Returns a copy of the query with the specified filters.
|
155
154
|
#
|
156
|
-
#
|
157
|
-
#
|
158
|
-
#
|
159
|
-
# If the query has no criteria, then it will match all items in the
|
160
|
-
# collection.
|
155
|
+
# If the query already has a scope, then the filters will be merged with
|
156
|
+
# the existing scope. Any items in the collection must match both the
|
157
|
+
# previous scope and the new criteria to be returned by the query.
|
161
158
|
#
|
162
|
-
#
|
163
|
-
# new criteria are appended to the old. Any items in the collection must
|
164
|
-
# match both the old and the new criteria to be returned by the query.
|
159
|
+
# @param hash [Hash{String=>Object}] the filters to apply to the query.
|
165
160
|
#
|
166
|
-
#
|
167
|
-
#
|
168
|
-
#
|
161
|
+
# @example Filtering Data By Equality
|
162
|
+
# # The query will only return items whose author is 'J.R.R. Tolkien'.
|
163
|
+
# query = query.where { { author: 'J.R.R. Tolkien' } }
|
169
164
|
#
|
170
|
-
#
|
171
|
-
# # The query will only return items whose author is 'J.R.R. Tolkien',
|
172
|
-
# # and whose series is not 'The Lord of the Rings'.
|
173
|
-
# query = query.where do
|
174
|
-
# {
|
175
|
-
# author: eq('J.R.R. Tolkien'),
|
176
|
-
# series: ne('The Lord of the Rings')
|
177
|
-
# }
|
178
|
-
# end
|
165
|
+
# @see #scope
|
179
166
|
#
|
180
167
|
# @overload where(&block)
|
181
|
-
#
|
182
|
-
# block to query criteria and generates a new query using those
|
183
|
-
# criteria.
|
168
|
+
# Returns a copy of the query with the specified filters.
|
184
169
|
#
|
185
|
-
#
|
186
|
-
#
|
187
|
-
#
|
188
|
-
# method call for a valid operation defined for the query.
|
170
|
+
# If the query already has a scope, then the filters will be merged with
|
171
|
+
# the existing scope. Any items in the collection must match both the
|
172
|
+
# previous scope and the new criteria to be returned by the query.
|
189
173
|
#
|
190
|
-
#
|
191
|
-
|
192
|
-
|
193
|
-
|
194
|
-
|
195
|
-
|
196
|
-
|
174
|
+
# @yieldreturn [Hash{String=>Object}] the filters to apply to the query.
|
175
|
+
# The hash keys should be the names of attributes or columns, and the
|
176
|
+
# corresponding values should be either the literal value for that
|
177
|
+
# attribute or a method call for a valid operation defined for the
|
178
|
+
# query.
|
179
|
+
def where(...)
|
180
|
+
dup.with_scope(scope.where(...)).reset!
|
197
181
|
end
|
198
182
|
|
199
183
|
protected
|
@@ -204,12 +188,6 @@ module Cuprum::Collections
|
|
204
188
|
# :nocov:
|
205
189
|
end
|
206
190
|
|
207
|
-
def with_criteria(criteria)
|
208
|
-
@criteria += criteria
|
209
|
-
|
210
|
-
self
|
211
|
-
end
|
212
|
-
|
213
191
|
def with_limit(count)
|
214
192
|
@limit = count
|
215
193
|
|
@@ -228,8 +206,18 @@ module Cuprum::Collections
|
|
228
206
|
self
|
229
207
|
end
|
230
208
|
|
209
|
+
def with_scope(scope)
|
210
|
+
@scope = scope
|
211
|
+
|
212
|
+
self
|
213
|
+
end
|
214
|
+
|
231
215
|
private
|
232
216
|
|
217
|
+
def default_scope
|
218
|
+
Cuprum::Collections::Scopes::AllScope.new
|
219
|
+
end
|
220
|
+
|
233
221
|
def validate_limit(count)
|
234
222
|
return if count.is_a?(Integer) && !count.negative?
|
235
223
|
|