@@ -322,7 +322,10 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
322322 // For upsert operations, we dont prefetch records here to avoid
323323 // unnecessary locks
324324 if (!_opCtx->isUpsert ()) {
325- _ensureRecordsFetched ();
325+ auto err = _ensureRecordsFetched ();
326+ if (err != txservice::TxErrorCode::NO_ERROR) {
327+ uassertStatusOK (TxErrorCodeToMongoStatus (err));
328+ }
326329 }
327330 }
328331 }
@@ -346,7 +349,7 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
346349 _updateRecordPtr ();
347350 }
348351
349- void _ensureRecordsFetched () {
352+ txservice::TxErrorCode _ensureRecordsFetched () {
350353 assert (_cursor);
351354
352355 const auto & batchVector = _cursor->getCurrentBatchVector ();
@@ -369,19 +372,22 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
369372 if (currentIndexScanBatchIdx >= _prefetchedBatchStartIdx &&
370373 currentIndexScanBatchIdx < prefetchedEndIdx) {
371374 // Records already fetched for current position
372- return ;
375+ return txservice::TxErrorCode::NO_ERROR ;
373376 }
374377
378+ // Get batch size from configuration
379+ size_t batchSize = _getBatchFetchSize ();
375380 // Need to fetch records starting from current scan index
376- _fetchRecordsForRange (currentIndexScanBatchIdx, batchVector);
381+ return _fetchRecordsForRange (currentIndexScanBatchIdx, batchSize , batchVector);
377382 }
378383
379- void _fetchRecordsForRange (size_t startIdx,
380- const std::vector<txservice::ScanBatchTuple>& batchVector) {
384+ txservice::TxErrorCode _fetchRecordsForRange (
385+ size_t startIdx,
386+ size_t batchSize,
387+ const std::vector<txservice::ScanBatchTuple>& batchVector) {
381388 assert (startIdx < batchVector.size ());
382389
383- // Get batch size from configuration (smaller than full scan batch)
384- size_t batchSize = _getBatchFetchSize ();
390+ // endIdx smaller than full scan batch)
385391 size_t endIdx = std::min (startIdx + batchSize, batchVector.size ());
386392
387393 // Extract RecordIds from _scanBatchVector (via getCurrentBatchVector) BEFORE batchGetKV
@@ -450,7 +456,7 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
450456 if (recordIds.empty ()) {
451457 MONGO_LOG (1 ) << " All records in range [" << startIdx << " -" << endIdx
452458 << " ) are deleted, skipping batch fetch" ;
453- return ;
459+ return txservice::TxErrorCode::NO_ERROR ;
454460 }
455461
456462 // Create records directly in _prefetchedRecords at the correct positions
@@ -489,8 +495,7 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
489495 // Clear prefetched records on error and return error
490496 _prefetchedRecords.clear ();
491497 _prefetchedBatchStartIdx = 0 ;
492- uassertStatusOK (TxErrorCodeToMongoStatus (err));
493- return ;
498+ return err;
494499 }
495500
496501#ifndef NDEBUG
@@ -510,6 +515,7 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
510515 MONGO_LOG (1 ) << " Fetched " << fetchTuples.size () << " records in range [" << startIdx << " -"
511516 << endIdx << " ) (with " << (neededSize - fetchTuples.size ())
512517 << " deleted entries)" ;
518+ return txservice::TxErrorCode::NO_ERROR;
513519 }
514520
515521 void _updateRecordPtr () {
@@ -539,15 +545,17 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
539545 } else {
540546 _recordPtr =
541547 nullptr ; // Record not fetched (error case or out of range)
542- MONGO_LOG (1 ) << " RecordId not found in prefetched records at offset "
548+ MONGO_LOG (0 ) << " RecordId not found in prefetched records at offset "
543549 << offset << " (scan index " << currentIndexScanBatchIdx
544550 << " ) for index " << _indexName->StringView ();
551+ MONGO_UNREACHABLE;
545552 }
546553 } else {
547554 _recordPtr = nullptr ; // Current index before prefetched range
548- MONGO_LOG (1 ) << " Current scan index " << currentIndexScanBatchIdx
555+ MONGO_LOG (0 ) << " Current scan index " << currentIndexScanBatchIdx
549556 << " is before prefetched range starting at "
550557 << _prefetchedBatchStartIdx;
558+ MONGO_UNREACHABLE;
551559 }
552560 } else {
553561 // For upsert operations, we dont prefetch records
@@ -640,6 +648,18 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
640648 }
641649 }
642650
651+ void _clearPrefetchedRecords () {
652+ _prefetchedRecords.clear ();
653+ _prefetchedBatchStartIdx = 0 ;
654+ _lastRecordsBatchCnt = 0 ;
655+ }
656+
657+ size_t _getBatchFetchSize () const {
658+ int batchSize = internalEloqIndexBatchFetchSize.load ();
659+ // Ensure reasonable bounds: 1 to 1000
660+ return std::max (1 , std::min (batchSize, 1000 ));
661+ }
662+
643663private:
644664 OperationContext* _opCtx; // not owned
645665 EloqRecoveryUnit* _ru; // not owned
@@ -677,18 +697,6 @@ class EloqIndexCursor final : public SortedDataInterface::Cursor {
677697 size_t _prefetchedBatchStartIdx{
678698 0 }; // Starting index in scan batch for current prefetched records
679699 size_t _lastRecordsBatchCnt{0 }; // Track batch count to detect new batches
680-
681- void _clearPrefetchedRecords () {
682- _prefetchedRecords.clear ();
683- _prefetchedBatchStartIdx = 0 ;
684- _lastRecordsBatchCnt = 0 ;
685- }
686-
687- size_t _getBatchFetchSize () const {
688- int batchSize = internalEloqIndexBatchFetchSize.load ();
689- // Ensure reasonable bounds: 1 to 1000
690- return std::max (1 , std::min (batchSize, 1000 ));
691- }
692700};
693701
694702class EloqIndex ::BulkBuilder : public SortedDataBuilderInterface {
0 commit comments