find-face.cpp
Go to the documentation of this file.
1 /* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
2 /*
3  * Copyright (c) 2014-2018, Regents of the University of California,
4  * Arizona Board of Regents,
5  * Colorado State University,
6  * University Pierre & Marie Curie, Sorbonne University,
7  * Washington University in St. Louis,
8  * Beijing Institute of Technology,
9  * The University of Memphis.
10  *
11  * This file is part of NFD (Named Data Networking Forwarding Daemon).
12  * See AUTHORS.md for complete list of NFD authors and contributors.
13  *
14  * NFD is free software: you can redistribute it and/or modify it under the terms
15  * of the GNU General Public License as published by the Free Software Foundation,
16  * either version 3 of the License, or (at your option) any later version.
17  *
18  * NFD is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
19  * without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
20  * PURPOSE. See the GNU General Public License for more details.
21  *
22  * You should have received a copy of the GNU General Public License along with
23  * NFD, e.g., in COPYING.md file. If not, see <http://www.gnu.org/licenses/>.
24  */
25 
26 #include "find-face.hpp"
27 #include "format-helpers.hpp"
28 
29 #include <ndn-cxx/util/logger.hpp>
30 
31 namespace nfd {
32 namespace tools {
33 namespace nfdc {
34 
35 NDN_LOG_INIT(nfdc.FindFace);
36 
38  : m_ctx(ctx)
39 {
40 }
41 
43 FindFace::execute(const FaceUri& faceUri, bool allowMulti)
44 {
45  FaceQueryFilter filter;
46  filter.setRemoteUri(faceUri.toString());
47  return this->execute(filter, allowMulti);
48 }
49 
51 FindFace::execute(uint64_t faceId)
52 {
53  FaceQueryFilter filter;
54  filter.setFaceId(faceId);
55  return this->execute(filter);
56 }
57 
59 FindFace::execute(const ndn::any& faceIdOrUri, bool allowMulti)
60 {
61  const uint64_t* faceId = ndn::any_cast<uint64_t>(&faceIdOrUri);
62  if (faceId != nullptr) {
63  return this->execute(*faceId);
64  }
65  else {
66  return this->execute(ndn::any_cast<FaceUri>(faceIdOrUri), allowMulti);
67  }
68 }
69 
71 FindFace::execute(const FaceQueryFilter& filter, bool allowMulti)
72 {
73  BOOST_ASSERT(m_res == Code::NOT_STARTED);
74  m_res = Code::IN_PROGRESS;
75  m_filter = filter;
76 
77  if (m_filter.hasRemoteUri()) {
78  auto remoteUri = this->canonize("remote", FaceUri(m_filter.getRemoteUri()));
79  if (!remoteUri) {
80  m_res = Code::CANONIZE_ERROR;
81  return m_res;
82  }
83  m_filter.setRemoteUri(remoteUri->toString());
84  }
85 
86  if (m_filter.hasLocalUri()) {
87  auto localUri = this->canonize("local", FaceUri(m_filter.getLocalUri()));
88  if (!localUri) {
89  m_res = Code::CANONIZE_ERROR;
90  return m_res;
91  }
92  m_filter.setLocalUri(localUri->toString());
93  }
94 
95  this->query();
96  if (m_res == Code::OK) {
97  if (m_results.size() == 0) {
98  m_res = Code::NOT_FOUND;
99  m_errorReason = "Face not found";
100  }
101  else if (m_results.size() > 1 && !allowMulti) {
102  m_res = Code::AMBIGUOUS;
103  m_errorReason = "Multiple faces match the query";
104  }
105  }
106  return m_res;
107 }
108 
109 optional<FaceUri>
110 FindFace::canonize(const std::string& fieldName, const FaceUri& input)
111 {
112  if (!FaceUri::canCanonize(input.getScheme())) {
113  NDN_LOG_DEBUG("Using " << fieldName << '=' << input << " without canonization");
114  return input;
115  }
116 
117  optional<FaceUri> result;
118  input.canonize(
119  [&result] (const FaceUri& canonicalUri) { result = canonicalUri; },
120  [this, fieldName] (const std::string& errorReason) {
121  m_errorReason = "Error during " + fieldName + " FaceUri canonization: " + errorReason;
122  },
123  m_ctx.face.getIoService(), m_ctx.getTimeout());
124  m_ctx.face.processEvents();
125 
126  return result;
127 }
128 
129 void
130 FindFace::query()
131 {
132  auto datasetCb = [this] (const std::vector<ndn::nfd::FaceStatus>& result) {
133  m_res = Code::OK;
134  m_results = result;
135  };
136  auto failureCb = [this] (uint32_t code, const std::string& reason) {
137  m_res = Code::ERROR;
138  m_errorReason = "Error " + to_string(code) + " when querying face: " + reason;
139  };
140 
141  if (m_filter.empty()) {
142  m_ctx.controller.fetch<ndn::nfd::FaceDataset>(
143  datasetCb, failureCb, m_ctx.makeCommandOptions());
144  }
145  else {
146  m_ctx.controller.fetch<ndn::nfd::FaceQueryDataset>(
147  m_filter, datasetCb, failureCb, m_ctx.makeCommandOptions());
148  }
149  m_ctx.face.processEvents();
150 }
151 
152 std::set<uint64_t>
154 {
155  std::set<uint64_t> faceIds;
156  for (const FaceStatus& faceStatus : m_results) {
157  faceIds.insert(faceStatus.getFaceId());
158  }
159  return faceIds;
160 }
161 
162 const FaceStatus&
164 {
165  BOOST_ASSERT(m_results.size() == 1);
166  return m_results.front();
167 }
168 
169 void
171 {
172  text::Separator sep(" ", ", ");
173  for (const auto& item : m_results) {
174  os << sep;
175  switch (style) {
177  os << item.getFaceId() << " (local=" << item.getLocalUri() << ')';
178  break;
179  }
180  }
181 }
182 
183 } // namespace nfdc
184 } // namespace tools
185 } // namespace nfd
ndn::nfd::CommandOptions makeCommandOptions() const
FindFace(ExecuteContext &ctx)
Definition: find-face.cpp:37
context for command execution
NDN_LOG_INIT(nfdc.CommandDefinition)
time::nanoseconds getTimeout() const
found exactly one face, or found multiple faces when allowMulti is true
error during FaceUri canonization
found multiple faces and allowMulti is false
void printDisambiguation(std::ostream &os, DisambiguationStyle style) const
print results for disambiguation
Definition: find-face.cpp:170
Copyright (c) 2014-2015, Regents of the University of California, Arizona Board of Regents...
Definition: algorithm.hpp:32
Code execute(const FaceUri &faceUri, bool allowMulti=false)
find face by FaceUri
Definition: find-face.cpp:43
const FaceStatus & getFaceStatus() const
Definition: find-face.cpp:163
print different string on first and subsequent usage
std::set< uint64_t > getFaceIds() const
Definition: find-face.cpp:153