Skip to content

Commit defe269

Browse files
committed
add error_on_scan config
1 parent c2e09bf commit defe269

File tree

5 files changed

+47
-1
lines changed

5 files changed

+47
-1
lines changed

README.md

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1303,6 +1303,7 @@ Listed below are all configuration options.
13031303
* `write_capacity` - is used at table or indices creation. Default is 20
13041304
(units)
13051305
* `warn_on_scan` - log warnings when scan table. Default is `true`
1306+
* `error_on_scan` - raises an error when scan table. Default is `false`
13061307
* `endpoint` - if provided, it communicates with the DynamoDB listening
13071308
at the endpoint. This is useful for testing with
13081309
[DynamoDB Local](http://docs.aws.amazon.com/amazondynamodb/latest/developerguide/Tools.DynamoDBLocal.html)

lib/dynamoid/config.rb

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -36,6 +36,7 @@ module Config
3636
option :read_capacity, default: 100
3737
option :write_capacity, default: 20
3838
option :warn_on_scan, default: true
39+
option :error_on_scan, default: false
3940
option :endpoint, default: nil
4041
option :identity_map, default: false
4142
option :timestamps, default: true

lib/dynamoid/criteria/chain.rb

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -563,7 +563,7 @@ def raw_pages
563563
if @key_fields_detector.key_present?
564564
raw_pages_via_query
565565
else
566-
issue_scan_warning if Dynamoid::Config.warn_on_scan && !@where_conditions.empty?
566+
validate_scan_conditions
567567
raw_pages_via_scan
568568
end
569569
end
@@ -598,6 +598,12 @@ def raw_pages_via_scan
598598
end
599599
end
600600

601+
def validate_scan_conditions
602+
raise Dynamoid::Errors::ScanProhibited if Dynamoid::Config.error_on_scan && !@where_conditions.empty?
603+
604+
issue_scan_warning if Dynamoid::Config.warn_on_scan && !@where_conditions.empty?
605+
end
606+
601607
def issue_scan_warning
602608
Dynamoid.logger.warn 'Queries without an index are forced to use scan and are generally much slower than indexed queries!'
603609
Dynamoid.logger.warn "You can index this query by adding index declaration to #{source.to_s.underscore}.rb:"

lib/dynamoid/errors.rb

Lines changed: 6 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -100,5 +100,11 @@ def initialize(model_class, attribute_name)
100100
class SubclassNotFound < Error; end
101101

102102
class Rollback < Error; end
103+
104+
class ScanProhibited < Error
105+
def initialize(_msg = nil)
106+
super('Scan operations prohibited. Modify Dynamoid::Config.error_on_scan to change this behavior.')
107+
end
108+
end
103109
end
104110
end

spec/dynamoid/criteria_spec.rb

Lines changed: 32 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -117,6 +117,23 @@
117117
end
118118
end
119119

120+
context 'when scans using non-indexed fields and error_on_scan config option is true' do
121+
before do
122+
@error_on_scan = Dynamoid::Config.error_on_scan
123+
Dynamoid::Config.error_on_scan = true
124+
end
125+
126+
after do
127+
Dynamoid::Config.error_on_scan = @error_on_scan
128+
end
129+
130+
it 'raises an error' do
131+
expect {
132+
User.where(name: 'x', password: 'password').all
133+
}.to raise_error(Dynamoid::Errors::ScanProhibited)
134+
end
135+
end
136+
120137
context 'when doing intentional, full-table scan (query is empty) and warn_on_scan config option is true' do
121138
before do
122139
@warn_on_scan = Dynamoid::Config.warn_on_scan
@@ -133,4 +150,19 @@
133150
User.all
134151
end
135152
end
153+
154+
context 'when doing intentional, full-table scan (query is empty) and error_on_scan config option is true' do
155+
before do
156+
@error_on_scan = Dynamoid::Config.error_on_scan
157+
Dynamoid::Config.error_on_scan = true
158+
end
159+
160+
after do
161+
Dynamoid::Config.error_on_scan = @error_on_scan
162+
end
163+
164+
it 'does not raise an error' do
165+
expect { User.all }.not_to raise_error(Dynamoid::Errors::ScanProhibited)
166+
end
167+
end
136168
end

0 commit comments

Comments
 (0)