fixed bugs and unittests
diff --git a/src/ca-module.cpp b/src/ca-module.cpp
index 0dd96da..74bfc18 100644
--- a/src/ca-module.cpp
+++ b/src/ca-module.cpp
@@ -189,6 +189,8 @@
   // NEW Naming Convention: /<CA-prefix>/CA/NEW/[SignedInterestParameters_Digest]
   // get ECDH pub key and cert request
   const auto& parameterTLV = request.getApplicationParameters();
+  parameterTLV.parse();
+
   if (!parameterTLV.hasValue()) {
     _LOG_ERROR("Empty TLV obtained from the Interest parameter.");
     return;
@@ -218,9 +220,13 @@
 
   // parse certificate request
   Block cert_req = parameterTLV.get(tlv_cert_request);
+  cert_req.parse();
+
   shared_ptr<security::v2::Certificate> clientCert = nullptr;
+
   try {
-    clientCert->wireDecode(cert_req);
+    security::v2::Certificate cert = security::v2::Certificate(cert_req.get(tlv::Data));
+    clientCert = make_shared<security::v2::Certificate>(cert);
   }
   catch (const std::exception& e) {
     _LOG_ERROR("Unrecognized certificate request: " << e.what());
@@ -233,7 +239,7 @@
     _LOG_ERROR("Client requests a too old notBefore timepoint.");
     return;
   }
-  if (expectedPeriod.second > currentTime + m_config.m_validityPeriod ||
+  if (expectedPeriod.second > currentTime + m_config.m_maxValidityPeriod ||
       expectedPeriod.second <= expectedPeriod.first) {
     _LOG_ERROR("Client requests an invalid validity period or a notAfter timepoint beyond the allowed time period.");
     return;
@@ -381,9 +387,8 @@
   result.setFreshnessPeriod(DEFAULT_DATA_FRESHNESS_PERIOD);
 
   // encrypt the content
-  auto payloadBuffer = payload.getBuffer();
-  auto contentBlock = encodeBlockWithAesGcm128(tlv::Content, m_aesKey, payloadBuffer->data(),
-                                               payloadBuffer->size(), (uint8_t*)"test", strlen("test"));
+  auto contentBlock = encodeBlockWithAesGcm128(tlv::Content, m_aesKey, payload.value(),
+                                               payload.value_size(), (uint8_t*)"test", strlen("test"));
   result.setContent(contentBlock);
   m_keyChain.sign(result, signingByIdentity(m_config.m_caPrefix));
   m_face.put(result);
@@ -410,7 +415,6 @@
   signatureInfo.setValidityPeriod(period);
   security::SigningInfo signingInfo(security::SigningInfo::SIGNER_TYPE_ID,
                                     m_config.m_caPrefix, signatureInfo);
-  newCert.setFreshnessPeriod(m_config.m_freshnessPeriod);
 
   m_keyChain.sign(newCert, signingInfo);
   _LOG_TRACE("new cert got signed" << newCert);
diff --git a/src/client-module.cpp b/src/client-module.cpp
index d6fdc14..dd572a1 100644
--- a/src/client-module.cpp
+++ b/src/client-module.cpp
@@ -188,7 +188,6 @@
   security::v2::Certificate certRequest;
   certRequest.setName(Name(m_key.getName()).append("cert-request").appendVersion());
   certRequest.setContentType(tlv::ContentType_Key);
-  certRequest.setFreshnessPeriod(time::hours(24));
   certRequest.setContent(m_key.getPublicKey().data(), m_key.getPublicKey().size());
   SignatureInfo signatureInfo;
   signatureInfo.setValidityPeriod(security::ValidityPeriod(notBefore, notAfter));
@@ -254,9 +253,8 @@
   interest->setCanBePrefix(false);
 
   // encrypt the Interest parameters
-  auto payload = challengeRequest.get(tlv_encrypted_payload).getBuffer();
-  auto paramBlock = encodeBlockWithAesGcm128(tlv_encrypted_payload, m_aesKey,
-                                             payload->data(), payload->size(), (const uint8_t*)"test", strlen("test"));
+  auto paramBlock = encodeBlockWithAesGcm128(tlv::ApplicationParameters, m_aesKey,
+                                             challengeRequest.value(), challengeRequest.value_size(), (const uint8_t*)"test", strlen("test"));
   interest->setApplicationParameters(paramBlock);
 
   m_keyChain.sign(*interest, signingByKey(m_key.getName()));
@@ -282,7 +280,11 @@
   m_freshBefore = time::system_clock::now() +
                   time::seconds(readNonNegativeInteger(contentTLV.get(tlv_remaining_time)));
 
-  m_issuedCertName.wireDecode(contentTLV.get(tlv_issued_cert_name));
+  if (contentTLV.find(tlv_issued_cert_name) != contentTLV.elements_end()) {
+    Block issuedCertNameBlock = contentTLV.get(tlv_issued_cert_name);
+    issuedCertNameBlock.parse();
+    m_issuedCertName.wireDecode(issuedCertNameBlock.get(tlv::Name));
+  }
 }
 
 shared_ptr<Interest>
diff --git a/src/protocol-detail/challenge.cpp b/src/protocol-detail/challenge.cpp
index 273e631..2923270 100644
--- a/src/protocol-detail/challenge.cpp
+++ b/src/protocol-detail/challenge.cpp
@@ -29,10 +29,10 @@
 CHALLENGE::encodeDataPayload(const CertificateRequest& request)
 {
   Block response = makeEmptyBlock(tlv_encrypted_payload);
-  makeNonNegativeIntegerBlock(tlv_status, request.m_status);
-  makeStringBlock(tlv_challenge_status, request.m_challengeStatus);
-  makeNonNegativeIntegerBlock(tlv_remaining_tries, request.m_remainingTries);
-  makeNonNegativeIntegerBlock(tlv_remaining_time, request.m_remainingTime);
+  response.push_back(makeNonNegativeIntegerBlock(tlv_status, request.m_status));
+  response.push_back(makeStringBlock(tlv_challenge_status, request.m_challengeStatus));
+  response.push_back(makeNonNegativeIntegerBlock(tlv_remaining_tries, request.m_remainingTries));
+  response.push_back(makeNonNegativeIntegerBlock(tlv_remaining_time, request.m_remainingTime));
   response.encode();
   return response;
 }
diff --git a/tests/unit-tests/ca-module.t.cpp b/tests/unit-tests/ca-module.t.cpp
index 25a5322..104c505 100644
--- a/tests/unit-tests/ca-module.t.cpp
+++ b/tests/unit-tests/ca-module.t.cpp
@@ -24,6 +24,7 @@
 #include "challenge-module.hpp"
 #include "challenge-module/challenge-pin.hpp"
 #include "challenge-module/challenge-email.hpp"
+#include "protocol-detail/info.hpp"
 
 #include <ndn-cxx/util/dummy-client-face.hpp>
 #include <ndn-cxx/security/signing-helpers.hpp>
@@ -73,6 +74,7 @@
   paramTLV.push_back(makeStringBlock(tlv_parameter_key, JSON_CLIENT_PROBE_INFO));
   paramTLV.push_back(makeStringBlock(tlv_parameter_value, "zhiyi"));
   paramTLV.encode();
+
   interest.setApplicationParameters(paramTLV);
 
   int count = 0;
@@ -81,7 +83,11 @@
       BOOST_CHECK(security::verifySignature(response, cert));
       Block contentBlock = response.getContent();
       contentBlock.parse();
-      BOOST_CHECK_EQUAL(readString(contentBlock.get(tlv_ca_prefix)), "/ndn/example");
+      Block probeResponse = contentBlock.get(tlv_probe_response);
+      probeResponse.parse();
+      Name caName;
+      caName.wireDecode(probeResponse.get(tlv::Name));
+      BOOST_CHECK_EQUAL(caName, "/ndn/example");
     });
   face.receive(interest);
 
@@ -109,8 +115,9 @@
   face.onSendData.connect([&] (const Data& response) {
       count++;
       BOOST_CHECK(security::verifySignature(response, cert));
-      auto contentJson = ClientModule::getJsonFromData(response);
-      auto caItem = ClientConfig::extractCaItem(contentJson);
+      auto contentBlock = response.getContent();
+      contentBlock.parse();
+      auto caItem = INFO::decodeClientConfigFromContent(contentBlock);
       BOOST_CHECK_EQUAL(caItem.m_caPrefix, "/ndn");
       BOOST_CHECK_EQUAL(caItem.m_probe, "");
       BOOST_CHECK_EQUAL(caItem.m_anchor.wireEncode(), cert.wireEncode());
@@ -134,16 +141,25 @@
 
   Interest interest("/ndn/CA/PROBE");
   interest.setCanBePrefix(false);
-  JsonSection paramJson;
-  paramJson.add(JSON_CLIENT_PROBE_INFO, "zhiyi");
-  interest.setApplicationParameters(ClientModule::paramFromJson(paramJson));
+
+  Block paramTLV = makeEmptyBlock(tlv::ApplicationParameters);
+  paramTLV.push_back(makeStringBlock(tlv_parameter_key, JSON_CLIENT_PROBE_INFO));
+  paramTLV.push_back(makeStringBlock(tlv_parameter_value, "zhiyi"));
+  paramTLV.encode();
+
+  interest.setApplicationParameters(paramTLV);
 
   int count = 0;
   face.onSendData.connect([&] (const Data& response) {
       count++;
       BOOST_CHECK(security::verifySignature(response, cert));
-      auto contentJson = ClientModule::getJsonFromData(response);
-      BOOST_CHECK(contentJson.get<std::string>(JSON_CA_NAME) != "");
+      auto contentBlock = response.getContent();
+      contentBlock.parse();
+      auto probeResponseBlock = contentBlock.get(tlv_probe_response);
+      probeResponseBlock.parse();
+      Name caPrefix;
+      caPrefix.wireDecode(probeResponseBlock.get(tlv::Name));
+      BOOST_CHECK(caPrefix != "");
     });
   face.receive(interest);
 
@@ -168,19 +184,28 @@
   client.getClientConf().m_caItems.push_back(item);
 
   auto interest = client.generateNewInterest(time::system_clock::now(),
-                                             time::system_clock::now() + time::days(10),
+                                             time::system_clock::now() + time::days(1),
                                              Name("/ndn/zhiyi"));
 
   int count = 0;
   face.onSendData.connect([&] (const Data& response) {
       count++;
       BOOST_CHECK(security::verifySignature(response, cert));
-      auto contentJson = ClientModule::getJsonFromData(response);
-      BOOST_CHECK(contentJson.get<std::string>(JSON_CA_ECDH) != "");
-      BOOST_CHECK(contentJson.get<std::string>(JSON_CA_SALT) != "");
-      BOOST_CHECK(contentJson.get<std::string>(JSON_CA_REQUEST_ID) != "");
-      auto challengesJson = contentJson.get_child(JSON_CA_CHALLENGES);
-      BOOST_CHECK(challengesJson.size() != 0);
+      auto contentBlock = response.getContent();
+      contentBlock.parse();
+
+      BOOST_CHECK(readString(contentBlock.get(tlv_ecdh_pub)) != "");
+      BOOST_CHECK(readString(contentBlock.get(tlv_salt)) != "");
+      BOOST_CHECK(readString(contentBlock.get(tlv_request_id)) != "");
+
+      auto challengeBlockCount = 0;
+      for (auto const& element: contentBlock.elements()) {
+        if (element.type() == tlv_challenge) {
+          challengeBlockCount++;
+        }
+      }
+
+      BOOST_CHECK(challengeBlockCount != 0);
 
       client.onNewResponse(response);
       BOOST_CHECK_EQUAL_COLLECTIONS(client.m_aesKey, client.m_aesKey + sizeof(client.m_aesKey),
@@ -246,7 +271,7 @@
   m_keyChain.sign(*data, signingByIdentity(ca.m_config.m_caPrefix));
 
   auto interest = client.generateNewInterest(time::system_clock::now(),
-                                             time::system_clock::now() + time::days(10),
+                                             time::system_clock::now() + time::days(1),
                                              Name("/ndn/zhiyi"), data);
 
   int count = 0;
@@ -277,7 +302,7 @@
   item.m_anchor = cert;
   client.getClientConf().m_caItems.push_back(item);
   auto newInterest = client.generateNewInterest(time::system_clock::now(),
-                                                time::system_clock::now() + time::days(10), Name("/ndn/zhiyi"));
+                                                time::system_clock::now() + time::days(1), Name("/ndn/zhiyi"));
 
   // generate CHALLENGE Interest
   ChallengePin pinChallenge;
@@ -288,7 +313,6 @@
   int count = 0;
   face.onSendData.connect([&] (const Data& response) {
     if (Name("/ndn/CA/NEW").isPrefixOf(response.getName())) {
-      auto contentJson = ClientModule::getJsonFromData(response);
       client.onNewResponse(response);
       auto paramJson = pinChallenge.getRequirementForChallenge(client.m_status, client.m_challengeStatus);
       challengeInterest = client.generateChallengeInterest(pinChallenge.genChallengeRequestTLV(client.m_status,
diff --git a/tests/unit-tests/client-module.t.cpp b/tests/unit-tests/client-module.t.cpp
index 638820f..888ad6b 100644
--- a/tests/unit-tests/client-module.t.cpp
+++ b/tests/unit-tests/client-module.t.cpp
@@ -61,7 +61,7 @@
   BOOST_CHECK(firstInterest->getName().at(-1).isParametersSha256Digest());
   // ignore the last name component (ParametersSha256Digest)
   BOOST_CHECK_EQUAL(firstInterest->getName().getPrefix(-1), "/site/CA/PROBE");
-  BOOST_CHECK_EQUAL(CaModule::jsonFromBlock(firstInterest->getApplicationParameters()).get<std::string>("email"),
+  BOOST_CHECK_EQUAL(readString(firstInterest->getApplicationParameters().get(tlv_parameter_value)),
                     "zhiyi@cs.ucla.edu");
 }