Skip to content

Commit fe785ae

Browse files
midnight-wondererneilshweky
authored andcommitted
RUBY-3087 reinstate ability to call insert_many with Enumerable inputs which are not Array instances (#2594)
* RUBY-3087 add a test for insert_many with enumerable inputs * RUBY-3087 raise exception on bulk_write without using an Array method * RUBY-3087 add test, docs * add docs, release notes * Fix the description of empty bulk_write spec to match the behavior * Update docs/release-notes.txt * change docstrings to use enumerables Co-authored-by: Neil Shweky <neilshweky@gmail.com>
1 parent 99ef742 commit fe785ae

File tree

4 files changed

+44
-8
lines changed

4 files changed

+44
-8
lines changed

lib/mongo/bulk_write.rb

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -115,7 +115,8 @@ def execute
115115
# )
116116
#
117117
# @param [ Mongo::Collection ] collection The collection.
118-
# @param [ Array<Hash, BSON::Document> ] requests The requests, cannot be empty.
118+
# @param [ Enumerable<Hash, BSON::Document> ] requests The requests,
119+
# cannot be empty.
119120
# @param [ Hash, BSON::Document ] options The options.
120121
#
121122
# @since 2.1.0
@@ -330,10 +331,9 @@ def can_hint?(connection)
330331
# ArgumentError ]
331332
# if the document is invalid.
332333
def validate_requests!
333-
if @requests.empty?
334-
raise ArgumentError, "Bulk write requests cannot be empty"
335-
end
334+
requests_empty = true
336335
@requests.each do |req|
336+
requests_empty = false
337337
if op = req.keys.first
338338
if [:update_one, :update_many].include?(op)
339339
if doc = maybe_first(req.dig(op, :update))
@@ -359,6 +359,8 @@ def validate_requests!
359359
end
360360
end
361361
end
362+
end.tap do
363+
raise ArgumentError, "Bulk write requests cannot be empty" if requests_empty
362364
end
363365
end
364366

lib/mongo/collection.rb

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -783,7 +783,7 @@ def insert_one(document, opts = {})
783783
# @example Insert documents into the collection.
784784
# collection.insert_many([{ name: 'test' }])
785785
#
786-
# @param [ Array<Hash> ] documents The documents to insert.
786+
# @param [ Enumerable<Hash> ] documents The documents to insert.
787787
# @param [ Hash ] options The insert options.
788788
#
789789
# @option options [ true | false ] :bypass_document_validation Whether or
@@ -811,7 +811,7 @@ def insert_many(documents, options = {})
811811
# @example Execute a bulk write.
812812
# collection.bulk_write(operations, options)
813813
#
814-
# @param [ Array<Hash> ] requests The bulk write requests.
814+
# @param [ Enumerable<Hash> ] requests The bulk write requests.
815815
# @param [ Hash ] options The options.
816816
#
817817
# @option options [ true | false ] :ordered Whether the operations

lib/mongo/collection/view/writable.rb

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -98,8 +98,6 @@ def find_one_and_delete(opts = {})
9898
end.first&.fetch('value', nil)
9999
end
100100

101-
# db['users'].bulk_write([{insert_one: {x: 1}}, {insert_one: {x: 2}}])
102-
103101
# Finds a single document and replaces it.
104102
#
105103
# @example Find a document and replace it, returning the original.

spec/mongo/collection_crud_spec.rb

Lines changed: 36 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -362,6 +362,42 @@
362362
expect(result.inserted_ids.size).to eq(2)
363363
end
364364

365+
context 'when an enumerable is used instead of an array' do
366+
367+
context 'when the enumerable is not empty' do
368+
369+
let(:source_data) do
370+
[{ name: 'test1' }, { name: 'test2' }]
371+
end
372+
373+
let(:result) do
374+
authorized_collection.insert_many(source_data.lazy)
375+
end
376+
377+
it 'should accepts them without raising an error' do
378+
expect { result }.to_not raise_error
379+
expect(result.inserted_count).to eq(source_data.size)
380+
end
381+
end
382+
383+
context 'when the enumerable is empty' do
384+
385+
let(:source_data) do
386+
[]
387+
end
388+
389+
let(:result) do
390+
authorized_collection.insert_many(source_data.lazy)
391+
end
392+
393+
it 'should raise ArgumentError' do
394+
expect do
395+
result
396+
end.to raise_error(ArgumentError, /Bulk write requests cannot be empty/)
397+
end
398+
end
399+
end
400+
365401
context 'when a session is provided' do
366402

367403
let(:session) do

0 commit comments

Comments
 (0)