disconnect fixes

This commit is contained in:
mat 2023-12-01 22:49:44 -06:00
parent fbee81e609
commit 45f9d27601
6 changed files with 32 additions and 11 deletions

View file

@ -1,18 +1,20 @@
//! Disconnect a client from the server.
use azalea_chat::FormattedText;
use azalea_entity::LocalEntity;
use bevy_app::{App, Plugin, PostUpdate};
use bevy_ecs::{
component::Component,
entity::Entity,
event::{EventReader, EventWriter},
prelude::Event,
query::Changed,
query::{Changed, With},
schedule::IntoSystemConfigs,
system::{Commands, Query},
};
use derive_more::Deref;
use crate::{client::JoinedClientBundle, raw_connection::RawConnection};
use crate::{client::JoinedClientBundle, events::LocalPlayerEvents, raw_connection::RawConnection};
pub struct DisconnectPlugin;
impl Plugin for DisconnectPlugin {
@ -33,7 +35,7 @@ impl Plugin for DisconnectPlugin {
#[derive(Event)]
pub struct DisconnectEvent {
pub entity: Entity,
pub reason: Option<String>,
pub reason: Option<FormattedText>,
}
/// System that removes the [`JoinedClientBundle`] from the entity when it
@ -43,7 +45,11 @@ pub fn remove_components_from_disconnected_players(
mut events: EventReader<DisconnectEvent>,
) {
for DisconnectEvent { entity, .. } in events.read() {
commands.entity(*entity).remove::<JoinedClientBundle>();
commands
.entity(*entity)
.remove::<JoinedClientBundle>()
// swarm detects when this tx gets dropped to fire SwarmEvent::Disconnect
.remove::<LocalPlayerEvents>();
}
}
@ -60,12 +66,15 @@ fn update_read_packets_task_running_component(
}
}
fn disconnect_on_connection_dead(
query: Query<(Entity, &IsConnectionAlive), Changed<IsConnectionAlive>>,
query: Query<(Entity, &IsConnectionAlive), (Changed<IsConnectionAlive>, With<LocalEntity>)>,
mut disconnect_events: EventWriter<DisconnectEvent>,
) {
for (entity, &is_connection_alive) in &query {
if !*is_connection_alive {
disconnect_events.send(DisconnectEvent { entity, reason: None });
disconnect_events.send(DisconnectEvent {
entity,
reason: None,
});
}
}
}

View file

@ -3,6 +3,7 @@
use std::sync::Arc;
use azalea_chat::FormattedText;
use azalea_protocol::packets::game::{
clientbound_player_combat_kill_packet::ClientboundPlayerCombatKillPacket, ClientboundGamePacket,
};
@ -20,11 +21,12 @@ use tokio::sync::mpsc;
use crate::{
chat::{ChatPacket, ChatReceivedEvent},
disconnect::DisconnectEvent,
packet_handling::game::{
AddPlayerEvent, DeathEvent, KeepAliveEvent, PacketEvent, RemovePlayerEvent,
UpdatePlayerEvent,
},
PlayerInfo, disconnect::DisconnectEvent,
PlayerInfo,
};
// (for contributors):
@ -94,7 +96,7 @@ pub enum Event {
/// A `KeepAlive` packet was sent by the server.
KeepAlive(u64),
/// The client disconnected from the server.
Disconnect(Option<String>),
Disconnect(Option<FormattedText>),
}
/// A component that contains an event sender for events that are only

View file

@ -104,7 +104,7 @@ pub fn process_packet_events(ecs: &mut World) {
let mut disconnect_events = system_state.get_mut(ecs);
disconnect_events.send(DisconnectEvent {
entity: player_entity,
reason: Some(p.reason.to_ansi()),
reason: Some(p.reason.clone()),
});
}
ClientboundConfigurationPacket::FinishConfiguration(p) => {

View file

@ -401,7 +401,7 @@ pub fn process_packet_events(ecs: &mut World) {
let mut disconnect_events = system_state.get_mut(ecs);
disconnect_events.send(DisconnectEvent {
entity: player_entity,
reason: Some(p.reason.to_ansi()),
reason: Some(p.reason.clone()),
});
}
ClientboundGamePacket::UpdateRecipes(_p) => {

View file

@ -133,7 +133,10 @@ impl RawConnectionReader {
Ok(raw_packet) => {
self.incoming_packet_queue.lock().push(raw_packet);
// tell the client to run all the systems
self.run_schedule_sender.send(()).unwrap();
if self.run_schedule_sender.send(()).is_err() {
// the client was dropped
break;
}
}
Err(error) => {
if !matches!(*error, ReadPacketError::ConnectionClosed) {

View file

@ -354,6 +354,13 @@ async fn handle(mut bot: Client, event: Event, _state: State) -> anyhow::Result<
println!("login packet");
}
}
Event::Disconnect(reason) => {
if let Some(reason) = reason {
println!("bot got kicked for reason: {}", reason.to_ansi());
} else {
println!("bot got kicked");
}
}
_ => {}
}