diff --git a/bmcweb.service.in b/bmcweb.service.in
index 644ecca..fdb023b 100644
--- a/bmcweb.service.in
+++ b/bmcweb.service.in
@@ -5,6 +5,7 @@
 After=network.target
 
 [Service]
+ExecReload=kill -s HUP $MAINPID
 ExecStart=@CMAKE_INSTALL_PREFIX@/bin/bmcweb
 Type=simple
 WorkingDirectory=/home/root
diff --git a/crow/include/crow/app.h b/crow/include/crow/app.h
index 95bbaed..4bdf9ff 100644
--- a/crow/include/crow/app.h
+++ b/crow/include/crow/app.h
@@ -99,12 +99,12 @@
         if (-1 == socketFd)
         {
             sslServer = std::move(std::make_unique<ssl_server_t>(
-                this, bindaddrStr, portUint, &middlewares, &sslContext, io));
+                this, bindaddrStr, portUint, sslContext, &middlewares, io));
         }
         else
         {
             sslServer = std::move(std::make_unique<ssl_server_t>(
-                this, socketFd, &middlewares, &sslContext, io));
+                this, socketFd, sslContext, &middlewares, io));
         }
         sslServer->setTickFunction(tickInterval, tickFunction);
         sslServer->run();
@@ -114,12 +114,12 @@
         if (-1 == socketFd)
         {
             server = std::move(std::make_unique<server_t>(
-                this, bindaddrStr, portUint, &middlewares, nullptr, io));
+                this, bindaddrStr, portUint, nullptr, &middlewares, io));
         }
         else
         {
             server = std::move(std::make_unique<server_t>(
-                this, socketFd, &middlewares, nullptr, io));
+                this, socketFd, nullptr, &middlewares, io));
         }
         server->setTickFunction(tickInterval, tickFunction);
         server->run();
@@ -153,36 +153,42 @@
     self_t& sslFile(const std::string& crt_filename,
                     const std::string& key_filename)
     {
-        sslContext.set_verify_mode(boost::asio::ssl::verify_peer);
-        sslContext.use_certificate_file(crt_filename, ssl_context_t::pem);
-        sslContext.use_private_key_file(key_filename, ssl_context_t::pem);
-        sslContext.set_options(boost::asio::ssl::context::default_workarounds |
-                               boost::asio::ssl::context::no_sslv2 |
-                               boost::asio::ssl::context::no_sslv3 |
-                               boost::asio::ssl::context::no_tlsv1 |
-                               boost::asio::ssl::context::no_tlsv1_1);
+        sslContext = std::make_shared<ssl_context_t>(
+            boost::asio::ssl::context::tls_server);
+        sslContext->set_verify_mode(boost::asio::ssl::verify_peer);
+        sslContext->use_certificate_file(crt_filename, ssl_context_t::pem);
+        sslContext->use_private_key_file(key_filename, ssl_context_t::pem);
+        sslContext->set_options(boost::asio::ssl::context::default_workarounds |
+                                boost::asio::ssl::context::no_sslv2 |
+                                boost::asio::ssl::context::no_sslv3 |
+                                boost::asio::ssl::context::no_tlsv1 |
+                                boost::asio::ssl::context::no_tlsv1_1);
         return *this;
     }
 
     self_t& sslFile(const std::string& pem_filename)
     {
-        sslContext.set_verify_mode(boost::asio::ssl::verify_peer);
-        sslContext.load_verify_file(pem_filename);
-        sslContext.set_options(boost::asio::ssl::context::default_workarounds |
-                               boost::asio::ssl::context::no_sslv2 |
-                               boost::asio::ssl::context::no_sslv3 |
-                               boost::asio::ssl::context::no_tlsv1 |
-                               boost::asio::ssl::context::no_tlsv1_1);
+        sslContext = std::make_shared<ssl_context_t>(
+            boost::asio::ssl::context::tls_server);
+        sslContext->set_verify_mode(boost::asio::ssl::verify_peer);
+        sslContext->load_verify_file(pem_filename);
+        sslContext->set_options(boost::asio::ssl::context::default_workarounds |
+                                boost::asio::ssl::context::no_sslv2 |
+                                boost::asio::ssl::context::no_sslv3 |
+                                boost::asio::ssl::context::no_tlsv1 |
+                                boost::asio::ssl::context::no_tlsv1_1);
         return *this;
     }
 
-    self_t& ssl(boost::asio::ssl::context&& ctx)
+    self_t& ssl(std::shared_ptr<boost::asio::ssl::context>&& ctx)
     {
         sslContext = std::move(ctx);
+        BMCWEB_LOG_INFO << "app::ssl context use_count="
+                        << sslContext.use_count();
         return *this;
     }
 
-    ssl_context_t sslContext{boost::asio::ssl::context::tls_server};
+    std::shared_ptr<ssl_context_t> sslContext = nullptr;
 
 #else
     template <typename T, typename... Remain> self_t& ssl_file(T&&, Remain&&...)
diff --git a/crow/include/crow/http_server.h b/crow/include/crow/http_server.h
index 36bab51..d8a258f 100644
--- a/crow/include/crow/http_server.h
+++ b/crow/include/crow/http_server.h
@@ -15,8 +15,10 @@
 #include <boost/date_time/posix_time/posix_time.hpp>
 #include <chrono>
 #include <cstdint>
+#include <filesystem>
 #include <future>
 #include <memory>
+#include <ssl_key_handler.hpp>
 #include <utility>
 #include <vector>
 
@@ -35,39 +37,39 @@
 {
   public:
     Server(Handler* handler, std::unique_ptr<tcp::acceptor>&& acceptor,
+           std::shared_ptr<boost::asio::ssl::context>& adaptor_ctx,
            std::tuple<Middlewares...>* middlewares = nullptr,
-           boost::asio::ssl::context* adaptor_ctx = nullptr,
            std::shared_ptr<boost::asio::io_context> io =
                std::make_shared<boost::asio::io_context>()) :
         ioService(std::move(io)),
-        acceptor(std::move(acceptor)), signals(*ioService, SIGINT, SIGTERM),
-        tickTimer(*ioService), handler(handler), middlewares(middlewares),
-        adaptorCtx(adaptor_ctx)
+        acceptor(std::move(acceptor)),
+        signals(*ioService, SIGINT, SIGTERM, SIGHUP), tickTimer(*ioService),
+        handler(handler), adaptorCtx(adaptor_ctx), middlewares(middlewares)
     {
     }
 
     Server(Handler* handler, const std::string& bindaddr, uint16_t port,
+           std::shared_ptr<boost::asio::ssl::context>& adaptor_ctx,
            std::tuple<Middlewares...>* middlewares = nullptr,
-           boost::asio::ssl::context* adaptor_ctx = nullptr,
            std::shared_ptr<boost::asio::io_context> io =
                std::make_shared<boost::asio::io_context>()) :
         Server(handler,
                std::make_unique<tcp::acceptor>(
                    *io, tcp::endpoint(boost::asio::ip::make_address(bindaddr),
                                       port)),
-               middlewares, adaptor_ctx, io)
+               adaptor_ctx, middlewares, io)
     {
     }
 
     Server(Handler* handler, int existing_socket,
+           std::shared_ptr<boost::asio::ssl::context>& adaptor_ctx,
            std::tuple<Middlewares...>* middlewares = nullptr,
-           boost::asio::ssl::context* adaptor_ctx = nullptr,
            std::shared_ptr<boost::asio::io_context> io =
                std::make_shared<boost::asio::io_context>()) :
         Server(handler,
                std::make_unique<tcp::acceptor>(*io, boost::asio::ip::tcp::v6(),
                                                existing_socket),
-               middlewares, adaptor_ctx, io)
+               adaptor_ctx, middlewares, io)
     {
     }
 
@@ -109,6 +111,7 @@
 
     void run()
     {
+        loadCertificate();
         updateDateStr();
 
         getCachedDateStr = [this]() -> std::string {
@@ -153,13 +156,63 @@
 
         BMCWEB_LOG_INFO << serverName << " server is running, local endpoint "
                         << acceptor->local_endpoint();
-
-        signals.async_wait([&](const boost::system::error_code& /*error*/,
-                               int /*signal_number*/) { stop(); });
-
+        startAsyncWaitForSignal();
         doAccept();
     }
 
+    void loadCertificate()
+    {
+#ifdef BMCWEB_ENABLE_SSL
+        namespace fs = std::filesystem;
+        // Cleanup older certificate file existing in the system
+        fs::path oldCert = "/home/root/server.pem";
+        if (fs::exists(oldCert))
+        {
+            fs::remove("/home/root/server.pem");
+        }
+        fs::path certPath = "/etc/ssl/certs/https/";
+        // if path does not exist create the path so that
+        // self signed certificate can be created in the
+        // path
+        if (!fs::exists(certPath))
+        {
+            fs::create_directories(certPath);
+        }
+        fs::path certFile = certPath / "server.pem";
+        BMCWEB_LOG_INFO << "Building SSL Context file=" << certFile;
+        std::string sslPemFile(certFile);
+        ensuressl::ensureOpensslKeyPresentAndValid(sslPemFile);
+        std::shared_ptr<boost::asio::ssl::context> sslContext =
+            ensuressl::getSslContext(sslPemFile);
+        adaptorCtx = sslContext;
+        handler->ssl(std::move(sslContext));
+#endif
+    }
+
+    void startAsyncWaitForSignal()
+    {
+        signals.async_wait([this](const boost::system::error_code& ec,
+                                  int signalNo) {
+            if (ec)
+            {
+                BMCWEB_LOG_INFO << "Error in signal handler" << ec.message();
+            }
+            else
+            {
+                if (signalNo == SIGHUP)
+                {
+                    BMCWEB_LOG_INFO << "Receivied reload signal";
+                    loadCertificate();
+                    this->startAsyncWaitForSignal();
+                }
+                else
+                {
+                    stop();
+                }
+            }
+        });
+    }
+
     void stop()
     {
         ioService->stop();
@@ -240,6 +293,6 @@
 #ifdef BMCWEB_ENABLE_SSL
     bool useSsl{false};
 #endif
-    boost::asio::ssl::context* adaptorCtx;
+    std::shared_ptr<boost::asio::ssl::context> adaptorCtx;
 }; // namespace crow
 } // namespace crow
diff --git a/include/ssl_key_handler.hpp b/include/ssl_key_handler.hpp
index e309d70..2b67661 100644
--- a/include/ssl_key_handler.hpp
+++ b/include/ssl_key_handler.hpp
@@ -279,28 +279,30 @@
     }
 }
 
-inline boost::asio::ssl::context getSslContext(const std::string &ssl_pem_file)
+inline std::shared_ptr<boost::asio::ssl::context>
+    getSslContext(const std::string &ssl_pem_file)
 {
-    boost::asio::ssl::context mSslContext{
-        boost::asio::ssl::context::tls_server};
-    mSslContext.set_options(boost::asio::ssl::context::default_workarounds |
-                            boost::asio::ssl::context::no_sslv2 |
-                            boost::asio::ssl::context::no_sslv3 |
-                            boost::asio::ssl::context::single_dh_use |
-                            boost::asio::ssl::context::no_tlsv1 |
-                            boost::asio::ssl::context::no_tlsv1_1);
+    std::shared_ptr<boost::asio::ssl::context> mSslContext =
+        std::make_shared<boost::asio::ssl::context>(
+            boost::asio::ssl::context::tls_server);
+    mSslContext->set_options(boost::asio::ssl::context::default_workarounds |
+                             boost::asio::ssl::context::no_sslv2 |
+                             boost::asio::ssl::context::no_sslv3 |
+                             boost::asio::ssl::context::single_dh_use |
+                             boost::asio::ssl::context::no_tlsv1 |
+                             boost::asio::ssl::context::no_tlsv1_1);
 
     // m_ssl_context.set_verify_mode(boost::asio::ssl::verify_peer);
-    mSslContext.use_certificate_file(ssl_pem_file,
-                                     boost::asio::ssl::context::pem);
-    mSslContext.use_private_key_file(ssl_pem_file,
-                                     boost::asio::ssl::context::pem);
+    mSslContext->use_certificate_file(ssl_pem_file,
+                                      boost::asio::ssl::context::pem);
+    mSslContext->use_private_key_file(ssl_pem_file,
+                                      boost::asio::ssl::context::pem);
 
     // Set up EC curves to auto (boost asio doesn't have a method for this)
     // There is a pull request to add this.  Once this is included in an asio
     // drop, use the right way
     // http://stackoverflow.com/questions/18929049/boost-asio-with-ecdsa-certificate-issue
-    if (SSL_CTX_set_ecdh_auto(mSslContext.native_handle(), 1) != 1)
+    if (SSL_CTX_set_ecdh_auto(mSslContext->native_handle(), 1) != 1)
     {
         BMCWEB_LOG_ERROR << "Error setting tmp ecdh list\n";
     }
@@ -316,7 +318,7 @@
                                 "ECDHE-ECDSA-AES128-SHA256:"
                                 "ECDHE-RSA-AES128-SHA256";
 
-    if (SSL_CTX_set_cipher_list(mSslContext.native_handle(),
+    if (SSL_CTX_set_cipher_list(mSslContext->native_handle(),
                                 mozillaModern.c_str()) != 1)
     {
         BMCWEB_LOG_ERROR << "Error setting cipher list\n";
diff --git a/redfish-core/include/redfish.hpp b/redfish-core/include/redfish.hpp
index 91578f1..9edffa9 100644
--- a/redfish-core/include/redfish.hpp
+++ b/redfish-core/include/redfish.hpp
@@ -16,6 +16,7 @@
 #pragma once
 
 #include "../lib/account_service.hpp"
+#include "../lib/certificate_service.hpp"
 #include "../lib/chassis.hpp"
 #include "../lib/cpudimm.hpp"
 #include "../lib/ethernet.hpp"
@@ -115,7 +116,12 @@
         nodes.emplace_back(std::make_unique<BaseMessageRegistry>(app));
         nodes.emplace_back(std::make_unique<OpenBMCMessageRegistryFile>(app));
         nodes.emplace_back(std::make_unique<OpenBMCMessageRegistry>(app));
-
+        nodes.emplace_back(std::make_unique<CertificateService>(app));
+        nodes.emplace_back(
+            std::make_unique<CertificateActionsReplaceCertificate>(app));
+        nodes.emplace_back(std::make_unique<CertificateLocations>(app));
+        nodes.emplace_back(std::make_unique<HTTPSCertificateCollection>(app));
+        nodes.emplace_back(std::make_unique<HTTPSCertificate>(app));
         for (const auto& node : nodes)
         {
             node->initPrivileges();
diff --git a/redfish-core/lib/certificate_service.hpp b/redfish-core/lib/certificate_service.hpp
new file mode 100644
index 0000000..8045e4e
--- /dev/null
+++ b/redfish-core/lib/certificate_service.hpp
@@ -0,0 +1,804 @@
+/*
+// Copyright (c) 2018 IBM Corporation
+//
+// Licensed under the Apache License, Version 2.0 (the "License");
+// you may not use this file except in compliance with the License.
+// You may obtain a copy of the License at
+//
+//      http://www.apache.org/licenses/LICENSE-2.0
+//
+// Unless required by applicable law or agreed to in writing, software
+// distributed under the License is distributed on an "AS IS" BASIS,
+// WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+// See the License for the specific language governing permissions and
+// limitations under the License.
+*/
+#pragma once
+
+#include "node.hpp"
+
+#include <variant>
+namespace redfish
+{
+namespace certs
+{
+constexpr char const *httpsObjectPath =
+    "/xyz/openbmc_project/certs/server/https";
+constexpr char const *certInstallIntf = "xyz.openbmc_project.Certs.Install";
+constexpr char const *certReplaceIntf = "xyz.openbmc_project.Certs.Replace";
+constexpr char const *certPropIntf = "xyz.openbmc_project.Certs.Certificate";
+constexpr char const *dbusPropIntf = "org.freedesktop.DBus.Properties";
+constexpr char const *dbusObjManagerIntf = "org.freedesktop.DBus.ObjectManager";
+constexpr char const *mapperBusName = "xyz.openbmc_project.ObjectMapper";
+constexpr char const *mapperObjectPath = "/xyz/openbmc_project/object_mapper";
+constexpr char const *mapperIntf = "xyz.openbmc_project.ObjectMapper";
+} // namespace certs
+
+/**
+ * The Certificate schema defines a Certificate Service which represents the
+ * actions available to manage certificates and links to where certificates
+ * are installed.
+ */
+class CertificateService : public Node
+{
+  public:
+    CertificateService(CrowApp &app) :
+        Node(app, "/redfish/v1/CertificateService/")
+    {
+        // TODO: Issue#61 No entries are available for Certificate
+        // sevice at https://www.dmtf.org/standards/redfish
+        // "redfish standard registries". Need to modify after DMTF
+        // publish Privilege details for certificate service
+        entityPrivileges = {
+            {boost::beast::http::verb::get, {{"Login"}}},
+            {boost::beast::http::verb::head, {{"Login"}}},
+            {boost::beast::http::verb::patch, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::put, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::delete_, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::post, {{"ConfigureComponents"}}}};
+    }
+
+  private:
+    void doGet(crow::Response &res, const crow::Request &req,
+               const std::vector<std::string> &params) override
+    {
+        res.jsonValue = {
+            {"@odata.type", "#CertificateService.v1_0_0.CertificateService"},
+            {"@odata.id", "/redfish/v1/CertificateService"},
+            {"@odata.context",
+             "/redfish/v1/$metadata#CertificateService.CertificateService"},
+            {"Id", "CertificateService"},
+            {"Name", "Certificate Service"},
+            {"Description", "Actions available to manage certificates"}};
+        res.jsonValue["CertificateLocations"] = {
+            {"@odata.id",
+             "/redfish/v1/CertificateService/CertificateLocations"}};
+        res.jsonValue["Actions"]["#CertificateService.ReplaceCertificate"] = {
+            {"target", "/redfish/v1/CertificateService/Actions/"
+                       "CertificateService.ReplaceCertificate"},
+            {"CertificateType@Redfish.AllowableValues", {"PEM"}}};
+        res.end();
+    }
+}; // CertificateService
+/**
+ * @brief Find the ID specified in the URL
+ * Finds the numbers specified after the last "/" in the URL and returns.
+ * @param[in] path URL
+ * @return -1 on failure and number on success
+ */
+long getIDFromURL(const std::string_view url)
+{
+    std::size_t found = url.rfind("/");
+    if (found == std::string::npos)
+    {
+        return -1;
+    }
+    if ((found + 1) < url.length())
+    {
+        char *endPtr;
+        std::string_view str = url.substr(found + 1);
+        long value = std::strtol(str.data(), &endPtr, 10);
+        if (endPtr != &str.back())
+        {
+            return -1;
+        }
+        return value;
+    }
+    return -1;
+}
+
+/**
+ * Class to create a temporary certificate file for uploading to system
+ */
+class CertificateFile
+{
+  public:
+    CertificateFile() = delete;
+    CertificateFile(const CertificateFile &) = delete;
+    CertificateFile &operator=(const CertificateFile &) = delete;
+    CertificateFile(CertificateFile &&) = delete;
+    CertificateFile &operator=(CertificateFile &&) = delete;
+    CertificateFile(const std::string &certString)
+    {
+        char dirTemplate[] = "/tmp/Certs.XXXXXX";
+        char *tempDirectory = mkdtemp(dirTemplate);
+        if (tempDirectory)
+        {
+            certDirectory = tempDirectory;
+            certificateFile = certDirectory / "cert.pem";
+            std::ofstream out(certificateFile, std::ofstream::out |
+                                                   std::ofstream::binary |
+                                                   std::ofstream::trunc);
+            out << certString;
+            out.close();
+            BMCWEB_LOG_DEBUG << "Creating certificate file" << certificateFile;
+        }
+    }
+    ~CertificateFile()
+    {
+        if (std::filesystem::exists(certDirectory))
+        {
+            BMCWEB_LOG_DEBUG << "Removing certificate file" << certificateFile;
+            try
+            {
+                std::filesystem::remove_all(certDirectory);
+            }
+            catch (const std::filesystem::filesystem_error &e)
+            {
+                BMCWEB_LOG_ERROR << "Failed to remove temp directory"
+                                 << certDirectory;
+            }
+        }
+    }
+    std::string getCertFilePath()
+    {
+        return certificateFile;
+    }
+
+  private:
+    std::filesystem::path certificateFile;
+    std::filesystem::path certDirectory;
+};
+
+/**
+ * @brief Parse and update Certficate Issue/Subject property
+ *
+ * @param[in] asyncResp Shared pointer to the response message
+ * @param[in] str  Issuer/Subject value in key=value pairs
+ * @param[in] type Issuer/Subject
+ * @return None
+ */
+static void updateCertIssuerOrSubject(nlohmann::json &out,
+                                      const std::string_view value)
+{
+    // example: O=openbmc-project.xyz,CN=localhost
+    std::string_view::iterator i = value.begin();
+    while (i != value.end())
+    {
+        std::string_view::iterator tokenBegin = i;
+        while (i != value.end() && *i != '=')
+        {
+            i++;
+        }
+        if (i == value.end())
+        {
+            break;
+        }
+        const std::string_view key(tokenBegin, i - tokenBegin);
+        i++;
+        tokenBegin = i;
+        while (i != value.end() && *i != ',')
+        {
+            i++;
+        }
+        const std::string_view val(tokenBegin, i - tokenBegin);
+        if (key == "L")
+        {
+            out["City"] = val;
+        }
+        else if (key == "CN")
+        {
+            out["CommonName"] = val;
+        }
+        else if (key == "C")
+        {
+            out["Country"] = val;
+        }
+        else if (key == "O")
+        {
+            out["Organization"] = val;
+        }
+        else if (key == "OU")
+        {
+            out["OrganizationalUnit"] = val;
+        }
+        else if (key == "ST")
+        {
+            out["State"] = val;
+        }
+        // skip comma character
+        if (i != value.end())
+        {
+            i++;
+        }
+    }
+}
+
+/**
+ * @brief Retrieve the certificates properties and append to the response
+ * message
+ *
+ * @param[in] asyncResp Shared pointer to the response message
+ * @param[in] objectPath  Path of the D-Bus service object
+ * @param[in] certId  Id of the certificate
+ * @param[in] certURL  URL of the certificate object
+ * @param[in] name  name of the certificate
+ * @return None
+ */
+static void getCertificateProperties(
+    const std::shared_ptr<AsyncResp> &asyncResp, const std::string &objectPath,
+    long certId, const std::string &certURL, const std::string &name)
+{
+    using PropertyType =
+        std::variant<std::string, uint64_t, std::vector<std::string>>;
+    using PropertiesMap = boost::container::flat_map<std::string, PropertyType>;
+    BMCWEB_LOG_DEBUG << "getCertificateProperties Path=" << objectPath
+                     << " certId=" << certId << " certURl=" << certURL;
+    crow::connections::systemBus->async_method_call(
+        [asyncResp, objectPath, certURL, certId,
+         name](const boost::system::error_code ec, const GetObjectType &resp) {
+            if (ec)
+            {
+                BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                messages::internalError(asyncResp->res);
+                return;
+            }
+            if (resp.size() > 1 || resp.empty())
+            {
+                BMCWEB_LOG_ERROR << "Invalid number of objects found "
+                                 << resp.size();
+                messages::internalError(asyncResp->res);
+                return;
+            }
+            const std::string &service = resp.begin()->first;
+            crow::connections::systemBus->async_method_call(
+                [asyncResp, certURL, certId,
+                 name](const boost::system::error_code ec,
+                       const PropertiesMap &properties) {
+                    if (ec)
+                    {
+                        BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                        messages::internalError(asyncResp->res);
+                        return;
+                    }
+                    asyncResp->res.jsonValue = {
+                        {"@odata.id", certURL},
+                        {"@odata.type", "#Certificate.v1_0_0.Certificate"},
+                        {"@odata.context",
+                         "/redfish/v1/$metadata#Certificate.Certificate"},
+                        {"Id", std::to_string(certId)},
+                        {"Name", name},
+                        {"Description", name}};
+                    for (const auto &property : properties)
+                    {
+                        if (property.first == "CertificateString")
+                        {
+                            asyncResp->res.jsonValue["CertificateString"] = "";
+                            const std::string *value =
+                                std::get_if<std::string>(&property.second);
+                            if (value)
+                            {
+                                asyncResp->res.jsonValue["CertificateString"] =
+                                    *value;
+                            }
+                        }
+                        else if (property.first == "KeyUsage")
+                        {
+                            nlohmann::json &keyUsage =
+                                asyncResp->res.jsonValue["KeyUsage"];
+                            keyUsage = nlohmann::json::array();
+                            const std::vector<std::string> *value =
+                                std::get_if<std::vector<std::string>>(
+                                    &property.second);
+                            if (value)
+                            {
+                                for (const std::string &usage : *value)
+                                {
+                                    keyUsage.push_back(usage);
+                                }
+                            }
+                        }
+                        else if (property.first == "Issuer")
+                        {
+                            const std::string *value =
+                                std::get_if<std::string>(&property.second);
+                            if (value)
+                            {
+                                updateCertIssuerOrSubject(
+                                    asyncResp->res.jsonValue["Issuer"], *value);
+                            }
+                        }
+                        else if (property.first == "Subject")
+                        {
+                            const std::string *value =
+                                std::get_if<std::string>(&property.second);
+                            if (value)
+                            {
+                                updateCertIssuerOrSubject(
+                                    asyncResp->res.jsonValue["Subject"],
+                                    *value);
+                            }
+                        }
+                        else if (property.first == "ValidNotAfter")
+                        {
+                            const uint64_t *value =
+                                std::get_if<uint64_t>(&property.second);
+                            if (value)
+                            {
+                                std::time_t time =
+                                    static_cast<std::time_t>(*value);
+                                asyncResp->res.jsonValue["ValidNotAfter"] =
+                                    crow::utility::getDateTime(time);
+                            }
+                        }
+                        else if (property.first == "ValidNotBefore")
+                        {
+                            const uint64_t *value =
+                                std::get_if<uint64_t>(&property.second);
+                            if (value)
+                            {
+                                std::time_t time =
+                                    static_cast<std::time_t>(*value);
+                                asyncResp->res.jsonValue["ValidNotBefore"] =
+                                    crow::utility::getDateTime(time);
+                            }
+                        }
+                    }
+                    asyncResp->res.addHeader("Location", certURL);
+                },
+                service, objectPath, certs::dbusPropIntf, "GetAll",
+                certs::certPropIntf);
+        },
+        certs::mapperBusName, certs::mapperObjectPath, certs::mapperIntf,
+        "GetObject", objectPath,
+        std::array<const char *, 1>{certs::certPropIntf});
+}
+
+using GetObjectType =
+    std::vector<std::pair<std::string, std::vector<std::string>>>;
+
+/**
+ * Action to replace an existing certificate
+ */
+class CertificateActionsReplaceCertificate : public Node
+{
+  public:
+    CertificateActionsReplaceCertificate(CrowApp &app) :
+        Node(app, "/redfish/v1/CertificateService/Actions/"
+                  "CertificateService.ReplaceCertificate/")
+    {
+        entityPrivileges = {
+            {boost::beast::http::verb::get, {{"Login"}}},
+            {boost::beast::http::verb::head, {{"Login"}}},
+            {boost::beast::http::verb::patch, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::put, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::delete_, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::post, {{"ConfigureComponents"}}}};
+    }
+
+  private:
+    void doPost(crow::Response &res, const crow::Request &req,
+                const std::vector<std::string> &params) override
+    {
+        std::string certificate;
+        nlohmann::json certificateUri;
+        std::optional<std::string> certificateType = "PEM";
+        auto asyncResp = std::make_shared<AsyncResp>(res);
+        if (!json_util::readJson(req, asyncResp->res, "CertificateString",
+                                 certificate, "CertificateUri", certificateUri,
+                                 "CertificateType", certificateType))
+        {
+            BMCWEB_LOG_ERROR << "Required parameters are missing";
+            messages::internalError(asyncResp->res);
+            return;
+        }
+
+        if (!certificateType)
+        {
+            // should never happen, but it never hurts to be paranoid.
+            return;
+        }
+        if (certificateType != "PEM")
+        {
+            messages::actionParameterNotSupported(
+                asyncResp->res, "CertificateType", "ReplaceCertificate");
+            return;
+        }
+
+        std::string certURI;
+        if (!redfish::json_util::readJson(certificateUri, asyncResp->res,
+                                          "@odata.id", certURI))
+        {
+            messages::actionParameterMissing(
+                asyncResp->res, "ReplaceCertificate", "CertificateUri");
+            return;
+        }
+
+        if (!boost::starts_with(
+                certURI,
+                "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/Certificates/"))
+        {
+            BMCWEB_LOG_ERROR << "Unsupported certificate URI" << certURI;
+            messages::actionParameterValueFormatError(asyncResp->res, certURI,
+                                                      "CertificateUri",
+                                                      "ReplaceCertificate");
+            return;
+        }
+
+        BMCWEB_LOG_INFO << "Certificate URI to replace" << certURI;
+        long id = getIDFromURL(certURI);
+        if (id < 0)
+        {
+            messages::actionParameterValueFormatError(asyncResp->res, certURI,
+                                                      "CertificateUri",
+                                                      "ReplaceCertificate");
+            return;
+        }
+        std::string objectPath;
+        std::string name;
+        if (boost::starts_with(
+                certURI,
+                "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/Certificates/"))
+        {
+            objectPath =
+                std::string(certs::httpsObjectPath) + "/" + std::to_string(id);
+            name = "HTTPS certificate";
+        }
+        else
+        {
+            messages::actionParameterNotSupported(
+                asyncResp->res, "CertificateUri", "ReplaceCertificate");
+            return;
+        }
+
+        std::shared_ptr<CertificateFile> certFile =
+            std::make_shared<CertificateFile>(certificate);
+
+        crow::connections::systemBus->async_method_call(
+            [asyncResp, objectPath, certFile, id, certURI, name](
+                const boost::system::error_code ec, const GetObjectType &resp) {
+                if (ec)
+                {
+                    BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                    messages::internalError(asyncResp->res);
+                    return;
+                }
+                if (resp.size() > 1 || resp.empty())
+                {
+                    BMCWEB_LOG_ERROR << "Invalid number of objects found "
+                                     << resp.size();
+                    messages::internalError(asyncResp->res);
+                    return;
+                }
+                const std::string &service = resp.begin()->first;
+                crow::connections::systemBus->async_method_call(
+                    [asyncResp, certFile, objectPath, certURI, id,
+                     name](const boost::system::error_code ec) {
+                        if (ec)
+                        {
+                            BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                            messages::internalError(asyncResp->res);
+                            return;
+                        }
+                        getCertificateProperties(asyncResp, objectPath, id,
+                                                 certURI, name);
+                        BMCWEB_LOG_DEBUG << "HTTPS certificate install file="
+                                         << certFile->getCertFilePath();
+                    },
+                    service, objectPath, certs::certReplaceIntf, "Replace",
+                    certFile->getCertFilePath());
+            },
+            certs::mapperBusName, certs::mapperObjectPath, certs::mapperIntf,
+            "GetObject", objectPath,
+            std::array<std::string, 1>({certs::certReplaceIntf}));
+    }
+}; // CertificateActionsReplaceCertificate
+
+/**
+ * Certificate resource describes a certificate used to prove the identity
+ * of a component, account or service.
+ */
+class HTTPSCertificate : public Node
+{
+  public:
+    template <typename CrowApp>
+    HTTPSCertificate(CrowApp &app) :
+        Node(app,
+             "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/Certificates/"
+             "<str>/",
+             std::string())
+    {
+        entityPrivileges = {
+            {boost::beast::http::verb::get, {{"Login"}}},
+            {boost::beast::http::verb::head, {{"Login"}}},
+            {boost::beast::http::verb::patch, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::put, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::delete_, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::post, {{"ConfigureComponents"}}}};
+    }
+
+    void doGet(crow::Response &res, const crow::Request &req,
+               const std::vector<std::string> &params) override
+    {
+        auto asyncResp = std::make_shared<AsyncResp>(res);
+        if (params.size() != 1)
+        {
+            messages::internalError(asyncResp->res);
+            return;
+        }
+        long id = getIDFromURL(req.url);
+
+        BMCWEB_LOG_DEBUG << "HTTPSCertificate::doGet ID=" << std::to_string(id);
+        std::string certURL =
+            "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/Certificates/" +
+            std::to_string(id);
+        std::string objectPath = certs::httpsObjectPath;
+        objectPath += "/";
+        objectPath += std::to_string(id);
+        getCertificateProperties(asyncResp, objectPath, id, certURL,
+                                 "HTTPS Certificate");
+    }
+
+}; // namespace redfish
+
+/**
+ * Collection of HTTPS certificates
+ */
+class HTTPSCertificateCollection : public Node
+{
+  public:
+    template <typename CrowApp>
+    HTTPSCertificateCollection(CrowApp &app) :
+        Node(app,
+             "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/Certificates/")
+    {
+        entityPrivileges = {
+            {boost::beast::http::verb::get, {{"Login"}}},
+            {boost::beast::http::verb::head, {{"Login"}}},
+            {boost::beast::http::verb::patch, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::put, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::delete_, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::post, {{"ConfigureComponents"}}}};
+    }
+    void doGet(crow::Response &res, const crow::Request &req,
+               const std::vector<std::string> &params) override
+    {
+        res.jsonValue = {
+            {"@odata.id",
+             "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/Certificates"},
+            {"@odata.type", "#CertificateCollection.CertificateCollection"},
+            {"@odata.context",
+             "/redfish/v1/"
+             "$metadata#CertificateCollection.CertificateCollection"},
+            {"Name", "HTTPS Certificates Collection"},
+            {"Description", "A Collection of HTTPS certificate instances"}};
+        auto asyncResp = std::make_shared<AsyncResp>(res);
+        crow::connections::systemBus->async_method_call(
+            [asyncResp](const boost::system::error_code ec,
+                        const GetObjectType &resp) {
+                if (ec)
+                {
+                    BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                    messages::internalError(asyncResp->res);
+                    return;
+                }
+                if (resp.size() > 1 || resp.empty())
+                {
+                    BMCWEB_LOG_ERROR << "Invalid number of objects found "
+                                     << resp.size();
+                    messages::internalError(asyncResp->res);
+                    return;
+                }
+                const std::string &service = resp.begin()->first;
+                crow::connections::systemBus->async_method_call(
+                    [asyncResp](const boost::system::error_code ec,
+                                const ManagedObjectType &certs) {
+                        if (ec)
+                        {
+                            BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                            messages::internalError(asyncResp->res);
+                            return;
+                        }
+                        nlohmann::json &members =
+                            asyncResp->res.jsonValue["Members"];
+                        members = nlohmann::json::array();
+                        for (const auto &cert : certs)
+                        {
+                            long id = getIDFromURL(cert.first.str);
+                            if (id != -1)
+                            {
+                                members.push_back(
+                                    {{"@odata.id",
+                                      "/redfish/v1/Managers/bmc/"
+                                      "NetworkProtocol/HTTPS/Certificates/" +
+                                          std::to_string(id)}});
+                            }
+                        }
+                        asyncResp->res.jsonValue["Members@odata.count"] =
+                            members.size();
+                    },
+                    service, certs::httpsObjectPath, certs::dbusObjManagerIntf,
+                    "GetManagedObjects");
+            },
+            certs::mapperBusName, certs::mapperObjectPath, certs::mapperIntf,
+            "GetObject", certs::httpsObjectPath,
+            std::array<const char *, 1>{certs::certInstallIntf});
+    }
+
+    void doPost(crow::Response &res, const crow::Request &req,
+                const std::vector<std::string> &params) override
+    {
+        BMCWEB_LOG_DEBUG << "HTTPSCertificateCollection::doPost";
+        auto asyncResp = std::make_shared<AsyncResp>(res);
+        asyncResp->res.jsonValue = {{"Name", "HTTPS Certificate"},
+                                    {"Description", "HTTPS Certificate"}};
+
+        std::shared_ptr<CertificateFile> certFile =
+            std::make_shared<CertificateFile>(req.body);
+
+        crow::connections::systemBus->async_method_call(
+            [asyncResp, certFile](const boost::system::error_code ec,
+                                  const GetObjectType &resp) {
+                if (ec)
+                {
+                    BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                    messages::internalError(asyncResp->res);
+                    return;
+                }
+                if (resp.size() > 1 || resp.empty())
+                {
+                    BMCWEB_LOG_ERROR << "Invalid number of objects found "
+                                     << resp.size();
+                    messages::internalError(asyncResp->res);
+                    return;
+                }
+                const std::string &service = resp.begin()->first;
+                crow::connections::systemBus->async_method_call(
+                    [asyncResp, certFile](const boost::system::error_code ec) {
+                        if (ec)
+                        {
+                            BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                            messages::internalError(asyncResp->res);
+                            return;
+                        }
+                        // TODO: Issue#84 supporting only 1 certificate
+                        long certId = 1;
+                        std::string certURL =
+                            "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/"
+                            "Certificates/" +
+                            std::to_string(certId);
+                        std::string objectPath =
+                            std::string(certs::httpsObjectPath) + "/" +
+                            std::to_string(certId);
+                        getCertificateProperties(asyncResp, objectPath, certId,
+                                                 certURL, "HTTPS Certificate");
+                        BMCWEB_LOG_DEBUG << "HTTPS certificate install file="
+                                         << certFile->getCertFilePath();
+                    },
+                    service, certs::httpsObjectPath, certs::certInstallIntf,
+                    "Install", certFile->getCertFilePath());
+            },
+            certs::mapperBusName, certs::mapperObjectPath, certs::mapperIntf,
+            "GetObject", certs::httpsObjectPath,
+            std::array<const char *, 1>{certs::certInstallIntf});
+    }
+}; // HTTPSCertificateCollection
+
+/**
+ * @brief Retrieve the certificates installed list and append to the response
+ *
+ * @param[in] asyncResp Shared pointer to the response message
+ * @param[in] certURL  Path of the certificate object
+ * @param[in] path  Path of the D-Bus service object
+ * @return None
+ */
+static void getCertificateLocations(std::shared_ptr<AsyncResp> &asyncResp,
+                                    const std::string &certURL,
+                                    const std::string &path)
+{
+    BMCWEB_LOG_DEBUG << "getCertificateLocations URI=" << certURL
+                     << " Path=" << path;
+    crow::connections::systemBus->async_method_call(
+        [asyncResp, path, certURL](const boost::system::error_code ec,
+                                   const GetObjectType &resp) {
+            if (ec)
+            {
+                BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                messages::internalError(asyncResp->res);
+                return;
+            }
+            if (resp.size() > 1 || resp.empty())
+            {
+                BMCWEB_LOG_ERROR << "Invalid number of objects found "
+                                 << resp.size();
+                messages::internalError(asyncResp->res);
+                return;
+            }
+            const std::string &service = resp.begin()->first;
+            crow::connections::systemBus->async_method_call(
+                [asyncResp, certURL](const boost::system::error_code ec,
+                                     const ManagedObjectType &certs) {
+                    if (ec)
+                    {
+                        BMCWEB_LOG_ERROR << "DBUS response error: " << ec;
+                        messages::internalError(asyncResp->res);
+                        return;
+                    }
+                    nlohmann::json &links =
+                        asyncResp->res.jsonValue["Links"]["Certificates"];
+                    for (auto &cert : certs)
+                    {
+                        long id = getIDFromURL(cert.first.str);
+                        if (id != -1)
+                        {
+                            links.push_back(
+                                {{"@odata.id", certURL + std::to_string(id)}});
+                        }
+                    }
+                    asyncResp->res
+                        .jsonValue["Links"]["Certificates@odata.count"] =
+                        links.size();
+                },
+                service, path, certs::dbusObjManagerIntf, "GetManagedObjects");
+        },
+        certs::mapperBusName, certs::mapperObjectPath, certs::mapperIntf,
+        "GetObject", path, std::array<std::string, 0>());
+}
+
+/**
+ * The certificate location schema defines a resource that an administrator
+ * can use in order to locate all certificates installed on a given service.
+ */
+class CertificateLocations : public Node
+{
+  public:
+    template <typename CrowApp>
+    CertificateLocations(CrowApp &app) :
+        Node(app, "/redfish/v1/CertificateService/CertificateLocations/")
+    {
+        entityPrivileges = {
+            {boost::beast::http::verb::get, {{"Login"}}},
+            {boost::beast::http::verb::head, {{"Login"}}},
+            {boost::beast::http::verb::patch, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::put, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::delete_, {{"ConfigureComponents"}}},
+            {boost::beast::http::verb::post, {{"ConfigureComponents"}}}};
+    }
+
+  private:
+    void doGet(crow::Response &res, const crow::Request &req,
+               const std::vector<std::string> &params) override
+    {
+        res.jsonValue = {
+            {"@odata.id",
+             "/redfish/v1/CertificateService/CertificateLocations"},
+            {"@odata.type",
+             "#CertificateLocations.v1_0_0.CertificateLocations"},
+            {"@odata.context",
+             "/redfish/v1/$metadata#CertificateLocations.CertificateLocations"},
+            {"Name", "Certificate Locations"},
+            {"Id", "CertificateLocations"},
+            {"Description",
+             "Defines a resource that an administrator can use in order to "
+             "locate all certificates installed on a given service"}};
+        auto asyncResp = std::make_shared<AsyncResp>(res);
+        nlohmann::json &links =
+            asyncResp->res.jsonValue["Links"]["Certificates"];
+        links = nlohmann::json::array();
+        getCertificateLocations(
+            asyncResp,
+            "/redfish/v1/Managers/bmc/NetworkProtocol/HTTPS/Certificates/",
+            certs::httpsObjectPath);
+    }
+}; // CertificateLocations
+} // namespace redfish
diff --git a/redfish-core/lib/network_protocol.hpp b/redfish-core/lib/network_protocol.hpp
index d24f246..23965fa 100644
--- a/redfish-core/lib/network_protocol.hpp
+++ b/redfish-core/lib/network_protocol.hpp
@@ -234,6 +234,9 @@
                     messages::internalError(asyncResp->res);
                     return;
                 }
+                asyncResp->res.jsonValue["HTTPS"]["Certificates"] = {
+                    {"@odata.id", "/redfish/v1/Managers/bmc/NetworkProtocol/"
+                                  "HTTPS/Certificates/"}};
 
                 for (auto& unit : resp)
                 {
@@ -252,7 +255,6 @@
                              "running") ||
                             (std::get<NET_PROTO_UNIT_SUB_STATE>(unit) ==
                              "listening");
-
                         crow::connections::systemBus->async_method_call(
                             [asyncResp, service{std::string(service)}](
                                 const boost::system::error_code ec,
diff --git a/redfish-core/lib/service_root.hpp b/redfish-core/lib/service_root.hpp
index ad2b2f2..3b9adbf 100644
--- a/redfish-core/lib/service_root.hpp
+++ b/redfish-core/lib/service_root.hpp
@@ -42,7 +42,7 @@
     void doGet(crow::Response& res, const crow::Request& req,
                const std::vector<std::string>& params) override
     {
-        res.jsonValue["@odata.type"] = "#ServiceRoot.v1_1_1.ServiceRoot";
+        res.jsonValue["@odata.type"] = "#ServiceRoot.v1_5_0.ServiceRoot";
         res.jsonValue["@odata.id"] = "/redfish/v1";
         res.jsonValue["@odata.context"] =
             "/redfish/v1/$metadata#ServiceRoot.ServiceRoot";
@@ -65,8 +65,9 @@
 
         res.jsonValue["UpdateService"] = {
             {"@odata.id", "/redfish/v1/UpdateService"}};
-
         res.jsonValue["UUID"] = uuid;
+        res.jsonValue["CertificateService"] = {
+            {"@odata.id", "/redfish/v1/CertificateService"}};
         res.end();
     }
 
diff --git a/src/webserver_main.cpp b/src/webserver_main.cpp
index a4cf582..1c9c1f1 100644
--- a/src/webserver_main.cpp
+++ b/src/webserver_main.cpp
@@ -61,15 +61,6 @@
     auto io = std::make_shared<boost::asio::io_context>();
     CrowApp app(io);
 
-#ifdef BMCWEB_ENABLE_SSL
-    std::string sslPemFile("server.pem");
-    std::cout << "Building SSL Context\n";
-
-    ensuressl::ensureOpensslKeyPresentAndValid(sslPemFile);
-    std::cout << "SSL Enabled\n";
-    auto sslContext = ensuressl::getSslContext(sslPemFile);
-    app.ssl(std::move(sslContext));
-#endif
     // Static assets need to be initialized before Authorization, because auth
     // needs to build the whitelist from the static routes
 
