diff options
author | Tor Brede Vekterli <vekterli@oath.com> | 2018-03-23 16:50:16 +0100 |
---|---|---|
committer | GitHub <noreply@github.com> | 2018-03-23 16:50:16 +0100 |
commit | 182feefa361e6c939aa72d896af6270f8dd64038 (patch) | |
tree | b46835d0402178c3574b8556cdb4de3f7981dc54 /storage | |
parent | ab83d23a88154dbacd62cc7203a72aa501d1a33d (diff) | |
parent | ca284490120ff726fd1e86910aaa14626b91b4e7 (diff) |
Merge pull request #5410 from vespa-engine/geirst/extend-cluster-state-transition-logging
Extend logging of cluster state transition to include derived bucket …
Diffstat (limited to 'storage')
-rw-r--r-- | storage/src/vespa/storage/storageserver/statemanager.cpp | 91 |
1 files changed, 82 insertions, 9 deletions
diff --git a/storage/src/vespa/storage/storageserver/statemanager.cpp b/storage/src/vespa/storage/storageserver/statemanager.cpp index 0efae3c5f8f..e643350aa65 100644 --- a/storage/src/vespa/storage/storageserver/statemanager.cpp +++ b/storage/src/vespa/storage/storageserver/statemanager.cpp @@ -2,26 +2,30 @@ #include "statemanager.h" #include <vespa/defaults.h> -#include <fstream> +#include <vespa/document/bucket/fixed_bucket_spaces.h> #include <vespa/metrics/jsonwriter.h> #include <vespa/metrics/metricmanager.h> +#include <vespa/storage/common/bucketoperationlogger.h> #include <vespa/storage/config/config-stor-server.h> -#include <vespa/storageapi/messageapi/storagemessage.h> #include <vespa/storage/storageserver/storagemetricsset.h> -#include <vespa/storage/common/bucketoperationlogger.h> +#include <vespa/storageapi/messageapi/storagemessage.h> #include <vespa/vdslib/state/cluster_state_bundle.h> -#include <sys/types.h> -#include <unistd.h> -#include <vespa/vespalib/util/stringfmt.h> -#include <vespa/vespalib/util/exceptions.h> #include <vespa/vespalib/io/fileutil.h> #include <vespa/vespalib/stllike/asciistream.h> +#include <vespa/vespalib/util/exceptions.h> +#include <vespa/vespalib/util/stringfmt.h> + +#include <fstream> +#include <sys/types.h> +#include <unistd.h> #include <vespa/log/log.h> LOG_SETUP(".state.manager"); namespace storage { +using lib::ClusterStateBundle; + StateManager::StateManager(StorageComponentRegister& compReg, metrics::MetricManager& metricManager, std::unique_ptr<HostInfo> hostInfo, @@ -352,6 +356,73 @@ StateManager::enableNextClusterState() _systemStateHistory.emplace_back(_component.getClock().getTimeInMillis(), _systemState); } +namespace { + +using BucketSpaceToTransitionString = std::unordered_map<document::BucketSpace, + vespalib::string, + document::BucketSpace::hash>; + +void +considerInsertDerivedTransition(const lib::State ¤tBaseline, + const lib::State &newBaseline, + const lib::State ¤tDerived, + const lib::State &newDerived, + const document::BucketSpace &bucketSpace, + BucketSpaceToTransitionString &transitions) +{ + bool considerDerivedTransition = ((currentDerived != newDerived) && + ((currentDerived != currentBaseline) || (newDerived != newBaseline))); + if (considerDerivedTransition && (transitions.find(bucketSpace) == transitions.end())) { + transitions[bucketSpace] = vespalib::make_string("%s space: '%s' to '%s'", + document::FixedBucketSpaces::to_string(bucketSpace).c_str(), + currentDerived.getName().c_str(), + newDerived.getName().c_str()); + } +} + +BucketSpaceToTransitionString +calculateDerivedClusterStateTransitions(const ClusterStateBundle ¤tState, + const ClusterStateBundle &newState, + const lib::Node node) +{ + BucketSpaceToTransitionString result; + const lib::State ¤tBaseline = currentState.getBaselineClusterState()->getNodeState(node).getState(); + const lib::State &newBaseline = newState.getBaselineClusterState()->getNodeState(node).getState(); + for (const auto &entry : currentState.getDerivedClusterStates()) { + const lib::State ¤tDerived = entry.second->getNodeState(node).getState(); + const lib::State &newDerived = newState.getDerivedClusterState(entry.first)->getNodeState(node).getState(); + considerInsertDerivedTransition(currentBaseline, newBaseline, currentDerived, newDerived, entry.first, result); + } + for (const auto &entry : newState.getDerivedClusterStates()) { + const lib::State &newDerived = entry.second->getNodeState(node).getState(); + const lib::State ¤tDerived = currentState.getDerivedClusterState(entry.first)->getNodeState(node).getState(); + considerInsertDerivedTransition(currentBaseline, newBaseline, currentDerived, newDerived, entry.first, result); + } + return result; +} + +vespalib::string +transitionsToString(const BucketSpaceToTransitionString &transitions) +{ + if (transitions.empty()) { + return ""; + } + vespalib::asciistream stream; + stream << "["; + bool first = true; + for (const auto &entry : transitions) { + if (!first) { + stream << ", "; + } + stream << entry.second; + first = false; + } + stream << "] "; + return stream.str(); +} + +} + void StateManager::logNodeClusterStateTransition( const ClusterStateBundle& currentState, @@ -360,11 +431,13 @@ StateManager::logNodeClusterStateTransition( lib::Node self(thisNode()); const lib::State& before(currentState.getBaselineClusterState()->getNodeState(self).getState()); const lib::State& after(newState.getBaselineClusterState()->getNodeState(self).getState()); - if (before != after) { - LOG(info, "Transitioning from state '%s' to '%s' " + auto derivedTransitions = calculateDerivedClusterStateTransitions(currentState, newState, self); + if ((before != after) || !derivedTransitions.empty()) { + LOG(info, "Transitioning from baseline state '%s' to '%s' %s" "(cluster state version %u)", before.getName().c_str(), after.getName().c_str(), + transitionsToString(derivedTransitions).c_str(), newState.getVersion()); } } |