use enum class for status

Change-Id: Iaba23e0754335a7fecec2d6c4b3446988b2fd9d0
diff --git a/ca.conf.sample b/ca.conf.sample
index a4ec7df..977005a 100644
--- a/ca.conf.sample
+++ b/ca.conf.sample
@@ -10,7 +10,7 @@
   ]
   "supported-challenges":
   [
-    { "challenge": "PIN" },
-    { "challenge": "Email" }
+    { "challenge": "pin" },
+    { "challenge": "email" }
   ]
 }
diff --git a/src/ca-config.cpp b/src/ca-config.cpp
index 1bd8e04..e6ab0f6 100644
--- a/src/ca-config.cpp
+++ b/src/ca-config.cpp
@@ -58,6 +58,8 @@
   m_caInfo = configJson.get(CONFIG_CA_INFO, "");
   // CA max validity period
   m_maxValidityPeriod = time::seconds(configJson.get(CONFIG_MAX_VALIDITY_PERIOD, 3600));
+  // CA max suffix length
+  m_maxSuffixLength = configJson.get(CONFIG_MAX_SUFFIX_LENGTH, 1);
   // probe
   m_probeParameterKeys.clear();
   auto probeParameters = configJson.get_child_optional(CONFIG_PROBE_PARAMETERS);
diff --git a/src/ca-config.hpp b/src/ca-config.hpp
index e624e34..fbdfb24 100644
--- a/src/ca-config.hpp
+++ b/src/ca-config.hpp
@@ -21,9 +21,10 @@
 #ifndef NDNCERT_CA_CONFIG_HPP
 #define NDNCERT_CA_CONFIG_HPP
 
+#include <ndn-cxx/security/v2/certificate.hpp>
+
 #include "certificate-request.hpp"
 #include "client-config.hpp"
-#include <ndn-cxx/security/v2/certificate.hpp>
 
 namespace ndn {
 namespace ndncert {
@@ -59,6 +60,7 @@
  *  "ca-prefix": "",
  *  "ca-info": "",
  *  "max-validity-period": "",
+ *  "max-suffix-length": "",
  *  "probe-parameters":
  *  [
  *    {"probe-parameter-key": ""},
@@ -114,6 +116,11 @@
    */
   time::seconds m_maxValidityPeriod;
   /**
+   * Maximum allowed suffix length of requested name.
+   * E.g., When its value is 2, at most 2 name components can be assigned after m_caPrefix.
+   */
+  size_t m_maxSuffixLength;
+  /**
    * A list of supported challenges.
    */
   std::list<std::string> m_supportedChallenges;
diff --git a/src/ca-detail/ca-sqlite.cpp b/src/ca-detail/ca-sqlite.cpp
index 7d0444a..8312eaa 100644
--- a/src/ca-detail/ca-sqlite.cpp
+++ b/src/ca-detail/ca-sqlite.cpp
@@ -126,7 +126,7 @@
 
   if (statement.step() == SQLITE_ROW) {
     Name caName(statement.getBlock(2));
-    int status = statement.getInt(3);
+    Status status = static_cast<Status>(statement.getInt(3));
     std::string challengeStatus = statement.getString(4);
     security::v2::Certificate cert(statement.getBlock(6));
     std::string challengeType = statement.getString(7);
@@ -179,7 +179,7 @@
                              values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?))_SQLTEXT_");
     statement.bind(1, request.m_requestId, SQLITE_TRANSIENT);
     statement.bind(2, request.m_caPrefix.wireEncode(), SQLITE_TRANSIENT);
-    statement.bind(3, request.m_status);
+    statement.bind(3, static_cast<int>(request.m_status));
     statement.bind(4, request.m_challengeStatus, SQLITE_TRANSIENT);
     statement.bind(5, request.m_cert.getKeyName().wireEncode(),
                    SQLITE_TRANSIENT);
@@ -205,7 +205,7 @@
                              values (?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?, ?))_SQLTEXT_");
     statement.bind(1, request.m_requestId, SQLITE_TRANSIENT);
     statement.bind(2, request.m_caPrefix.wireEncode(), SQLITE_TRANSIENT);
-    statement.bind(3, request.m_status);
+    statement.bind(3, static_cast<int>(request.m_status));
     statement.bind(4, request.m_challengeStatus, SQLITE_TRANSIENT);
     statement.bind(5, request.m_cert.getKeyName().wireEncode(),
                    SQLITE_TRANSIENT);
@@ -231,7 +231,7 @@
                              SET status = ?, challenge_status = ?, challenge_type = ?, challenge_secrets = ?,
                              challenge_tp = ?, remaining_tries = ?, remaining_time = ?, request_type = ?
                              WHERE request_id = ?)_SQLTEXT_");
-  statement.bind(1, request.m_status);
+  statement.bind(1, static_cast<int>(request.m_status));
   statement.bind(2, request.m_challengeStatus, SQLITE_TRANSIENT);
   statement.bind(3, request.m_challengeType, SQLITE_TRANSIENT);
   statement.bind(4, convertJson2String(request.m_challengeSecrets), SQLITE_TRANSIENT);
@@ -258,7 +258,7 @@
   while (statement.step() == SQLITE_ROW) {
     std::string requestId = statement.getString(1);
     Name caName(statement.getBlock(2));
-    int status = statement.getInt(3);
+    Status status = static_cast<Status>(statement.getInt(3));
     std::string challengeStatus = statement.getString(4);
     security::v2::Certificate cert(statement.getBlock(6));
     std::string challengeType = statement.getString(7);
@@ -289,7 +289,7 @@
   while (statement.step() == SQLITE_ROW) {
     std::string requestId = statement.getString(1);
     Name caName(statement.getBlock(2));
-    int status = statement.getInt(3);
+    Status status = static_cast<Status>(statement.getInt(3));
     std::string challengeStatus = statement.getString(4);
     security::v2::Certificate cert(statement.getBlock(6));
     std::string challengeType = statement.getString(7);
diff --git a/src/ca-module.cpp b/src/ca-module.cpp
index 47ab755..da087a0 100644
--- a/src/ca-module.cpp
+++ b/src/ca-module.cpp
@@ -343,7 +343,7 @@
 
   // create new request instance
   std::string requestId = std::to_string(random::generateWord64());
-  CertificateRequest certRequest(m_config.m_caPrefix, requestId, requestType, STATUS_BEFORE_CHALLENGE, *clientCert);
+  CertificateRequest certRequest(m_config.m_caPrefix, requestId, requestType, Status::BEFORE_CHALLENGE, *clientCert);
 
   try {
     m_storage->addRequest(certRequest);
@@ -416,7 +416,7 @@
 
   if (challenge == nullptr) {
     _LOG_TRACE("Unrecognized challenge type " << challengeType);
-    certRequest.m_status = STATUS_FAILURE;
+    certRequest.m_status = Status::FAILURE;
     certRequest.m_challengeStatus = CHALLENGE_STATUS_UNKNOWN_CHALLENGE;
     payload = CHALLENGE::encodeDataPayload(certRequest);
   }
@@ -424,18 +424,18 @@
     _LOG_TRACE("CHALLENGE module to be load: " << challengeType);
     // let challenge module handle the request
     challenge->handleChallengeRequest(paramTLV, certRequest);
-    if (certRequest.m_status == STATUS_FAILURE) {
+    if (certRequest.m_status == Status::FAILURE) {
       // if challenge failed
       m_storage->deleteRequest(certRequest.m_requestId);
       payload = CHALLENGE::encodeDataPayload(certRequest);
       _LOG_TRACE("Challenge failed");
     }
-    else if (certRequest.m_status == STATUS_PENDING) {
+    else if (certRequest.m_status == Status::PENDING) {
       // if challenge succeeded
       if (certRequest.m_requestType == REQUEST_TYPE_NEW) {
         auto issuedCert = issueCertificate(certRequest);
         certRequest.m_cert = issuedCert;
-        certRequest.m_status = STATUS_SUCCESS;
+        certRequest.m_status = Status::SUCCESS;
         try {
           m_storage->addCertificate(certRequest.m_requestId, issuedCert);
           m_storage->deleteRequest(certRequest.m_requestId);
@@ -455,7 +455,7 @@
         _LOG_TRACE("Challenge succeeded. Certificate has been issued");
       }
       else if (certRequest.m_requestType == REQUEST_TYPE_REVOKE) {
-        certRequest.m_status = STATUS_SUCCESS;
+        certRequest.m_status = Status::SUCCESS;
         try {
           m_storage->deleteRequest(certRequest.m_requestId);
           _LOG_TRACE("Certificate Revoked");
diff --git a/src/certificate-request.cpp b/src/certificate-request.cpp
index 4a4c4b4..b205531 100644
--- a/src/certificate-request.cpp
+++ b/src/certificate-request.cpp
@@ -26,31 +26,31 @@
 
 CertificateRequest::CertificateRequest() = default;
 
-CertificateRequest::CertificateRequest(const Name& caName, const std::string& requestId, int requestType, int status,
+CertificateRequest::CertificateRequest(const Name& caName, const std::string& requestId, int requestType, Status status,
                                        const security::v2::Certificate& cert)
-  : m_caPrefix(caName)
-  , m_requestId(requestId)
-  , m_requestType(requestType)
-  , m_status(status)
-  , m_cert(cert)
+    : m_caPrefix(caName)
+    , m_requestId(requestId)
+    , m_requestType(requestType)
+    , m_status(status)
+    , m_cert(cert)
 {
 }
 
-CertificateRequest::CertificateRequest(const Name& caName, const std::string& requestId, int requestType, int status,
+CertificateRequest::CertificateRequest(const Name& caName, const std::string& requestId, int requestType, Status status,
                                        const std::string& challengeStatus, const std::string& challengeType,
                                        const std::string& challengeTp, int remainingTime, int remainingTries,
                                        const JsonSection& challengeSecrets, const security::v2::Certificate& cert)
-  : m_caPrefix(caName)
-  , m_requestId(requestId)
-  , m_requestType(requestType)
-  , m_status(status)
-  , m_cert(cert)
-  , m_challengeStatus(challengeStatus)
-  , m_challengeType(challengeType)
-  , m_challengeTp(challengeTp)
-  , m_remainingTime(remainingTime)
-  , m_remainingTries(remainingTries)
-  , m_challengeSecrets(challengeSecrets)
+    : m_caPrefix(caName)
+    , m_requestId(requestId)
+    , m_requestType(requestType)
+    , m_status(status)
+    , m_cert(cert)
+    , m_challengeStatus(challengeStatus)
+    , m_challengeType(challengeType)
+    , m_challengeTp(challengeTp)
+    , m_remainingTime(remainingTime)
+    , m_remainingTries(remainingTries)
+    , m_challengeSecrets(challengeSecrets)
 {
 }
 
@@ -67,10 +67,8 @@
   os << "  " << request.m_caPrefix << "\n";
   os << "Request ID:\n";
   os << "  " << request.m_requestId << "\n";
-  if (request.m_status != -1) {
-    os << "Request Status:\n";
-    os << "  " << request.m_status << "\n";
-  }
+  os << "Request Status:\n";
+  os << "  " << statusToString(request.m_status) << "\n";
   if (request.m_challengeStatus != "") {
     os << "Challenge Status:\n";
     os << "  " << request.m_challengeStatus << "\n";
@@ -85,5 +83,5 @@
   return os;
 }
 
-} // namespace ndncert
-} // namespace ndn
+}  // namespace ndncert
+}  // namespace ndn
diff --git a/src/certificate-request.hpp b/src/certificate-request.hpp
index 4c067c5..bed7660 100644
--- a/src/certificate-request.hpp
+++ b/src/certificate-request.hpp
@@ -49,9 +49,9 @@
 {
 public:
   CertificateRequest();
-  CertificateRequest(const Name& caName, const std::string& requestId, int requestType, int status,
+  CertificateRequest(const Name& caName, const std::string& requestId, int requestType, Status status,
                      const security::v2::Certificate& cert);
-  CertificateRequest(const Name& caName, const std::string& requestId, int requestType, int status,
+  CertificateRequest(const Name& caName, const std::string& requestId, int requestType, Status status,
                      const std::string& challengeStatus, const std::string& challengeType,
                      const std::string& challengeTp, int remainingTime, int remainingTries,
                      const JsonSection& challengeSecrets, const security::v2::Certificate& cert);
@@ -63,7 +63,7 @@
   Name m_caPrefix;
   std::string m_requestId = "";
   int m_requestType = -1;
-  int m_status = -1;
+  Status m_status = Status::NOT_STARTED;
   security::v2::Certificate m_cert;
   std::shared_ptr<Data> m_probeToken = nullptr;
 
diff --git a/src/challenge-module.hpp b/src/challenge-module.hpp
index 4cc5fa9..fb687e1 100644
--- a/src/challenge-module.hpp
+++ b/src/challenge-module.hpp
@@ -70,13 +70,13 @@
 
   // For Client
   virtual JsonSection
-  getRequirementForChallenge(int status, const std::string& challengeStatus) = 0;
+  getRequirementForChallenge(Status status, const std::string& challengeStatus) = 0;
 
   virtual JsonSection
-  genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params) = 0;
+  genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params) = 0;
 
   virtual Block
-  genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params) = 0;
+  genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params) = 0;
 
   // helpers
   static std::string
diff --git a/src/challenge-module/challenge-credential.cpp b/src/challenge-module/challenge-credential.cpp
index 08131c1..da24fef 100644
--- a/src/challenge-module/challenge-credential.cpp
+++ b/src/challenge-module/challenge-credential.cpp
@@ -96,7 +96,7 @@
         credential = io::load<security::v2::Certificate>(ss);
         if (credential == nullptr) {
           _LOG_ERROR("Cannot load credential parameter: cert");
-          request.m_status = STATUS_FAILURE;
+          request.m_status = Status::FAILURE;
           request.m_challengeStatus = FAILURE_INVALID_FORMAT_CREDENTIAL;
           updateRequestOnChallengeEnd(request);
           return;
@@ -107,7 +107,7 @@
         selfSigned = io::load<security::v2::Certificate>(ss);
         if (selfSigned == nullptr) {
           _LOG_ERROR("Cannot load credential parameter: cert");
-          request.m_status = STATUS_FAILURE;
+          request.m_status = Status::FAILURE;
           request.m_challengeStatus = FAILURE_INVALID_FORMAT_SELF_SIGNED;
           updateRequestOnChallengeEnd(request);
           return;
@@ -126,7 +126,7 @@
       if (security::verifySignature(*selfSigned, anchor) &&
           security::verifySignature(*selfSigned, *credential) &&
           readString(selfSigned->getContent()) == request.m_requestId) {
-        request.m_status = STATUS_PENDING;
+        request.m_status = Status::PENDING;
         request.m_challengeStatus = CHALLENGE_STATUS_SUCCESS;
         updateRequestOnChallengeEnd(request);
         return;
@@ -135,7 +135,7 @@
   }
 
   _LOG_TRACE("Cannot verify the credential + self-signed Data + data content");
-  request.m_status = STATUS_FAILURE;
+  request.m_status = Status::FAILURE;
   request.m_challengeStatus = FAILURE_INVALID_CREDENTIAL;
   updateRequestOnChallengeEnd(request);
   return;
@@ -143,10 +143,10 @@
 
 // For Client
 JsonSection
-ChallengeCredential::getRequirementForChallenge(int status, const std::string& challengeStatus)
+ChallengeCredential::getRequirementForChallenge(Status status, const std::string& challengeStatus)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     result.put(JSON_CREDENTIAL_CERT, "Please_copy_anchor_signed_cert_here");
     result.put(JSON_PROOF_OF_PRIVATE_KEY, "Please_copy_key_signed_request_id_data_here");
   }
@@ -157,10 +157,10 @@
 }
 
 JsonSection
-ChallengeCredential::genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengeCredential::genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     result.put(JSON_CREDENTIAL_CERT, params.get(JSON_CREDENTIAL_CERT, ""));
     result.put(JSON_PROOF_OF_PRIVATE_KEY, params.get(JSON_PROOF_OF_PRIVATE_KEY, ""));
   }
@@ -171,10 +171,10 @@
 }
 
 Block
-ChallengeCredential::genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengeCredential::genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   Block request = makeEmptyBlock(tlv_encrypted_payload);
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
     request.push_back(makeStringBlock(tlv_parameter_key, JSON_CREDENTIAL_CERT));
     request.push_back(makeStringBlock(tlv_parameter_value, params.get(JSON_CREDENTIAL_CERT, "")));
diff --git a/src/challenge-module/challenge-credential.hpp b/src/challenge-module/challenge-credential.hpp
index ad2b197..c0e0e48 100644
--- a/src/challenge-module/challenge-credential.hpp
+++ b/src/challenge-module/challenge-credential.hpp
@@ -57,13 +57,13 @@
 
   // For Client
   JsonSection
-  getRequirementForChallenge(int status, const std::string& challengeStatus) override;
+  getRequirementForChallenge(Status status, const std::string& challengeStatus) override;
 
   JsonSection
-  genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
   Block
-  genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
 PUBLIC_WITH_TESTS_ELSE_PRIVATE:
   void
diff --git a/src/challenge-module/challenge-email.cpp b/src/challenge-module/challenge-email.cpp
index c1e498a..cd08d9b 100644
--- a/src/challenge-module/challenge-email.cpp
+++ b/src/challenge-module/challenge-email.cpp
@@ -56,7 +56,7 @@
     // for the first time, init the challenge
     std::string emailAddress = readString(params.get(tlv_parameter_value));
     if (!isValidEmailAddress(emailAddress)) {
-      request.m_status = STATUS_FAILURE;
+      request.m_status = Status::FAILURE;
       request.m_challengeStatus = FAILURE_INVALID_EMAIL;
       return;
     }
@@ -74,7 +74,7 @@
         return;
       }
     }
-    request.m_status = STATUS_CHALLENGE;
+    request.m_status = Status::CHALLENGE;
     request.m_challengeStatus = NEED_CODE;
     request.m_challengeType = CHALLENGE_TYPE;
     std::string emailCode = generateSecretCode();
@@ -96,7 +96,7 @@
     const auto realCode = request.m_challengeSecrets.get<std::string>(JSON_CODE);
     if (currentTime - time::fromIsoString(request.m_challengeTp) >= m_secretLifetime) {
       // secret expires
-      request.m_status = STATUS_FAILURE;
+      request.m_status = Status::FAILURE;
       request.m_challengeStatus = CHALLENGE_STATUS_FAILURE_TIMEOUT;
       updateRequestOnChallengeEnd(request);
       _LOG_TRACE("Secret expired. Challenge failed.");
@@ -104,7 +104,7 @@
     }
     else if (givenCode == realCode) {
       // the code is correct
-      request.m_status = STATUS_PENDING;
+      request.m_status = Status::PENDING;
       request.m_challengeStatus = CHALLENGE_STATUS_SUCCESS;
       updateRequestOnChallengeEnd(request);
       _LOG_TRACE("Secret code matched. Challenge succeeded.");
@@ -122,7 +122,7 @@
       }
       else {
         // run out times
-        request.m_status = STATUS_FAILURE;
+        request.m_status = Status::FAILURE;
         request.m_challengeStatus = CHALLENGE_STATUS_FAILURE_MAXRETRY;
         updateRequestOnChallengeEnd(request);
         _LOG_TRACE("Secret code didn't match. Ran out tires. Challenge failed.");
@@ -132,23 +132,23 @@
   }
   else {
     _LOG_ERROR("The challenge status is wrong");
-    request.m_status = STATUS_FAILURE;
+    request.m_status = Status::FAILURE;
     return;
   }
 }
 
 // For Client
 JsonSection
-ChallengeEmail::getRequirementForChallenge(int status, const std::string& challengeStatus)
+ChallengeEmail::getRequirementForChallenge(Status status, const std::string& challengeStatus)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     result.put(JSON_EMAIL, "Please_input_your_email_address");
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == NEED_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == NEED_CODE) {
     result.put(JSON_CODE, "Please_input_your_verification_code");
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == WRONG_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == WRONG_CODE) {
     result.put(JSON_CODE, "Incorrect_code_please_try_again");
   }
   else {
@@ -158,18 +158,18 @@
 }
 
 JsonSection
-ChallengeEmail::genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengeEmail::genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     result.put(JSON_CLIENT_SELECTED_CHALLENGE, CHALLENGE_TYPE);
     result.put(JSON_EMAIL, params.get(JSON_EMAIL, ""));
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == NEED_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == NEED_CODE) {
     result.put(JSON_CLIENT_SELECTED_CHALLENGE, CHALLENGE_TYPE);
     result.put(JSON_CODE, params.get(JSON_CODE, ""));
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == WRONG_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == WRONG_CODE) {
     result.put(JSON_CLIENT_SELECTED_CHALLENGE, CHALLENGE_TYPE);
     result.put(JSON_CODE, params.get(JSON_CODE, ""));
   }
@@ -180,20 +180,20 @@
 }
 
 Block
-ChallengeEmail::genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengeEmail::genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   Block request = makeEmptyBlock(tlv_encrypted_payload);
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
     request.push_back(makeStringBlock(tlv_parameter_key, JSON_EMAIL));
     request.push_back(makeStringBlock(tlv_parameter_value, params.get(JSON_EMAIL,"")));
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == NEED_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == NEED_CODE) {
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
     request.push_back(makeStringBlock(tlv_parameter_key, JSON_CODE));
     request.push_back(makeStringBlock(tlv_parameter_value, params.get(JSON_CODE,"")));
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == WRONG_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == WRONG_CODE) {
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
     request.push_back(makeStringBlock(tlv_parameter_key, JSON_CODE));
     request.push_back(makeStringBlock(tlv_parameter_value, params.get(JSON_CODE,"")));
diff --git a/src/challenge-module/challenge-email.hpp b/src/challenge-module/challenge-email.hpp
index 4421bd3..b43a3de 100644
--- a/src/challenge-module/challenge-email.hpp
+++ b/src/challenge-module/challenge-email.hpp
@@ -63,13 +63,13 @@
 
   // For Client
   JsonSection
-  getRequirementForChallenge(int status, const std::string& challengeStatus) override;
+  getRequirementForChallenge(Status status, const std::string& challengeStatus) override;
 
   JsonSection
-  genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
   Block
-  genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
 PUBLIC_WITH_TESTS_ELSE_PRIVATE:
   static bool
diff --git a/src/challenge-module/challenge-pin.cpp b/src/challenge-module/challenge-pin.cpp
index e809213..55b9435 100644
--- a/src/challenge-module/challenge-pin.cpp
+++ b/src/challenge-module/challenge-pin.cpp
@@ -49,7 +49,7 @@
   if (request.m_challengeStatus == "") {
     _LOG_TRACE("Challenge Interest arrives. Init the challenge");
     // for the first time, init the challenge
-    request.m_status = STATUS_CHALLENGE;
+    request.m_status = Status::CHALLENGE;
     request.m_challengeStatus = NEED_CODE;
     request.m_challengeType = CHALLENGE_TYPE;
     std::string secretCode = generateSecretCode();
@@ -69,7 +69,7 @@
     const auto realCode = request.m_challengeSecrets.get<std::string>(JSON_PIN_CODE);
     if (currentTime - time::fromIsoString(request.m_challengeTp) >= m_secretLifetime) {
       // secret expires
-      request.m_status = STATUS_FAILURE;
+      request.m_status = Status::FAILURE;
       request.m_challengeStatus = CHALLENGE_STATUS_FAILURE_TIMEOUT;
       updateRequestOnChallengeEnd(request);
       _LOG_TRACE("Secret expired. Challenge failed.");
@@ -77,7 +77,7 @@
     }
     else if (givenCode == realCode) {
       // the code is correct
-      request.m_status = STATUS_PENDING;
+      request.m_status = Status::PENDING;
       request.m_challengeStatus = CHALLENGE_STATUS_SUCCESS;
       updateRequestOnChallengeEnd(request);
       _LOG_TRACE("PIN code matched. Challenge succeeded.");
@@ -95,7 +95,7 @@
       }
       else {
         // run out times
-        request.m_status = STATUS_FAILURE;
+        request.m_status = Status::FAILURE;
         request.m_challengeStatus = CHALLENGE_STATUS_FAILURE_MAXRETRY;
         updateRequestOnChallengeEnd(request);
         _LOG_TRACE("PIN code didn't match. Ran out tires. Challenge failed.");
@@ -105,23 +105,23 @@
   }
   else {
     _LOG_ERROR("The challenge status is wrong");
-    request.m_status = STATUS_FAILURE;
+    request.m_status = Status::FAILURE;
     return;
   }
 }
 
 // For Client
 JsonSection
-ChallengePin::getRequirementForChallenge(int status, const std::string& challengeStatus)
+ChallengePin::getRequirementForChallenge(Status status, const std::string& challengeStatus)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     // do nothing
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == NEED_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == NEED_CODE) {
     result.put(JSON_PIN_CODE, "Please_input_your_verification_code");
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == WRONG_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == WRONG_CODE) {
     result.put(JSON_PIN_CODE, "Incorrect_PIN_code_please_try_again");
   }
   else {
@@ -131,18 +131,18 @@
 }
 
 JsonSection
-ChallengePin::genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengePin::genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     // do nothing
     result.put(JSON_CLIENT_SELECTED_CHALLENGE, CHALLENGE_TYPE);
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == NEED_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == NEED_CODE) {
     result.put(JSON_CLIENT_SELECTED_CHALLENGE, CHALLENGE_TYPE);
     result.put(JSON_PIN_CODE, params.get(JSON_PIN_CODE, ""));
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == WRONG_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == WRONG_CODE) {
     result.put(JSON_CLIENT_SELECTED_CHALLENGE, CHALLENGE_TYPE);
     result.put(JSON_PIN_CODE, params.get(JSON_PIN_CODE, ""));
   }
@@ -153,19 +153,19 @@
 }
 
 Block
-ChallengePin::genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengePin::genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   Block request = makeEmptyBlock(tlv_encrypted_payload);
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     // do nothing
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == NEED_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == NEED_CODE) {
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
     request.push_back(makeStringBlock(tlv_parameter_key, JSON_PIN_CODE));
     request.push_back(makeStringBlock(tlv_parameter_value, params.get(JSON_PIN_CODE,"")));
   }
-  else if (status == STATUS_CHALLENGE && challengeStatus == WRONG_CODE) {
+  else if (status == Status::CHALLENGE && challengeStatus == WRONG_CODE) {
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
     request.push_back(makeStringBlock(tlv_parameter_key, JSON_PIN_CODE));
     request.push_back(makeStringBlock(tlv_parameter_value, params.get(JSON_PIN_CODE,"")));
diff --git a/src/challenge-module/challenge-pin.hpp b/src/challenge-module/challenge-pin.hpp
index 7ae1d75..44db7d8 100644
--- a/src/challenge-module/challenge-pin.hpp
+++ b/src/challenge-module/challenge-pin.hpp
@@ -57,13 +57,13 @@
 
   // For Client
   JsonSection
-  getRequirementForChallenge(int status, const std::string& challengeStatus) override;
+  getRequirementForChallenge(Status status, const std::string& challengeStatus) override;
 
   JsonSection
-  genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
   Block
-  genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
 
 PUBLIC_WITH_TESTS_ELSE_PRIVATE:
diff --git a/src/challenge-module/challenge-private-key.cpp b/src/challenge-module/challenge-private-key.cpp
index 0b77af9..74af413 100644
--- a/src/challenge-module/challenge-private-key.cpp
+++ b/src/challenge-module/challenge-private-key.cpp
@@ -48,7 +48,7 @@
 {
   if (request.m_requestType == REQUEST_TYPE_NEW) {
       _LOG_TRACE("Cannot use this private key challenge for new certificate request");
-      request.m_status = STATUS_FAILURE;
+      request.m_status = Status::FAILURE;
       request.m_challengeStatus = FAILURE_INVALID_REQUEST_TYPE;
       updateRequestOnChallengeEnd(request);
   }
@@ -62,7 +62,7 @@
         selfSigned = io::load<security::v2::Certificate>(ss);
         if (selfSigned == nullptr) {
           _LOG_ERROR("Cannot load credential parameter: cert");
-          request.m_status = STATUS_FAILURE;
+          request.m_status = Status::FAILURE;
           request.m_challengeStatus = FAILURE_INVALID_FORMAT_SELF_SIGNED;
           updateRequestOnChallengeEnd(request);
           return;
@@ -77,24 +77,24 @@
   // verify the credential and the self-signed cert
   if (security::verifySignature(*selfSigned, request.m_cert) &&
     readString(selfSigned->getContent()) == request.m_requestId) {
-    request.m_status = STATUS_PENDING;
+    request.m_status = Status::PENDING;
     request.m_challengeStatus = CHALLENGE_STATUS_SUCCESS;
     updateRequestOnChallengeEnd(request);
     return;
   }
 
   _LOG_TRACE("Cannot verify the credential + self-signed Data + data content");
-  request.m_status = STATUS_FAILURE;
+  request.m_status = Status::FAILURE;
   request.m_challengeStatus = FAILURE_INVALID_CREDENTIAL;
   updateRequestOnChallengeEnd(request);
 }
 
 // For Client
 JsonSection
-ChallengePrivateKey::getRequirementForChallenge(int status, const std::string& challengeStatus)
+ChallengePrivateKey::getRequirementForChallenge(Status status, const std::string& challengeStatus)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     result.put(JSON_PROOF_OF_PRIVATE_KEY, "Please_copy_key_signed_request_id_data_here");
   }
   else {
@@ -104,10 +104,10 @@
 }
 
 JsonSection
-ChallengePrivateKey::genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengePrivateKey::genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   JsonSection result;
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     result.put(JSON_PROOF_OF_PRIVATE_KEY, params.get(JSON_PROOF_OF_PRIVATE_KEY, ""));
   }
   else {
@@ -117,10 +117,10 @@
 }
 
 Block
-ChallengePrivateKey::genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params)
+ChallengePrivateKey::genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params)
 {
   Block request = makeEmptyBlock(tlv_encrypted_payload);
-  if (status == STATUS_BEFORE_CHALLENGE && challengeStatus == "") {
+  if (status == Status::BEFORE_CHALLENGE && challengeStatus == "") {
     request.push_back(makeStringBlock(tlv_selected_challenge, CHALLENGE_TYPE));
     request.push_back(makeStringBlock(tlv_parameter_key, JSON_PROOF_OF_PRIVATE_KEY));
     request.push_back(makeStringBlock(tlv_parameter_value, params.get(JSON_PROOF_OF_PRIVATE_KEY, "")));
diff --git a/src/challenge-module/challenge-private-key.hpp b/src/challenge-module/challenge-private-key.hpp
index 8e78d5a..5f0b936 100644
--- a/src/challenge-module/challenge-private-key.hpp
+++ b/src/challenge-module/challenge-private-key.hpp
@@ -54,13 +54,13 @@
 
   // For Client
   JsonSection
-  getRequirementForChallenge(int status, const std::string& challengeStatus) override;
+  getRequirementForChallenge(Status status, const std::string& challengeStatus) override;
 
   JsonSection
-  genChallengeRequestJson(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestJson(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
   Block
-  genChallengeRequestTLV(int status, const std::string& challengeStatus, const JsonSection& params) override;
+  genChallengeRequestTLV(Status status, const std::string& challengeStatus, const JsonSection& params) override;
 
 PUBLIC_WITH_TESTS_ELSE_PRIVATE:
   static const std::string FAILURE_INVALID_REQUEST_TYPE;
diff --git a/src/client-module.cpp b/src/client-module.cpp
index 52cb62c..6ebe9d7 100644
--- a/src/client-module.cpp
+++ b/src/client-module.cpp
@@ -19,21 +19,23 @@
  */
 
 #include "client-module.hpp"
-#include "logging.hpp"
-#include "challenge-module.hpp"
-#include "crypto-support/enc-tlv.hpp"
-#include "protocol-detail/info.hpp"
-#include "protocol-detail/probe.hpp"
-#include "protocol-detail/new.hpp"
-#include "protocol-detail/challenge.hpp"
-#include "protocol-detail/revoke.hpp"
-#include <ndn-cxx/util/io.hpp>
+
 #include <ndn-cxx/security/signing-helpers.hpp>
-#include <ndn-cxx/security/verification-helpers.hpp>
-#include <ndn-cxx/util/random.hpp>
 #include <ndn-cxx/security/transform/base64-encode.hpp>
 #include <ndn-cxx/security/transform/buffer-source.hpp>
 #include <ndn-cxx/security/transform/stream-sink.hpp>
+#include <ndn-cxx/security/verification-helpers.hpp>
+#include <ndn-cxx/util/io.hpp>
+#include <ndn-cxx/util/random.hpp>
+
+#include "challenge-module.hpp"
+#include "crypto-support/enc-tlv.hpp"
+#include "logging.hpp"
+#include "protocol-detail/challenge.hpp"
+#include "protocol-detail/info.hpp"
+#include "protocol-detail/new.hpp"
+#include "protocol-detail/probe.hpp"
+#include "protocol-detail/revoke.hpp"
 
 namespace ndn {
 namespace ndncert {
@@ -41,7 +43,7 @@
 _LOG_INIT(ndncert.client);
 
 ClientModule::ClientModule(security::v2::KeyChain& keyChain)
-  : m_keyChain(keyChain)
+    : m_keyChain(keyChain)
 {
 }
 
@@ -107,8 +109,7 @@
   interest->setMustBeFresh(true);
   interest->setCanBePrefix(false);
   interest->setApplicationParameters(
-    PROBE::encodeApplicationParametersFromProbeInfo(ca, probeInfo)
-  );
+      PROBE::encodeApplicationParametersFromProbeInfo(ca, probeInfo));
 
   // update local state
   m_ca = ca;
@@ -143,7 +144,7 @@
                                   const Name& identityName, const shared_ptr<Data>& probeToken)
 {
   // Name requestedName = identityName;
-  if (!identityName.empty()) { // if identityName is not empty, find the corresponding CA
+  if (!identityName.empty()) {  // if identityName is not empty, find the corresponding CA
     bool findCa = false;
     for (const auto& caItem : m_config.m_caItems) {
       if (caItem.m_caPrefix.isPrefixOf(identityName)) {
@@ -151,12 +152,12 @@
         findCa = true;
       }
     }
-    if (!findCa) { // if cannot find, cannot proceed
+    if (!findCa) {  // if cannot find, cannot proceed
       return nullptr;
     }
     m_identityName = identityName;
   }
-  else { // if identityName is empty, check m_identityName or generate a random name
+  else {  // if identityName is empty, check m_identityName or generate a random name
     if (!m_identityName.empty()) {
       // do nothing
     }
@@ -203,8 +204,7 @@
   interest->setMustBeFresh(true);
   interest->setCanBePrefix(false);
   interest->setApplicationParameters(
-    NEW::encodeApplicationParameters(m_ecdh.getBase64PubKey(), certRequest, probeToken)
-  );
+      NEW::encodeApplicationParameters(m_ecdh.getBase64PubKey(), certRequest, probeToken));
 
   // sign the Interest packet
   m_keyChain.sign(*interest, signingByKey(m_key.getName()));
@@ -214,7 +214,7 @@
 std::list<std::string>
 ClientModule::onNewResponse(const Data& reply)
 {
-    return onRequestInitResponse(reply, REQUEST_TYPE_NEW);
+  return onRequestInitResponse(reply, REQUEST_TYPE_NEW);
 }
 
 std::list<std::string>
@@ -228,7 +228,7 @@
   contentTLV.parse();
 
   // ECDH
-  const auto& peerKeyBase64Str = readString(contentTLV.get(tlv_ecdh_pub));  
+  const auto& peerKeyBase64Str = readString(contentTLV.get(tlv_ecdh_pub));
   const auto& saltStr = readString(contentTLV.get(tlv_salt));
   uint64_t saltInt = std::stoull(saltStr);
   m_ecdh.deriveSecret(peerKeyBase64Str);
@@ -238,7 +238,7 @@
        (uint8_t*)&saltInt, sizeof(saltInt), m_aesKey, sizeof(m_aesKey));
 
   // update state
-  m_status = readNonNegativeInteger(contentTLV.get(tlv_status));
+  m_status = static_cast<Status>(readNonNegativeInteger(contentTLV.get(tlv_status)));
   m_requestId = readString(contentTLV.get(tlv_request_id));
   m_challengeList.clear();
   for (auto const& element : contentTLV.elements()) {
@@ -252,37 +252,36 @@
 shared_ptr<Interest>
 ClientModule::generateRevokeInterest(const security::v2::Certificate& certificate)
 {
-    // Name requestedName = identityName;
-    bool findCa = false;
-    for (const auto& caItem : m_config.m_caItems) {
-        if (caItem.m_caName.isPrefixOf(certificate.getName())) {
-            m_ca = caItem;
-            findCa = true;
-        }
+  // Name requestedName = identityName;
+  bool findCa = false;
+  for (const auto& caItem : m_config.m_caItems) {
+    if (caItem.m_caName.isPrefixOf(certificate.getName())) {
+      m_ca = caItem;
+      findCa = true;
     }
-    if (!findCa) { // if cannot find, cannot proceed
-        _LOG_TRACE("Cannot find corresponding CA for the certificate.");
-        return nullptr;
-    }
+  }
+  if (!findCa) {  // if cannot find, cannot proceed
+    _LOG_TRACE("Cannot find corresponding CA for the certificate.");
+    return nullptr;
+  }
 
-    // generate Interest packet
-    Name interestName = m_ca.m_caPrefix;
-    interestName.append("CA").append("REVOKE");
-    auto interest = make_shared<Interest>(interestName);
-    interest->setMustBeFresh(true);
-    interest->setCanBePrefix(false);
-    interest->setApplicationParameters(
-            REVOKE::encodeApplicationParameters(m_ecdh.getBase64PubKey(), certificate)
-    );
+  // generate Interest packet
+  Name interestName = m_ca.m_caPrefix;
+  interestName.append("CA").append("REVOKE");
+  auto interest = make_shared<Interest>(interestName);
+  interest->setMustBeFresh(true);
+  interest->setCanBePrefix(false);
+  interest->setApplicationParameters(
+      REVOKE::encodeApplicationParameters(m_ecdh.getBase64PubKey(), certificate));
 
-    // return the Interest packet
-    return interest;
+  // return the Interest packet
+  return interest;
 }
 
 std::list<std::string>
 ClientModule::onRevokeResponse(const Data& reply)
 {
-    return onRequestInitResponse(reply, REQUEST_TYPE_REVOKE);
+  return onRequestInitResponse(reply, REQUEST_TYPE_REVOKE);
 }
 
 shared_ptr<Interest>
@@ -299,7 +298,8 @@
 
   // encrypt the Interest parameters
   auto paramBlock = encodeBlockWithAesGcm128(tlv::ApplicationParameters, m_aesKey,
-                                             challengeRequest.value(), challengeRequest.value_size(), (const uint8_t*)"test", strlen("test"));
+                                             challengeRequest.value(), challengeRequest.value_size(),
+                                             (const uint8_t*)"test", strlen("test"));
   interest->setApplicationParameters(paramBlock);
 
   m_keyChain.sign(*interest, signingByKey(m_key.getName()));
@@ -319,7 +319,7 @@
   contentTLV.parse();
 
   // update state
-  m_status = readNonNegativeInteger(contentTLV.get(tlv_status));
+  m_status = static_cast<Status>(readNonNegativeInteger(contentTLV.get(tlv_status)));
   m_challengeStatus = readString(contentTLV.get(tlv_challenge_status));
   m_remainingTries = readNonNegativeInteger(contentTLV.get(tlv_remaining_tries));
   m_freshBefore = time::system_clock::now() +
@@ -370,7 +370,7 @@
 void
 ClientModule::endSession()
 {
-  if (getApplicationStatus() == STATUS_SUCCESS || getApplicationStatus() == STATUS_ENDED) {
+  if (getApplicationStatus() == Status::SUCCESS || getApplicationStatus() == Status::ENDED) {
     return;
   }
   if (m_isNewlyCreatedIdentity) {
@@ -383,10 +383,9 @@
     auto identity = m_keyChain.getPib().getIdentity(m_identityName);
     m_keyChain.deleteKey(identity, m_key);
   }
-  m_status = STATUS_ENDED;
+  m_status = Status::ENDED;
 }
 
-
 std::vector<std::string>
 ClientModule::parseProbeComponents(const std::string& probe)
 {
@@ -402,5 +401,5 @@
   return components;
 }
 
-} // namespace ndncert
-} // namespace ndn
+}  // namespace ndncert
+}  // namespace ndn
diff --git a/src/client-module.hpp b/src/client-module.hpp
index eefccad..f90cff3 100644
--- a/src/client-module.hpp
+++ b/src/client-module.hpp
@@ -55,7 +55,7 @@
     return m_config;
   }
 
-  int
+  Status
   getApplicationStatus() const
   {
     return m_status;
@@ -135,7 +135,7 @@
   Name m_identityName;
 
   std::string m_requestId = "";
-  int m_status = STATUS_NOT_STARTED;
+  Status m_status = Status::NOT_STARTED;
   std::string m_challengeStatus = "";
   std::string m_challengeType = "";
   std::string m_certId = "";
diff --git a/src/ndncert-common.cpp b/src/ndncert-common.cpp
new file mode 100644
index 0000000..0a6c994
--- /dev/null
+++ b/src/ndncert-common.cpp
@@ -0,0 +1,49 @@
+/* -*- Mode:C++; c-file-style:"gnu"; indent-tabs-mode:nil; -*- */
+/**
+ * Copyright (c) 2017-2020, Regents of the University of California.
+ *
+ * This file is part of ndncert, a certificate management system based on NDN.
+ *
+ * ndncert is free software: you can redistribute it and/or modify it under the terms
+ * of the GNU General Public License as published by the Free Software Foundation, either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * ndncert is distributed in the hope that it will be useful, but WITHOUT ANY
+ * WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A
+ * PARTICULAR PURPOSE.  See the GNU General Public License for more details.
+ *
+ * You should have received copies of the GNU General Public License along with
+ * ndncert, e.g., in COPYING.md file.  If not, see <http://www.gnu.org/licenses/>.
+ *
+ * See AUTHORS.md for complete list of ndncert authors and contributors.
+ */
+
+#include "ndncert-common.hpp"
+
+namespace ndn {
+namespace ndncert {
+
+std::string statusToString(Status status) {
+  switch (status)
+  {
+  case Status::BEFORE_CHALLENGE:
+    return "Before challenge";
+  case Status::CHALLENGE:
+    return "In challenge";
+  case Status::PENDING:
+    return "Pending after challenge";
+  case Status::SUCCESS:
+    return "Success";
+  case Status::FAILURE:
+    return "Failure";
+  case Status::NOT_STARTED:
+    return "Not started";
+  case Status::ENDED:
+    return "Ended";
+  default:
+    return "Unrecognized status";
+  }
+}
+
+}  // namespace ndncert
+}  // namespace ndn
diff --git a/src/ndncert-common.hpp b/src/ndncert-common.hpp
index 4109d58..cbbba39 100644
--- a/src/ndncert-common.hpp
+++ b/src/ndncert-common.hpp
@@ -35,44 +35,42 @@
 #define PROTECTED_WITH_TESTS_ELSE_PRIVATE private
 #endif
 
-#include <cstddef>
-#include <cstdint>
-
-#include <ndn-cxx/interest.hpp>
-#include <ndn-cxx/data.hpp>
-#include <ndn-cxx/name.hpp>
-#include <ndn-cxx/face.hpp>
-#include <ndn-cxx/link.hpp>
-#include <ndn-cxx/encoding/block.hpp>
-#include <ndn-cxx/lp/nack.hpp>
-#include <ndn-cxx/security/key-chain.hpp>
-#include <ndn-cxx/security/v2/certificate.hpp>
-
 #include <boost/algorithm/string.hpp>
 #include <boost/assert.hpp>
 #include <boost/noncopyable.hpp>
 #include <boost/throw_exception.hpp>
+#include <cstddef>
+#include <cstdint>
+#include <ndn-cxx/data.hpp>
+#include <ndn-cxx/encoding/block.hpp>
+#include <ndn-cxx/face.hpp>
+#include <ndn-cxx/interest.hpp>
+#include <ndn-cxx/link.hpp>
+#include <ndn-cxx/lp/nack.hpp>
+#include <ndn-cxx/name.hpp>
+#include <ndn-cxx/security/key-chain.hpp>
+#include <ndn-cxx/security/v2/certificate.hpp>
 
 namespace ndn {
 namespace ndncert {
 
-using std::size_t;
 using boost::noncopyable;
-using std::shared_ptr;
-using std::unique_ptr;
-using std::weak_ptr;
-using std::make_shared;
-using ndn::make_unique;
-using std::enable_shared_from_this;
-using std::function;
-using std::bind;
-using ndn::Interest;
+using ndn::Block;
 using ndn::Data;
+using ndn::Interest;
+using ndn::make_unique;
 using ndn::Name;
 using ndn::PartialName;
-using ndn::Block;
 using ndn::time::system_clock;
 using ndn::time::toUnixTimestamp;
+using std::bind;
+using std::enable_shared_from_this;
+using std::function;
+using std::make_shared;
+using std::shared_ptr;
+using std::size_t;
+using std::unique_ptr;
+using std::weak_ptr;
 
 enum : uint32_t {
   tlv_ca_prefix = 129,
@@ -81,6 +79,7 @@
   tlv_parameter_value = 135,
   tlv_ca_certificate = 137,
   tlv_max_validity_period = 139,
+  tlv_max_suffix_length = 177,
   tlv_probe_response = 141,
   tlv_allow_longer_name = 143,
   tlv_ecdh_pub = 145,
@@ -99,7 +98,6 @@
   tlv_error_code = 171,
   tlv_error_info = 173,
   tlv_authentication_tag = 175,
-  tlv_max_suffix_length = 177,
   tlv_cert_to_revoke = 179
 };
 
@@ -111,8 +109,9 @@
 const std::string CONFIG_PROBE_PARAMETER = "probe-parameter-key";
 const std::string CONFIG_SUPPORTED_CHALLENGES = "supported-challenges";
 const std::string CONFIG_CHALLENGE = "challenge";
+const std::string CONFIG_MAX_SUFFIX_LENGTH = "max-suffix-length";
 
-// JSON format for Certificate Issuer (CA)
+// // JSON format for Certificate Issuer (CA)
 const std::string JSON_CA_NAME = "name";
 const std::string JSON_CA_CONFIG = "ca-config";
 const std::string JSON_CA_ECDH = "ecdh-pub";
@@ -123,13 +122,13 @@
 const std::string JSON_CA_CHALLENGE_ID = "challenge-id";
 const std::string JSON_CA_CERT_ID = "certificate-id";
 
-// JSON format for Challenge Module
+// // JSON format for Challenge Module
 const std::string JSON_CHALLENGE_STATUS = "challenge-status";
 const std::string JSON_CHALLENGE_REMAINING_TRIES = "remaining-tries";
 const std::string JSON_CHALLENGE_REMAINING_TIME = "remaining-time";
 const std::string JSON_CHALLENGE_ISSUED_CERT_NAME = "issued-cert-name";
 
-// JSON format for Certificate Requester
+// // JSON format for Certificate Requester
 const std::string JSON_CLIENT_PROBE_INFO = "probe-info";
 const std::string JSON_CLIENT_ECDH = "ecdh-pub";
 const std::string JSON_CLIENT_CERT_REQ = "cert-request";
@@ -137,14 +136,28 @@
 const std::string JSON_CLIENT_CERT_TO_REVOKE = "cert-to-revoke";
 
 // NDNCERT Status Enum
-enum {
-  STATUS_BEFORE_CHALLENGE = 0,
-  STATUS_CHALLENGE = 1,
-  STATUS_PENDING = 2,
-  STATUS_SUCCESS = 3,
-  STATUS_FAILURE = 4,
-  STATUS_NOT_STARTED = 5,
-  STATUS_ENDED = 6
+enum class Status : uint16_t {
+  BEFORE_CHALLENGE = 0,
+  CHALLENGE = 1,
+  PENDING = 2,
+  SUCCESS = 3,
+  FAILURE = 4,
+  NOT_STARTED = 5,
+  ENDED = 6
+};
+
+std::string statusToString(Status status);
+
+enum class Error : uint16_t {
+  BAD_INTEREST_FORMAT = 1,
+  BAD_PARAMETER_FORMAT = 2,
+  BAD_SIGNATURE = 3,
+  INVALID_PARAMETER = 4,
+  NAME_NOT_ALLOWED = 5,
+  BAD_VALIDITY_PERIOD = 6,
+  OUT_OF_TRIES = 7,
+  OUT_OF_TIME = 8,
+  NO_AVAILABLE_NAMES = 9
 };
 
 // Pre-defined challenge status
@@ -153,7 +166,7 @@
 const std::string CHALLENGE_STATUS_FAILURE_MAXRETRY = "failure-max-retry";
 const std::string CHALLENGE_STATUS_UNKNOWN_CHALLENGE = "unknown-challenge";
 
-} // namespace ndncert
-} // namespace ndn
+}  // namespace ndncert
+}  // namespace ndn
 
-#endif // NDNCERT_NDNCERT_COMMON_HPP
+#endif  // NDNCERT_NDNCERT_COMMON_HPP
diff --git a/src/protocol-detail/challenge.cpp b/src/protocol-detail/challenge.cpp
index 2923270..e4d5ecb 100644
--- a/src/protocol-detail/challenge.cpp
+++ b/src/protocol-detail/challenge.cpp
@@ -29,7 +29,7 @@
 CHALLENGE::encodeDataPayload(const CertificateRequest& request)
 {
   Block response = makeEmptyBlock(tlv_encrypted_payload);
-  response.push_back(makeNonNegativeIntegerBlock(tlv_status, request.m_status));
+  response.push_back(makeNonNegativeIntegerBlock(tlv_status, static_cast<size_t>(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));
diff --git a/src/protocol-detail/new.cpp b/src/protocol-detail/new.cpp
index 20eaafb..0c33ba8 100644
--- a/src/protocol-detail/new.cpp
+++ b/src/protocol-detail/new.cpp
@@ -63,7 +63,7 @@
   response.push_back(makeStringBlock(tlv_ecdh_pub, ecdhKey));
   response.push_back(makeStringBlock(tlv_salt, salt));
   response.push_back(makeStringBlock(tlv_request_id, request.m_requestId));
-  response.push_back(makeNonNegativeIntegerBlock(tlv_status, request.m_status));
+  response.push_back(makeNonNegativeIntegerBlock(tlv_status, static_cast<size_t>(request.m_status)));
   for (const auto& entry: challenges) {
     response.push_back(makeStringBlock(tlv_challenge, entry));
   }
diff --git a/src/protocol-detail/revoke.cpp b/src/protocol-detail/revoke.cpp
index 5bde720..b31ae55 100644
--- a/src/protocol-detail/revoke.cpp
+++ b/src/protocol-detail/revoke.cpp
@@ -62,7 +62,7 @@
   response.push_back(makeStringBlock(tlv_ecdh_pub, ecdhKey));
   response.push_back(makeStringBlock(tlv_salt, salt));
   response.push_back(makeStringBlock(tlv_request_id, request.m_requestId));
-  response.push_back(makeNonNegativeIntegerBlock(tlv_status, request.m_status));
+  response.push_back(makeNonNegativeIntegerBlock(tlv_status, static_cast<size_t>(request.m_status)));
   for (const auto& entry: challenges) {
     response.push_back(makeStringBlock(tlv_challenge, entry));
   }
diff --git a/tests/unit-tests/bench.t.cpp b/tests/unit-tests/bench.t.cpp
index 3f015b8..a8602ef 100644
--- a/tests/unit-tests/bench.t.cpp
+++ b/tests/unit-tests/bench.t.cpp
@@ -120,7 +120,7 @@
       BOOST_CHECK(security::verifySignature(response, cert));
 
       client.onChallengeResponse(response);
-      BOOST_CHECK_EQUAL(client.m_status, STATUS_CHALLENGE);
+      BOOST_CHECK(client.m_status == Status::CHALLENGE);
       BOOST_CHECK_EQUAL(client.m_challengeStatus, ChallengePin::NEED_CODE);
 
       auto paramJson = pinChallenge.getRequirementForChallenge(client.m_status, client.m_challengeStatus);
@@ -133,7 +133,7 @@
       BOOST_CHECK(security::verifySignature(response, cert));
 
       client.onChallengeResponse(response);
-      BOOST_CHECK_EQUAL(client.m_status, STATUS_CHALLENGE);
+      BOOST_CHECK(client.m_status == Status::CHALLENGE);
       BOOST_CHECK_EQUAL(client.m_challengeStatus, ChallengePin::WRONG_CODE);
 
       auto paramJson = pinChallenge.getRequirementForChallenge(client.m_status, client.m_challengeStatus);
@@ -154,7 +154,7 @@
       BOOST_CHECK(security::verifySignature(response, cert));
 
       client.onChallengeResponse(response);
-      BOOST_CHECK_EQUAL(client.m_status, STATUS_SUCCESS);
+      BOOST_CHECK(client.m_status == Status::SUCCESS);
       BOOST_CHECK_EQUAL(client.m_challengeStatus, CHALLENGE_STATUS_SUCCESS);
     }
   });
diff --git a/tests/unit-tests/ca-memory.t.cpp b/tests/unit-tests/ca-memory.t.cpp
index a1bcd28..01812af 100644
--- a/tests/unit-tests/ca-memory.t.cpp
+++ b/tests/unit-tests/ca-memory.t.cpp
@@ -82,31 +82,31 @@
   auto cert1 = key1.getDefaultCertificate();
 
   // add operation
-  CertificateRequest request1(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, cert1);
+  CertificateRequest request1(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, cert1);
   BOOST_CHECK_NO_THROW(storage.addRequest(request1));
 
   // get operation
   auto result = storage.getRequest("123");
   BOOST_CHECK_EQUAL(request1.m_cert, result.m_cert);
-  BOOST_CHECK_EQUAL(request1.m_status, result.m_status);
+  BOOST_CHECK(request1.m_status == result.m_status);
   BOOST_CHECK_EQUAL(request1.m_caPrefix, result.m_caPrefix);
 
   JsonSection json;
   json.put("code", "1234");
 
   // update operation
-  CertificateRequest request2(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_CHALLENGE, CHALLENGE_STATUS_SUCCESS,
-                             "Email", time::toIsoString(time::system_clock::now()), 3600, 3, json, cert1);
+  CertificateRequest request2(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::CHALLENGE, CHALLENGE_STATUS_SUCCESS,
+                              "Email", time::toIsoString(time::system_clock::now()), 3600, 3, json, cert1);
   storage.updateRequest(request2);
   result = storage.getRequest("123");
   BOOST_CHECK_EQUAL(request2.m_cert, result.m_cert);
-  BOOST_CHECK_EQUAL(request2.m_status, result.m_status);
+  BOOST_CHECK(request2.m_status == result.m_status);
   BOOST_CHECK_EQUAL(request2.m_caPrefix, result.m_caPrefix);
 
   auto identity2 = addIdentity(Name("/ndn/site2"));
   auto key2 = identity2.getDefaultKey();
   auto cert2 = key2.getDefaultCertificate();
-  CertificateRequest request3(Name("/ndn/site2"), "456", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, cert2);
+  CertificateRequest request3(Name("/ndn/site2"), "456", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, cert2);
   storage.addRequest(request3);
 
   // list operation
@@ -118,8 +118,8 @@
   BOOST_CHECK_EQUAL(allRequests.size(), 1);
 }
 
-BOOST_AUTO_TEST_SUITE_END() // TestCaModule
+BOOST_AUTO_TEST_SUITE_END()  // TestCaModule
 
-} // namespace tests
-} // namespace ndncert
-} // namespace ndn
+}  // namespace tests
+}  // namespace ndncert
+}  // namespace ndn
diff --git a/tests/unit-tests/ca-module.t.cpp b/tests/unit-tests/ca-module.t.cpp
index 0bd93bf..9e0289a 100644
--- a/tests/unit-tests/ca-module.t.cpp
+++ b/tests/unit-tests/ca-module.t.cpp
@@ -315,7 +315,7 @@
       BOOST_CHECK(security::verifySignature(response, cert));
 
       client.onChallengeResponse(response);
-      BOOST_CHECK_EQUAL(client.m_status, STATUS_CHALLENGE);
+      BOOST_CHECK(client.m_status == Status::CHALLENGE);
       BOOST_CHECK_EQUAL(client.m_challengeStatus, ChallengePin::NEED_CODE);
 
       auto paramJson = pinChallenge.getRequirementForChallenge(client.m_status, client.m_challengeStatus);
@@ -328,7 +328,7 @@
       BOOST_CHECK(security::verifySignature(response, cert));
 
       client.onChallengeResponse(response);
-      BOOST_CHECK_EQUAL(client.m_status, STATUS_CHALLENGE);
+      BOOST_CHECK(client.m_status == Status::CHALLENGE);
       BOOST_CHECK_EQUAL(client.m_challengeStatus, ChallengePin::WRONG_CODE);
 
       auto paramJson = pinChallenge.getRequirementForChallenge(client.m_status, client.m_challengeStatus);
@@ -347,7 +347,7 @@
       BOOST_CHECK(security::verifySignature(response, cert));
 
       client.onChallengeResponse(response);
-      BOOST_CHECK_EQUAL(client.m_status, STATUS_SUCCESS);
+      BOOST_CHECK(client.m_status == Status::SUCCESS);
       BOOST_CHECK_EQUAL(client.m_challengeStatus, CHALLENGE_STATUS_SUCCESS);
     }
   });
@@ -385,7 +385,7 @@
   signatureInfo.setValidityPeriod(security::ValidityPeriod(time::system_clock::now(),
           time::system_clock::now() + time::hours(10)));
   m_keyChain.sign(clientCert, signingByKey(clientKey.getName()).setSignatureInfo(signatureInfo));
-  CertificateRequest certRequest(Name("/ndn"), "122", REQUEST_TYPE_NEW, STATUS_SUCCESS, clientCert);
+  CertificateRequest certRequest(Name("/ndn"), "122", REQUEST_TYPE_NEW, Status::SUCCESS, clientCert);
   auto issuedCert = ca.issueCertificate(certRequest);
 
   ClientModule client(m_keyChain);
diff --git a/tests/unit-tests/ca-sqlite.t.cpp b/tests/unit-tests/ca-sqlite.t.cpp
index aa70f3a..467ddb3 100644
--- a/tests/unit-tests/ca-sqlite.t.cpp
+++ b/tests/unit-tests/ca-sqlite.t.cpp
@@ -81,30 +81,30 @@
   auto cert1 = key1.getDefaultCertificate();
 
   // add operation
-  CertificateRequest request1(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, cert1);
+  CertificateRequest request1(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, cert1);
   BOOST_CHECK_NO_THROW(storage.addRequest(request1));
 
   // get operation
   auto result = storage.getRequest("123");
   BOOST_CHECK_EQUAL(request1.m_cert, result.m_cert);
-  BOOST_CHECK_EQUAL(request1.m_status, result.m_status);
+  BOOST_CHECK(request1.m_status == result.m_status);
   BOOST_CHECK_EQUAL(request1.m_caPrefix, result.m_caPrefix);
 
   // update operation
   JsonSection json;
   json.put("test", "4567");
-  CertificateRequest request2(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_CHALLENGE, CHALLENGE_STATUS_SUCCESS,
+  CertificateRequest request2(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::CHALLENGE, CHALLENGE_STATUS_SUCCESS,
                              "Email", time::toIsoString(time::system_clock::now()), 3600, 3, json, cert1);
   storage.updateRequest(request2);
   result = storage.getRequest("123");
   BOOST_CHECK_EQUAL(request2.m_cert, result.m_cert);
-  BOOST_CHECK_EQUAL(request2.m_status, result.m_status);
+  BOOST_CHECK(request2.m_status == result.m_status);
   BOOST_CHECK_EQUAL(request2.m_caPrefix, result.m_caPrefix);
 
   auto identity2 = addIdentity(Name("/ndn/site2"));
   auto key2 = identity2.getDefaultKey();
   auto cert2 = key2.getDefaultCertificate();
-  CertificateRequest request3(Name("/ndn/site2"), "456", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, cert2);
+  CertificateRequest request3(Name("/ndn/site2"), "456", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, cert2);
   storage.addRequest(request3);
 
   // list operation
diff --git a/tests/unit-tests/challenge-credential.t.cpp b/tests/unit-tests/challenge-credential.t.cpp
index 7b101d7..e600e20 100644
--- a/tests/unit-tests/challenge-credential.t.cpp
+++ b/tests/unit-tests/challenge-credential.t.cpp
@@ -55,7 +55,7 @@
   auto identityA = addIdentity(Name("/example"));
   auto keyA = identityA.getDefaultKey();
   auto certA = key.getDefaultCertificate();
-  CertificateRequest request(Name("/example"), "123", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, certA);
+  CertificateRequest request(Name("/example"), "123", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, certA);
 
   // create requester's existing cert
   auto identityB = addIdentity(Name("/trust/cert"));
@@ -96,7 +96,7 @@
   params.encode();
 
   challenge.handleChallengeRequest(params, request);
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_PENDING);
+  BOOST_CHECK(request.m_status == Status::PENDING);
   BOOST_CHECK_EQUAL(request.m_challengeStatus, CHALLENGE_STATUS_SUCCESS);
 }
 
diff --git a/tests/unit-tests/challenge-email.t.cpp b/tests/unit-tests/challenge-email.t.cpp
index 50e30c5..4beb6b4 100644
--- a/tests/unit-tests/challenge-email.t.cpp
+++ b/tests/unit-tests/challenge-email.t.cpp
@@ -45,7 +45,7 @@
   auto identity = addIdentity(Name("/ndn/site1"));
   auto key = identity.getDefaultKey();
   auto cert = key.getDefaultCertificate();
-  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, cert);
+  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, cert);
 
   Block paramTLV = makeEmptyBlock(tlv_encrypted_payload);
   paramTLV.push_back(makeStringBlock(tlv_parameter_key, ChallengeEmail::JSON_EMAIL));
@@ -54,7 +54,7 @@
   ChallengeEmail challenge("./tests/unit-tests/test-send-email.sh");
   challenge.handleChallengeRequest(paramTLV, request);
 
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_CHALLENGE);
+  BOOST_CHECK(request.m_status == Status::CHALLENGE);
   BOOST_CHECK_EQUAL(request.m_challengeStatus, ChallengeEmail::NEED_CODE);
   BOOST_CHECK(request.m_challengeSecrets.get<std::string>(ChallengeEmail::JSON_CODE) != "");
   BOOST_CHECK(request.m_remainingTime != 0);
@@ -95,7 +95,7 @@
   auto identity = addIdentity(Name("/ndn/site1"));
   auto key = identity.getDefaultKey();
   auto cert = key.getDefaultCertificate();
-  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, cert);
+  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, cert);
 
   Block paramTLV = makeEmptyBlock(tlv_encrypted_payload);
   paramTLV.push_back(makeStringBlock(tlv_parameter_key, ChallengeEmail::JSON_EMAIL));
@@ -105,7 +105,7 @@
   challenge.handleChallengeRequest(paramTLV, request);
 
   BOOST_CHECK_EQUAL(request.m_challengeStatus, ChallengeEmail::FAILURE_INVALID_EMAIL);
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_FAILURE);
+  BOOST_CHECK(request.m_status == Status::FAILURE);
 }
 
 BOOST_AUTO_TEST_CASE(OnChallengeRequestWithCode)
@@ -115,7 +115,7 @@
   auto cert = key.getDefaultCertificate();
   JsonSection json;
   json.put(ChallengeEmail::JSON_CODE, "4567");
-  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_CHALLENGE, ChallengeEmail::NEED_CODE,
+  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::CHALLENGE, ChallengeEmail::NEED_CODE,
                              "Email", time::toIsoString(time::system_clock::now()), 3600, 3, json, cert);
 
   Block paramTLV = makeEmptyBlock(tlv_encrypted_payload);
@@ -126,7 +126,7 @@
   challenge.handleChallengeRequest(paramTLV, request);
 
   BOOST_CHECK_EQUAL(request.m_challengeStatus, CHALLENGE_STATUS_SUCCESS);
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_PENDING);
+  BOOST_CHECK(request.m_status == Status::PENDING);
   BOOST_CHECK_EQUAL(request.m_challengeSecrets.empty(), true);
 }
 
@@ -137,7 +137,7 @@
   auto cert = key.getDefaultCertificate();
   JsonSection json;
   json.put(ChallengeEmail::JSON_CODE, "4567");
-  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_CHALLENGE, ChallengeEmail::NEED_CODE,
+  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::CHALLENGE, ChallengeEmail::NEED_CODE,
                              "email", time::toIsoString(time::system_clock::now()), 3600, 3, json, cert);
 
   Block paramTLV = makeEmptyBlock(tlv_encrypted_payload);
@@ -148,7 +148,7 @@
   challenge.handleChallengeRequest(paramTLV, request);
 
   BOOST_CHECK_EQUAL(request.m_challengeStatus, ChallengeEmail::WRONG_CODE);
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_CHALLENGE);
+  BOOST_CHECK(request.m_status == Status::CHALLENGE);
   BOOST_CHECK_EQUAL(request.m_challengeSecrets.empty(), false);
 }
 
diff --git a/tests/unit-tests/challenge-pin.t.cpp b/tests/unit-tests/challenge-pin.t.cpp
index 9cabf38..ef0a572 100644
--- a/tests/unit-tests/challenge-pin.t.cpp
+++ b/tests/unit-tests/challenge-pin.t.cpp
@@ -38,12 +38,12 @@
   auto identity = addIdentity(Name("/ndn/site1"));
   auto key = identity.getDefaultKey();
   auto cert = key.getDefaultCertificate();
-  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_BEFORE_CHALLENGE, cert);
+  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::BEFORE_CHALLENGE, cert);
 
   ChallengePin challenge;
   challenge.handleChallengeRequest(makeEmptyBlock(tlv_encrypted_payload), request);
 
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_CHALLENGE);
+  BOOST_CHECK(request.m_status == Status::CHALLENGE);
   BOOST_CHECK_EQUAL(request.m_challengeStatus, ChallengePin::NEED_CODE);
   BOOST_CHECK_EQUAL(request.m_challengeType, "pin");
 }
@@ -55,7 +55,7 @@
   auto cert = key.getDefaultCertificate();
   JsonSection secret;
   secret.add(ChallengePin::JSON_PIN_CODE, "12345");
-  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_CHALLENGE, ChallengePin::NEED_CODE, "pin",
+  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::CHALLENGE, ChallengePin::NEED_CODE, "pin",
                              time::toIsoString(time::system_clock::now()), 3600, 3, secret, cert);
 
   Block paramTLV = makeEmptyBlock(tlv_encrypted_payload);
@@ -65,7 +65,7 @@
   ChallengePin challenge;
   challenge.handleChallengeRequest(paramTLV, request);
 
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_PENDING);
+  BOOST_CHECK(request.m_status == Status::PENDING);
   BOOST_CHECK_EQUAL(request.m_challengeStatus, CHALLENGE_STATUS_SUCCESS);
   BOOST_CHECK_EQUAL(request.m_challengeSecrets.empty(), true);
 }
@@ -77,7 +77,7 @@
   auto cert = key.getDefaultCertificate();
   JsonSection secret;
   secret.add(ChallengePin::JSON_PIN_CODE, "12345");
-  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, STATUS_CHALLENGE, ChallengePin::NEED_CODE, "pin",
+  CertificateRequest request(Name("/ndn/site1"), "123", REQUEST_TYPE_NEW, Status::CHALLENGE, ChallengePin::NEED_CODE, "pin",
                              time::toIsoString(time::system_clock::now()), 3600, 3, secret, cert);
 
   Block paramTLV = makeEmptyBlock(tlv_encrypted_payload);
@@ -87,7 +87,7 @@
   ChallengePin challenge;
   challenge.handleChallengeRequest(paramTLV, request);
 
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_CHALLENGE);
+  BOOST_CHECK(request.m_status == Status::CHALLENGE);
   BOOST_CHECK_EQUAL(request.m_challengeStatus, ChallengePin::WRONG_CODE);
   BOOST_CHECK_EQUAL(request.m_challengeSecrets.empty(), false);
 }
diff --git a/tests/unit-tests/challenge-private-key.t.cpp b/tests/unit-tests/challenge-private-key.t.cpp
index 6c26d41..20eceaa 100644
--- a/tests/unit-tests/challenge-private-key.t.cpp
+++ b/tests/unit-tests/challenge-private-key.t.cpp
@@ -38,7 +38,7 @@
   auto identityA = addIdentity(Name("/example"));
   auto keyA = identityA.getDefaultKey();
   auto certA = keyA.getDefaultCertificate();
-  CertificateRequest request(Name("/example"), "123", REQUEST_TYPE_REVOKE, STATUS_BEFORE_CHALLENGE, certA);
+  CertificateRequest request(Name("/example"), "123", REQUEST_TYPE_REVOKE, Status::BEFORE_CHALLENGE, certA);
 
   security::v2::Certificate privateKeyProof;
   privateKeyProof.setName(Name(keyA.getName()).append("proof-of-private-key").appendVersion());
@@ -64,7 +64,7 @@
   params.encode();
 
   challenge.handleChallengeRequest(params, request);
-  BOOST_CHECK_EQUAL(request.m_status, STATUS_PENDING);
+  BOOST_CHECK(request.m_status == Status::PENDING);
   BOOST_CHECK_EQUAL(request.m_challengeStatus, CHALLENGE_STATUS_SUCCESS);
 }
 
diff --git a/tools/ndncert-ca-server.cpp b/tools/ndncert-ca-server.cpp
index 10d6a6f..82f7c70 100644
--- a/tools/ndncert-ca-server.cpp
+++ b/tools/ndncert-ca-server.cpp
@@ -83,7 +83,7 @@
 
   if (wantRepoOut) {
       ca.setStatusUpdateCallback([&] (const CertificateRequest& request) {
-          if (request.m_status == STATUS_SUCCESS && request.m_requestType == REQUEST_TYPE_NEW) {
+          if (request.m_status == Status::SUCCESS && request.m_requestType == REQUEST_TYPE_NEW) {
             auto issuedCert = request.m_cert;
             boost::asio::ip::tcp::iostream requestStream;
 #if BOOST_VERSION >= 106700
diff --git a/tools/ndncert-ca-status.cpp b/tools/ndncert-ca-status.cpp
index ecfc9c6..cf1c862 100644
--- a/tools/ndncert-ca-status.cpp
+++ b/tools/ndncert-ca-status.cpp
@@ -77,7 +77,7 @@
   for (const auto& entry : requestList) {
     std::cerr << "Request ID: " << entry.m_requestId << "\t"
               << "Request Type" << entry.m_requestType << "\t"
-              << "Current Status: " << entry.m_status << std::endl
+              << "Current Status: " << statusToString(entry.m_status) << std::endl
               << "Applying CA: " << entry.m_caPrefix << std::endl
               << "Applying for key: " << entry.m_cert.getName() << std::endl
               << "Challenge remaining tries: " << entry.m_remainingTries << std::endl
diff --git a/tools/ndncert-client.cpp b/tools/ndncert-client.cpp
index 0073521..52d0fdb 100644
--- a/tools/ndncert-client.cpp
+++ b/tools/ndncert-client.cpp
@@ -18,23 +18,23 @@
  * See AUTHORS.md for complete list of ndncert authors and contributors.
  */
 
-#include "challenge-module.hpp"
-#include "protocol-detail/info.hpp"
-#include "client-module.hpp"
-#include <iostream>
-#include <string>
-
 #include <boost/asio.hpp>
 #include <boost/program_options/options_description.hpp>
 #include <boost/program_options/parsers.hpp>
 #include <boost/program_options/variables_map.hpp>
-
+#include <iostream>
 #include <ndn-cxx/security/verification-helpers.hpp>
+#include <string>
+
+#include "challenge-module.hpp"
+#include "client-module.hpp"
+#include "protocol-detail/info.hpp"
 
 namespace ndn {
 namespace ndncert {
 
-static void startApplication();
+static void
+startApplication();
 
 int nStep;
 Face face;
@@ -127,7 +127,7 @@
 challengeCb(const Data& reply)
 {
   client.onChallengeResponse(reply);
-  if (client.getApplicationStatus() == STATUS_SUCCESS) {
+  if (client.getApplicationStatus() == Status::SUCCESS) {
     std::cerr << "DONE! Certificate has already been issued \n";
     face.expressInterest(*client.generateCertFetchInterest(), bind(&certFetchCb, _2),
                          bind(&onNackCb), bind(&timeoutCb));
@@ -149,8 +149,8 @@
     }
   }
   face.expressInterest(*client.generateChallengeInterest(challenge->genChallengeRequestTLV(client.getApplicationStatus(),
-                                                                                            client.getChallengeStatus(),
-                                                                                            requirement)),
+                                                                                           client.getChallengeStatus(),
+                                                                                           requirement)),
                        bind(&challengeCb, _2), bind(&onNackCb), bind(&timeoutCb));
 }
 
@@ -169,7 +169,7 @@
     std::cerr << "Step " << nStep++ << ": Please type in the challenge index that you want to perform\n";
     count = 0;
     for (auto item : challengeList) {
-      std::cerr << "\t" << count++ << " : "<< item << std::endl;
+      std::cerr << "\t" << count++ << " : " << item << std::endl;
     }
     getline(std::cin, choice);
     try {
@@ -208,8 +208,8 @@
     }
   }
   face.expressInterest(*client.generateChallengeInterest(challenge->genChallengeRequestTLV(client.getApplicationStatus(),
-                                                                                            client.getChallengeStatus(),
-                                                                                            requirement)),
+                                                                                           client.getChallengeStatus(),
+                                                                                           requirement)),
                        bind(&challengeCb, _2), bind(&onNackCb), bind(&timeoutCb));
 }
 
@@ -378,11 +378,8 @@
   namespace po = boost::program_options;
   std::string configFilePath = std::string(SYSCONFDIR) + "/ndncert/client.conf";
   po::options_description description("General Usage\n ndncert-client [-h] [-c] [-v]\n");
-  description.add_options()
-    ("help,h", "produce help message")
-    ("config-file,c",     po::value<std::string>(&configFilePath), "configuration file name")
-    ("validity-period,v", po::value<int>(&validityPeriod)->default_value(-1),
-                          "desired validity period (hours) of the certificate being requested");
+  description.add_options()("help,h", "produce help message")("config-file,c", po::value<std::string>(&configFilePath), "configuration file name")("validity-period,v", po::value<int>(&validityPeriod)->default_value(-1),
+                                                                                                                                                   "desired validity period (hours) of the certificate being requested");
   po::positional_options_description p;
 
   po::variables_map vm;
@@ -410,10 +407,11 @@
   return 0;
 }
 
-} // namespace ndncert
-} // namespace ndn
+}  // namespace ndncert
+}  // namespace ndn
 
-int main(int argc, char* argv[])
+int
+main(int argc, char* argv[])
 {
   return ndn::ndncert::main(argc, argv);
 }