xmpp_component.hpp 3.64 KB
Newer Older
1 2 3 4 5
#ifndef XMPP_COMPONENT_INCLUDED
# define XMPP_COMPONENT_INCLUDED

#include <network/socket_handler.hpp>
#include <xmpp/xmpp_parser.hpp>
6
#include <bridge/bridge.hpp>
7 8

#include <unordered_map>
9 10
#include <memory>
#include <string>
11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57

/**
 * An XMPP component, communicating with an XMPP server using the protocole
 * described in XEP-0114: Jabber Component Protocol
 *
 * TODO: implement XEP-0225: Component Connections
 */
class XmppComponent: public SocketHandler
{
public:
  explicit XmppComponent(const std::string& hostname, const std::string& secret);
  ~XmppComponent();
  void on_connected();
  void on_connection_close();
  void parse_in_buffer();

  /**
   * Connect to the XMPP server
   */
  void start();
  /**
   * Serialize the stanza and add it to the out_buf to be sent to the
   * server.
   */
  void send_stanza(const Stanza& stanza);
  /**
   * Handle the opening of the remote stream
   */
  void on_remote_stream_open(const XmlNode& node);
  /**
   * Handle the closing of the remote stream
   */
  void on_remote_stream_close(const XmlNode& node);
  /**
   * Handle received stanzas
   */
  void on_stanza(const Stanza& stanza);
  /**
   * Send an error stanza. Message being the name of the element inside the
   * stanza, and explanation being a short human-readable sentence
   * describing the error.
   */
  void send_stream_error(const std::string& message, const std::string& explanation);
  /**
   * Send the closing signal for our document (not closing the connection though).
   */
  void close_document();
58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73
  /**
   * Send a message from from@served_hostname, with the given body
   */
  void send_message(const std::string& from, const std::string& body, const std::string& to);
  /**
   * Send a join from a new participant
   */
  void send_user_join(const std::string& from, const std::string& nick, const std::string& to);
  /**
   * Send the self join to the user
   */
  void send_self_join(const std::string& from, const std::string& nick, const std::string& to);
  /**
   * Send the MUC topic to the user
   */
  void send_topic(const std::string& from, const std::string& topic, const std::string& to);
louiz’'s avatar
louiz’ committed
74 75 76 77
  /**
   * Send a (non-private) message to the MUC
   */
  void send_muc_message(const std::string& muc_name, const std::string& nick, const std::string body_str, const std::string& jid_to);
louiz’'s avatar
louiz’ committed
78 79 80 81
  /**
   * Send an unavailable presence for this nick
   */
  void send_muc_leave(std::string&& muc_name, std::string&& nick, std::string&& message, const std::string& jid_to, const bool self);
louiz’'s avatar
louiz’ committed
82 83 84 85
  /**
   * Indicate that a participant changed his nick
   */
  void send_nick_change(const std::string& muc_name, const std::string& old_nick, const std::string& new_nick, const std::string& jid_to, const bool self);
86 87 88 89
  /**
   * Handle the various stanza types
   */
  void handle_handshake(const Stanza& stanza);
90
  void handle_presence(const Stanza& stanza);
louiz’'s avatar
louiz’ committed
91
  void handle_message(const Stanza& stanza);
92 93

private:
94 95 96 97 98 99
  /**
   * Return the bridge associated with the given full JID. Create a new one
   * if none already exist.
   */
  Bridge* get_user_bridge(const std::string& user_jid);

100 101 102 103 104 105 106 107
  XmppParser parser;
  std::string stream_id;
  std::string served_hostname;
  std::string secret;
  bool authenticated;

  std::unordered_map<std::string, std::function<void(const Stanza&)>> stanza_handlers;

108 109 110 111 112 113
  /**
   * One bridge for each user of the component. Indexed by the user's full
   * jid
   */
  std::unordered_map<std::string, std::unique_ptr<Bridge>> bridges;

114 115 116 117 118 119 120 121
  XmppComponent(const XmppComponent&) = delete;
  XmppComponent(XmppComponent&&) = delete;
  XmppComponent& operator=(const XmppComponent&) = delete;
  XmppComponent& operator=(XmppComponent&&) = delete;
};

#endif // XMPP_COMPONENT_INCLUDED