MCPcopy Create free account
hub / github.com/MaterializeInc/materialize / group_commit

Method group_commit

src/adapter/src/coord/appends.rs:342–633  ·  view source on GitHub ↗
(&mut self, permit: Option<GroupCommitPermit>)

Source from the content-addressed store, hash-verified

340 /// Returns the timestamp of the write.
341 #[instrument(name = "coord::group_commit")]
342 pub(crate) async fn group_commit(&mut self, permit: Option<GroupCommitPermit>) -> Timestamp {
343 let mut validated_writes = Vec::new();
344 let mut deferred_writes = Vec::new();
345 let mut group_write_locks = GroupCommitWriteLocks::default();
346
347 // TODO(parkmycar): Refactor away this allocation. Currently `drain(..)` requires holding
348 // a mutable borrow on the Coordinator and so does trying to grant a write lock.
349 let pending_writes: Vec<_> = self.pending_writes.drain(..).collect();
350
351 // Validate, merge, and possibly acquire write locks for as many pending writes as possible.
352 for pending_write in pending_writes {
353 match pending_write {
354 // We always allow system writes to proceed.
355 PendingWriteTxn::System { .. } => validated_writes.push(pending_write),
356 // We have a set of locks! Validate they're correct (expected).
357 PendingWriteTxn::User {
358 span,
359 write_locks: Some(write_locks),
360 writes,
361 responder: UserWriteResponder::Session(pending_txn),
362 } => match write_locks.validate(writes.keys().copied()) {
363 Ok(validated_locks) => {
364 // Merge all of our write locks together since we can allow concurrent
365 // writes at the same timestamp.
366 group_write_locks.merge(validated_locks);
367
368 let validated_write = PendingWriteTxn::User {
369 span,
370 writes,
371 write_locks: None,
372 responder: UserWriteResponder::Session(pending_txn),
373 };
374 validated_writes.push(validated_write);
375 }
376 // This is very unexpected since callers of this method should be validating.
377 //
378 // We cannot allow these write to occur since if the correct set of locks was
379 // not taken we could violate serializability.
380 Err(missing) => {
381 let writes: Vec<_> = writes.keys().collect();
382 panic!(
383 "got to group commit with partial set of locks!\nmissing: {:?}, writes: {:?}, txn: {:?}",
384 missing, writes, pending_txn,
385 );
386 }
387 },
388 // If we don't have any locks, try to acquire them, otherwise defer the write.
389 PendingWriteTxn::User {
390 span,
391 writes,
392 write_locks: None,
393 responder: UserWriteResponder::Session(pending_txn),
394 } => {
395 let missing = group_write_locks.missing_locks(writes.keys().copied());
396
397 if missing.is_empty() {
398 // We have all the locks! Queue the pending write.
399 let validated_write = PendingWriteTxn::User {

Callers 2

try_group_commitMethod · 0.80
executeMethod · 0.80

Calls 15

SessionClass · 0.85
nowFunction · 0.85
spawnFunction · 0.85
missing_locksMethod · 0.80
insert_lockMethod · 0.80
all_or_nothingMethod · 0.80
defer_opMethod · 0.80
get_local_write_tsMethod · 0.80
unwrap_or_terminateMethod · 0.80
is_someMethod · 0.80

Tested by

no test coverage detected