forked from lavina/lavina
1
0
Fork 0

Compare commits

...

3 Commits

2 changed files with 80 additions and 30 deletions

View File

@ -414,6 +414,7 @@ impl Player {
} else { } else {
let room = self.services.rooms.get_room(&self.services, &room_id).await; let room = self.services.rooms.get_room(&self.services, &room_id).await;
if let Some(room) = room { if let Some(room) = room {
room.subscribe(&self.player_id, self.handle.clone()).await;
self.my_rooms.insert(room_id, RoomRef::Local(room)); self.my_rooms.insert(room_id, RoomRef::Local(room));
} else { } else {
tracing::error!("Room #{room_id:?} not found"); tracing::error!("Room #{room_id:?} not found");

View File

@ -23,36 +23,17 @@ impl<'a> XmppConnection<'a> {
server, server,
// resources in MUCs are members' personas not implemented (yet?) // resources in MUCs are members' personas not implemented (yet?)
resource: Some(_), resource: Some(_),
}) if server.0 == self.hostname_rooms => { }) if server.0 == self.hostname_rooms => match p.r#type.as_deref() {
let mut muc_presence = self.retrieve_muc_presence(&name).await?; None => {
muc_presence.id = p.id; self.join_muc(output, p.id, name).await?;
let subject = Message::<()> {
from: Some(Jid {
name: Some(name.clone()),
server: Server(self.hostname_rooms.clone()),
resource: None,
}),
id: None,
to: Some(Jid {
name: Some(self.user.xmpp_name.clone()),
server: Server(self.hostname.clone()),
resource: Some(self.user.xmpp_resource.clone()),
}),
r#type: MessageType::Groupchat,
lang: None,
subject: Some(Subject(None)),
body: None,
custom: vec![],
};
muc_presence.serialize(output);
let messages = self.retrieve_message_history(&name).await?;
for message in messages {
message.serialize(output)
} }
// The subject is the last stanza sent during a MUC join process. Some("unavailable") => {
subject.serialize(output); self.leave_muc(output, p.id, name).await?;
} }
_ => {
tracing::error!("Unimplemented case")
}
},
_ => { _ => {
// TODO other presence cases // TODO other presence cases
let response = Presence::<()>::default(); let response = Presence::<()>::default();
@ -62,6 +43,74 @@ impl<'a> XmppConnection<'a> {
Ok(()) Ok(())
} }
async fn join_muc(&mut self, output: &mut Vec<Event<'static>>, id: Option<String>, name: Name) -> Result<()> {
// Response presence
let mut muc_presence = self.retrieve_muc_presence(&name).await?;
muc_presence.id = id;
muc_presence.serialize(output);
// N last messages from the room history before the user joined
let messages = self.retrieve_message_history(&name).await?;
for message in messages {
message.serialize(output)
}
// The subject is the last stanza sent during a MUC join process.
let subject = Message::<()> {
from: Some(Jid {
name: Some(name.clone()),
server: Server(self.hostname_rooms.clone()),
resource: None,
}),
id: None,
to: Some(Jid {
name: Some(self.user.xmpp_name.clone()),
server: Server(self.hostname.clone()),
resource: Some(self.user.xmpp_resource.clone()),
}),
r#type: MessageType::Groupchat,
lang: None,
subject: Some(Subject(None)),
body: None,
custom: vec![],
};
subject.serialize(output);
Ok(())
}
async fn leave_muc(&mut self, output: &mut Vec<Event<'static>>, id: Option<String>, name: Name) -> Result<()> {
self.user_handle.leave_room(RoomId::try_from(name.0.clone())?).await?;
let response = Presence {
to: Some(Jid {
name: Some(self.user.xmpp_name.clone()),
server: Server(self.hostname.clone()),
resource: Some(self.user.xmpp_resource.clone()),
}),
from: Some(Jid {
name: Some(name.clone()),
server: Server(self.hostname_rooms.clone()),
resource: Some(self.user.xmpp_muc_name.clone()),
}),
r#type: Some("unavailable".into()),
custom: vec![XUser {
item: XUserItem {
affiliation: Affiliation::Member,
role: Role::None,
jid: Jid {
name: Some(self.user.xmpp_name.clone()),
server: Server(self.hostname.clone()),
resource: Some(self.user.xmpp_resource.clone()),
},
},
self_presence: true,
just_created: false,
}],
..Default::default()
};
response.serialize(output);
Ok(())
}
#[tracing::instrument(skip(self, output, r#type), name = "XmppConnection::self_presence")] #[tracing::instrument(skip(self, output, r#type), name = "XmppConnection::self_presence")]
async fn self_presence(&mut self, output: &mut Vec<Event<'static>>, r#type: Option<&str>) { async fn self_presence(&mut self, output: &mut Vec<Event<'static>>, r#type: Option<&str>) {
match r#type { match r#type {
@ -92,7 +141,7 @@ impl<'a> XmppConnection<'a> {
#[tracing::instrument(skip(self), name = "XmppConnection::retrieve_muc_presence")] #[tracing::instrument(skip(self), name = "XmppConnection::retrieve_muc_presence")]
async fn retrieve_muc_presence(&mut self, name: &Name) -> Result<Presence<XUser>> { async fn retrieve_muc_presence(&mut self, name: &Name) -> Result<Presence<XUser>> {
let a = self.user_handle.join_room(RoomId::try_from(name.0.clone())?).await?; let _ = self.user_handle.join_room(RoomId::try_from(name.0.clone())?).await?;
// TODO handle bans // TODO handle bans
let response = Presence { let response = Presence {
to: Some(Jid { to: Some(Jid {