문서 메뉴
문서 홈
/
MongoDB 매뉴얼
/ / / /

Session.commitTransaction()

이 페이지의 내용

  • 정의
  • 행동
  • 예제
Session.commitTransaction()

다중 문서 트랜잭션 에서 작업으로 인한 변경 사항을 저장하고 트랜잭션을 종료합니다.

다중 문서 트랜잭션은 샤딩된 cluster와 복제본 세트 모두에 사용할 수 있습니다.

Session.commitTransaction() 값을 반환하지 않습니다.

중요

Mongo쉬 방법

이 페이지에서는 mongosh 메서드를 설명합니다. 이는 데이터베이스 명령 또는 Node.js와 같은 언어별 드라이버에 대한 설명서가 아닙니다.

데이터베이스 명령에 대해서는 commitTransaction 명령을 참조하십시오.

MongoDB API 드라이버의 경우 언어별 MongoDB 드라이버 설명서를 참조하세요.

레거시 mongo 셸 문서는 해당 MongoDB 서버 릴리스 문서를 참조하세요.

Mongo 셸 V4.4

트랜잭션을 커밋할 때 세션은 트랜잭션 시작 시 지정된 쓰기 고려를 사용합니다. Session.startTransaction()을 참조하세요.

"w: 1" 쓰기 고려를 사용하여 커밋하는 경우 트랜잭션이 페일오버 프로세스 중에 롤백될 수 있습니다.

트랜잭션이 커밋되면 트랜잭션에서 이루어진 모든 데이터 변경 사항이 저장되고 트랜잭션 외부에서 볼 수 있습니다. 즉, 트랜잭션은 다른 트랜잭션을 롤백하는 동안 다른 변경 사항을 커밋하지 않습니다.

트랜잭션이 커밋될 때까지 트랜잭션에서 변경된 데이터는 트랜잭션 외부에 표시되지 않습니다.

그러나 트랜잭션이 여러 샤드에 쓰기를 수행하는 경우, 모든 외부 읽기 작업이 커밋된 트랜잭션의 결과가 샤드 전체에 표시될 때까지 기다릴 필요는 없습니다. 예를 들어, 트랜잭션이 커밋되고 쓰기 1이 샤드 A에 표시되지만 쓰기 2가 샤드 B에 아직 표시되지 않는 경우, 읽기 고려 "local"의 외부 읽기는 쓰기 2를 보지 않고 쓰기 1의 결과를 읽을 수 있습니다.

커밋 작업에 오류가 발생하면 MongoDB 드라이버는 retryWritesfalse로 설정되었는지 여부에 관계없이 커밋 작업을 한 번 다시 시도합니다. 자세한 내용은 트랜잭션 오류 처리를 참조하세요.

hr 데이터베이스의 직원 기록이 변경될 때 reporting 데이터베이스의 events collection이 hr 변경 사항과 동기화되도록 하려는 시나리오를 생각해 보겠습니다. 즉, 이러한 쓰기가 단일 트랜잭션으로 수행되어 두 작업이 모두 성공하거나 실패하도록 해야 합니다.

hr 데이터베이스의 employees 컬렉션에는 다음 문서가 포함되어 있습니다.

{ "_id" : ObjectId("5af0776263426f87dd69319a"), "employee" : 3, "name" : { "title" : "Mr.", "name" : "Iba Ochs" }, "status" : "Active", "department" : "ABC" }
{ "_id" : ObjectId("5af0776263426f87dd693198"), "employee" : 1, "name" : { "title" : "Miss", "name" : "Ann Thrope" }, "status" : "Active", "department" : "ABC" }
{ "_id" : ObjectId("5af0776263426f87dd693199"), "employee" : 2, "name" : { "title" : "Mrs.", "name" : "Eppie Delta" }, "status" : "Active", "department" : "XYZ" }

reporting 데이터베이스의 events 컬렉션에는 다음 문서가 포함되어 있습니다.

{ "_id" : ObjectId("5af07daa051d92f02462644a"), "employee" : 1, "status" : { "new" : "Active", "old" : null }, "department" : { "new" : "ABC", "old" : null } }
{ "_id" : ObjectId("5af07daa051d92f02462644b"), "employee" : 2, "status" : { "new" : "Active", "old" : null }, "department" : { "new" : "XYZ", "old" : null } }
{ "_id" : ObjectId("5af07daa051d92f02462644c"), "employee" : 3, "status" : { "new" : "Active", "old" : null }, "department" : { "new" : "ABC", "old" : null } }

다음 예에서는 트랜잭션을 열고 employees 상태에서 직원의 상태를 Inactive로 업데이트하고 events 컬렉션에 해당 문서를 삽입하고 두 작업을 단일 트랜잭션으로 커밋합니다.

// Runs the txnFunc and retries if TransientTransactionError encountered
function runTransactionWithRetry(txnFunc, session) {
while (true) {
try {
txnFunc(session); // performs transaction
break;
} catch (error) {
// If transient error, retry the whole transaction
if (error?.errorLabels?.includes("TransientTransactionError") ) {
print("TransientTransactionError, retrying transaction ...");
continue;
} else {
throw error;
}
}
}
}
// Retries commit if UnknownTransactionCommitResult encountered
function commitWithRetry(session) {
while (true) {
try {
session.commitTransaction(); // Uses write concern set at transaction start.
print("Transaction committed.");
break;
} catch (error) {
// Can retry commit
if (error?.errorLabels?.includes("UnknownTransactionCommitResult") ) {
print("UnknownTransactionCommitResult, retrying commit operation ...");
continue;
} else {
print("Error during commit ...");
throw error;
}
}
}
}
// Updates two collections in a transactions
function updateEmployeeInfo(session) {
employeesCollection = session.getDatabase("hr").employees;
eventsCollection = session.getDatabase("reporting").events;
session.startTransaction( { readConcern: { level: "snapshot" }, writeConcern: { w: "majority" } } );
try{
employeesCollection.updateOne( { employee: 3 }, { $set: { status: "Inactive" } } );
eventsCollection.insertOne( { employee: 3, status: { new: "Inactive", old: "Active" } } );
} catch (error) {
print("Caught exception during transaction, aborting.");
session.abortTransaction();
throw error;
}
commitWithRetry(session);
}
// Start a session.
session = db.getMongo().startSession( { readPreference: { mode: "primary" } } );
try{
runTransactionWithRetry(updateEmployeeInfo, session);
} catch (error) {
// Do something with error
} finally {
session.endSession();
}

다음도 참조하세요.

← Session.abortTransaction()

이 페이지의 내용