diff options
| author | mat <git@matdoes.dev> | 2025-06-11 22:22:26 +0000 |
|---|---|---|
| committer | mat <git@matdoes.dev> | 2025-06-11 22:22:26 +0000 |
| commit | 1b348ceeffc61e49b19f2982e7a9de479c1678de (patch) | |
| tree | bead28ce1a076a3af5ca5df2c326c9e94b63dd92 /azalea-client/tests | |
| parent | 067ec06f26ecaf7a319eb3ce61307b9730176313 (diff) | |
| download | azalea-drasl-1b348ceeffc61e49b19f2982e7a9de479c1678de.tar.xz | |
implement reverting block state predictions on ack
Diffstat (limited to 'azalea-client/tests')
| -rw-r--r-- | azalea-client/tests/mine_block_rollback.rs | 49 | ||||
| -rw-r--r-- | azalea-client/tests/mine_block_without_rollback.rs | 51 |
2 files changed, 100 insertions, 0 deletions
diff --git a/azalea-client/tests/mine_block_rollback.rs b/azalea-client/tests/mine_block_rollback.rs new file mode 100644 index 00000000..e9b46d13 --- /dev/null +++ b/azalea-client/tests/mine_block_rollback.rs @@ -0,0 +1,49 @@ +use azalea_client::{mining::StartMiningBlockEvent, test_utils::prelude::*}; +use azalea_core::{ + position::{BlockPos, ChunkPos}, + resource_location::ResourceLocation, +}; +use azalea_protocol::packets::{ + ConnectionProtocol, + game::{ClientboundBlockChangedAck, ClientboundBlockUpdate}, +}; +use azalea_registry::{Block, DataRegistry, DimensionType}; + +#[test] +fn test_mine_block_rollback() { + init_tracing(); + + let mut simulation = Simulation::new(ConnectionProtocol::Game); + simulation.receive_packet(make_basic_login_packet( + DimensionType::new_raw(0), + ResourceLocation::new("azalea:overworld"), + )); + + simulation.receive_packet(make_basic_empty_chunk(ChunkPos::new(0, 0), (384 + 64) / 16)); + simulation.tick(); + + let pos = BlockPos::new(1, 2, 3); + simulation.receive_packet(ClientboundBlockUpdate { + pos, + // tnt is used for this test because it's insta-mineable so we don't have to waste ticks + // waiting + block_state: Block::Tnt.into(), + }); + simulation.tick(); + assert_eq!(simulation.get_block_state(pos), Some(Block::Tnt.into())); + println!("set serverside tnt"); + + simulation.send_event(StartMiningBlockEvent { + entity: simulation.entity, + position: pos, + }); + simulation.tick(); + assert_eq!(simulation.get_block_state(pos), Some(Block::Air.into())); + println!("set clientside air"); + + // server didn't send the new block, so the change should be rolled back + simulation.receive_packet(ClientboundBlockChangedAck { seq: 1 }); + simulation.tick(); + assert_eq!(simulation.get_block_state(pos), Some(Block::Tnt.into())); + println!("reset serverside tnt"); +} diff --git a/azalea-client/tests/mine_block_without_rollback.rs b/azalea-client/tests/mine_block_without_rollback.rs new file mode 100644 index 00000000..02fb1a77 --- /dev/null +++ b/azalea-client/tests/mine_block_without_rollback.rs @@ -0,0 +1,51 @@ +use azalea_client::{mining::StartMiningBlockEvent, test_utils::prelude::*}; +use azalea_core::{ + position::{BlockPos, ChunkPos}, + resource_location::ResourceLocation, +}; +use azalea_protocol::packets::{ + ConnectionProtocol, + game::{ClientboundBlockChangedAck, ClientboundBlockUpdate}, +}; +use azalea_registry::{Block, DataRegistry, DimensionType}; + +#[test] +fn test_mine_block_without_rollback() { + init_tracing(); + + let mut simulation = Simulation::new(ConnectionProtocol::Game); + simulation.receive_packet(make_basic_login_packet( + DimensionType::new_raw(0), + ResourceLocation::new("azalea:overworld"), + )); + + simulation.receive_packet(make_basic_empty_chunk(ChunkPos::new(0, 0), (384 + 64) / 16)); + simulation.tick(); + + let pos = BlockPos::new(1, 2, 3); + simulation.receive_packet(ClientboundBlockUpdate { + pos, + // tnt is used for this test because it's insta-mineable so we don't have to waste ticks + // waiting + block_state: Block::Tnt.into(), + }); + simulation.tick(); + assert_eq!(simulation.get_block_state(pos), Some(Block::Tnt.into())); + + simulation.send_event(StartMiningBlockEvent { + entity: simulation.entity, + position: pos, + }); + simulation.tick(); + assert_eq!(simulation.get_block_state(pos), Some(Block::Air.into())); + + // server acknowledged our change by sending a BlockUpdate + BlockChangedAck, so + // no rollback + simulation.receive_packet(ClientboundBlockUpdate { + pos, + block_state: Block::Air.into(), + }); + simulation.receive_packet(ClientboundBlockChangedAck { seq: 1 }); + simulation.tick(); + assert_eq!(simulation.get_block_state(pos), Some(Block::Air.into())); +} |
