/**
|
* Tests that failing while preparing a transaction leaves the server transaction metrics in an illegal state.
|
*
|
*/
|
(function() {
|
"use strict";
|
load("jstests/core/txns/libs/prepare_helpers.js");
|
|
const dbName = "test";
|
const collName = "fail_prepare_transaction";
|
const testDB = db.getSiblingDB(dbName);
|
const testColl = testDB.getCollection(collName);
|
|
testColl.drop({writeConcern: {w: "majority"}});
|
assert.commandWorked(testDB.runCommand({create: collName, writeConcern: {w: "majority"}}));
|
|
const session = testDB.getMongo().startSession({causalConsistency: false});
|
const sessionDB = session.getDatabase(dbName);
|
const sessionColl = sessionDB.getCollection(collName);
|
|
const doc1 = {_id: 1, x: 1};
|
|
session.startTransaction({readConcern: {level: 'snapshot'}});
|
assert.commandWorked(sessionColl.insert(doc1));
|
// Assuming prepareTransaction was to fail and enter the abortGuard.
|
assert.commandFailed(session.getDatabase('admin').adminCommand({prepareTransaction: 1}));
|
let newStatus = assert.commandWorked(testDB.adminCommand({serverStatus: 1}));
|
|
// This breaks the invariant that metrics cannot be negative.
|
assert.eq(newStatus.transactions["currentPrepared"], -1);
|
assert.eq(newStatus.transactions["totalPreparedThenAborted"], 1);
|
assert.eq(newStatus.transactions["totalPreparedThenCommitted"], 0);
|
assert.eq(newStatus.transactions["totalPrepared"], 0);
|
session.endSession();
|
}());
|