@@ -150,23 +150,23 @@ where
150150
151151 pub ( crate ) async fn update ( & self , update : SO :: Update ) -> Result < DataStoreUpdateResult , Error > {
152152 let _guard = self . mutation_lock . lock ( ) . await ;
153- let ( res, data_to_persist) = {
154- let mut locked_objects = self . objects . lock ( ) . expect ( "lock" ) ;
155- if let Some ( object) = locked_objects. get_mut ( & update. id ( ) ) {
156- let updated = object. update ( update) ;
157- if updated {
158- ( DataStoreUpdateResult :: Updated , Some ( Self :: encode_object ( object) ) )
159- } else {
160- ( DataStoreUpdateResult :: Unchanged , None )
161- }
162- } else {
163- ( DataStoreUpdateResult :: NotFound , None )
153+ let id = update. id ( ) ;
154+ let updated_object = {
155+ let locked_objects = self . objects . lock ( ) . expect ( "lock" ) ;
156+ let Some ( object) = locked_objects. get ( & id) else {
157+ return Ok ( DataStoreUpdateResult :: NotFound ) ;
158+ } ;
159+ let mut updated_object = object. clone ( ) ;
160+ if !updated_object. update ( update) {
161+ return Ok ( DataStoreUpdateResult :: Unchanged ) ;
164162 }
163+ updated_object
165164 } ;
166- if let Some ( ( store_key, data) ) = data_to_persist {
167- self . persist_encoded ( store_key, data) . await ?;
168- }
169- Ok ( res)
165+
166+ self . persist ( & updated_object) . await ?;
167+ let mut locked_objects = self . objects . lock ( ) . expect ( "lock" ) ;
168+ locked_objects. insert ( id, updated_object) ;
169+ Ok ( DataStoreUpdateResult :: Updated )
170170 }
171171
172172 /// Returns in-memory objects matching `f`.
@@ -410,4 +410,15 @@ mod tests {
410410 assert_eq ! ( Err ( Error :: PersistenceFailed ) , data_store. insert_or_update( new_object) . await ) ;
411411 assert ! ( data_store. get( & new_id) . is_none( ) ) ;
412412 }
413+
414+ #[ tokio:: test]
415+ async fn update_does_not_mutate_memory_if_persist_fails ( ) {
416+ let id = TestObjectId { id : [ 42u8 ; 4 ] } ;
417+ let object = TestObject { id, data : [ 23u8 ; 3 ] } ;
418+ let data_store = new_failing_data_store ( vec ! [ object] ) ;
419+
420+ let update = TestObjectUpdate { id, data : [ 24u8 ; 3 ] } ;
421+ assert_eq ! ( Err ( Error :: PersistenceFailed ) , data_store. update( update) . await ) ;
422+ assert_eq ! ( Some ( object) , data_store. get( & id) ) ;
423+ }
413424}
0 commit comments