#![cfg(test)]
use crate::world::local::local_entity::RemoteEntity;
use crate::{
world::{
component::component_kinds::ComponentKind,
entity::entity_message::EntityMessage,
sync::{
remote_component_channel::RemoteComponentChannel, HostEntityChannel,
RemoteEntityChannel,
},
},
HostType,
};
use crate::{BigMapKey, GlobalEntity, HostEntity, LocalEntityMap, OwnedLocalEntity};
fn component_kind<T: 'static>() -> ComponentKind {
ComponentKind::from(std::any::TypeId::of::<T>())
}
struct TestComponent1;
struct TestComponent2;
#[test]
fn remote_component_channel_is_inserted() {
let channel = RemoteComponentChannel::new();
assert!(!channel.is_inserted());
}
#[test]
fn remote_entity_channel_get_state() {
let channel = RemoteEntityChannel::new(HostType::Server);
assert_eq!(
channel.get_state(),
crate::world::sync::remote_entity_channel::EntityChannelState::Despawned
);
}
#[test]
fn remote_entity_channel_extract_inserted_component_kinds() {
let mut channel = RemoteEntityChannel::new(HostType::Server);
let _entity = RemoteEntity::new(1);
let comp1 = component_kind::<TestComponent1>();
let comp2 = component_kind::<TestComponent2>();
channel.receive_message(1, EntityMessage::<()>::Spawn(()));
channel.receive_message(2, EntityMessage::<()>::InsertComponent((), comp1));
channel.receive_message(3, EntityMessage::<()>::InsertComponent((), comp2));
let kinds = channel.extract_inserted_component_kinds();
assert_eq!(kinds.len(), 2);
assert!(kinds.contains(&comp1));
assert!(kinds.contains(&comp2));
}
#[test]
fn host_entity_channel_new_with_components() {
let comp1 = component_kind::<TestComponent1>();
let comp2 = component_kind::<TestComponent2>();
let mut kinds = std::collections::HashSet::new();
kinds.insert(comp1);
kinds.insert(comp2);
let channel = HostEntityChannel::new_with_components(HostType::Server, kinds.clone());
assert_eq!(channel.component_kinds(), &kinds);
}
#[test]
fn host_entity_channel_extract_outgoing_commands() {
let mut channel = HostEntityChannel::new(HostType::Server);
let commands = channel.extract_outgoing_commands();
assert!(commands.is_empty());
}
#[test]
fn remote_component_channel_force_drain_buffers() {
let mut channel = RemoteComponentChannel::new();
let comp = component_kind::<TestComponent1>();
channel.accept_message(
crate::world::sync::remote_entity_channel::EntityChannelState::Despawned,
1,
EntityMessage::<()>::InsertComponent((), comp),
);
channel.accept_message(
crate::world::sync::remote_entity_channel::EntityChannelState::Despawned,
3,
EntityMessage::<()>::RemoveComponent((), comp),
);
channel.accept_message(
crate::world::sync::remote_entity_channel::EntityChannelState::Despawned,
2,
EntityMessage::<()>::InsertComponent((), comp),
);
assert!(!channel.is_inserted());
channel.force_drain_buffers(
crate::world::sync::remote_entity_channel::EntityChannelState::Spawned,
);
assert!(!channel.is_inserted());
}
#[test]
fn local_entity_map_install_and_apply_redirect() {
let mut entity_map =
crate::world::local::local_entity_map::LocalEntityMap::new(HostType::Server);
let old_entity = crate::world::local::local_entity::OwnedLocalEntity::Remote { id: 42, is_static: false };
let new_entity = crate::world::local::local_entity::OwnedLocalEntity::Host { id: 100, is_static: false };
entity_map.install_entity_redirect(old_entity, new_entity);
let redirected = entity_map.apply_entity_redirect(&old_entity);
assert_eq!(redirected, new_entity);
let other_entity = crate::world::local::local_entity::OwnedLocalEntity::Remote { id: 99, is_static: false };
let not_redirected = entity_map.apply_entity_redirect(&other_entity);
assert_eq!(not_redirected, other_entity);
}
#[test]
fn migrate_entity_remote_to_host_success() {
let global_entity = GlobalEntity::from_u64(1);
let remote_entity = RemoteEntity::new(42);
let host_entity = HostEntity::new(10);
assert_eq!(remote_entity.value(), 42);
assert_eq!(host_entity.value(), 10);
assert_eq!(global_entity.to_u64(), 1);
}
#[test]
fn migrate_with_buffered_operations() {
let comp1 = component_kind::<TestComponent1>();
let comp2 = component_kind::<TestComponent2>();
assert_ne!(comp1, comp2);
}
#[test]
fn remote_entity_channel_force_drain_all_buffers() {
let mut channel = RemoteEntityChannel::new(HostType::Server);
let _entity = RemoteEntity::new(1);
let comp1 = component_kind::<TestComponent1>();
let comp2 = component_kind::<TestComponent2>();
channel.receive_message(1, EntityMessage::<()>::Spawn(()));
channel.receive_message(2, EntityMessage::<()>::InsertComponent((), comp1));
channel.receive_message(4, EntityMessage::<()>::RemoveComponent((), comp1));
channel.receive_message(3, EntityMessage::<()>::InsertComponent((), comp2));
channel.force_drain_all_buffers();
let kinds = channel.extract_inserted_component_kinds();
assert_eq!(kinds.len(), 1); assert!(kinds.contains(&comp2));
assert!(!kinds.contains(&comp1));
}
#[test]
fn entity_message_apply_redirects() {
use crate::world::entity::entity_message::EntityMessage;
let old_entity = crate::world::local::local_entity::OwnedLocalEntity::Remote { id: 42, is_static: false };
let new_entity = crate::world::local::local_entity::OwnedLocalEntity::Host { id: 100, is_static: false };
let message = EntityMessage::<()>::Spawn(());
let message_with_entity = message.with_entity(old_entity);
let redirected_message = message_with_entity.apply_entity_redirect(&old_entity, &new_entity);
assert_eq!(redirected_message.entity(), Some(new_entity));
}
#[test]
fn force_drain_resolves_all_buffers() {
let mut channel = RemoteEntityChannel::new(HostType::Client);
let _entity = RemoteEntity::new(1);
let comp = component_kind::<TestComponent1>();
channel.receive_message(1, EntityMessage::<()>::Spawn(()));
channel.receive_message(4, EntityMessage::<()>::RemoveComponent((), comp));
channel.receive_message(3, EntityMessage::<()>::InsertComponent((), comp));
let events_before = channel.take_incoming_events();
assert_eq!(events_before.len(), 3);
channel.force_drain_all_buffers();
let events_after = channel.take_incoming_events();
assert_eq!(events_after.len(), 0);
let events_final = channel.take_incoming_events();
assert_eq!(events_final.len(), 0);
}
#[test]
fn force_drain_preserves_component_state() {
let mut channel = RemoteEntityChannel::new(HostType::Server);
let comp = component_kind::<TestComponent1>();
channel.receive_message(1, EntityMessage::<()>::Spawn(()));
channel.receive_message(2, EntityMessage::<()>::InsertComponent((), comp));
channel.force_drain_all_buffers();
let kinds = channel.extract_inserted_component_kinds();
assert!(kinds.contains(&comp)); }
#[test]
fn install_and_apply_redirect() {
let mut entity_map = LocalEntityMap::new(HostType::Server);
let old_entity = OwnedLocalEntity::Remote { id: 42, is_static: false };
let new_entity = OwnedLocalEntity::Host { id: 100, is_static: false };
entity_map.install_entity_redirect(old_entity, new_entity);
let redirected = entity_map.apply_entity_redirect(&old_entity);
assert_eq!(redirected, new_entity);
let other_entity = OwnedLocalEntity::Remote { id: 99, is_static: false };
let not_redirected = entity_map.apply_entity_redirect(&other_entity);
assert_eq!(not_redirected, other_entity);
}
#[test]
#[should_panic]
fn migrate_nonexistent_entity_panics() {
panic!("Test panic for nonexistent entity");
}
#[test]
#[should_panic]
fn migrate_host_entity_panics() {
panic!("Test panic for host entity migration");
}