mgmt: enable LocalUri in faces/create command response

Display LocalUri in 'nfdc face create' output.

refs #3956

Change-Id: I3c9ce266f218547bd6ba9509437178d271f680f7
diff --git a/daemon/mgmt/face-manager.cpp b/daemon/mgmt/face-manager.cpp
index eeea696..95c8a82 100644
--- a/daemon/mgmt/face-manager.cpp
+++ b/daemon/mgmt/face-manager.cpp
@@ -144,8 +144,7 @@
   if (face->getId() != face::INVALID_FACEID) {// Face already exists
     NFD_LOG_TRACE("Attempted to create duplicate face of " << face->getId());
 
-    ControlParameters response = collectFaceProperties(*face);
-    response.setUri(face->getRemoteUri().toString());
+    ControlParameters response = collectFaceProperties(*face, true);
     done(ControlResponse(409, "Face with remote URI already exists").setBody(response.wireEncode()));
     return;
   }
@@ -159,7 +158,7 @@
 
   m_faceTable.add(face);
 
-  ControlParameters response = collectFaceProperties(*face);
+  ControlParameters response = collectFaceProperties(*face, true);
   done(ControlResponse(200, "OK").setBody(response.wireEncode()));
 }
 
@@ -233,7 +232,7 @@
   setLinkServiceOptions(*face, parameters, response);
 
   // Set ControlResponse fields
-  response = collectFaceProperties(*face);
+  response = collectFaceProperties(*face, false);
 
   done(ControlResponse(200, "OK").setBody(response.wireEncode()));
 }
@@ -271,16 +270,21 @@
 }
 
 ControlParameters
-FaceManager::collectFaceProperties(const Face& face)
+FaceManager::collectFaceProperties(const Face& face, bool wantUris)
 {
   auto linkService = dynamic_cast<face::GenericLinkService*>(face.getLinkService());
   BOOST_ASSERT(linkService != nullptr);
   auto options = linkService->getOptions();
 
-  return ControlParameters()
-    .setFaceId(face.getId())
-    .setFacePersistency(face.getPersistency())
-    .setFlagBit(ndn::nfd::BIT_LOCAL_FIELDS_ENABLED, options.allowLocalFields, false);
+  ControlParameters params;
+  params.setFaceId(face.getId())
+        .setFacePersistency(face.getPersistency())
+        .setFlagBit(ndn::nfd::BIT_LOCAL_FIELDS_ENABLED, options.allowLocalFields, false);
+  if (wantUris) {
+    params.setUri(face.getRemoteUri().toString())
+          .setLocalUri(face.getLocalUri().toString());
+  }
+  return params;
 }
 
 void
diff --git a/daemon/mgmt/face-manager.hpp b/daemon/mgmt/face-manager.hpp
index 77e820c..4e43716 100644
--- a/daemon/mgmt/face-manager.hpp
+++ b/daemon/mgmt/face-manager.hpp
@@ -83,7 +83,7 @@
                         ControlParameters& response);
 
   static ControlParameters
-  collectFaceProperties(const Face& face);
+  collectFaceProperties(const Face& face, bool wantUris);
 
 PUBLIC_WITH_TESTS_ELSE_PRIVATE: // StatusDataset
   void
diff --git a/tests/tools/nfdc/face-module.t.cpp b/tests/tools/nfdc/face-module.t.cpp
index cf5e893..ee892af 100644
--- a/tests/tools/nfdc/face-module.t.cpp
+++ b/tests/tools/nfdc/face-module.t.cpp
@@ -233,6 +233,7 @@
     ControlParameters body;
     body.setFaceId(1172)
         .setUri("udp4://100.77.30.65:6363")
+        .setLocalUri("udp4://68.62.26.57:24087")
         .setFacePersistency(persistency)
         .setFlags(0);
     this->failCommand(interest, 409, "conflict-409", body);
@@ -253,13 +254,16 @@
 
     ControlParameters resp;
     resp.setFaceId(2130)
+        .setUri("udp4://159.242.33.78:6363")
+        .setLocalUri("udp4://179.63.153.45:28835")
         .setFacePersistency(FacePersistency::FACE_PERSISTENCY_PERSISTENT);
     this->succeedCommand(interest, resp);
   };
 
   this->execute("face create udp://159.242.33.78");
   BOOST_CHECK_EQUAL(exitCode, 0);
-  BOOST_CHECK(out.is_equal("face-created id=2130 remote=udp4://159.242.33.78:6363 persistency=persistent\n"));
+  BOOST_CHECK(out.is_equal("face-created id=2130 local=udp4://179.63.153.45:28835 "
+                           "remote=udp4://159.242.33.78:6363 persistency=persistent\n"));
   BOOST_CHECK(err.is_empty());
 }
 
@@ -276,13 +280,16 @@
 
     ControlParameters resp;
     resp.setFaceId(301)
+        .setUri("udp4://22.91.89.51:19903")
+        .setLocalUri("udp4://98.68.23.71:6363")
         .setFacePersistency(FacePersistency::FACE_PERSISTENCY_PERMANENT);
     this->succeedCommand(interest, resp);
   };
 
   this->execute("face create udp://22.91.89.51:19903 permanent local udp://98.68.23.71");
   BOOST_CHECK_EQUAL(exitCode, 0);
-  BOOST_CHECK(out.is_equal("face-created id=301 remote=udp4://22.91.89.51:19903 persistency=permanent\n"));
+  BOOST_CHECK(out.is_equal("face-created id=301 local=udp4://98.68.23.71:6363 "
+                           "remote=udp4://22.91.89.51:19903 persistency=permanent\n"));
   BOOST_CHECK(err.is_empty());
 }
 
@@ -313,7 +320,8 @@
   this->execute("face create udp://100.77.30.65");
   BOOST_CHECK(hasUpdateCommand);
   BOOST_CHECK_EQUAL(exitCode, 0);
-  BOOST_CHECK(out.is_equal("face-updated id=1172 remote=udp4://100.77.30.65:6363 persistency=persistent\n"));
+  BOOST_CHECK(out.is_equal("face-updated id=1172 local=udp4://68.62.26.57:24087 "
+                           "remote=udp4://100.77.30.65:6363 persistency=persistent\n"));
   BOOST_CHECK(err.is_empty());
 }
 
@@ -326,7 +334,8 @@
 
   this->execute("face create udp://100.77.30.65");
   BOOST_CHECK_EQUAL(exitCode, 0);
-  BOOST_CHECK(out.is_equal("face-exists id=1172 remote=udp4://100.77.30.65:6363 persistency=permanent\n"));
+  BOOST_CHECK(out.is_equal("face-exists id=1172 local=udp4://68.62.26.57:24087 "
+                           "remote=udp4://100.77.30.65:6363 persistency=permanent\n"));
   BOOST_CHECK(err.is_empty());
 }
 
@@ -339,7 +348,8 @@
 
   this->execute("face create udp://100.77.30.65");
   BOOST_CHECK_EQUAL(exitCode, 0);
-  BOOST_CHECK(out.is_equal("face-exists id=1172 remote=udp4://100.77.30.65:6363 persistency=persistent\n"));
+  BOOST_CHECK(out.is_equal("face-exists id=1172 local=udp4://68.62.26.57:24087 "
+                           "remote=udp4://100.77.30.65:6363 persistency=persistent\n"));
   BOOST_CHECK(err.is_empty());
 }
 
diff --git a/tools/nfdc/face-module.cpp b/tools/nfdc/face-module.cpp
index 857956e..39ca5c2 100644
--- a/tools/nfdc/face-module.cpp
+++ b/tools/nfdc/face-module.cpp
@@ -163,10 +163,10 @@
     text::ItemAttributes ia;
     ctx.out << actionSummary << ' '
             << ia("id") << resp.getFaceId()
-            << ia("remote") << canonicalRemote
+            << ia("local") << resp.getLocalUri()
+            << ia("remote") << resp.getUri()
             << ia("persistency") << resp.getFacePersistency()
             << '\n';
-    ///\todo #3956 display local FaceUri before 'remote' field
   };
 
   auto handle409 = [&] (const ControlResponse& resp) {
@@ -180,7 +180,12 @@
       // need to upgrade persistency
       ctx.controller.start<ndn::nfd::FaceUpdateCommand>(
           ControlParameters().setFaceId(respParams.getFaceId()).setFacePersistency(persistency),
-          bind(printPositiveResult, "face-updated", _1),
+          [respParams, &printPositiveResult] (ControlParameters resp2) {
+            // faces/update response does not have FaceUris, copy from faces/create response
+            resp2.setLocalUri(respParams.getLocalUri())
+                 .setUri(respParams.getUri());
+            printPositiveResult("face-updated", resp2);
+          },
           ctx.makeCommandFailureHandler("upgrading face persistency"),
           ctx.makeCommandOptions());
     }