aboutsummaryrefslogtreecommitdiff
path: root/zenserver/zenserver.cpp
diff options
context:
space:
mode:
authorStefan Boberg <[email protected]>2021-10-21 14:17:18 +0200
committerStefan Boberg <[email protected]>2021-10-21 14:17:18 +0200
commitefd06036c133654a1799f398345fd1bb3cc632b6 (patch)
treedc81e110be0aa8cb025662860843f7f4997f790a /zenserver/zenserver.cpp
parentMerge branch 'main' into gc (diff)
parentzenserver: Tweaked state initialization so we know when we're running for the... (diff)
downloadzen-efd06036c133654a1799f398345fd1bb3cc632b6.tar.xz
zen-efd06036c133654a1799f398345fd1bb3cc632b6.zip
Merged from main
Diffstat (limited to 'zenserver/zenserver.cpp')
-rw-r--r--zenserver/zenserver.cpp184
1 files changed, 110 insertions, 74 deletions
diff --git a/zenserver/zenserver.cpp b/zenserver/zenserver.cpp
index d3a0afaed..c96fec986 100644
--- a/zenserver/zenserver.cpp
+++ b/zenserver/zenserver.cpp
@@ -116,6 +116,7 @@ ZEN_THIRD_PARTY_INCLUDES_END
namespace zen {
using namespace std::literals;
+using namespace fmt::literals;
class ZenServer : public IHttpStatusProvider
{
@@ -160,77 +161,7 @@ public:
throw std::runtime_error("Failed to create mutex '{}' - is another instance already running?"_format(MutexName).c_str());
}
- // Check root manifest to deal with schema versioning
-
- bool WipeState = false;
- std::string WipeReason = "Unspecified";
-
- std::filesystem::path ManifestPath = m_DataRoot / "root_manifest";
- FileContents ManifestData = zen::ReadFile(ManifestPath);
-
- if (ManifestData.ErrorCode)
- {
- WipeState = true;
- WipeReason = "No manifest present at '{}'"_format(ManifestPath);
- }
- else
- {
- IoBuffer Manifest = ManifestData.Flatten();
-
- if (CbValidateError ValidationResult = ValidateCompactBinary(Manifest, CbValidateMode::All);
- ValidationResult != CbValidateError::None)
- {
- ZEN_ERROR("Manifest validation failed: {}, state will be wiped", ValidationResult);
-
- WipeState = true;
- WipeReason = "Validation of manifest at '{}' failed: {}"_format(ManifestPath, ValidationResult);
- }
- else
- {
- m_RootManifest = LoadCompactBinaryObject(Manifest);
-
- const int32_t ManifestVersion = m_RootManifest["schema_version"].AsInt32(0);
-
- if (ManifestVersion != ZEN_SCHEMA_VERSION)
- {
- WipeState = true;
- WipeReason = "Manifest schema version: {}, differs from required: {}"_format(ManifestVersion, ZEN_SCHEMA_VERSION);
- }
- }
- }
-
- // Handle any state wipe
-
- if (WipeState)
- {
- ZEN_WARN("Wiping state at '{}' - reason: '{}'", m_DataRoot, WipeReason);
-
- std::error_code Ec;
- for (const std::filesystem::directory_entry& DirEntry : std::filesystem::directory_iterator{m_DataRoot, Ec})
- {
- if (DirEntry.is_directory())
- {
- ZEN_INFO("Deleting '{}'", DirEntry.path());
-
- std::filesystem::remove_all(DirEntry.path(), Ec);
-
- if (Ec)
- {
- ZEN_WARN("Delete of '{}' returned error: '{}'", DirEntry.path(), Ec.message());
- }
- }
- }
-
- ZEN_INFO("Wiped all directories in data root");
-
- // Write new manifest
-
- CbObjectWriter Cbo;
- Cbo << "schema_version" << ZEN_SCHEMA_VERSION;
- m_RootManifest = Cbo.Save();
-
- WriteFile(ManifestPath, m_RootManifest.GetBuffer().AsIoBuffer());
- }
+ InitializeState(ServiceConfig);
// Ok so now we're configured, let's kick things off
@@ -254,8 +185,8 @@ public:
ZEN_INFO("instantiating project service");
- m_ProjectStore = new zen::ProjectStore(*m_CasStore, m_DataRoot / "projects");
- m_HttpProjectService.reset(new zen::HttpProjectService{*m_CasStore, m_ProjectStore});
+ m_ProjectStore = new zen::ProjectStore(*m_CidStore, m_DataRoot / "projects");
+ m_HttpProjectService.reset(new zen::HttpProjectService{*m_CidStore, m_ProjectStore});
#if ZEN_USE_NAMED_PIPES
m_LocalProjectService = zen::LocalProjectService::New(*m_CasStore, m_ProjectStore);
@@ -329,6 +260,7 @@ public:
}
}
+ void InitializeState(ZenServiceConfig& ServiceConfig);
void InitializeStructuredCache(ZenServiceConfig& ServiceConfig);
#if ZEN_ENABLE_MESH
@@ -341,7 +273,9 @@ public:
void Run()
{
- Scrub();
+ // This is disabled for now, awaiting better scheduling
+ //
+ // Scrub();
if (m_ProcessMonitor.IsActive())
{
@@ -567,6 +501,101 @@ private:
};
void
+ZenServer::InitializeState(ZenServiceConfig& ServiceConfig)
+{
+ // Check root manifest to deal with schema versioning
+
+ bool WipeState = false;
+ std::string WipeReason = "Unspecified";
+
+ bool UpdateManifest = false;
+ std::filesystem::path ManifestPath = m_DataRoot / "root_manifest";
+ FileContents ManifestData = zen::ReadFile(ManifestPath);
+
+ if (ManifestData.ErrorCode)
+ {
+ if (ServiceConfig.IsFirstRun)
+ {
+ ZEN_INFO("Initializing state at '{}'", m_DataRoot);
+
+ UpdateManifest = true;
+ }
+ else
+ {
+ WipeState = true;
+ WipeReason = "No manifest present at '{}'"_format(ManifestPath);
+ }
+ }
+ else
+ {
+ IoBuffer Manifest = ManifestData.Flatten();
+
+ if (CbValidateError ValidationResult = ValidateCompactBinary(Manifest, CbValidateMode::All);
+ ValidationResult != CbValidateError::None)
+ {
+ ZEN_ERROR("Manifest validation failed: {}, state will be wiped", ValidationResult);
+
+ WipeState = true;
+ WipeReason = "Validation of manifest at '{}' failed: {}"_format(ManifestPath, ValidationResult);
+ }
+ else
+ {
+ m_RootManifest = LoadCompactBinaryObject(Manifest);
+
+ const int32_t ManifestVersion = m_RootManifest["schema_version"].AsInt32(0);
+
+ if (ManifestVersion != ZEN_SCHEMA_VERSION)
+ {
+ WipeState = true;
+ WipeReason = "Manifest schema version: {}, differs from required: {}"_format(ManifestVersion, ZEN_SCHEMA_VERSION);
+ }
+ }
+ }
+
+ // Handle any state wipe
+
+ if (WipeState)
+ {
+ ZEN_WARN("Wiping state at '{}' - reason: '{}'", m_DataRoot, WipeReason);
+
+ std::error_code Ec;
+ for (const std::filesystem::directory_entry& DirEntry : std::filesystem::directory_iterator{m_DataRoot, Ec})
+ {
+ if (DirEntry.is_directory() && (DirEntry.path().filename() != "logs"))
+ {
+ ZEN_INFO("Deleting '{}'", DirEntry.path());
+
+ std::filesystem::remove_all(DirEntry.path(), Ec);
+
+ if (Ec)
+ {
+ ZEN_WARN("Delete of '{}' returned error: '{}'", DirEntry.path(), Ec.message());
+ }
+ }
+ }
+
+ ZEN_INFO("Wiped all directories in data root");
+
+ UpdateManifest = true;
+ }
+
+ if (UpdateManifest)
+ {
+ // Write new manifest
+
+ const DateTime Now = DateTime::Now();
+
+ CbObjectWriter Cbo;
+ Cbo << "schema_version" << ZEN_SCHEMA_VERSION << "created" << Now << "updated" << Now << "state_id" << Oid::NewOid();
+ Cbo << m_RootManifest["id"];
+
+ m_RootManifest = Cbo.Save();
+
+ WriteFile(ManifestPath, m_RootManifest.GetBuffer().AsIoBuffer());
+ }
+}
+
+void
ZenServer::InitializeStructuredCache(ZenServiceConfig& ServiceConfig)
{
using namespace std::literals;
@@ -800,6 +829,13 @@ main(int argc, char* argv[])
ZenServerOptions GlobalOptions;
ZenServiceConfig ServiceConfig;
ParseGlobalCliOptions(argc, argv, GlobalOptions, ServiceConfig);
+
+ if (!std::filesystem::exists(GlobalOptions.DataDir))
+ {
+ ServiceConfig.IsFirstRun = true;
+ std::filesystem::create_directories(GlobalOptions.DataDir);
+ }
+
InitializeLogging(GlobalOptions);
#if ZEN_PLATFORM_WINDOWS