diff --git a/xmpp-vala/src/module/bind.vala b/xmpp-vala/src/module/bind.vala index 89398bfb..4df8881a 100644 --- a/xmpp-vala/src/module/bind.vala +++ b/xmpp-vala/src/module/bind.vala @@ -69,6 +69,10 @@ namespace Xmpp.Bind { public Jid? my_jid; public bool finished = false; + public static Jid? get_my_jid(XmppStream stream) { + return stream.get_flag(IDENTITY).my_jid; + } + public override string get_ns() { return NS_URI; } public override string get_id() { return IDENTITY.id; } } diff --git a/xmpp-vala/src/module/xep/0353_jingle_message_initiation.vala b/xmpp-vala/src/module/xep/0353_jingle_message_initiation.vala new file mode 100644 index 00000000..acb2ba2e --- /dev/null +++ b/xmpp-vala/src/module/xep/0353_jingle_message_initiation.vala @@ -0,0 +1,97 @@ +using Gee; + +namespace Xmpp.Xep.JingleMessageInitiation { + private const string NS_URI = "urn:xmpp:jingle-message:0"; + + public class Module : XmppStreamModule { + public static ModuleIdentity IDENTITY = new ModuleIdentity(NS_URI, "0353_jingle_message_initiation"); + + public signal void session_proposed(Jid from, Jid to, string sid, Gee.List descriptions); + public signal void session_retracted(Jid from, Jid to, string sid); + public signal void session_accepted(Jid from, string sid); + public signal void session_rejected(Jid from, Jid to, string sid); + + public void send_session_accept_to_self(XmppStream stream, string sid) { + MessageStanza accepted_message = new MessageStanza() { to=Bind.Flag.get_my_jid(stream).bare_jid }; + accepted_message.stanza.put_node( + new StanzaNode.build("accept", NS_URI).add_self_xmlns() + .put_attribute("id", sid, NS_URI)); + stream.get_module(MessageModule.IDENTITY).send_message.begin(stream, accepted_message); + } + + public void send_session_reject_to_self(XmppStream stream, string sid) { + MessageStanza accepted_message = new MessageStanza() { to=Bind.Flag.get_my_jid(stream).bare_jid }; + accepted_message.stanza.put_node( + new StanzaNode.build("reject", NS_URI).add_self_xmlns() + .put_attribute("id", sid, NS_URI)); + stream.get_module(MessageModule.IDENTITY).send_message.begin(stream, accepted_message); + } + + public void send_session_proceed_to_peer(XmppStream stream, Jid to, string sid) { + MessageStanza accepted_message = new MessageStanza() { to=to }; + accepted_message.stanza.put_node( + new StanzaNode.build("proceed", NS_URI).add_self_xmlns() + .put_attribute("id", sid, NS_URI)); + stream.get_module(MessageModule.IDENTITY).send_message.begin(stream, accepted_message); + } + + public void send_session_reject_to_peer(XmppStream stream, Jid to, string sid) { + MessageStanza accepted_message = new MessageStanza() { to=to }; + accepted_message.stanza.put_node( + new StanzaNode.build("reject", NS_URI).add_self_xmlns() + .put_attribute("id", sid, NS_URI)); + stream.get_module(MessageModule.IDENTITY).send_message.begin(stream, accepted_message); + } + + private void on_received_message(XmppStream stream, MessageStanza message) { + Xep.MessageArchiveManagement.MessageFlag? mam_flag = Xep.MessageArchiveManagement.MessageFlag.get_flag(message); + if (mam_flag != null) return; + + StanzaNode? mi_node = null; + foreach (StanzaNode node in message.stanza.sub_nodes) { + if (node.ns_uri == NS_URI) { + mi_node = node; + } + } + if (mi_node == null) return; + + switch (mi_node.name) { + case "accept": + case "proceed": + if (!message.from.equals_bare(Bind.Flag.get_my_jid(stream))) return; + session_accepted(message.from, mi_node.get_attribute("id")); + break; + case "propose": + ArrayList descriptions = new ArrayList(); + + foreach (StanzaNode node in mi_node.sub_nodes) { + if (node.name != "description") continue; + descriptions.add(node); + } + + if (descriptions.size > 0) { + session_proposed(message.from, message.to, mi_node.get_attribute("id"), descriptions); + } + break; + case "retract": + session_retracted(message.from, message.to, mi_node.get_attribute("id")); + break; + case "reject": + if (!message.from.equals_bare(Bind.Flag.get_my_jid(stream))) return; + session_rejected(message.from, message.to, mi_node.get_attribute("id")); + break; + } + } + + public override void attach(XmppStream stream) { + stream.get_module(MessageModule.IDENTITY).received_message.connect(on_received_message); + } + + public override void detach(XmppStream stream) { + stream.get_module(MessageModule.IDENTITY).received_message.disconnect(on_received_message); + } + + public override string get_ns() { return NS_URI; } + public override string get_id() { return IDENTITY.id; } + } +}