1 // Copyright (c) 2013 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.
5 #include "remoting/host/host_change_notification_listener.h"
8 #include "base/location.h"
9 #include "base/logging.h"
10 #include "base/single_thread_task_runner.h"
11 #include "base/thread_task_runner_handle.h"
12 #include "remoting/base/constants.h"
13 #include "remoting/protocol/jingle_messages.h"
14 #include "third_party/libjingle/source/talk/xmllite/xmlelement.h"
15 #include "third_party/libjingle/source/talk/xmpp/constants.h"
18 using buzz::XmlElement;
22 HostChangeNotificationListener::HostChangeNotificationListener(
24 const std::string& host_id,
25 SignalStrategy* signal_strategy,
26 const std::string& directory_bot_jid)
27 : listener_(listener),
29 signal_strategy_(signal_strategy),
30 directory_bot_jid_(directory_bot_jid),
32 DCHECK(signal_strategy_);
34 signal_strategy_->AddListener(this);
37 HostChangeNotificationListener::~HostChangeNotificationListener() {
38 signal_strategy_->RemoveListener(this);
41 void HostChangeNotificationListener::OnSignalStrategyStateChange(
42 SignalStrategy::State state) {
45 bool HostChangeNotificationListener::OnSignalStrategyIncomingStanza(
46 const buzz::XmlElement* stanza) {
47 if (stanza->Name() != buzz::QN_IQ || stanza->Attr(buzz::QN_TYPE) != "set")
50 const XmlElement* host_changed_element =
51 stanza->FirstNamed(QName(kChromotingXmlNamespace, "host-changed"));
52 if (!host_changed_element)
55 const std::string& host_id =
56 host_changed_element->Attr(QName(kChromotingXmlNamespace, "hostid"));
57 const std::string& from = stanza->Attr(buzz::QN_FROM);
58 const std::string& to = stanza->Attr(buzz::QN_TO);
59 if (host_id == host_id_ && from == directory_bot_jid_ &&
60 to == signal_strategy_->GetLocalJid()) {
61 const std::string& operation =
62 host_changed_element->Attr(QName(kChromotingXmlNamespace, "operation"));
63 if (operation == "delete") {
64 // OnHostDeleted() may want delete |signal_strategy_|, but SignalStrategy
65 // objects cannot be deleted from a Listener callback, so OnHostDeleted()
66 // has to be invoked later.
67 base::ThreadTaskRunnerHandle::Get()->PostTask(
68 FROM_HERE, base::Bind(&HostChangeNotificationListener::OnHostDeleted,
69 weak_factory_.GetWeakPtr()));
72 LOG(ERROR) << "Invalid host-changed message received: " << stanza->Str();
77 void HostChangeNotificationListener::OnHostDeleted() {
78 listener_->OnHostDeleted();
81 } // namespace remoting