diff options
author | Randolph Tan <randolph@10gen.com> | 2017-07-03 17:49:48 -0400 |
---|---|---|
committer | Randolph Tan <randolph@10gen.com> | 2017-07-12 13:20:42 -0400 |
commit | 1550eb477fcf883e861f63ffc988a6060a2fbfb1 (patch) | |
tree | 2ae92c69ae385f2788ec7ab2fad3aa77e7495ee9 /src | |
parent | 1d6008b049e65615b13404f0b877034cfa980220 (diff) | |
download | mongo-1550eb477fcf883e861f63ffc988a6060a2fbfb1.tar.gz |
SERVER-28912 Thread statement id from batched insert command oplog entry
Diffstat (limited to 'src')
45 files changed, 381 insertions, 279 deletions
diff --git a/src/mongo/db/catalog/capped_utils.cpp b/src/mongo/db/catalog/capped_utils.cpp index 3db41392e06..9af076ab62c 100644 --- a/src/mongo/db/catalog/capped_utils.cpp +++ b/src/mongo/db/catalog/capped_utils.cpp @@ -217,8 +217,11 @@ mongo::Status mongo::cloneCollectionAsCapped(OperationContext* opCtx, WriteUnitOfWork wunit(opCtx); OpDebug* const nullOpDebug = nullptr; toCollection - ->insertDocument( - opCtx, objToClone.value(), nullOpDebug, true, opCtx->writesAreReplicated()) + ->insertDocument(opCtx, + InsertStatement(objToClone.value()), + nullOpDebug, + true, + opCtx->writesAreReplicated()) .transitional_ignore(); wunit.commit(); diff --git a/src/mongo/db/catalog/collection.h b/src/mongo/db/catalog/collection.h index 002a5c21366..a07039e74c9 100644 --- a/src/mongo/db/catalog/collection.h +++ b/src/mongo/db/catalog/collection.h @@ -38,9 +38,11 @@ #include "mongo/bson/mutable/damage_vector.h" #include "mongo/db/catalog/coll_mod.h" #include "mongo/db/catalog/collection_info_cache.h" +#include "mongo/db/catalog/collection_options.h" #include "mongo/db/catalog/index_catalog.h" #include "mongo/db/cursor_manager.h" #include "mongo/db/exec/collection_scan_common.h" +#include "mongo/db/logical_session_id.h" #include "mongo/db/namespace_string.h" #include "mongo/db/op_observer.h" #include "mongo/db/query/collation/collator_interface.h" @@ -62,6 +64,7 @@ class MatchExpression; class MultiIndexBlock; class OpDebug; class OperationContext; +struct OplogUpdateEntryArgs; class RecordCursor; class RecordFetcher; class UpdateDriver; @@ -91,6 +94,17 @@ struct CompactStats { long long corruptDocuments = 0; }; +struct InsertStatement { +public: + InsertStatement() = default; + explicit InsertStatement(BSONObj toInsert) : doc(toInsert) {} + + InsertStatement(StmtId statementId, BSONObj toInsert) : stmtId(statementId), doc(toInsert) {} + + StmtId stmtId = kUninitializedStmtId; + BSONObj doc; +}; + /** * Queries with the awaitData option use this notifier object to wait for more data to be * inserted into the capped collection. @@ -230,14 +244,14 @@ public: bool noWarn) = 0; virtual Status insertDocuments(OperationContext* opCtx, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, OpDebug* opDebug, bool enforceQuota, bool fromMigrate) = 0; virtual Status insertDocument(OperationContext* opCtx, - const BSONObj& doc, + const InsertStatement& doc, OpDebug* opDebug, bool enforceQuota, bool fromMigrate) = 0; @@ -454,8 +468,8 @@ public: * 'opDebug' Optional argument. When not null, will be used to record operation statistics. */ inline Status insertDocuments(OperationContext* const opCtx, - const std::vector<BSONObj>::const_iterator begin, - const std::vector<BSONObj>::const_iterator end, + const std::vector<InsertStatement>::const_iterator begin, + const std::vector<InsertStatement>::const_iterator end, OpDebug* const opDebug, const bool enforceQuota, const bool fromMigrate = false) { @@ -470,7 +484,7 @@ public: * 'enforceQuota' If false, quotas will be ignored. */ inline Status insertDocument(OperationContext* const opCtx, - const BSONObj& doc, + const InsertStatement& doc, OpDebug* const opDebug, const bool enforceQuota, const bool fromMigrate = false) { diff --git a/src/mongo/db/catalog/collection_impl.cpp b/src/mongo/db/catalog/collection_impl.cpp index da81803a1b0..e1300d2ce96 100644 --- a/src/mongo/db/catalog/collection_impl.cpp +++ b/src/mongo/db/catalog/collection_impl.cpp @@ -342,8 +342,8 @@ Status CollectionImpl::insertDocumentsForOplog(OperationContext* opCtx, Status CollectionImpl::insertDocuments(OperationContext* opCtx, - const vector<BSONObj>::const_iterator begin, - const vector<BSONObj>::const_iterator end, + const vector<InsertStatement>::const_iterator begin, + const vector<InsertStatement>::const_iterator end, OpDebug* opDebug, bool enforceQuota, bool fromMigrate) { @@ -355,7 +355,7 @@ Status CollectionImpl::insertDocuments(OperationContext* opCtx, if (!collElem || _ns == collElem.str()) { const std::string msg = str::stream() << "Failpoint (failCollectionInserts) has been enabled (" << data - << "), so rejecting insert (first doc): " << *begin; + << "), so rejecting insert (first doc): " << begin->doc; log() << msg; return {ErrorCodes::FailPointEnabled, msg}; } @@ -365,14 +365,14 @@ Status CollectionImpl::insertDocuments(OperationContext* opCtx, const bool hasIdIndex = _indexCatalog.findIdIndex(opCtx); for (auto it = begin; it != end; it++) { - if (hasIdIndex && (*it)["_id"].eoo()) { + if (hasIdIndex && it->doc["_id"].eoo()) { return Status(ErrorCodes::InternalError, str::stream() << "Collection::insertDocument got document without _id for ns:" << _ns.ns()); } - auto status = checkValidation(opCtx, *it); + auto status = checkValidation(opCtx, it->doc); if (!status.isOK()) return status; } @@ -396,11 +396,11 @@ Status CollectionImpl::insertDocuments(OperationContext* opCtx, } Status CollectionImpl::insertDocument(OperationContext* opCtx, - const BSONObj& docToInsert, + const InsertStatement& docToInsert, OpDebug* opDebug, bool enforceQuota, bool fromMigrate) { - vector<BSONObj> docs; + vector<InsertStatement> docs; docs.push_back(docToInsert); return insertDocuments(opCtx, docs.begin(), docs.end(), opDebug, enforceQuota, fromMigrate); } @@ -447,11 +447,11 @@ Status CollectionImpl::insertDocument(OperationContext* opCtx, } } - vector<BSONObj> docs; - docs.push_back(doc); + vector<InsertStatement> inserts; + inserts.emplace_back(doc); getGlobalServiceContext()->getOpObserver()->onInserts( - opCtx, ns(), uuid(), docs.begin(), docs.end(), false); + opCtx, ns(), uuid(), inserts.begin(), inserts.end(), false); opCtx->recoveryUnit()->onCommit([this]() { notifyCappedWaitersIfNeeded(); }); @@ -459,8 +459,8 @@ Status CollectionImpl::insertDocument(OperationContext* opCtx, } Status CollectionImpl::_insertDocuments(OperationContext* opCtx, - const vector<BSONObj>::const_iterator begin, - const vector<BSONObj>::const_iterator end, + const vector<InsertStatement>::const_iterator begin, + const vector<InsertStatement>::const_iterator end, bool enforceQuota, OpDebug* opDebug) { dassert(opCtx->lockState()->isCollectionLockedForMode(ns().toString(), MODE_IX)); @@ -486,7 +486,7 @@ Status CollectionImpl::_insertDocuments(OperationContext* opCtx, std::vector<Record> records; records.reserve(count); for (auto it = begin; it != end; it++) { - Record record = {RecordId(), RecordData(it->objdata(), it->objsize())}; + Record record = {RecordId(), RecordData(it->doc.objdata(), it->doc.objsize())}; records.push_back(record); } Status status = _recordStore->insertRecords(opCtx, &records, _enforceQuota(enforceQuota)); @@ -501,7 +501,7 @@ Status CollectionImpl::_insertDocuments(OperationContext* opCtx, invariant(RecordId::min() < loc); invariant(loc < RecordId::max()); - BsonRecord bsonRecord = {loc, &(*it)}; + BsonRecord bsonRecord = {loc, &(it->doc)}; bsonRecords.push_back(bsonRecord); } diff --git a/src/mongo/db/catalog/collection_impl.h b/src/mongo/db/catalog/collection_impl.h index c65983d39e6..6686eda48b8 100644 --- a/src/mongo/db/catalog/collection_impl.h +++ b/src/mongo/db/catalog/collection_impl.h @@ -150,8 +150,8 @@ public: * 'opDebug' Optional argument. When not null, will be used to record operation statistics. */ Status insertDocuments(OperationContext* opCtx, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, OpDebug* opDebug, bool enforceQuota, bool fromMigrate = false) final; @@ -164,7 +164,7 @@ public: * 'enforceQuota' If false, quotas will be ignored. */ Status insertDocument(OperationContext* opCtx, - const BSONObj& doc, + const InsertStatement& doc, OpDebug* opDebug, bool enforceQuota, bool fromMigrate = false) final; @@ -365,8 +365,8 @@ private: Status _insertDocument(OperationContext* opCtx, const BSONObj& doc, bool enforceQuota); Status _insertDocuments(OperationContext* opCtx, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, bool enforceQuota, OpDebug* opDebug); diff --git a/src/mongo/db/catalog/collection_mock.h b/src/mongo/db/catalog/collection_mock.h index 8fe55e28a1d..21fa1d643ce 100644 --- a/src/mongo/db/catalog/collection_mock.h +++ b/src/mongo/db/catalog/collection_mock.h @@ -133,8 +133,8 @@ public: } Status insertDocuments(OperationContext* opCtx, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, OpDebug* opDebug, bool enforceQuota, bool fromMigrate) { @@ -142,7 +142,7 @@ public: } Status insertDocument(OperationContext* opCtx, - const BSONObj& doc, + const InsertStatement& doc, OpDebug* opDebug, bool enforceQuota, bool fromMigrate) { diff --git a/src/mongo/db/cloner.cpp b/src/mongo/db/cloner.cpp index a160d1fe383..42081c94b79 100644 --- a/src/mongo/db/cloner.cpp +++ b/src/mongo/db/cloner.cpp @@ -265,7 +265,8 @@ struct Cloner::Fun { BSONObj doc = tmp; OpDebug* const nullOpDebug = nullptr; - Status status = collection->insertDocument(opCtx, doc, nullOpDebug, true); + Status status = + collection->insertDocument(opCtx, InsertStatement(doc), nullOpDebug, true); if (!status.isOK() && status.code() != ErrorCodes::DuplicateKey) { error() << "error: exception cloning object in " << from_collection << ' ' << redact(status) << " obj:" << redact(doc); diff --git a/src/mongo/db/commands/mr.cpp b/src/mongo/db/commands/mr.cpp index 7adc840069c..2c8a1b72b23 100644 --- a/src/mongo/db/commands/mr.cpp +++ b/src/mongo/db/commands/mr.cpp @@ -757,7 +757,7 @@ void State::insert(const NamespaceString& nss, const BSONObj& o) { // TODO: Consider whether to pass OpDebug for stats tracking under SERVER-23261. OpDebug* const nullOpDebug = nullptr; - uassertStatusOK(coll->insertDocument(_opCtx, bo, nullOpDebug, true)); + uassertStatusOK(coll->insertDocument(_opCtx, InsertStatement(bo), nullOpDebug, true)); wuow.commit(); }); } @@ -789,7 +789,7 @@ void State::_insertToInc(BSONObj& o) { // TODO: Consider whether to pass OpDebug for stats tracking under SERVER-23261. OpDebug* const nullOpDebug = nullptr; - uassertStatusOK(coll->insertDocument(_opCtx, o, nullOpDebug, true, false)); + uassertStatusOK(coll->insertDocument(_opCtx, InsertStatement(o), nullOpDebug, true, false)); wuow.commit(); }); } diff --git a/src/mongo/db/commands/test_commands.cpp b/src/mongo/db/commands/test_commands.cpp index b07a5aa9e39..618e655fdce 100644 --- a/src/mongo/db/commands/test_commands.cpp +++ b/src/mongo/db/commands/test_commands.cpp @@ -99,7 +99,7 @@ public: } } OpDebug* const nullOpDebug = nullptr; - Status status = collection->insertDocument(opCtx, obj, nullOpDebug, false); + Status status = collection->insertDocument(opCtx, InsertStatement(obj), nullOpDebug, false); if (status.isOK()) { wunit.commit(); } diff --git a/src/mongo/db/db.cpp b/src/mongo/db/db.cpp index 0ab4437f521..64446785910 100644 --- a/src/mongo/db/db.cpp +++ b/src/mongo/db/db.cpp @@ -218,7 +218,7 @@ void logStartup(OperationContext* opCtx) { invariant(collection); OpDebug* const nullOpDebug = nullptr; - uassertStatusOK(collection->insertDocument(opCtx, o, nullOpDebug, false)); + uassertStatusOK(collection->insertDocument(opCtx, InsertStatement(o), nullOpDebug, false)); wunit.commit(); } diff --git a/src/mongo/db/exec/update.cpp b/src/mongo/db/exec/update.cpp index 879a5c7db05..70b13c08b07 100644 --- a/src/mongo/db/exec/update.cpp +++ b/src/mongo/db/exec/update.cpp @@ -481,8 +481,12 @@ void UpdateStage::doInsert() { WriteUnitOfWork wunit(getOpCtx()); invariant(_collection); const bool enforceQuota = !request->isGod(); - uassertStatusOK(_collection->insertDocument( - getOpCtx(), newObj, _params.opDebug, enforceQuota, request->isFromMigration())); + // TODO: SERVER-28912 include StmtId + uassertStatusOK(_collection->insertDocument(getOpCtx(), + InsertStatement(newObj), + _params.opDebug, + enforceQuota, + request->isFromMigration())); // Technically, we should save/restore state here, but since we are going to return // immediately after, it would just be wasted work. diff --git a/src/mongo/db/introspect.cpp b/src/mongo/db/introspect.cpp index f3d6680b242..aa0cb13e2e9 100644 --- a/src/mongo/db/introspect.cpp +++ b/src/mongo/db/introspect.cpp @@ -142,7 +142,8 @@ void profile(OperationContext* opCtx, NetworkOp op) { if (coll) { WriteUnitOfWork wuow(opCtx); OpDebug* const nullOpDebug = nullptr; - coll->insertDocument(opCtx, p, nullOpDebug, false).transitional_ignore(); + coll->insertDocument(opCtx, InsertStatement(p), nullOpDebug, false) + .transitional_ignore(); wuow.commit(); break; diff --git a/src/mongo/db/logical_session_id.h b/src/mongo/db/logical_session_id.h index 979f2bcc585..ef73bc0fcd1 100644 --- a/src/mongo/db/logical_session_id.h +++ b/src/mongo/db/logical_session_id.h @@ -40,6 +40,7 @@ namespace mongo { using TxnNumber = std::int64_t; using StmtId = std::int32_t; +const StmtId kUninitializedStmtId = -1; const TxnNumber kUninitializedTxnNumber = -1; class BSONObjBuilder; diff --git a/src/mongo/db/op_observer.h b/src/mongo/db/op_observer.h index d0b0fb03955..c4d8983c811 100644 --- a/src/mongo/db/op_observer.h +++ b/src/mongo/db/op_observer.h @@ -31,12 +31,14 @@ #include <string> #include "mongo/base/disallow_copying.h" +#include "mongo/db/catalog/collection.h" #include "mongo/db/catalog/collection_options.h" #include "mongo/db/jsobj.h" #include "mongo/db/s/collection_sharding_state.h" namespace mongo { struct CollectionOptions; +struct InsertStatement; class NamespaceString; class OperationContext; @@ -87,8 +89,8 @@ public: virtual void onInserts(OperationContext* opCtx, const NamespaceString& nss, OptionalCollectionUUID uuid, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, bool fromMigrate) = 0; virtual void onUpdate(OperationContext* opCtx, const OplogUpdateEntryArgs& args) = 0; virtual CollectionShardingState::DeleteState aboutToDelete(OperationContext* opCtx, diff --git a/src/mongo/db/op_observer_impl.cpp b/src/mongo/db/op_observer_impl.cpp index 5d84cc77f72..cd2509f195f 100644 --- a/src/mongo/db/op_observer_impl.cpp +++ b/src/mongo/db/op_observer_impl.cpp @@ -79,23 +79,24 @@ void OpObserverImpl::onCreateIndex(OperationContext* opCtx, void OpObserverImpl::onInserts(OperationContext* opCtx, const NamespaceString& nss, OptionalCollectionUUID uuid, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, bool fromMigrate) { - repl::logOps(opCtx, "i", nss, uuid, begin, end, fromMigrate); + repl::logInsertOps(opCtx, nss, uuid, begin, end, fromMigrate); auto css = CollectionShardingState::get(opCtx, nss.ns()); for (auto it = begin; it != end; it++) { - AuthorizationManager::get(opCtx->getServiceContext())->logOp(opCtx, "i", nss, *it, nullptr); + AuthorizationManager::get(opCtx->getServiceContext()) + ->logOp(opCtx, "i", nss, it->doc, nullptr); if (!fromMigrate) { - css->onInsertOp(opCtx, *it); + css->onInsertOp(opCtx, it->doc); } } if (nss.ns() == FeatureCompatibilityVersion::kCollection) { for (auto it = begin; it != end; it++) { - FeatureCompatibilityVersion::onInsertOrUpdate(*it); + FeatureCompatibilityVersion::onInsertOrUpdate(it->doc); } } diff --git a/src/mongo/db/op_observer_impl.h b/src/mongo/db/op_observer_impl.h index 35cd9184cca..a05efbb2861 100644 --- a/src/mongo/db/op_observer_impl.h +++ b/src/mongo/db/op_observer_impl.h @@ -47,8 +47,8 @@ public: void onInserts(OperationContext* opCtx, const NamespaceString& nss, OptionalCollectionUUID uuid, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, bool fromMigrate) override; void onUpdate(OperationContext* opCtx, const OplogUpdateEntryArgs& args) override; CollectionShardingState::DeleteState aboutToDelete(OperationContext* opCtx, diff --git a/src/mongo/db/op_observer_noop.cpp b/src/mongo/db/op_observer_noop.cpp index 47fafed9b97..4cbb3df65a9 100644 --- a/src/mongo/db/op_observer_noop.cpp +++ b/src/mongo/db/op_observer_noop.cpp @@ -43,8 +43,8 @@ void OpObserverNoop::onCreateIndex( void OpObserverNoop::onInserts(OperationContext*, const NamespaceString&, OptionalCollectionUUID, - std::vector<BSONObj>::const_iterator, - std::vector<BSONObj>::const_iterator, + std::vector<InsertStatement>::const_iterator, + std::vector<InsertStatement>::const_iterator, bool) {} void OpObserverNoop::onUpdate(OperationContext*, const OplogUpdateEntryArgs&) {} diff --git a/src/mongo/db/op_observer_noop.h b/src/mongo/db/op_observer_noop.h index 2aa4df846a0..8f3c949720d 100644 --- a/src/mongo/db/op_observer_noop.h +++ b/src/mongo/db/op_observer_noop.h @@ -47,8 +47,8 @@ public: void onInserts(OperationContext* opCtx, const NamespaceString& nss, OptionalCollectionUUID uuid, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, bool fromMigrate) override; void onUpdate(OperationContext* opCtx, const OplogUpdateEntryArgs& args) override; CollectionShardingState::DeleteState aboutToDelete(OperationContext* opCtx, diff --git a/src/mongo/db/ops/write_ops_exec.cpp b/src/mongo/db/ops/write_ops_exec.cpp index dae915b51f7..76e1d9a0acc 100644 --- a/src/mongo/db/ops/write_ops_exec.cpp +++ b/src/mongo/db/ops/write_ops_exec.cpp @@ -300,8 +300,8 @@ WriteResult performCreateIndexes(OperationContext* opCtx, const InsertOp& wholeO void insertDocuments(OperationContext* opCtx, Collection* collection, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end) { + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end) { // Intentionally not using writeConflictRetry. That is handled by the caller so it can react to // oversized batches. WriteUnitOfWork wuow(opCtx); @@ -315,7 +315,7 @@ void insertDocuments(OperationContext* opCtx, */ bool insertBatchAndHandleErrors(OperationContext* opCtx, const InsertOp& wholeOp, - const std::vector<BSONObj>& batch, + const std::vector<InsertStatement>& batch, LastOpFixer* lastOpFixer, WriteResult* out) { if (batch.empty()) @@ -443,7 +443,7 @@ WriteResult performInserts(OperationContext* opCtx, const InsertOp& wholeOp) { out.results.reserve(wholeOp.getDocuments().size()); size_t bytesInBatch = 0; - std::vector<BSONObj> batch; + std::vector<InsertStatement> batch; const size_t maxBatchSize = internalInsertMaxBatchSize.load(); batch.reserve(std::min(wholeOp.getDocuments().size(), maxBatchSize)); @@ -455,8 +455,10 @@ WriteResult performInserts(OperationContext* opCtx, const InsertOp& wholeOp) { // correct order. In an ordered insert, if one of the docs ahead of us fails, we should // behave as-if we never got to this document. } else { - batch.push_back(fixedDoc.getValue().isEmpty() ? doc : std::move(fixedDoc.getValue())); - bytesInBatch += batch.back().objsize(); + // TODO: SERVER-28912 get StmtId from request + batch.emplace_back(fixedDoc.getValue().isEmpty() ? doc + : std::move(fixedDoc.getValue())); + bytesInBatch += batch.back().doc.objsize(); if (!isLastDoc && batch.size() < maxBatchSize && bytesInBatch < insertVectorMaxBytes) continue; // Add more to batch before inserting. } diff --git a/src/mongo/db/repl/collection_bulk_loader_impl.cpp b/src/mongo/db/repl/collection_bulk_loader_impl.cpp index daf349029b7..82a769c6c17 100644 --- a/src/mongo/db/repl/collection_bulk_loader_impl.cpp +++ b/src/mongo/db/repl/collection_bulk_loader_impl.cpp @@ -168,7 +168,7 @@ Status CollectionBulkLoaderImpl::insertDocuments(const std::vector<BSONObj>::con // For capped collections, we use regular insertDocument, which will update // pre-existing indexes. const auto status = _autoColl->getCollection()->insertDocument( - _opCtx.get(), *iter, nullptr, false); + _opCtx.get(), InsertStatement(*iter), nullptr, false); if (!status.isOK()) { return status; } diff --git a/src/mongo/db/repl/databases_cloner_test.cpp b/src/mongo/db/repl/databases_cloner_test.cpp index 7f3755f9a11..533198f9e66 100644 --- a/src/mongo/db/repl/databases_cloner_test.cpp +++ b/src/mongo/db/repl/databases_cloner_test.cpp @@ -151,8 +151,9 @@ protected: ++_storageInterfaceWorkDone.documentsInsertedCount; return Status::OK(); }; - _storageInterface.insertDocumentsFn = [this]( - OperationContext* opCtx, const NamespaceString& nss, const std::vector<BSONObj>& ops) { + _storageInterface.insertDocumentsFn = [this](OperationContext* opCtx, + const NamespaceString& nss, + const std::vector<InsertStatement>& ops) { _storageInterfaceWorkDone.insertedOplogEntries = true; ++_storageInterfaceWorkDone.oplogEntriesInserted; return Status::OK(); diff --git a/src/mongo/db/repl/initial_syncer_test.cpp b/src/mongo/db/repl/initial_syncer_test.cpp index 8dc0b62f53a..c19c5fe152b 100644 --- a/src/mongo/db/repl/initial_syncer_test.cpp +++ b/src/mongo/db/repl/initial_syncer_test.cpp @@ -240,8 +240,9 @@ protected: ++_storageInterfaceWorkDone.documentsInsertedCount; return Status::OK(); }; - _storageInterface->insertDocumentsFn = [this]( - OperationContext* opCtx, const NamespaceString& nss, const std::vector<BSONObj>& ops) { + _storageInterface->insertDocumentsFn = [this](OperationContext* opCtx, + const NamespaceString& nss, + const std::vector<InsertStatement>& ops) { LockGuard lock(_storageInterfaceWorkDoneMutex); _storageInterfaceWorkDone.insertedOplogEntries = true; ++_storageInterfaceWorkDone.oplogEntriesInserted; diff --git a/src/mongo/db/repl/oplog.cpp b/src/mongo/db/repl/oplog.cpp index 05a8fd40e78..eeba58d69ec 100644 --- a/src/mongo/db/repl/oplog.cpp +++ b/src/mongo/db/repl/oplog.cpp @@ -260,7 +260,8 @@ OplogDocWriter _logOpWriter(OperationContext* opCtx, bool fromMigrate, OpTime optime, long long hashNew, - Date_t wallTime) { + Date_t wallTime, + StmtId statementId) { BSONObjBuilder b(256); b.append("ts", optime.getTimestamp()); @@ -283,6 +284,10 @@ OplogDocWriter _logOpWriter(OperationContext* opCtx, b.appendDate("wall", wallTime); } + if (statementId != kUninitializedStmtId) { + // TODO: SERVER-28912 append stmtId to oplog entry + } + return OplogDocWriter(OplogDocWriter(b.obj(), obj)); } } // end anon namespace @@ -398,20 +403,29 @@ OpTime logOp(OperationContext* opCtx, OplogSlot slot; getNextOpTime(opCtx, oplog, replCoord, replMode, 1, &slot); - auto writer = _logOpWriter( - opCtx, opstr, nss, uuid, obj, o2, fromMigrate, slot.opTime, slot.hash, Date_t::now()); + // TODO: SERVER-28912 Include statementId for other ops + auto writer = _logOpWriter(opCtx, + opstr, + nss, + uuid, + obj, + o2, + fromMigrate, + slot.opTime, + slot.hash, + Date_t::now(), + kUninitializedStmtId); const DocWriter* basePtr = &writer; _logOpsInner(opCtx, nss, &basePtr, 1, oplog, replMode, slot.opTime); return slot.opTime; } -void logOps(OperationContext* opCtx, - const char* opstr, - const NamespaceString& nss, - OptionalCollectionUUID uuid, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, - bool fromMigrate) { +void logInsertOps(OperationContext* opCtx, + const NamespaceString& nss, + OptionalCollectionUUID uuid, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, + bool fromMigrate) { invariant(begin != end); auto replCoord = ReplicationCoordinator::get(opCtx); @@ -430,16 +444,18 @@ void logOps(OperationContext* opCtx, getNextOpTime(opCtx, oplog, replCoord, replMode, count, slots.get()); auto wallTime = Date_t::now(); for (size_t i = 0; i < count; i++) { + auto insertStatement = begin[i]; writers.emplace_back(_logOpWriter(opCtx, - opstr, + "i", nss, uuid, - begin[i], + insertStatement.doc, NULL, fromMigrate, slots[i].opTime, slots[i].hash, - wallTime)); + wallTime, + insertStatement.stmtId)); } std::unique_ptr<DocWriter const* []> basePtrs(new DocWriter const*[count]); @@ -935,9 +951,11 @@ Status applyOperation_inlock(OperationContext* opCtx, if (fieldO.type() == Array) { // Batched inserts. - std::vector<BSONObj> insertObjs; + std::vector<InsertStatement> insertObjs; for (auto elem : fieldO.Obj()) { - insertObjs.push_back(elem.Obj()); + // Note: we don't care about statement ids here since the secondaries don't create + // their own oplog entries. + insertObjs.emplace_back(elem.Obj()); } uassert(ErrorCodes::OperationFailed, str::stream() << "Failed to apply insert due to empty array element: " @@ -983,7 +1001,8 @@ Status applyOperation_inlock(OperationContext* opCtx, WriteUnitOfWork wuow(opCtx); try { OpDebug* const nullOpDebug = nullptr; - status = collection->insertDocument(opCtx, o, nullOpDebug, true); + status = + collection->insertDocument(opCtx, InsertStatement(o), nullOpDebug, true); } catch (DBException dbe) { status = dbe.toStatus(); } diff --git a/src/mongo/db/repl/oplog.h b/src/mongo/db/repl/oplog.h index 13fdf0275eb..ae388a5e429 100644 --- a/src/mongo/db/repl/oplog.h +++ b/src/mongo/db/repl/oplog.h @@ -34,6 +34,7 @@ #include "mongo/base/status.h" #include "mongo/bson/bsonobj.h" #include "mongo/bson/timestamp.h" +#include "mongo/db/catalog/collection.h" #include "mongo/db/catalog/collection_options.h" #include "mongo/db/repl/optime.h" #include "mongo/db/repl/replication_coordinator.h" @@ -73,6 +74,16 @@ extern int OPLOG_VERSION; /* Log operation(s) to the local oplog * + */ + +void logInsertOps(OperationContext* opCtx, + const NamespaceString& nss, + OptionalCollectionUUID uuid, + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end, + bool fromMigrate); + +/** * @param opstr * "i" insert * "u" update @@ -80,17 +91,7 @@ extern int OPLOG_VERSION; * "c" db cmd * "n" no-op * "db" declares presence of a database (ns is set to the db name + '.') - */ - -void logOps(OperationContext* opCtx, - const char* opstr, - const NamespaceString& nss, - OptionalCollectionUUID uuid, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end, - bool fromMigrate); - -/** + * * For 'u' records, 'obj' captures the mutation made to the object but not * the object itself. 'o2' captures the the criteria for the object that will be modified. * Returns the optime of the oplog entry written to the oplog. diff --git a/src/mongo/db/repl/oplog_buffer_collection.cpp b/src/mongo/db/repl/oplog_buffer_collection.cpp index 4adefe18d65..2e0ccc8278c 100644 --- a/src/mongo/db/repl/oplog_buffer_collection.cpp +++ b/src/mongo/db/repl/oplog_buffer_collection.cpp @@ -175,7 +175,7 @@ void OplogBufferCollection::pushAllNonBlocking(OperationContext* opCtx, return; } size_t numDocs = std::distance(begin, end); - Batch docsToInsert(numDocs); + std::vector<InsertStatement> docsToInsert(numDocs); stdx::lock_guard<stdx::mutex> lk(_mutex); auto ts = _lastPushedTimestamp; auto sentinelCount = _sentinelCount; @@ -184,7 +184,7 @@ void OplogBufferCollection::pushAllNonBlocking(OperationContext* opCtx, auto previousTimestamp = ts; std::tie(doc, ts, sentinelCount) = addIdToDocument(value, ts, sentinelCount); invariant(value.isEmpty() ? ts == previousTimestamp : ts > previousTimestamp); - return doc; + return InsertStatement(doc); }); auto status = _storageInterface->insertDocuments(opCtx, _nss, docsToInsert); diff --git a/src/mongo/db/repl/rs_rollback_no_uuid_test.cpp b/src/mongo/db/repl/rs_rollback_no_uuid_test.cpp index 81ad629302c..75f5c71d14e 100644 --- a/src/mongo/db/repl/rs_rollback_no_uuid_test.cpp +++ b/src/mongo/db/repl/rs_rollback_no_uuid_test.cpp @@ -958,11 +958,12 @@ TEST_F(RSRollbackTest, RollbackApplyOpsCommand) { } ASSERT(coll); OpDebug* const nullOpDebug = nullptr; - ASSERT_OK( - coll->insertDocument(_opCtx.get(), BSON("_id" << 1 << "v" << 2), nullOpDebug, false)); - ASSERT_OK( - coll->insertDocument(_opCtx.get(), BSON("_id" << 2 << "v" << 4), nullOpDebug, false)); - ASSERT_OK(coll->insertDocument(_opCtx.get(), BSON("_id" << 4), nullOpDebug, false)); + ASSERT_OK(coll->insertDocument( + _opCtx.get(), InsertStatement(BSON("_id" << 1 << "v" << 2)), nullOpDebug, false)); + ASSERT_OK(coll->insertDocument( + _opCtx.get(), InsertStatement(BSON("_id" << 2 << "v" << 4)), nullOpDebug, false)); + ASSERT_OK(coll->insertDocument( + _opCtx.get(), InsertStatement(BSON("_id" << 4)), nullOpDebug, false)); wuow.commit(); } const auto commonOperation = diff --git a/src/mongo/db/repl/rs_rollback_test.cpp b/src/mongo/db/repl/rs_rollback_test.cpp index 6b0ba57b556..3d2bd032c64 100644 --- a/src/mongo/db/repl/rs_rollback_test.cpp +++ b/src/mongo/db/repl/rs_rollback_test.cpp @@ -1034,11 +1034,12 @@ TEST_F(RSRollbackTest, RollbackApplyOpsCommand) { } ASSERT(coll); OpDebug* const nullOpDebug = nullptr; - ASSERT_OK( - coll->insertDocument(_opCtx.get(), BSON("_id" << 1 << "v" << 2), nullOpDebug, false)); - ASSERT_OK( - coll->insertDocument(_opCtx.get(), BSON("_id" << 2 << "v" << 4), nullOpDebug, false)); - ASSERT_OK(coll->insertDocument(_opCtx.get(), BSON("_id" << 4), nullOpDebug, false)); + ASSERT_OK(coll->insertDocument( + _opCtx.get(), InsertStatement(BSON("_id" << 1 << "v" << 2)), nullOpDebug, false)); + ASSERT_OK(coll->insertDocument( + _opCtx.get(), InsertStatement(BSON("_id" << 2 << "v" << 4)), nullOpDebug, false)); + ASSERT_OK(coll->insertDocument( + _opCtx.get(), InsertStatement(BSON("_id" << 4)), nullOpDebug, false)); wuow.commit(); } UUID uuid = coll->uuid().get(); diff --git a/src/mongo/db/repl/storage_interface.h b/src/mongo/db/repl/storage_interface.h index ccc5d03001f..ce3059e9e81 100644 --- a/src/mongo/db/repl/storage_interface.h +++ b/src/mongo/db/repl/storage_interface.h @@ -36,6 +36,7 @@ #include "mongo/base/disallow_copying.h" #include "mongo/base/string_data.h" +#include "mongo/db/catalog/collection.h" #include "mongo/db/namespace_string.h" #include "mongo/db/query/index_bounds.h" #include "mongo/db/repl/collection_bulk_loader.h" @@ -112,7 +113,7 @@ public: */ virtual Status insertDocuments(OperationContext* opCtx, const NamespaceString& nss, - const std::vector<BSONObj>& docs) = 0; + const std::vector<InsertStatement>& docs) = 0; /** * Creates the initial oplog, errors if it exists. diff --git a/src/mongo/db/repl/storage_interface_impl.cpp b/src/mongo/db/repl/storage_interface_impl.cpp index 251518cc1d0..0dcb15a0110 100644 --- a/src/mongo/db/repl/storage_interface_impl.cpp +++ b/src/mongo/db/repl/storage_interface_impl.cpp @@ -264,7 +264,7 @@ StorageInterfaceImpl::createCollectionForBulkLoading( Status StorageInterfaceImpl::insertDocument(OperationContext* opCtx, const NamespaceString& nss, const BSONObj& doc) { - return insertDocuments(opCtx, nss, {doc}); + return insertDocuments(opCtx, nss, {InsertStatement(doc)}); } namespace { @@ -293,8 +293,8 @@ StatusWith<Collection*> getCollection(const AutoGetCollectionType& autoGetCollec Status insertDocumentsSingleBatch(OperationContext* opCtx, const NamespaceString& nss, - std::vector<BSONObj>::const_iterator begin, - std::vector<BSONObj>::const_iterator end) { + std::vector<InsertStatement>::const_iterator begin, + std::vector<InsertStatement>::const_iterator end) { AutoGetCollection autoColl(opCtx, nss, MODE_IX); auto collectionResult = @@ -319,7 +319,7 @@ Status insertDocumentsSingleBatch(OperationContext* opCtx, Status StorageInterfaceImpl::insertDocuments(OperationContext* opCtx, const NamespaceString& nss, - const std::vector<BSONObj>& docs) { + const std::vector<InsertStatement>& docs) { if (docs.size() > 1U) { try { if (insertDocumentsSingleBatch(opCtx, nss, docs.cbegin(), docs.cend()).isOK()) { diff --git a/src/mongo/db/repl/storage_interface_impl.h b/src/mongo/db/repl/storage_interface_impl.h index d01fa7ff0e2..c121806e640 100644 --- a/src/mongo/db/repl/storage_interface_impl.h +++ b/src/mongo/db/repl/storage_interface_impl.h @@ -70,7 +70,7 @@ public: Status insertDocuments(OperationContext* opCtx, const NamespaceString& nss, - const std::vector<BSONObj>& docs) override; + const std::vector<InsertStatement>& docs) override; Status dropReplicatedDatabases(OperationContext* opCtx) override; diff --git a/src/mongo/db/repl/storage_interface_impl_test.cpp b/src/mongo/db/repl/storage_interface_impl_test.cpp index 9f98851679a..70e801e2fe3 100644 --- a/src/mongo/db/repl/storage_interface_impl_test.cpp +++ b/src/mongo/db/repl/storage_interface_impl_test.cpp @@ -135,6 +135,14 @@ int64_t getIndexKeyCount(OperationContext* opCtx, IndexCatalog* cat, IndexDescri return numKeys; } +std::vector<InsertStatement> transformInserts(std::vector<BSONObj> docs) { + std::vector<InsertStatement> inserts(docs.size()); + std::transform(docs.cbegin(), docs.cend(), inserts.begin(), [](const BSONObj& doc) { + return InsertStatement(doc); + }); + return inserts; +} + class StorageInterfaceImplTest : public ServiceContextMongoDTest { protected: OperationContext* getOperationContext() { @@ -279,7 +287,7 @@ TEST_F(StorageInterfaceImplTest, IncrementRollbackIDRollsToZeroWhenExceedingMaxI auto maxDoc = {BSON("_id" << StorageInterfaceImpl::kRollbackIdDocumentId << StorageInterfaceImpl::kRollbackIdFieldName << std::numeric_limits<int>::max())}; - ASSERT_OK(storage.insertDocuments(opCtx, nss, maxDoc)); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts(maxDoc))); _assertRollbackIDDocument(opCtx, std::numeric_limits<int>::max()); auto rbid = unittest::assertGet(storage.getRollbackID(opCtx)); @@ -306,7 +314,7 @@ TEST_F(StorageInterfaceImplTest, GetRollbackIDReturnsBadStatusIfDocumentHasBadFi createCollection(opCtx, nss); auto badDoc = {BSON("_id" << StorageInterfaceImpl::kRollbackIdDocumentId << "bad field" << 3)}; - ASSERT_OK(storage.insertDocuments(opCtx, nss, badDoc)); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts(badDoc))); ASSERT_EQUALS(mongo::AssertionException::convertExceptionCode(40415), storage.getRollbackID(opCtx).getStatus()); } @@ -321,7 +329,7 @@ TEST_F(StorageInterfaceImplTest, GetRollbackIDReturnsBadStatusIfRollbackIDIsNotI auto badDoc = {BSON("_id" << StorageInterfaceImpl::kRollbackIdDocumentId << StorageInterfaceImpl::kRollbackIdFieldName << "bad id")}; - ASSERT_OK(storage.insertDocuments(opCtx, nss, badDoc)); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts(badDoc))); ASSERT_EQUALS(ErrorCodes::TypeMismatch, storage.getRollbackID(opCtx).getStatus()); } @@ -350,7 +358,7 @@ TEST_F(StorageInterfaceImplTest, // Non-oplog collection will enforce mandatory _id field requirement on insertion. StorageInterfaceImpl storage; auto op = makeOplogEntry({Timestamp(Seconds(1), 0), 1LL}); - auto status = storage.insertDocuments(opCtx, nss, {op}); + auto status = storage.insertDocuments(opCtx, nss, transformInserts({op})); ASSERT_EQUALS(ErrorCodes::InternalError, status); ASSERT_STRING_CONTAINS(status.reason(), "Collection::insertDocument got document without _id"); } @@ -366,24 +374,24 @@ TEST_F(StorageInterfaceImplTest, createCollection(opCtx, nss, options); // StorageInterfaceImpl::insertDocuments should fall back on inserting the batch one at a time. StorageInterfaceImpl storage; - auto doc1 = BSON("_id" << 1); - auto doc2 = BSON("_id" << 2); - std::vector<BSONObj> docs({doc1, doc2}); + auto doc1 = InsertStatement(BSON("_id" << 1)); + auto doc2 = InsertStatement(BSON("_id" << 2)); + std::vector<InsertStatement> docs{doc1, doc2}; // Confirm that Collection::insertDocuments fails to insert the batch all at once. { AutoGetCollection autoCollection(opCtx, nss, MODE_IX); WriteUnitOfWork wunit(opCtx); ASSERT_EQUALS(ErrorCodes::OperationCannotBeBatched, autoCollection.getCollection()->insertDocuments( - opCtx, docs.begin(), docs.cend(), nullptr, false)); + opCtx, docs.cbegin(), docs.cend(), nullptr, false)); } ASSERT_OK(storage.insertDocuments(opCtx, nss, docs)); // Check collection contents. OplogInterface returns documents in reverse natural order. OplogInterfaceLocal oplog(opCtx, nss.ns()); auto iter = oplog.makeIterator(); - ASSERT_BSONOBJ_EQ(doc2, unittest::assertGet(iter->next()).first); - ASSERT_BSONOBJ_EQ(doc1, unittest::assertGet(iter->next()).first); + ASSERT_BSONOBJ_EQ(doc2.doc, unittest::assertGet(iter->next()).first); + ASSERT_BSONOBJ_EQ(doc1.doc, unittest::assertGet(iter->next()).first); ASSERT_EQUALS(ErrorCodes::CollectionIsEmpty, iter->next().getStatus()); } @@ -398,7 +406,7 @@ TEST_F(StorageInterfaceImplTest, InsertDocumentsSavesOperationsReturnsOpTimeOfLa StorageInterfaceImpl storage; auto op1 = makeOplogEntry({Timestamp(Seconds(1), 0), 1LL}); auto op2 = makeOplogEntry({Timestamp(Seconds(1), 0), 1LL}); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {op1, op2})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({op1, op2}))); // Check contents of oplog. OplogInterface iterates over oplog collection in reverse. repl::OplogInterfaceLocal oplog(opCtx, nss.ns()); @@ -414,7 +422,7 @@ TEST_F(StorageInterfaceImplTest, auto nss = makeNamespace(_agent); StorageInterfaceImpl storage; auto opCtx = getOperationContext(); - auto status = storage.insertDocuments(opCtx, nss, {op}); + auto status = storage.insertDocuments(opCtx, nss, transformInserts({op})); ASSERT_EQUALS(ErrorCodes::NamespaceNotFound, status); ASSERT_STRING_CONTAINS(status.reason(), "The collection must exist before inserting documents"); } @@ -888,11 +896,11 @@ TEST_F(StorageInterfaceImplTest, ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments(opCtx, nss, - {BSON("_id" << 0), - BSON("_id" << 1), - BSON("_id" << 2), - BSON("_id" << 3), - BSON("_id" << 4)})); + transformInserts({BSON("_id" << 0), + BSON("_id" << 1), + BSON("_id" << 2), + BSON("_id" << 3), + BSON("_id" << 4)}))); // startKey not provided ASSERT_BSONOBJ_EQ( @@ -1024,11 +1032,11 @@ TEST_F(StorageInterfaceImplTest, ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments(opCtx, nss, - {BSON("_id" << 0), - BSON("_id" << 1), - BSON("_id" << 2), - BSON("_id" << 3), - BSON("_id" << 4)})); + transformInserts({BSON("_id" << 0), + BSON("_id" << 1), + BSON("_id" << 2), + BSON("_id" << 3), + BSON("_id" << 4)}))); // startKey not provided ASSERT_BSONOBJ_EQ( @@ -1138,7 +1146,7 @@ TEST_F(StorageInterfaceImplTest, auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_BSONOBJ_EQ( BSON("_id" << 1), _assetGetFront(storage.findDocuments(opCtx, @@ -1165,7 +1173,7 @@ TEST_F(StorageInterfaceImplTest, auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_BSONOBJ_EQ( BSON("_id" << 0), _assetGetFront(storage.findDocuments(opCtx, @@ -1186,7 +1194,7 @@ TEST_F(StorageInterfaceImplTest, FindDocumentsCollScanReturnsNoSuchKeyIfStartKey auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_EQUALS(ErrorCodes::NoSuchKey, storage .findDocuments(opCtx, @@ -1206,7 +1214,7 @@ TEST_F(StorageInterfaceImplTest, auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_EQUALS(ErrorCodes::InvalidOptions, storage .findDocuments(opCtx, @@ -1280,14 +1288,14 @@ TEST_F(StorageInterfaceImplTest, ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments(opCtx, nss, - {BSON("_id" << 0), - BSON("_id" << 1), - BSON("_id" << 2), - BSON("_id" << 3), - BSON("_id" << 4), - BSON("_id" << 5), - BSON("_id" << 6), - BSON("_id" << 7)})); + transformInserts({BSON("_id" << 0), + BSON("_id" << 1), + BSON("_id" << 2), + BSON("_id" << 3), + BSON("_id" << 4), + BSON("_id" << 5), + BSON("_id" << 6), + BSON("_id" << 7)}))); // startKey not provided ASSERT_BSONOBJ_EQ( @@ -1390,14 +1398,14 @@ TEST_F(StorageInterfaceImplTest, ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments(opCtx, nss, - {BSON("_id" << 0), - BSON("_id" << 1), - BSON("_id" << 2), - BSON("_id" << 3), - BSON("_id" << 4), - BSON("_id" << 5), - BSON("_id" << 6), - BSON("_id" << 7)})); + transformInserts({BSON("_id" << 0), + BSON("_id" << 1), + BSON("_id" << 2), + BSON("_id" << 3), + BSON("_id" << 4), + BSON("_id" << 5), + BSON("_id" << 6), + BSON("_id" << 7)}))); // startKey not provided ASSERT_BSONOBJ_EQ( @@ -1498,7 +1506,7 @@ TEST_F(StorageInterfaceImplTest, auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_BSONOBJ_EQ( BSON("_id" << 1), _assetGetFront(storage.deleteDocuments(opCtx, @@ -1519,7 +1527,7 @@ TEST_F(StorageInterfaceImplTest, auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_BSONOBJ_EQ( BSON("_id" << 0), _assetGetFront(storage.deleteDocuments(opCtx, @@ -1539,7 +1547,7 @@ TEST_F(StorageInterfaceImplTest, DeleteDocumentsCollScanReturnsNoSuchKeyIfStartK auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_EQUALS(ErrorCodes::NoSuchKey, storage .deleteDocuments(opCtx, @@ -1559,7 +1567,7 @@ TEST_F(StorageInterfaceImplTest, auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); ASSERT_EQUALS(ErrorCodes::InvalidOptions, storage .deleteDocuments(opCtx, @@ -1603,7 +1611,7 @@ TEST_F(StorageInterfaceImplTest, ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); auto doc1 = BSON("_id" << 0 << "x" << 0); auto doc2 = BSON("_id" << 1 << "x" << 1); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc1, doc2})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc1, doc2}))); ASSERT_EQUALS(ErrorCodes::TooManyMatchingDocuments, storage.findSingleton(opCtx, nss).getStatus()); } @@ -1669,7 +1677,7 @@ TEST_F(StorageInterfaceImplTest, PutSingletonUpdatesFirstDocumentWhenCollectionI ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); auto doc1 = BSON("_id" << 0 << "x" << 0); auto doc2 = BSON("_id" << 1 << "x" << 1); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc1, doc2})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc1, doc2}))); auto update = BSON("$set" << BSON("x" << 2)); ASSERT_OK(storage.putSingleton(opCtx, nss, update)); _assertDocumentsInCollectionEquals(opCtx, nss, {BSON("_id" << 0 << "x" << 2), doc2}); @@ -1701,7 +1709,7 @@ TEST_F(StorageInterfaceImplTest, FindByIdReturnsNoSuchKeyWhenDocumentIsNotFound) auto doc1 = BSON("_id" << 0 << "x" << 0); auto doc2 = BSON("_id" << 1 << "x" << 1); auto doc3 = BSON("_id" << 2 << "x" << 2); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc1, doc3})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc1, doc3}))); ASSERT_EQUALS(ErrorCodes::NoSuchKey, storage.findById(opCtx, nss, doc2["_id"]).getStatus()); } @@ -1713,7 +1721,7 @@ TEST_F(StorageInterfaceImplTest, FindByIdReturnsDocumentWhenDocumentExists) { auto doc1 = BSON("_id" << 0 << "x" << 0); auto doc2 = BSON("_id" << 1 << "x" << 1); auto doc3 = BSON("_id" << 2 << "x" << 2); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc1, doc2, doc3})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc1, doc2, doc3}))); ASSERT_BSONOBJ_EQ(doc2, unittest::assertGet(storage.findById(opCtx, nss, doc2["_id"]))); } @@ -1744,7 +1752,7 @@ TEST_F(StorageInterfaceImplTest, DeleteByIdReturnsNoSuchKeyWhenDocumentIsNotFoun auto doc1 = BSON("_id" << 0 << "x" << 0); auto doc2 = BSON("_id" << 1 << "x" << 1); auto doc3 = BSON("_id" << 2 << "x" << 2); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc1, doc3})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc1, doc3}))); ASSERT_EQUALS(ErrorCodes::NoSuchKey, storage.deleteById(opCtx, nss, doc2["_id"]).getStatus()); _assertDocumentsInCollectionEquals(opCtx, nss, {doc1, doc3}); } @@ -1757,7 +1765,7 @@ TEST_F(StorageInterfaceImplTest, DeleteByIdReturnsDocumentWhenDocumentExists) { auto doc1 = BSON("_id" << 0 << "x" << 0); auto doc2 = BSON("_id" << 1 << "x" << 1); auto doc3 = BSON("_id" << 2 << "x" << 2); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc1, doc2, doc3})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc1, doc2, doc3}))); ASSERT_BSONOBJ_EQ(doc2, unittest::assertGet(storage.deleteById(opCtx, nss, doc2["_id"]))); _assertDocumentsInCollectionEquals(opCtx, nss, {doc1, doc3}); } @@ -1795,7 +1803,10 @@ TEST_F(StorageInterfaceImplTest, UpsertSingleDocumentReplacesExistingDocumentInC auto originalDoc = BSON("_id" << 1 << "x" << 1); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 0 << "x" << 0), originalDoc, BSON("_id" << 2 << "x" << 2)})); + opCtx, + nss, + transformInserts( + {BSON("_id" << 0 << "x" << 0), originalDoc, BSON("_id" << 2 << "x" << 2)}))); ASSERT_OK(storage.upsertById(opCtx, nss, originalDoc["_id"], BSON("x" << 100))); @@ -1813,7 +1824,9 @@ TEST_F(StorageInterfaceImplTest, UpsertSingleDocumentInsertsNewDocumentInCollect ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 0 << "x" << 0), BSON("_id" << 2 << "x" << 2)})); + opCtx, + nss, + transformInserts({BSON("_id" << 0 << "x" << 0), BSON("_id" << 2 << "x" << 2)}))); ASSERT_OK(storage.upsertById(opCtx, nss, BSON("" << 1).firstElement(), BSON("x" << 100))); @@ -1839,7 +1852,10 @@ TEST_F(StorageInterfaceImplTest, auto originalDoc = BSON("_id" << 1 << "x" << 1); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 0 << "x" << 0), originalDoc, BSON("_id" << 2 << "x" << 2)})); + opCtx, + nss, + transformInserts( + {BSON("_id" << 0 << "x" << 0), originalDoc, BSON("_id" << 2 << "x" << 2)}))); ASSERT_OK(storage.upsertById(opCtx, nss, originalDoc["_id"], BSON("x" << 100))); @@ -1949,7 +1965,7 @@ TEST_F( ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); auto doc = BSON("_id" << 0 << "x" << 0); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc}))); _assertDocumentsInCollectionEquals(opCtx, nss, {doc}); // This test fixture disables replicated writes by default. We want to re-enable this setting @@ -1974,7 +1990,7 @@ TEST_F( ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); auto doc = BSON("_id" << 0 << "x" << 0); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc}))); _assertDocumentsInCollectionEquals(opCtx, nss, {doc}); // This test fixture disables replicated writes by default. We want to re-enable this setting @@ -2025,7 +2041,7 @@ TEST_F(StorageInterfaceImplTest, DeleteByFilterLeavesCollectionUnchangedIfNoDocu ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); auto docs = {BSON("_id" << 0 << "x" << 0), BSON("_id" << 2 << "x" << 2)}; - ASSERT_OK(storage.insertDocuments(opCtx, nss, docs)); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts(docs))); auto filter = BSON("x" << 1); ASSERT_OK(storage.deleteByFilter(opCtx, nss, filter)); @@ -2043,7 +2059,7 @@ TEST_F(StorageInterfaceImplTest, DeleteByFilterRemoveDocumentsThatMatchFilter) { BSON("_id" << 1 << "x" << 1), BSON("_id" << 2 << "x" << 2), BSON("_id" << 3 << "x" << 3)}; - ASSERT_OK(storage.insertDocuments(opCtx, nss, docs)); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts(docs))); auto filter = BSON("x" << BSON("$in" << BSON_ARRAY(1 << 2))); ASSERT_OK(storage.deleteByFilter(opCtx, nss, filter)); @@ -2059,7 +2075,7 @@ TEST_F(StorageInterfaceImplTest, DeleteByFilterUsesIdHackIfFilterContainsIdField ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); auto docs = {BSON("_id" << 0 << "x" << 0), BSON("_id" << 1 << "x" << 1)}; - ASSERT_OK(storage.insertDocuments(opCtx, nss, docs)); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts(docs))); auto filter = BSON("_id" << 1); ASSERT_OK(storage.deleteByFilter(opCtx, nss, filter)); @@ -2082,7 +2098,7 @@ TEST_F(StorageInterfaceImplTest, DeleteByFilterRemovesDocumentsInIllegalClientSy BSON("_id" << 1 << "x" << 1), BSON("_id" << 2 << "x" << 2), BSON("_id" << 3 << "x" << 3)}; - ASSERT_OK(storage.insertDocuments(opCtx, nss, docs)); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts(docs))); auto filter = BSON("$or" << BSON_ARRAY(BSON("x" << 0) << BSON("_id" << 2))); ASSERT_OK(storage.deleteByFilter(opCtx, nss, filter)); @@ -2113,7 +2129,7 @@ TEST_F(StorageInterfaceImplTest, << "DEF"); auto doc4 = BSON("_id" << 4 << "x" << "def"); - ASSERT_OK(storage.insertDocuments(opCtx, nss, {doc1, doc2, doc3, doc4})); + ASSERT_OK(storage.insertDocuments(opCtx, nss, transformInserts({doc1, doc2, doc3, doc4}))); // This filter should remove doc1 and doc2 because the values of the field "x" // are equivalent to "aBc" under the case-insensive collation. @@ -2159,7 +2175,7 @@ TEST_F(StorageInterfaceImplTest, GetCollectionCountReturnsCollectionCount) { auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); auto count = unittest::assertGet(storage.getCollectionCount(opCtx, nss)); ASSERT_EQUALS(3UL, count); } @@ -2198,7 +2214,7 @@ TEST_F(StorageInterfaceImplTest, GetCollectionSizeReturnsCollectionSize) { auto nss = makeNamespace(_agent); ASSERT_OK(storage.createCollection(opCtx, nss, CollectionOptions())); ASSERT_OK(storage.insertDocuments( - opCtx, nss, {BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)})); + opCtx, nss, transformInserts({BSON("_id" << 1), BSON("_id" << 2), BSON("_id" << 0)}))); auto size = unittest::assertGet(storage.getCollectionSize(opCtx, nss)); ASSERT_NOT_EQUALS(0UL, size); } diff --git a/src/mongo/db/repl/storage_interface_mock.h b/src/mongo/db/repl/storage_interface_mock.h index dfb8e81d928..5b9ee48dc43 100644 --- a/src/mongo/db/repl/storage_interface_mock.h +++ b/src/mongo/db/repl/storage_interface_mock.h @@ -91,8 +91,9 @@ public: const std::vector<BSONObj>& secondaryIndexSpecs)>; using InsertDocumentFn = stdx::function<Status( OperationContext* opCtx, const NamespaceString& nss, const BSONObj& doc)>; - using InsertDocumentsFn = stdx::function<Status( - OperationContext* opCtx, const NamespaceString& nss, const std::vector<BSONObj>& docs)>; + using InsertDocumentsFn = stdx::function<Status(OperationContext* opCtx, + const NamespaceString& nss, + const std::vector<InsertStatement>& docs)>; using DropUserDatabasesFn = stdx::function<Status(OperationContext* opCtx)>; using CreateOplogFn = stdx::function<Status(OperationContext* opCtx, const NamespaceString& nss)>; @@ -140,7 +141,7 @@ public: Status insertDocuments(OperationContext* opCtx, const NamespaceString& nss, - const std::vector<BSONObj>& docs) override { + const std::vector<InsertStatement>& docs) override { return insertDocumentsFn(opCtx, nss, docs); } @@ -261,10 +262,11 @@ public: [](OperationContext* opCtx, const NamespaceString& nss, const BSONObj& doc) { return Status{ErrorCodes::IllegalOperation, "InsertDocumentFn not implemented."}; }; - InsertDocumentsFn insertDocumentsFn = - [](OperationContext* opCtx, const NamespaceString& nss, const std::vector<BSONObj>& docs) { - return Status{ErrorCodes::IllegalOperation, "InsertDocumentsFn not implemented."}; - }; + InsertDocumentsFn insertDocumentsFn = [](OperationContext* opCtx, + const NamespaceString& nss, + const std::vector<InsertStatement>& docs) { + return Status{ErrorCodes::IllegalOperation, "InsertDocumentsFn not implemented."}; + }; DropUserDatabasesFn dropUserDBsFn = [](OperationContext* opCtx) { return Status{ErrorCodes::IllegalOperation, "DropUserDatabasesFn not implemented."}; }; diff --git a/src/mongo/db/repl/sync_tail.cpp b/src/mongo/db/repl/sync_tail.cpp index 425b0868bf6..aa4e61b98e9 100644 --- a/src/mongo/db/repl/sync_tail.cpp +++ b/src/mongo/db/repl/sync_tail.cpp @@ -469,12 +469,12 @@ void scheduleWritesToOplog(OperationContext* opCtx, opCtx->lockState()->setShouldConflictWithSecondaryBatchApplication(false); UnreplicatedWritesBlock uwb(opCtx); - std::vector<BSONObj> docs; + std::vector<InsertStatement> docs; docs.reserve(end - begin); for (size_t i = begin; i < end; i++) { // Add as unowned BSON to avoid unnecessary ref-count bumps. // 'ops' will outlive 'docs' so the BSON lifetime will be guaranteed. - docs.emplace_back(ops[i].raw.objdata()); + docs.emplace_back(BSONObj(ops[i].raw.objdata())); } fassertStatusOK(40141, @@ -1014,7 +1014,7 @@ bool SyncTail::fetchAndInsertMissingDocument(OperationContext* opCtx, const BSON invariant(coll); OpDebug* const nullOpDebug = nullptr; - Status status = coll->insertDocument(opCtx, missingObj, nullOpDebug, true); + Status status = coll->insertDocument(opCtx, InsertStatement(missingObj), nullOpDebug, true); uassert(15917, str::stream() << "Failed to insert missing document: " << status.toString(), status.isOK()); diff --git a/src/mongo/db/repl/sync_tail_test.cpp b/src/mongo/db/repl/sync_tail_test.cpp index eb0a0f48391..da881a4f311 100644 --- a/src/mongo/db/repl/sync_tail_test.cpp +++ b/src/mongo/db/repl/sync_tail_test.cpp @@ -221,9 +221,10 @@ void SyncTailTest::setUp() { ReplicationCoordinator::set(service, stdx::make_unique<ReplicationCoordinatorMock>(service)); auto storageInterface = stdx::make_unique<StorageInterfaceMock>(); _storageInterface = storageInterface.get(); - storageInterface->insertDocumentsFn = [](OperationContext*, - const NamespaceString&, - const std::vector<BSONObj>&) { return Status::OK(); }; + storageInterface->insertDocumentsFn = + [](OperationContext*, const NamespaceString&, const std::vector<InsertStatement>&) { + return Status::OK(); + }; StorageInterface::set(service, std::move(storageInterface)); DropPendingCollectionReaper::set( service, stdx::make_unique<DropPendingCollectionReaper>(_storageInterface)); @@ -678,9 +679,11 @@ TEST_F(SyncTailTest, MultiApplyAssignsOperationsToWriterThreadsBasedOnNamespaceH auto op2 = makeInsertDocumentOplogEntry({Timestamp(Seconds(2), 0), 1LL}, nss2, BSON("x" << 2)); NamespaceString nssForInsert; - std::vector<BSONObj> operationsWrittenToOplog; + std::vector<InsertStatement> operationsWrittenToOplog; _storageInterface->insertDocumentsFn = [&mutex, &nssForInsert, &operationsWrittenToOplog]( - OperationContext* opCtx, const NamespaceString& nss, const std::vector<BSONObj>& docs) { + OperationContext* opCtx, + const NamespaceString& nss, + const std::vector<InsertStatement>& docs) { stdx::lock_guard<stdx::mutex> lock(mutex); nssForInsert = nss; operationsWrittenToOplog = docs; @@ -710,8 +713,8 @@ TEST_F(SyncTailTest, MultiApplyAssignsOperationsToWriterThreadsBasedOnNamespaceH stdx::lock_guard<stdx::mutex> lock(mutex); ASSERT_EQUALS(2U, operationsWrittenToOplog.size()); ASSERT_EQUALS(NamespaceString(rsOplogName), nssForInsert); - ASSERT_BSONOBJ_EQ(op1.raw, operationsWrittenToOplog[0]); - ASSERT_BSONOBJ_EQ(op2.raw, operationsWrittenToOplog[1]); + ASSERT_BSONOBJ_EQ(op1.raw, operationsWrittenToOplog[0].doc); + ASSERT_BSONOBJ_EQ(op2.raw, operationsWrittenToOplog[1].doc); } TEST_F(SyncTailTest, MultiSyncApplyUsesSyncApplyToApplyOperation) { diff --git a/src/mongo/db/views/durable_view_catalog.cpp b/src/mongo/db/views/durable_view_catalog.cpp index 65a00e4600b..8e436995952 100644 --- a/src/mongo/db/views/durable_view_catalog.cpp +++ b/src/mongo/db/views/durable_view_catalog.cpp @@ -144,8 +144,8 @@ void DurableViewCatalogImpl::upsert(OperationContext* opCtx, Snapshotted<BSONObj> oldView; if (!id.isNormal() || !systemViews->findDoc(opCtx, id, &oldView)) { LOG(2) << "insert view " << view << " into " << _db->getSystemViewsName(); - uassertStatusOK( - systemViews->insertDocument(opCtx, view, &CurOp::get(opCtx)->debug(), enforceQuota)); + uassertStatusOK(systemViews->insertDocument( + opCtx, InsertStatement(view), &CurOp::get(opCtx)->debug(), enforceQuota)); } else { OplogUpdateEntryArgs args; args.nss = systemViewsNs; diff --git a/src/mongo/dbtests/counttests.cpp b/src/mongo/dbtests/counttests.cpp index 9f3cf21c73b..8e36e525268 100644 --- a/src/mongo/dbtests/counttests.cpp +++ b/src/mongo/dbtests/counttests.cpp @@ -87,9 +87,11 @@ protected: oid.init(); b.appendOID("_id", &oid); b.appendElements(o); - _collection->insertDocument(&_opCtx, b.obj(), nullOpDebug, false).transitional_ignore(); + _collection->insertDocument(&_opCtx, InsertStatement(b.obj()), nullOpDebug, false) + .transitional_ignore(); } else { - _collection->insertDocument(&_opCtx, o, nullOpDebug, false).transitional_ignore(); + _collection->insertDocument(&_opCtx, InsertStatement(o), nullOpDebug, false) + .transitional_ignore(); } wunit.commit(); } diff --git a/src/mongo/dbtests/indexupdatetests.cpp b/src/mongo/dbtests/indexupdatetests.cpp index b30677d8d64..4d17c2be43f 100644 --- a/src/mongo/dbtests/indexupdatetests.cpp +++ b/src/mongo/dbtests/indexupdatetests.cpp @@ -113,14 +113,14 @@ public: OpDebug* const nullOpDebug = nullptr; coll->insertDocument(&_opCtx, - BSON("_id" << 1 << "a" - << "dup"), + InsertStatement(BSON("_id" << 1 << "a" + << "dup")), nullOpDebug, true) .transitional_ignore(); coll->insertDocument(&_opCtx, - BSON("_id" << 2 << "a" - << "dup"), + InsertStatement(BSON("_id" << 2 << "a" + << "dup")), nullOpDebug, true) .transitional_ignore(); @@ -169,14 +169,14 @@ public: OpDebug* const nullOpDebug = nullptr; coll->insertDocument(&_opCtx, - BSON("_id" << 1 << "a" - << "dup"), + InsertStatement(BSON("_id" << 1 << "a" + << "dup")), nullOpDebug, true) .transitional_ignore(); coll->insertDocument(&_opCtx, - BSON("_id" << 2 << "a" - << "dup"), + InsertStatement(BSON("_id" << 2 << "a" + << "dup")), nullOpDebug, true) .transitional_ignore(); @@ -224,13 +224,13 @@ public: OpDebug* const nullOpDebug = nullptr; ASSERT_OK(coll->insertDocument(&_opCtx, - BSON("_id" << 1 << "a" - << "dup"), + InsertStatement(BSON("_id" << 1 << "a" + << "dup")), nullOpDebug, true)); ASSERT_OK(coll->insertDocument(&_opCtx, - BSON("_id" << 2 << "a" - << "dup"), + InsertStatement(BSON("_id" << 2 << "a" + << "dup")), nullOpDebug, true)); wunit.commit(); @@ -287,7 +287,7 @@ public: int32_t nDocs = 1000; OpDebug* const nullOpDebug = nullptr; for (int32_t i = 0; i < nDocs; ++i) { - coll->insertDocument(&_opCtx, BSON("a" << i), nullOpDebug, true) + coll->insertDocument(&_opCtx, InsertStatement(BSON("a" << i)), nullOpDebug, true) .transitional_ignore(); } wunit.commit(); @@ -323,7 +323,7 @@ public: int32_t nDocs = 1000; OpDebug* const nullOpDebug = nullptr; for (int32_t i = 0; i < nDocs; ++i) { - coll->insertDocument(&_opCtx, BSON("a" << i), nullOpDebug, true) + coll->insertDocument(&_opCtx, InsertStatement(BSON("a" << i)), nullOpDebug, true) .transitional_ignore(); } wunit.commit(); @@ -362,7 +362,7 @@ public: int32_t nDocs = 1000; OpDebug* const nullOpDebug = nullptr; for (int32_t i = 0; i < nDocs; ++i) { - coll->insertDocument(&_opCtx, BSON("_id" << i), nullOpDebug, true) + coll->insertDocument(&_opCtx, InsertStatement(BSON("_id" << i)), nullOpDebug, true) .transitional_ignore(); } wunit.commit(); @@ -401,7 +401,7 @@ public: int32_t nDocs = 1000; OpDebug* const nullOpDebug = nullptr; for (int32_t i = 0; i < nDocs; ++i) { - coll->insertDocument(&_opCtx, BSON("_id" << i), nullOpDebug, true) + coll->insertDocument(&_opCtx, InsertStatement(BSON("_id" << i)), nullOpDebug, true) .transitional_ignore(); } wunit.commit(); diff --git a/src/mongo/dbtests/multikey_paths_test.cpp b/src/mongo/dbtests/multikey_paths_test.cpp index 9acec0370e0..6eede918112 100644 --- a/src/mongo/dbtests/multikey_paths_test.cpp +++ b/src/mongo/dbtests/multikey_paths_test.cpp @@ -147,7 +147,7 @@ TEST_F(MultikeyPathsTest, PathsUpdatedOnIndexCreation) { const bool enforceQuota = true; ASSERT_OK(collection->insertDocument( _opCtx.get(), - BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3)), + InsertStatement(BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3))), nullOpDebug, enforceQuota)); wuow.commit(); @@ -179,12 +179,12 @@ TEST_F(MultikeyPathsTest, PathsUpdatedOnIndexCreationWithMultipleDocuments) { const bool enforceQuota = true; ASSERT_OK(collection->insertDocument( _opCtx.get(), - BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3)), + InsertStatement(BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3))), nullOpDebug, enforceQuota)); ASSERT_OK(collection->insertDocument( _opCtx.get(), - BSON("_id" << 1 << "a" << BSON_ARRAY(1 << 2 << 3) << "b" << 5), + InsertStatement(BSON("_id" << 1 << "a" << BSON_ARRAY(1 << 2 << 3) << "b" << 5)), nullOpDebug, enforceQuota)); wuow.commit(); @@ -228,7 +228,7 @@ TEST_F(MultikeyPathsTest, PathsUpdatedOnDocumentInsert) { const bool enforceQuota = true; ASSERT_OK(collection->insertDocument( _opCtx.get(), - BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3)), + InsertStatement(BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3))), nullOpDebug, enforceQuota)); wuow.commit(); @@ -242,7 +242,7 @@ TEST_F(MultikeyPathsTest, PathsUpdatedOnDocumentInsert) { const bool enforceQuota = true; ASSERT_OK(collection->insertDocument( _opCtx.get(), - BSON("_id" << 1 << "a" << BSON_ARRAY(1 << 2 << 3) << "b" << 5), + InsertStatement(BSON("_id" << 1 << "a" << BSON_ARRAY(1 << 2 << 3) << "b" << 5)), nullOpDebug, enforceQuota)); wuow.commit(); @@ -272,8 +272,10 @@ TEST_F(MultikeyPathsTest, PathsUpdatedOnDocumentUpdate) { WriteUnitOfWork wuow(_opCtx.get()); OpDebug* const nullOpDebug = nullptr; const bool enforceQuota = true; - ASSERT_OK(collection->insertDocument( - _opCtx.get(), BSON("_id" << 0 << "a" << 5), nullOpDebug, enforceQuota)); + ASSERT_OK(collection->insertDocument(_opCtx.get(), + InsertStatement(BSON("_id" << 0 << "a" << 5)), + nullOpDebug, + enforceQuota)); wuow.commit(); } @@ -331,7 +333,7 @@ TEST_F(MultikeyPathsTest, PathsNotUpdatedOnDocumentDelete) { const bool enforceQuota = true; ASSERT_OK(collection->insertDocument( _opCtx.get(), - BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3)), + InsertStatement(BSON("_id" << 0 << "a" << 5 << "b" << BSON_ARRAY(1 << 2 << 3))), nullOpDebug, enforceQuota)); wuow.commit(); @@ -389,7 +391,8 @@ TEST_F(MultikeyPathsTest, PathsUpdatedForMultipleIndexesOnDocumentInsert) { const bool enforceQuota = true; ASSERT_OK(collection->insertDocument( _opCtx.get(), - BSON("_id" << 0 << "a" << BSON_ARRAY(1 << 2 << 3) << "b" << 5 << "c" << 8), + InsertStatement( + BSON("_id" << 0 << "a" << BSON_ARRAY(1 << 2 << 3) << "b" << 5 << "c" << 8)), nullOpDebug, enforceQuota)); wuow.commit(); diff --git a/src/mongo/dbtests/pdfiletests.cpp b/src/mongo/dbtests/pdfiletests.cpp index 98641b42627..cd62222ffc1 100644 --- a/src/mongo/dbtests/pdfiletests.cpp +++ b/src/mongo/dbtests/pdfiletests.cpp @@ -77,13 +77,13 @@ public: Collection* collection = _context.db()->getOrCreateCollection(&_opCtx, NamespaceString(ns())); OpDebug* const nullOpDebug = nullptr; - ASSERT(!collection->insertDocument(&_opCtx, x, nullOpDebug, true).isOK()); + ASSERT(!collection->insertDocument(&_opCtx, InsertStatement(x), nullOpDebug, true).isOK()); StatusWith<BSONObj> fixed = fixDocumentForInsert(_opCtx.getServiceContext(), x); ASSERT(fixed.isOK()); x = fixed.getValue(); ASSERT(x["_id"].type() == jstOID); - ASSERT(collection->insertDocument(&_opCtx, x, nullOpDebug, true).isOK()); + ASSERT(collection->insertDocument(&_opCtx, InsertStatement(x), nullOpDebug, true).isOK()); wunit.commit(); } }; diff --git a/src/mongo/dbtests/query_stage_cached_plan.cpp b/src/mongo/dbtests/query_stage_cached_plan.cpp index 7aedbd9dd00..196e21e2a7c 100644 --- a/src/mongo/dbtests/query_stage_cached_plan.cpp +++ b/src/mongo/dbtests/query_stage_cached_plan.cpp @@ -94,7 +94,8 @@ public: const bool enforceQuota = false; OpDebug* const nullOpDebug = nullptr; - ASSERT_OK(collection->insertDocument(&_opCtx, obj, nullOpDebug, enforceQuota)); + ASSERT_OK( + collection->insertDocument(&_opCtx, InsertStatement(obj), nullOpDebug, enforceQuota)); wuow.commit(); } diff --git a/src/mongo/dbtests/query_stage_count.cpp b/src/mongo/dbtests/query_stage_count.cpp index 3ff097f8cc8..705fe19f3fc 100644 --- a/src/mongo/dbtests/query_stage_count.cpp +++ b/src/mongo/dbtests/query_stage_count.cpp @@ -108,7 +108,8 @@ public: void insert(const BSONObj& doc) { WriteUnitOfWork wunit(&_opCtx); OpDebug* const nullOpDebug = nullptr; - _coll->insertDocument(&_opCtx, doc, nullOpDebug, false).transitional_ignore(); + _coll->insertDocument(&_opCtx, InsertStatement(doc), nullOpDebug, false) + .transitional_ignore(); wunit.commit(); } diff --git a/src/mongo/dbtests/query_stage_ixscan.cpp b/src/mongo/dbtests/query_stage_ixscan.cpp index 79c5b112bf3..2c81fbb357a 100644 --- a/src/mongo/dbtests/query_stage_ixscan.cpp +++ b/src/mongo/dbtests/query_stage_ixscan.cpp @@ -69,7 +69,7 @@ public: void insert(const BSONObj& doc) { WriteUnitOfWork wunit(&_opCtx); OpDebug* const nullOpDebug = nullptr; - ASSERT_OK(_coll->insertDocument(&_opCtx, doc, nullOpDebug, false)); + ASSERT_OK(_coll->insertDocument(&_opCtx, InsertStatement(doc), nullOpDebug, false)); wunit.commit(); } diff --git a/src/mongo/dbtests/querytests.cpp b/src/mongo/dbtests/querytests.cpp index 30270318110..772cd354c0b 100644 --- a/src/mongo/dbtests/querytests.cpp +++ b/src/mongo/dbtests/querytests.cpp @@ -109,9 +109,11 @@ protected: oid.init(); b.appendOID("_id", &oid); b.appendElements(o); - _collection->insertDocument(&_opCtx, b.obj(), nullOpDebug, false).transitional_ignore(); + _collection->insertDocument(&_opCtx, InsertStatement(b.obj()), nullOpDebug, false) + .transitional_ignore(); } else { - _collection->insertDocument(&_opCtx, o, nullOpDebug, false).transitional_ignore(); + _collection->insertDocument(&_opCtx, InsertStatement(o), nullOpDebug, false) + .transitional_ignore(); } wunit.commit(); } diff --git a/src/mongo/dbtests/repltests.cpp b/src/mongo/dbtests/repltests.cpp index d7008d2fbbf..533898e95a2 100644 --- a/src/mongo/dbtests/repltests.cpp +++ b/src/mongo/dbtests/repltests.cpp @@ -235,7 +235,8 @@ protected: OpDebug* const nullOpDebug = nullptr; if (o.hasField("_id")) { repl::UnreplicatedWritesBlock uwb(&_opCtx); - coll->insertDocument(&_opCtx, o, nullOpDebug, true).transitional_ignore(); + coll->insertDocument(&_opCtx, InsertStatement(o), nullOpDebug, true) + .transitional_ignore(); wunit.commit(); return; } @@ -246,7 +247,8 @@ protected: b.appendOID("_id", &id); b.appendElements(o); repl::UnreplicatedWritesBlock uwb(&_opCtx); - coll->insertDocument(&_opCtx, b.obj(), nullOpDebug, true).transitional_ignore(); + coll->insertDocument(&_opCtx, InsertStatement(b.obj()), nullOpDebug, true) + .transitional_ignore(); wunit.commit(); } static BSONObj wid(const char* json) { diff --git a/src/mongo/dbtests/rollbacktests.cpp b/src/mongo/dbtests/rollbacktests.cpp index 3cab6c741ab..93892934753 100644 --- a/src/mongo/dbtests/rollbacktests.cpp +++ b/src/mongo/dbtests/rollbacktests.cpp @@ -92,7 +92,7 @@ Status truncateCollection(OperationContext* opCtx, const NamespaceString& nss) { void insertRecord(OperationContext* opCtx, const NamespaceString& nss, const BSONObj& data) { Collection* coll = dbHolder().get(opCtx, nss.db())->getCollection(opCtx, nss); OpDebug* const nullOpDebug = nullptr; - ASSERT_OK(coll->insertDocument(opCtx, data, nullOpDebug, false)); + ASSERT_OK(coll->insertDocument(opCtx, InsertStatement(data), nullOpDebug, false)); } void assertOnlyRecord(OperationContext* opCtx, const NamespaceString& nss, const BSONObj& data) { Collection* coll = dbHolder().get(opCtx, nss.db())->getCollection(opCtx, nss); diff --git a/src/mongo/dbtests/validate_tests.cpp b/src/mongo/dbtests/validate_tests.cpp index 546b3d7a007..0337435a98e 100644 --- a/src/mongo/dbtests/validate_tests.cpp +++ b/src/mongo/dbtests/validate_tests.cpp @@ -115,9 +115,11 @@ public: ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK(coll->insertDocument(&_opCtx, BSON("_id" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK(coll->insertDocument(&_opCtx, BSON("_id" << 2), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2)), nullOpDebug, true)); wunit.commit(); } @@ -164,11 +166,11 @@ public: WriteUnitOfWork wunit(&_opCtx); ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 1 << "a" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1 << "a" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 2 << "a" << 2), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2 << "a" << 2)), nullOpDebug, true)); wunit.commit(); } @@ -228,13 +230,13 @@ public: WriteUnitOfWork wunit(&_opCtx); ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 1 << "a" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1 << "a" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 2 << "a" << 2), nullOpDebug, true)); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 3 << "b" << 3), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2 << "a" << 2)), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 3 << "b" << 3)), nullOpDebug, true)); wunit.commit(); } @@ -287,9 +289,11 @@ public: ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK(coll->insertDocument(&_opCtx, BSON("_id" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK(coll->insertDocument(&_opCtx, BSON("_id" << 2), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2)), nullOpDebug, true)); wunit.commit(); } @@ -364,10 +368,10 @@ public: coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK(coll->insertDocument(&_opCtx, doc1, nullOpDebug, true)); + ASSERT_OK(coll->insertDocument(&_opCtx, InsertStatement(doc1), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK(coll->insertDocument(&_opCtx, doc2, nullOpDebug, true)); - ASSERT_OK(coll->insertDocument(&_opCtx, doc3, nullOpDebug, true)); + ASSERT_OK(coll->insertDocument(&_opCtx, InsertStatement(doc2), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument(&_opCtx, InsertStatement(doc3), nullOpDebug, true)); wunit.commit(); } @@ -432,13 +436,13 @@ public: ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 1 << "a" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1 << "a" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 2 << "a" << 2), nullOpDebug, true)); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 3 << "b" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2 << "a" << 2)), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 3 << "b" << 1)), nullOpDebug, true)); wunit.commit(); } @@ -492,15 +496,18 @@ public: ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 1 << "a" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1 << "a" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 2 << "a" << 2), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2 << "a" << 2)), nullOpDebug, true)); // Explicitly test that multi-key partial indexes containing documents that // don't match the filter expression are handled correctly. ASSERT_OK(coll->insertDocument( - &_opCtx, BSON("_id" << 3 << "a" << BSON_ARRAY(-1 << -2 << -3)), nullOpDebug, true)); + &_opCtx, + InsertStatement(BSON("_id" << 3 << "a" << BSON_ARRAY(-1 << -2 << -3))), + nullOpDebug, + true)); wunit.commit(); } @@ -554,8 +561,11 @@ public: WriteUnitOfWork wunit(&_opCtx); ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK(coll->insertDocument( - &_opCtx, BSON("_id" << 1 << "x" << 1 << "a" << 2), nullOpDebug, true)); + ASSERT_OK( + coll->insertDocument(&_opCtx, + InsertStatement(BSON("_id" << 1 << "x" << 1 << "a" << 2)), + nullOpDebug, + true)); wunit.commit(); } @@ -614,17 +624,23 @@ public: ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK(coll->insertDocument( - &_opCtx, BSON("_id" << 1 << "a" << 1 << "b" << 4), nullOpDebug, true)); - id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK(coll->insertDocument( - &_opCtx, BSON("_id" << 2 << "a" << 2 << "b" << 5), nullOpDebug, true)); ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 3 << "a" << 3), nullOpDebug, true)); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 4 << "b" << 6), nullOpDebug, true)); + coll->insertDocument(&_opCtx, + InsertStatement(BSON("_id" << 1 << "a" << 1 << "b" << 4)), + nullOpDebug, + true)); + id1 = coll->getCursor(&_opCtx)->next()->id; ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 5 << "c" << 7), nullOpDebug, true)); + coll->insertDocument(&_opCtx, + InsertStatement(BSON("_id" << 2 << "a" << 2 << "b" << 5)), + nullOpDebug, + true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 3 << "a" << 3)), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 4 << "b" << 6)), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 5 << "c" << 7)), nullOpDebug, true)); wunit.commit(); } @@ -691,13 +707,13 @@ public: ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 1 << "a" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1 << "a" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 2 << "a" << 2), nullOpDebug, true)); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 3 << "b" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2 << "a" << 2)), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 3 << "b" << 1)), nullOpDebug, true)); wunit.commit(); } @@ -756,13 +772,13 @@ public: ASSERT_OK(db->dropCollection(&_opCtx, _ns)); coll = db->createCollection(&_opCtx, _ns); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 1 << "a" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 1 << "a" << 1)), nullOpDebug, true)); id1 = coll->getCursor(&_opCtx)->next()->id; - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 2 << "a" << 2), nullOpDebug, true)); - ASSERT_OK( - coll->insertDocument(&_opCtx, BSON("_id" << 3 << "b" << 1), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 2 << "a" << 2)), nullOpDebug, true)); + ASSERT_OK(coll->insertDocument( + &_opCtx, InsertStatement(BSON("_id" << 3 << "b" << 1)), nullOpDebug, true)); wunit.commit(); } |