mgmt: add face event notification and notification stream
refs: #1244
Change-Id: I14bd327be53bcb607b457d6cb4bd66bd28a2feaa
diff --git a/daemon/mgmt/face-manager.cpp b/daemon/mgmt/face-manager.cpp
index 237a914..e4769ff 100644
--- a/daemon/mgmt/face-manager.cpp
+++ b/daemon/mgmt/face-manager.cpp
@@ -12,6 +12,8 @@
#include "face/tcp-factory.hpp"
#include "face/udp-factory.hpp"
+#include <ndn-cpp-dev/management/nfd-face-event-notification.hpp>
+
#ifdef HAVE_UNIX_SOCKETS
#include "face/unix-stream-factory.hpp"
#endif // HAVE_UNIX_SOCKETS
@@ -54,18 +56,24 @@
Name::Component("list"),
&FaceManager::listFaces
),
+
+ UnsignedVerbAndProcessor(
+ Name::Component("events"),
+ &FaceManager::ignoreUnsignedVerb
+ ),
};
const Name FaceManager::LIST_COMMAND_PREFIX("/localhost/nfd/faces/list");
const size_t FaceManager::LIST_COMMAND_NCOMPS = LIST_COMMAND_PREFIX.size();
-
+const Name FaceManager::EVENTS_COMMAND_PREFIX("/localhost/nfd/faces/events");
FaceManager::FaceManager(FaceTable& faceTable,
shared_ptr<InternalFace> face)
: ManagerBase(face, FACE_MANAGER_PRIVILEGE)
, m_faceTable(faceTable)
, m_statusPublisher(m_faceTable, m_face, LIST_COMMAND_PREFIX)
+ , m_notificationStream(m_face, EVENTS_COMMAND_PREFIX)
, m_signedVerbDispatch(SIGNED_COMMAND_VERBS,
SIGNED_COMMAND_VERBS +
(sizeof(SIGNED_COMMAND_VERBS) / sizeof(SignedVerbAndProcessor)))
@@ -76,6 +84,9 @@
{
face->setInterestFilter("/localhost/nfd/faces",
bind(&FaceManager::onFaceRequest, this, _2));
+
+ m_faceTable.onAdd += bind(&FaceManager::onAddFace, this, _1);
+ m_faceTable.onRemove += bind(&FaceManager::onRemoveFace, this, _1);
}
FaceManager::~FaceManager()
@@ -632,15 +643,35 @@
ndn::nfd::FaceManagementOptions& options)
{
shared_ptr<Face> target = m_faceTable.get(options.getFaceId());
- if (target)
+ if (static_cast<bool>(target))
{
- // don't call m_faceTable.remove(target): it's called by target->close() via onFail
target->close();
}
sendResponse(requestName, 200, "Success");
}
void
+FaceManager::onAddFace(shared_ptr<Face> face)
+{
+ ndn::nfd::FaceEventNotification faceCreated(ndn::nfd::FACE_EVENT_CREATED,
+ face->getId(),
+ face->getUri().toString());
+
+ m_notificationStream.postNotification(faceCreated);
+}
+
+void
+FaceManager::onRemoveFace(shared_ptr<Face> face)
+{
+ ndn::nfd::FaceEventNotification faceDestroyed(ndn::nfd::FACE_EVENT_DESTROYED,
+ face->getId(),
+ face->getUri().toString());
+
+ m_notificationStream.postNotification(faceDestroyed);
+}
+
+
+void
FaceManager::listFaces(const Interest& request)
{
const Name& command = request.getName();
diff --git a/daemon/mgmt/face-manager.hpp b/daemon/mgmt/face-manager.hpp
index 8efb509..6787084 100644
--- a/daemon/mgmt/face-manager.hpp
+++ b/daemon/mgmt/face-manager.hpp
@@ -13,6 +13,7 @@
#include "mgmt/manager-base.hpp"
#include "mgmt/config-file.hpp"
#include "mgmt/face-status-publisher.hpp"
+#include "mgmt/notification-stream.hpp"
#include "fw/face-table.hpp"
#include <ndn-cpp-dev/management/nfd-face-management-options.hpp>
@@ -69,6 +70,9 @@
destroyFace(const Name& requestName,
ndn::nfd::FaceManagementOptions& options);
+ void
+ ignoreUnsignedVerb(const Interest& request);
+
bool
extractOptions(const Interest& request,
ndn::nfd::FaceManagementOptions& extractedOptions);
@@ -81,6 +85,12 @@
void
onConnectFailed(const Name& requestName, const std::string& reason);
+ void
+ onAddFace(shared_ptr<Face> face);
+
+ void
+ onRemoveFace(shared_ptr<Face> face);
+
private:
void
onConfig(const ConfigSection& configSection, bool isDryRun, const std::string& filename);
@@ -115,6 +125,7 @@
FactoryMap m_factories;
FaceTable& m_faceTable;
FaceStatusPublisher m_statusPublisher;
+ NotificationStream m_notificationStream;
typedef function<void(FaceManager*,
const Name&,
@@ -147,6 +158,8 @@
static const Name LIST_COMMAND_PREFIX;
static const size_t LIST_COMMAND_NCOMPS;
+
+ static const Name EVENTS_COMMAND_PREFIX;
};
inline bool
@@ -170,6 +183,12 @@
}
+inline void
+FaceManager::ignoreUnsignedVerb(const Interest& request)
+{
+ // do nothing
+}
+
} // namespace nfd
#endif // NFD_MGMT_FACE_MANAGER_HPP
diff --git a/daemon/mgmt/notification-stream.hpp b/daemon/mgmt/notification-stream.hpp
new file mode 100644
index 0000000..2741035
--- /dev/null
+++ b/daemon/mgmt/notification-stream.hpp
@@ -0,0 +1,60 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/**
+ * Copyright (C) 2014 Named Data Networking Project
+ * See COPYING for copyright and distribution information.
+ */
+#ifndef NFD_MGMT_NOTIFICATION_STREAM_HPP
+#define NFD_MGMT_NOTIFICATION_STREAM_HPP
+
+#include "mgmt/app-face.hpp"
+
+namespace nfd {
+
+class NotificationStream
+{
+public:
+ NotificationStream(shared_ptr<AppFace> face, const Name& prefix);
+
+ ~NotificationStream();
+
+ template <typename T> void
+ postNotification(const T& notification);
+
+private:
+ shared_ptr<AppFace> m_face;
+ const Name m_prefix;
+ uint64_t m_sequenceNo;
+};
+
+inline
+NotificationStream::NotificationStream(shared_ptr<AppFace> face, const Name& prefix)
+ : m_face(face)
+ , m_prefix(prefix)
+ , m_sequenceNo(0)
+{
+}
+
+template <typename T>
+inline void
+NotificationStream::postNotification(const T& notification)
+{
+ Name dataName(m_prefix);
+ dataName.appendSegment(m_sequenceNo);
+ shared_ptr<Data> data(make_shared<Data>(dataName));
+ data->setContent(notification.wireEncode());
+
+ m_face->sign(*data);
+ m_face->put(*data);
+
+ ++m_sequenceNo;
+}
+
+inline
+NotificationStream::~NotificationStream()
+{
+}
+
+} // namespace nfd
+
+
+#endif // NFD_MGMT_NOTIFICATION_STREAM_HPP