iq_sender.h 3.6 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121
  1. // Copyright 2014 The Chromium Authors. All rights reserved.
  2. // Use of this source code is governed by a BSD-style license that can be
  3. // found in the LICENSE file.
  4. #ifndef REMOTING_SIGNALING_IQ_SENDER_H_
  5. #define REMOTING_SIGNALING_IQ_SENDER_H_
  6. #include <map>
  7. #include <memory>
  8. #include <string>
  9. #include "base/callback.h"
  10. #include "base/compiler_specific.h"
  11. #include "base/memory/raw_ptr.h"
  12. #include "base/memory/weak_ptr.h"
  13. #include "remoting/signaling/signal_strategy.h"
  14. namespace base {
  15. class TimeDelta;
  16. } // namespace base
  17. namespace jingle_xmpp {
  18. class XmlElement;
  19. } // namespace jingle_xmpp
  20. namespace remoting {
  21. class IqRequest;
  22. class SignalStrategy;
  23. // IqSender handles sending iq requests and routing of responses to
  24. // those requests.
  25. class IqSender : public SignalStrategy::Listener {
  26. public:
  27. // Callback that is called when an Iq response is received. Called
  28. // with the |response| set to nullptr in case of a timeout.
  29. using ReplyCallback =
  30. base::OnceCallback<void(IqRequest* request,
  31. const jingle_xmpp::XmlElement* response)>;
  32. explicit IqSender(SignalStrategy* signal_strategy);
  33. IqSender(const IqSender&) = delete;
  34. IqSender& operator=(const IqSender&) = delete;
  35. ~IqSender() override;
  36. // Send an iq stanza. Returns an IqRequest object that represends
  37. // the request. |callback| is called when response to |stanza| is
  38. // received. Destroy the returned IqRequest to cancel the callback.
  39. // Caller must take ownership of the result. Result must be
  40. // destroyed before sender is destroyed.
  41. std::unique_ptr<IqRequest> SendIq(
  42. std::unique_ptr<jingle_xmpp::XmlElement> stanza,
  43. ReplyCallback callback);
  44. // Same as above, but also formats the message.
  45. std::unique_ptr<IqRequest> SendIq(
  46. const std::string& type,
  47. const std::string& addressee,
  48. std::unique_ptr<jingle_xmpp::XmlElement> iq_body,
  49. ReplyCallback callback);
  50. // SignalStrategy::Listener implementation.
  51. void OnSignalStrategyStateChange(SignalStrategy::State state) override;
  52. bool OnSignalStrategyIncomingStanza(const jingle_xmpp::XmlElement* stanza) override;
  53. private:
  54. typedef std::map<std::string, IqRequest*> IqRequestMap;
  55. friend class IqRequest;
  56. // Helper function used to create iq stanzas.
  57. static std::unique_ptr<jingle_xmpp::XmlElement> MakeIqStanza(
  58. const std::string& type,
  59. const std::string& addressee,
  60. std::unique_ptr<jingle_xmpp::XmlElement> iq_body);
  61. // Removes |request| from the list of pending requests. Called by IqRequest.
  62. void RemoveRequest(IqRequest* request);
  63. raw_ptr<SignalStrategy> signal_strategy_;
  64. IqRequestMap requests_;
  65. };
  66. // This call must only be used on the thread it was created on.
  67. class IqRequest {
  68. public:
  69. IqRequest(IqSender* sender,
  70. IqSender::ReplyCallback callback,
  71. const std::string& addressee);
  72. IqRequest(const IqRequest&) = delete;
  73. IqRequest& operator=(const IqRequest&) = delete;
  74. ~IqRequest();
  75. // Sets timeout for the request. When the timeout expires the
  76. // callback is called with the |response| set to nullptr.
  77. void SetTimeout(base::TimeDelta timeout);
  78. private:
  79. friend class IqSender;
  80. void CallCallback(const jingle_xmpp::XmlElement* stanza);
  81. void OnTimeout();
  82. // Called by IqSender when a response is received.
  83. void OnResponse(const jingle_xmpp::XmlElement* stanza);
  84. void DeliverResponse(std::unique_ptr<jingle_xmpp::XmlElement> stanza);
  85. raw_ptr<IqSender> sender_;
  86. IqSender::ReplyCallback callback_;
  87. std::string addressee_;
  88. base::WeakPtrFactory<IqRequest> weak_factory_{this};
  89. };
  90. } // namespace remoting
  91. #endif // REMOTING_SIGNALING_IQ_SENDER_H_