Skip to content

Commit aa6c268

Browse files
committed
post merge fixy-wixy
1 parent 9cd2f7e commit aa6c268

File tree

2 files changed

+8
-174
lines changed

2 files changed

+8
-174
lines changed

nexus/db-queries/src/db/datastore/instance.rs

Lines changed: 0 additions & 103 deletions
Original file line numberDiff line numberDiff line change
@@ -412,109 +412,6 @@ impl DataStore {
412412
Ok(updated)
413413
}
414414

415-
/// Attempts to acquire the instance-updater lock for the saga with ID
416-
/// `saga_id` at the current generation.
417-
///
418-
/// # Arguments
419-
///
420-
/// - `instance_id`: the UUID of the Instance to lock
421-
/// - `current_gen`: the current generation of the instance's `updater_id`
422-
/// - `saga_id`: the UUID of the saga that's attempting to lock this
423-
/// instance.
424-
///
425-
/// # Returns
426-
///
427-
/// - [`Ok`]`(`[`Some`]`(`[`InstanceUpdaterLock`]`))` if the lock was acquired.
428-
/// - [`Ok`]`(`[`None`]`)` if the lock could not be acquired (i.e. the
429-
/// generation has advanced since `current_gen` was captured)
430-
/// - [`Err`] if a database error occurred.
431-
pub async fn instance_updater_try_lock(
432-
&self,
433-
opctx: &OpContext,
434-
authz_instance: &authz::Instance,
435-
current_gen: Generation,
436-
saga_lock_id: &Uuid,
437-
) -> Result<Option<Generation>, Error> {
438-
use db::schema::instance::dsl;
439-
440-
// The generation to advance to.
441-
let new_gen = Generation(current_gen.0.next());
442-
443-
let instance_id = authz_instance.id();
444-
445-
let locked = diesel::update(dsl::instance)
446-
.filter(dsl::time_deleted.is_null())
447-
.filter(dsl::id.eq(instance_id))
448-
// If the generation is the same as the captured generation, we can
449-
// lock this instance.
450-
.filter(dsl::updater_gen.eq(current_gen))
451-
.set((
452-
dsl::updater_gen.eq(new_gen),
453-
dsl::updater_id.eq(Some(*saga_lock_id)),
454-
))
455-
.check_if_exists::<Instance>(instance_id)
456-
.execute_and_check(&*self.pool_connection_authorized(opctx).await?)
457-
.await
458-
.map(|r| match r.status {
459-
UpdateStatus::Updated => Some(new_gen),
460-
UpdateStatus::NotUpdatedButExists => None,
461-
})
462-
.map_err(|e| {
463-
public_error_from_diesel(
464-
e,
465-
ErrorHandler::NotFoundByLookup(
466-
ResourceType::Instance,
467-
LookupType::ById(instance_id),
468-
),
469-
)
470-
})?;
471-
472-
Ok(locked)
473-
}
474-
475-
/// Release the instance-updater lock.
476-
pub async fn instance_updater_unlock(
477-
&self,
478-
opctx: &OpContext,
479-
authz_instance: &authz::Instance,
480-
saga_lock_id: &Uuid,
481-
) -> Result<bool, Error> {
482-
use db::schema::instance::dsl;
483-
484-
let instance_id = authz_instance.id();
485-
486-
let unlocked = diesel::update(dsl::instance)
487-
.filter(dsl::time_deleted.is_null())
488-
.filter(dsl::id.eq(authz_instance.id()))
489-
// Only unlock the instance if:
490-
// - the provided updater ID matches that of the saga that has
491-
// currently locked this instance.
492-
.filter(dsl::updater_id.eq(Some(*saga_lock_id)))
493-
.set((
494-
dsl::updater_gen.eq(dsl::updater_gen + 1),
495-
dsl::updater_id.eq(None::<Uuid>),
496-
))
497-
.check_if_exists::<Instance>(instance_id)
498-
.execute_and_check(&*self.pool_connection_authorized(opctx).await?)
499-
.await
500-
.map(|r| match r.status {
501-
UpdateStatus::Updated => true,
502-
// TODO(eliza): should this be an error?
503-
UpdateStatus::NotUpdatedButExists => false,
504-
})
505-
.map_err(|e| {
506-
public_error_from_diesel(
507-
e,
508-
ErrorHandler::NotFoundByLookup(
509-
ResourceType::Instance,
510-
LookupType::ById(instance_id),
511-
),
512-
)
513-
})?;
514-
515-
Ok(unlocked)
516-
}
517-
518415
/// Updates an instance record and a VMM record with a single database
519416
/// command.
520417
///

nexus/src/app/sagas/instance_update/mod.rs

Lines changed: 8 additions & 71 deletions
Original file line numberDiff line numberDiff line change
@@ -129,81 +129,18 @@ async fn siu_lock_instance(
129129
crate::context::op_context_for_saga_action(&sagactx, serialized_authn);
130130
let datastore = osagactx.datastore();
131131
let log = osagactx.log();
132-
let instance_id = authz_instance.id();
133132
slog::info!(
134-
log,
133+
osagactx.log(),
135134
"instance update: attempting to lock instance";
136-
"instance_id" => %instance_id,
135+
"instance_id" => %instance.id(),
137136
"saga_id" => %lock_id,
138137
);
139-
140-
loop {
141-
let instance = datastore
142-
.instance_refetch(&opctx, &authz_instance)
143-
.await
144-
.map_err(ActionError::action_failed)?;
145-
// Look at the current lock state of the instance and determine whether
146-
// we can lock it.
147-
match instance.runtime_state.updater_id {
148-
Some(ref id) if id == &lock_id => {
149-
slog::info!(
150-
log,
151-
"instance update: instance already locked by this saga";
152-
"instance_id" => %instance_id,
153-
"saga_id" => %lock_id,
154-
);
155-
return Ok(instance.runtime_state.updater_gen);
156-
}
157-
Some(ref id) => {
158-
slog::info!(
159-
log,
160-
"instance update: instance locked by another saga";
161-
"instance_id" => %instance_id,
162-
"saga_id" => %lock_id,
163-
"locked_by" => %lock_id,
164-
);
165-
return Err(ActionError::action_failed(serde_json::json!({
166-
"error": "instance locked by another saga",
167-
"saga_id": lock_id,
168-
"locked_by": id,
169-
})));
170-
}
171-
None => {}
172-
};
173-
let gen = instance.runtime_state.updater_gen;
174-
slog::debug!(
175-
log,
176-
"instance update: trying to acquire updater lock...";
177-
"instance_id" => %instance_id,
178-
"saga_id" => %lock_id,
179-
"updater_gen" => ?gen,
180-
);
181-
let lock = datastore
182-
.instance_updater_try_lock(&opctx, &authz_instance, gen, &lock_id)
183-
.await
184-
.map_err(ActionError::action_failed)?;
185-
match lock {
186-
Some(lock_gen) => {
187-
slog::info!(
188-
log,
189-
"instance update: acquired updater lock";
190-
"instance_id" => %instance_id,
191-
"saga_id" => %lock_id,
192-
"updater_gen" => ?gen,
193-
);
194-
return Ok(lock_gen);
195-
}
196-
None => {
197-
slog::debug!(
198-
log,
199-
"instance update: generation has advanced, retrying...";
200-
"instance_id" => %instance_id,
201-
"saga_id" => %lock_id,
202-
"updater_gen" => ?gen,
203-
);
204-
}
205-
}
206-
}
138+
osagactx
139+
.datastore()
140+
.instance_updater_lock(&opctx, authz_instance, &lock_id)
141+
.await
142+
.map_err(ActionError::action_failed)
143+
.map(|_| ())
207144
}
208145

209146
async fn siu_fetch_state(

0 commit comments

Comments
 (0)