diff --git a/arangod/Aql/AstNode.cpp b/arangod/Aql/AstNode.cpp index 91a6b0f58d..c114e9012a 100644 --- a/arangod/Aql/AstNode.cpp +++ b/arangod/Aql/AstNode.cpp @@ -39,6 +39,7 @@ #endif #include +#include #include #include #include diff --git a/arangod/Aql/Collection.cpp b/arangod/Aql/Collection.cpp index 5da350c950..28cc0db2b4 100644 --- a/arangod/Aql/Collection.cpp +++ b/arangod/Aql/Collection.cpp @@ -85,7 +85,7 @@ size_t Collection::count() const { } else { // local case // cache the result - numDocuments = static_cast(collection->_numberDocuments); + numDocuments = static_cast(collection->numberDocuments()); } } diff --git a/arangod/Aql/Functions.cpp b/arangod/Aql/Functions.cpp index 2c75efd892..12ee64c54f 100644 --- a/arangod/Aql/Functions.cpp +++ b/arangod/Aql/Functions.cpp @@ -3350,16 +3350,16 @@ AqlValue Functions::CollectionCount( auto resolver = trx->resolver(); TRI_voc_cid_t cid = resolver->getCollectionIdLocal(collectionName); trx->addCollectionAtRuntime(cid, collectionName); - auto document = trx->documentCollection(cid); + auto collection = trx->documentCollection(cid); - if (document == nullptr) { + if (collection == nullptr) { THROW_ARANGO_EXCEPTION_FORMAT(TRI_ERROR_ARANGO_COLLECTION_NOT_FOUND, "'%s'", collectionName.c_str()); } TransactionBuilderLeaser builder(trx); // TODO Temporary until move to LogicalCollection is complete - builder->add(VPackValue(document->_numberDocuments)); + builder->add(VPackValue(collection->numberDocuments())); return AqlValue(builder.get()); } diff --git a/arangod/Aql/IndexBlock.cpp b/arangod/Aql/IndexBlock.cpp index 7e1f042176..5f0f8fa277 100644 --- a/arangod/Aql/IndexBlock.cpp +++ b/arangod/Aql/IndexBlock.cpp @@ -32,6 +32,7 @@ #include "Basics/StaticStrings.h" #include "Utils/OperationCursor.h" #include "V8/v8-globals.h" +#include "VocBase/MasterPointer.h" #include "VocBase/vocbase.h" #include diff --git a/arangod/Aql/ShortestPathBlock.cpp b/arangod/Aql/ShortestPathBlock.cpp index c6eb437593..97985b0638 100644 --- a/arangod/Aql/ShortestPathBlock.cpp +++ b/arangod/Aql/ShortestPathBlock.cpp @@ -25,10 +25,14 @@ #include "Aql/ExecutionEngine.h" #include "Aql/ExecutionPlan.h" -#include "VocBase/EdgeCollectionInfo.h" #include "Utils/AqlTransaction.h" #include "Utils/OperationCursor.h" #include "Utils/Transaction.h" +#include "VocBase/EdgeCollectionInfo.h" +#include "VocBase/MasterPointer.h" + +#include +#include //////////////////////////////////////////////////////////////////////////////// /// @brief typedef the template instantiation of the PathFinder diff --git a/arangod/Aql/ShortestPathNode.cpp b/arangod/Aql/ShortestPathNode.cpp index 8291d9071f..aca1bf2038 100644 --- a/arangod/Aql/ShortestPathNode.cpp +++ b/arangod/Aql/ShortestPathNode.cpp @@ -31,6 +31,9 @@ #include "Utils/CollectionNameResolver.h" #include "V8Server/V8Traverser.h" +#include +#include + using namespace arangodb::basics; using namespace arangodb::aql; diff --git a/arangod/Aql/TraversalBlock.cpp b/arangod/Aql/TraversalBlock.cpp index 06c48cbb0c..cfb75e6e6c 100644 --- a/arangod/Aql/TraversalBlock.cpp +++ b/arangod/Aql/TraversalBlock.cpp @@ -32,10 +32,12 @@ #include "Cluster/ClusterTraverser.h" #include "Utils/OperationCursor.h" #include "Utils/Transaction.h" -#include "VocBase/SingleServerTraverser.h" #include "V8/v8-globals.h" +#include "VocBase/MasterPointer.h" +#include "VocBase/SingleServerTraverser.h" #include +#include #include using namespace arangodb::aql; diff --git a/arangod/Aql/TraversalNode.cpp b/arangod/Aql/TraversalNode.cpp index f65e78c3a4..8982a0633c 100644 --- a/arangod/Aql/TraversalNode.cpp +++ b/arangod/Aql/TraversalNode.cpp @@ -30,6 +30,9 @@ #include "Aql/TraversalOptions.h" #include "Indexes/Index.h" +#include +#include + using namespace arangodb::basics; using namespace arangodb::aql; diff --git a/arangod/Indexes/FulltextIndex.cpp b/arangod/Indexes/FulltextIndex.cpp index cbb2a484ca..2282c08dc0 100644 --- a/arangod/Indexes/FulltextIndex.cpp +++ b/arangod/Indexes/FulltextIndex.cpp @@ -22,10 +22,11 @@ //////////////////////////////////////////////////////////////////////////////// #include "FulltextIndex.h" -#include "Logger/Logger.h" #include "Basics/StringRef.h" #include "Basics/Utf8Helper.h" +#include "Basics/VelocyPackHelper.h" #include "FulltextIndex/fulltext-index.h" +#include "Logger/Logger.h" #include "VocBase/collection.h" #include "VocBase/transaction.h" diff --git a/arangod/Indexes/GeoIndex.cpp b/arangod/Indexes/GeoIndex.cpp index a6f93978fe..45de2a7e16 100644 --- a/arangod/Indexes/GeoIndex.cpp +++ b/arangod/Indexes/GeoIndex.cpp @@ -24,6 +24,7 @@ #include "GeoIndex.h" #include "Logger/Logger.h" #include "Basics/StringRef.h" +#include "Basics/VelocyPackHelper.h" #include "VocBase/collection.h" #include "VocBase/transaction.h" diff --git a/arangod/Replication/ContinuousSyncer.cpp b/arangod/Replication/ContinuousSyncer.cpp index 3832e613bd..fc08e7042e 100644 --- a/arangod/Replication/ContinuousSyncer.cpp +++ b/arangod/Replication/ContinuousSyncer.cpp @@ -24,6 +24,7 @@ #include "ContinuousSyncer.h" #include "ApplicationFeatures/ApplicationServer.h" #include "Basics/Exceptions.h" +#include "Basics/StaticStrings.h" #include "Basics/StringBuffer.h" #include "Basics/VelocyPackHelper.h" #include "Basics/WriteLocker.h" diff --git a/arangod/Replication/InitialSyncer.cpp b/arangod/Replication/InitialSyncer.cpp index 96a6f8921d..c9cac25cfd 100644 --- a/arangod/Replication/InitialSyncer.cpp +++ b/arangod/Replication/InitialSyncer.cpp @@ -1651,7 +1651,7 @@ int64_t InitialSyncer::getSize(arangodb::LogicalCollection* col) { } auto document = trx.documentCollection(); - return static_cast(document->_numberDocuments); + return static_cast(document->numberDocuments()); } //////////////////////////////////////////////////////////////////////////////// diff --git a/arangod/StorageEngine/MMFilesCleanupThread.cpp b/arangod/StorageEngine/MMFilesCleanupThread.cpp index 2fc9e4fecb..da76c62444 100644 --- a/arangod/StorageEngine/MMFilesCleanupThread.cpp +++ b/arangod/StorageEngine/MMFilesCleanupThread.cpp @@ -152,8 +152,6 @@ void MMFilesCleanupThread::cleanupCollection(arangodb::LogicalCollection* collec // but if we are in server shutdown, we can force unloading of collections bool isInShutdown = application_features::ApplicationServer::isStopping(); - TRI_collection_t* document = collection->_collection; - // loop until done while (true) { @@ -217,7 +215,7 @@ void MMFilesCleanupThread::cleanupCollection(arangodb::LogicalCollection* collec } } - if (!document->isFullyCollected()) { + if (!collection->isFullyCollected()) { bool isDeleted = false; // if there is still some garbage collection to perform, diff --git a/arangod/StorageEngine/MMFilesCompactorThread.cpp b/arangod/StorageEngine/MMFilesCompactorThread.cpp index dd65855462..9b316adfb9 100644 --- a/arangod/StorageEngine/MMFilesCompactorThread.cpp +++ b/arangod/StorageEngine/MMFilesCompactorThread.cpp @@ -597,7 +597,6 @@ bool MMFilesCompactorThread::compactCollection(LogicalCollection* collection, bo // return false; // } - TRI_collection_t* document = collection->_collection; wasBlocked = false; // if we cannot acquire the read lock instantly, we will exit directly. @@ -617,7 +616,7 @@ bool MMFilesCompactorThread::compactCollection(LogicalCollection* collection, bo // we already have created a compactor file in progress. // if this happens, then a previous compaction attempt for this collection // failed or is not finished yet - document->setCompactionStatus(ReasonCompactionBlocked); + collection->setCompactionStatus(ReasonCompactionBlocked); wasBlocked = true; return false; } @@ -627,7 +626,7 @@ bool MMFilesCompactorThread::compactCollection(LogicalCollection* collection, bo if (datafiles.empty()) { // collection has no datafiles - document->setCompactionStatus(ReasonNoDatafiles); + collection->setCompactionStatus(ReasonNoDatafiles); return false; } @@ -638,7 +637,7 @@ bool MMFilesCompactorThread::compactCollection(LogicalCollection* collection, bo size_t const n = datafiles.size(); LOG_TOPIC(DEBUG, Logger::COMPACTOR) << "inspecting datafiles of collection '" << collection->name() << "' for compaction opportunities"; - size_t start = document->getNextCompactionStartIndex(); + size_t start = collection->getNextCompactionStartIndex(); // get number of documents from collection uint64_t const numDocuments = getNumberOfDocuments(collection); @@ -797,10 +796,10 @@ bool MMFilesCompactorThread::compactCollection(LogicalCollection* collection, bo if (toCompact.empty()) { // nothing to compact. now reset start index - document->setNextCompactionStartIndex(0); + collection->setNextCompactionStartIndex(0); // cleanup local variables - document->setCompactionStatus(ReasonNothingToCompact); + collection->setCompactionStatus(ReasonNothingToCompact); LOG_TOPIC(DEBUG, Logger::COMPACTOR) << "inspecting datafiles of collection yielded: " << ReasonNothingToCompact; return false; } @@ -808,9 +807,8 @@ bool MMFilesCompactorThread::compactCollection(LogicalCollection* collection, bo // handle datafiles with dead objects TRI_ASSERT(toCompact.size() >= 1); TRI_ASSERT(reason != nullptr); - document->setCompactionStatus(reason); - - document->setNextCompactionStartIndex(start); + collection->setCompactionStatus(reason); + collection->setNextCompactionStartIndex(start); compactDatafiles(collection, toCompact); return true; @@ -882,7 +880,7 @@ void MMFilesCompactorThread::run() { try { double const now = TRI_microtime(); - if (document->lastCompaction() + compactionCollectionInterval() <= now) { + if (collection->lastCompactionStamp() + compactionCollectionInterval() <= now) { auto ce = collection->ditches()->createCompactionDitch(__FILE__, __LINE__); @@ -896,7 +894,7 @@ void MMFilesCompactorThread::run() { if (!worked && !wasBlocked) { // set compaction stamp - document->lastCompaction(now); + collection->lastCompactionStamp(now); } // if we worked or were blocked, then we don't set the compaction stamp to // force another round of compaction @@ -962,7 +960,7 @@ uint64_t MMFilesCompactorThread::getNumberOfDocuments(LogicalCollection* collect return 16384; // assume some positive value } - return static_cast(collection->_numberDocuments); + return collection->numberDocuments(); } /// @brief write a copy of the marker into the datafile diff --git a/arangod/StorageEngine/MMFilesEngine.cpp b/arangod/StorageEngine/MMFilesEngine.cpp index d74ae4a868..acff68fe57 100644 --- a/arangod/StorageEngine/MMFilesEngine.cpp +++ b/arangod/StorageEngine/MMFilesEngine.cpp @@ -1961,7 +1961,7 @@ int MMFilesEngine::transferMarkersWorker(LogicalCollection* collection, // used only for crash / recovery tests int numMarkers = 0; - TRI_voc_tick_t const minTransferTick = collection->_collection->_tickMax; + TRI_voc_tick_t const minTransferTick = collection->maxTick(); TRI_ASSERT(!operations.empty()); for (auto it2 = operations.begin(); it2 != operations.end(); ++it2) { @@ -2080,8 +2080,8 @@ void MMFilesEngine::finishMarker(char const* walPosition, // update ticks TRI_UpdateTicksDatafile(datafile, marker); - TRI_ASSERT(collection->_collection->_tickMax < tick); - collection->_collection->_tickMax = tick; + TRI_ASSERT(collection->maxTick() < tick); + collection->maxTick(tick); cache->operations->emplace_back(wal::CollectorOperation( datafilePosition, marker->getSize(), walPosition, cache->lastFid)); diff --git a/arangod/Utils/CollectionExport.cpp b/arangod/Utils/CollectionExport.cpp index c1c5bf265f..1091a77591 100644 --- a/arangod/Utils/CollectionExport.cpp +++ b/arangod/Utils/CollectionExport.cpp @@ -90,7 +90,7 @@ void CollectionExport::run(uint64_t maxWaitTime, size_t limit) { uint64_t const maxTries = maxWaitTime / SleepTime; while (++tries < maxTries) { - if (_document->isFullyCollected()) { + if (_collection->isFullyCollected()) { break; } usleep(SleepTime); diff --git a/arangod/Utils/CollectionKeys.cpp b/arangod/Utils/CollectionKeys.cpp index 6cfe1bc0eb..a7c6f68b79 100644 --- a/arangod/Utils/CollectionKeys.cpp +++ b/arangod/Utils/CollectionKeys.cpp @@ -31,8 +31,9 @@ #include "Utils/StandaloneTransactionContext.h" #include "VocBase/DatafileHelper.h" #include "VocBase/Ditch.h" -#include "VocBase/collection.h" #include "VocBase/LogicalCollection.h" +#include "VocBase/MasterPointer.h" +#include "VocBase/collection.h" #include "VocBase/ticks.h" #include "VocBase/vocbase.h" #include "Wal/LogfileManager.h" diff --git a/arangod/Utils/Transaction.cpp b/arangod/Utils/Transaction.cpp index 05c8445243..3fc6ee61e6 100644 --- a/arangod/Utils/Transaction.cpp +++ b/arangod/Utils/Transaction.cpp @@ -2645,7 +2645,7 @@ OperationResult Transaction::countLocal(std::string const& collectionName) { // TODO Temporary until the move to LogicalCollection is completed LogicalCollection* collection = documentCollection(trxCollection(cid)); - uint64_t num = collection->_numberDocuments; + uint64_t num = collection->numberDocuments(); res = unlock(trxCollection(cid), TRI_TRANSACTION_READ); diff --git a/arangod/V8Server/v8-collection.cpp b/arangod/V8Server/v8-collection.cpp index 1edebb8a8b..e2a82803c7 100644 --- a/arangod/V8Server/v8-collection.cpp +++ b/arangod/V8Server/v8-collection.cpp @@ -32,6 +32,7 @@ #include "Basics/StaticStrings.h" #include "Basics/VelocyPackHelper.h" #include "Basics/WriteLocker.h" +#include "Cluster/ClusterInfo.h" #include "Cluster/ClusterMethods.h" #include "Indexes/PrimaryIndex.h" #include "RestServer/DatabaseFeature.h" diff --git a/arangod/V8Server/v8-vocindex.cpp b/arangod/V8Server/v8-vocindex.cpp index 9c27d0b5d0..5346e547be 100644 --- a/arangod/V8Server/v8-vocindex.cpp +++ b/arangod/V8Server/v8-vocindex.cpp @@ -27,6 +27,7 @@ #include "Basics/StringUtils.h" #include "Basics/tri-strings.h" #include "Basics/VelocyPackHelper.h" +#include "Cluster/ClusterInfo.h" #include "Cluster/ClusterMethods.h" #include "FulltextIndex/fulltext-index.h" #include "Indexes/EdgeIndex.h" diff --git a/arangod/VocBase/Ditch.cpp b/arangod/VocBase/Ditch.cpp index f6aee99397..d1d5b394ac 100644 --- a/arangod/VocBase/Ditch.cpp +++ b/arangod/VocBase/Ditch.cpp @@ -24,7 +24,7 @@ #include "Ditch.h" #include "Logger/Logger.h" #include "Basics/MutexLocker.h" -#include "VocBase/collection.h" +#include "VocBase/datafile.h" using namespace arangodb; diff --git a/arangod/VocBase/LogicalCollection.cpp b/arangod/VocBase/LogicalCollection.cpp index 9e7d4d1e70..9b520d3ca3 100644 --- a/arangod/VocBase/LogicalCollection.cpp +++ b/arangod/VocBase/LogicalCollection.cpp @@ -325,9 +325,13 @@ LogicalCollection::LogicalCollection( _masterPointers(), _useSecondaryIndexes(true), _numberDocuments(0), + _maxTick(0), _keyGenerator(), _collection(nullptr), - _lock() { + _nextCompactionStartIndex(0), + _lastCompactionStatus(nullptr), + _lastCompactionStamp(0.0), + _uncollectedLogfileEntries(0) { _keyGenerator.reset(KeyGenerator::factory(other->keyOptions())); @@ -343,6 +347,8 @@ LogicalCollection::LogicalCollection( for (auto const& idx : other->_indexes) { _indexes.emplace_back(idx); } + + setCompactionStatus("compaction not yet started"); } // @brief Constructor used in coordinator case. @@ -384,9 +390,13 @@ LogicalCollection::LogicalCollection(TRI_vocbase_t* vocbase, VPackSlice info) _masterPointers(), _useSecondaryIndexes(true), _numberDocuments(0), + _maxTick(0), _keyGenerator(), _collection(nullptr), - _lock() { + _nextCompactionStartIndex(0), + _lastCompactionStatus(nullptr), + _lastCompactionStamp(0.0), + _uncollectedLogfileEntries(0) { if (!IsAllowedName(info)) { THROW_ARANGO_EXCEPTION(TRI_ERROR_ARANGO_ILLEGAL_NAME); @@ -472,6 +482,8 @@ LogicalCollection::LogicalCollection(TRI_vocbase_t* vocbase, VPackSlice info) if (ServerState::instance()->isDBServer()) { _followers.reset(new FollowerInfo(this)); } + + setCompactionStatus("compaction not yet started"); } LogicalCollection::~LogicalCollection() { @@ -520,6 +532,30 @@ bool LogicalCollection::IsAllowedName(VPackSlice parameters) { return true; } +/// @brief whether or not a collection is fully collected +bool LogicalCollection::isFullyCollected() { + int64_t uncollected = _uncollectedLogfileEntries.load(); + + return (uncollected == 0); +} + +void LogicalCollection::setNextCompactionStartIndex(size_t index) { + MUTEX_LOCKER(mutexLocker, _compactionStatusLock); + _nextCompactionStartIndex = index; +} + +size_t LogicalCollection::getNextCompactionStartIndex() { + MUTEX_LOCKER(mutexLocker, _compactionStatusLock); + return _nextCompactionStartIndex; +} + +void LogicalCollection::setCompactionStatus(char const* reason) { + TRI_ASSERT(reason != nullptr); + + MUTEX_LOCKER(mutexLocker, _compactionStatusLock); + _lastCompactionStatus = reason; +} + size_t LogicalCollection::journalSize() const { return _journalSize; } @@ -970,9 +1006,6 @@ std::shared_ptr LogicalCollection::figures() { auto builder = std::make_shared(); if (ServerState::instance()->isCoordinator()) { - builder->openObject(); - builder->close(); - int res = figuresOnCoordinator(dbName(), cid_as_string(), builder); if (res != TRI_ERROR_NO_ERROR) { @@ -980,9 +1013,7 @@ std::shared_ptr LogicalCollection::figures() { } } else { TRI_ASSERT(_collection != nullptr); - // add figures from TRI_collection_t builder->openObject(); - _collection->figures(builder); // add index information size_t sizeIndexes = _masterPointers.memory(); @@ -997,6 +1028,34 @@ std::shared_ptr LogicalCollection::figures() { builder->add("size", VPackValue(sizeIndexes)); builder->close(); // indexes + builder->add("lastTick", VPackValue(_maxTick)); + builder->add("uncollectedLogfileEntries", VPackValue(_uncollectedLogfileEntries)); + + // fills in compaction status + char const* lastCompactionStatus = "-"; + char lastCompactionStampString[21]; + lastCompactionStampString[0] = '-'; + lastCompactionStampString[1] = '\0'; + + double lastCompactionStamp; + + { + MUTEX_LOCKER(mutexLocker, _compactionStatusLock); + lastCompactionStatus = _lastCompactionStatus; + lastCompactionStamp = _lastCompactionStamp; + } + + if (lastCompactionStatus != nullptr) { + struct tm tb; + time_t tt = static_cast(lastCompactionStamp); + TRI_gmtime(tt, &tb); + strftime(&lastCompactionStampString[0], sizeof(lastCompactionStampString), "%Y-%m-%dT%H:%M:%SZ", &tb); + } + + builder->add("compactionStatus", VPackValue(VPackValueType::Object)); + builder->add("message", VPackValue(lastCompactionStatus)); + builder->add("time", VPackValue(&lastCompactionStampString[0])); + builder->close(); // compactionStatus // add engine-specific figures getPhysical()->figures(builder); @@ -2098,6 +2157,7 @@ int LogicalCollection::remove(arangodb::Transaction* trx, } operation.indexed(); + TRI_ASSERT(_numberDocuments > 0); _numberDocuments--; TRI_IF_FAILURE("RemoveDocumentNoOperation") { return TRI_ERROR_DEBUG; } diff --git a/arangod/VocBase/LogicalCollection.h b/arangod/VocBase/LogicalCollection.h index 4ecea1b744..e6e1b81b2e 100644 --- a/arangod/VocBase/LogicalCollection.h +++ b/arangod/VocBase/LogicalCollection.h @@ -89,6 +89,28 @@ class LogicalCollection { static bool IsAllowedName(arangodb::velocypack::Slice parameters); + // TODO: MOVE TO PHYSICAL? + bool isFullyCollected(); + int64_t uncollectedLogfileEntries() const { return _uncollectedLogfileEntries.load(); } + + void increaseUncollectedLogfileEntries(int64_t value) { + _uncollectedLogfileEntries += value; + } + + void decreaseUncollectedLogfileEntries(int64_t value) { + _uncollectedLogfileEntries -= value; + if (_uncollectedLogfileEntries < 0) { + _uncollectedLogfileEntries = 0; + } + } + + void setNextCompactionStartIndex(size_t); + size_t getNextCompactionStartIndex(); + void setCompactionStatus(char const*); + double lastCompactionStamp() const { return _lastCompactionStamp; } + void lastCompactionStamp(double value) { _lastCompactionStamp = value; } + + // SECTION: Meta Information uint32_t version() const { return _version; @@ -120,6 +142,19 @@ class LogicalCollection { TRI_vocbase_col_status_e tryFetchStatus(bool&); std::string statusString(); + TRI_voc_tick_t maxTick() const { return _maxTick; } + void maxTick(TRI_voc_tick_t value) { _maxTick = value; } + + uint64_t numberDocuments() const { return _numberDocuments; } + + // TODO: REMOVE THESE OR MAKE PRIVATE + void incNumberDocuments() { ++_numberDocuments; } + + void decNumberDocuments() { + TRI_ASSERT(_numberDocuments > 0); + --_numberDocuments; + } + // TODO this should be part of physical collection! size_t journalSize() const; @@ -489,11 +524,10 @@ class LogicalCollection { // whether or not secondary indexes should be filled bool _useSecondaryIndexes; - // FIXME Both of them are not initialized properly! - public: - // FIXME Must be private. OpenIterator uses this. - int64_t _numberDocuments; - private: + uint64_t _numberDocuments; + + TRI_voc_tick_t _maxTick; + std::unique_ptr _keyGenerator; // TODO REMOVE ME! @@ -502,10 +536,20 @@ class LogicalCollection { mutable arangodb::basics::ReadWriteLock _lock; // lock protecting the status and name + + private: mutable arangodb::basics::ReadWriteLock _idxLock; // lock protecting the indexes + mutable arangodb::basics::ReadWriteLock _infoLock; // lock protecting the info + + arangodb::Mutex _compactionStatusLock; + size_t _nextCompactionStartIndex; + char const* _lastCompactionStatus; + double _lastCompactionStamp; + + std::atomic _uncollectedLogfileEntries; }; } // namespace arangodb diff --git a/arangod/VocBase/collection.cpp b/arangod/VocBase/collection.cpp index 42c91ae137..1ea19f1d71 100644 --- a/arangod/VocBase/collection.cpp +++ b/arangod/VocBase/collection.cpp @@ -85,81 +85,10 @@ int TRI_AddOperationTransaction(TRI_transaction_t*, arangodb::wal::DocumentOperation&, bool&); TRI_collection_t::TRI_collection_t(TRI_vocbase_t* vocbase) - : _vocbase(vocbase), - _tickMax(0), - _uncollectedLogfileEntries(0), - _nextCompactionStartIndex(0), - _lastCompactionStatus(nullptr), - _lastCompaction(0.0) { - setCompactionStatus("compaction not yet started"); -} + : _vocbase(vocbase) {} TRI_collection_t::~TRI_collection_t() {} -/// @brief whether or not a collection is fully collected -bool TRI_collection_t::isFullyCollected() { - int64_t uncollected = _uncollectedLogfileEntries.load(); - - return (uncollected == 0); -} - -void TRI_collection_t::setNextCompactionStartIndex(size_t index) { - MUTEX_LOCKER(mutexLocker, _compactionStatusLock); - _nextCompactionStartIndex = index; -} - -size_t TRI_collection_t::getNextCompactionStartIndex() { - MUTEX_LOCKER(mutexLocker, _compactionStatusLock); - return _nextCompactionStartIndex; -} - -void TRI_collection_t::setCompactionStatus(char const* reason) { - TRI_ASSERT(reason != nullptr); - struct tm tb; - time_t tt = time(nullptr); - TRI_gmtime(tt, &tb); - - MUTEX_LOCKER(mutexLocker, _compactionStatusLock); - _lastCompactionStatus = reason; - - strftime(&_lastCompactionStamp[0], sizeof(_lastCompactionStamp), - "%Y-%m-%dT%H:%M:%SZ", &tb); -} - -void TRI_collection_t::getCompactionStatus(char const*& reason, - char* dst, size_t maxSize) { - memset(dst, 0, maxSize); - if (maxSize > sizeof(_lastCompactionStamp)) { - maxSize = sizeof(_lastCompactionStamp); - } - MUTEX_LOCKER(mutexLocker, _compactionStatusLock); - reason = _lastCompactionStatus; - memcpy(dst, &_lastCompactionStamp[0], maxSize); -} - -void TRI_collection_t::figures(std::shared_ptr& builder) { - builder->add("uncollectedLogfileEntries", VPackValue(_uncollectedLogfileEntries)); - builder->add("lastTick", VPackValue(_tickMax)); - - // fills in compaction status - char const* lastCompactionStatus = nullptr; - char lastCompactionStamp[21]; - getCompactionStatus(lastCompactionStatus, - &lastCompactionStamp[0], - sizeof(lastCompactionStamp)); - - if (lastCompactionStatus == nullptr) { - lastCompactionStatus = "-"; - lastCompactionStamp[0] = '-'; - lastCompactionStamp[1] = '\0'; - } - - builder->add("compactionStatus", VPackValue(VPackValueType::Object)); - builder->add("message", VPackValue(lastCompactionStatus)); - builder->add("time", VPackValue(&lastCompactionStamp[0])); - builder->close(); // compactionStatus -} - /// @brief checks if a collection name is allowed /// Returns true if the name is allowed and false otherwise bool TRI_collection_t::IsAllowedName(bool allowSystem, std::string const& name) { @@ -309,7 +238,8 @@ static int OpenIteratorHandleDocumentMarker(TRI_df_marker_t const* marker, return res; } - ++collection->_numberDocuments; + + collection->incNumberDocuments(); // update the datafile info state->_dfi->numberAlive++; @@ -409,8 +339,7 @@ static int OpenIteratorHandleDeletionMarker(TRI_df_marker_t const* marker, state->_dfi->numberDeletions++; collection->deletePrimaryIndex(trx, found); - - --collection->_numberDocuments; + collection->decNumberDocuments(); // free the header collection->_masterPointers.release(found); @@ -422,7 +351,6 @@ static int OpenIteratorHandleDeletionMarker(TRI_df_marker_t const* marker, /// @brief iterator for open static bool OpenIterator(TRI_df_marker_t const* marker, OpenIteratorState* data, TRI_datafile_t* datafile) { - TRI_collection_t* document = data->_document; TRI_voc_tick_t const tick = marker->getTick(); TRI_df_marker_type_t const type = marker->getType(); @@ -459,12 +387,12 @@ static bool OpenIterator(TRI_df_marker_t const* marker, OpenIteratorState* data, datafile->_tickMax = tick; } - if (tick > document->_tickMax) { + if (tick > data->_collection->maxTick()) { if (type != TRI_DF_MARKER_HEADER && type != TRI_DF_MARKER_FOOTER && type != TRI_DF_MARKER_COL_HEADER && type != TRI_DF_MARKER_PROLOGUE) { - document->_tickMax = tick; + data->_collection->maxTick(tick); } } diff --git a/arangod/VocBase/collection.h b/arangod/VocBase/collection.h index 3183fa4138..904a792a45 100644 --- a/arangod/VocBase/collection.h +++ b/arangod/VocBase/collection.h @@ -25,22 +25,8 @@ #define ARANGOD_VOC_BASE_COLLECTION_H 1 #include "Basics/Common.h" -#include "Cluster/ClusterInfo.h" -#include "VocBase/MasterPointer.h" -#include "VocBase/MasterPointers.h" #include "VocBase/vocbase.h" -namespace arangodb { -namespace velocypack { -template -class Buffer; -class Slice; -} -namespace wal { -struct DocumentOperation; -} -} - /// @brief predefined collection name for users #define TRI_COL_NAME_USERS "_users" @@ -64,32 +50,8 @@ struct TRI_collection_t { /// returns true if the name is allowed and false otherwise static bool IsAllowedName(bool isSystem, std::string const& name); - bool isFullyCollected(); - - void setNextCompactionStartIndex(size_t); - size_t getNextCompactionStartIndex(); - void setCompactionStatus(char const*); - void getCompactionStatus(char const*&, char*, size_t); - - void figures(std::shared_ptr& result); - - double lastCompaction() const { return _lastCompaction; } - void lastCompaction(double value) { _lastCompaction = value; } - public: TRI_vocbase_t* _vocbase; - TRI_voc_tick_t _tickMax; - - public: - std::atomic _uncollectedLogfileEntries; - - private: - - arangodb::Mutex _compactionStatusLock; - size_t _nextCompactionStartIndex; - char const* _lastCompactionStatus; - char _lastCompactionStamp[21]; - double _lastCompaction; }; #endif diff --git a/arangod/VocBase/replication-dump.cpp b/arangod/VocBase/replication-dump.cpp index 57e5d09de6..7c45d255b8 100644 --- a/arangod/VocBase/replication-dump.cpp +++ b/arangod/VocBase/replication-dump.cpp @@ -23,6 +23,7 @@ #include "replication-dump.h" #include "Basics/ReadLocker.h" +#include "Basics/StaticStrings.h" #include "Basics/VPackStringBufferAdapter.h" #include "Logger/Logger.h" #include "VocBase/CompactionLocker.h" diff --git a/arangod/VocBase/transaction.cpp b/arangod/VocBase/transaction.cpp index 45063026ae..91878381dd 100644 --- a/arangod/VocBase/transaction.cpp +++ b/arangod/VocBase/transaction.cpp @@ -185,7 +185,6 @@ static void FreeOperations(TRI_transaction_t* trx) { } arangodb::LogicalCollection* collection = trxCollection->_collection; - TRI_collection_t* document = collection->_collection; if (mustRollback) { // revert all operations @@ -236,8 +235,7 @@ static void FreeOperations(TRI_transaction_t* trx) { collection->setRevision(trxCollection->_originalRevision, true); } else if (!collection->isVolatile() && !isSingleOperation) { // only count logfileEntries if the collection is durable - document->_uncollectedLogfileEntries += - trxCollection->_operations->size(); + collection->increaseUncollectedLogfileEntries(trxCollection->_operations->size()); } delete trxCollection->_operations; @@ -1074,8 +1072,7 @@ int TRI_AddOperationTransaction(TRI_transaction_t* trx, arangodb::aql::QueryCache::instance()->invalidate( trx->_vocbase, collection->name()); -// FIXME - ++(collection->_collection->_uncollectedLogfileEntries); + collection->increaseUncollectedLogfileEntries(1); if (operation.type == TRI_VOC_DOCUMENT_OPERATION_UPDATE || operation.type == TRI_VOC_DOCUMENT_OPERATION_REPLACE || diff --git a/arangod/VocBase/vocbase.cpp b/arangod/VocBase/vocbase.cpp index 38ea8423b6..f72cd55379 100644 --- a/arangod/VocBase/vocbase.cpp +++ b/arangod/VocBase/vocbase.cpp @@ -56,6 +56,7 @@ #include "VocBase/Ditch.h" #include "VocBase/collection.h" #include "VocBase/LogicalCollection.h" +#include "VocBase/MasterPointer.h" #include "VocBase/replication-applier.h" #include "VocBase/ticks.h" #include "VocBase/transaction.h" diff --git a/arangod/Wal/CollectorThread.cpp b/arangod/Wal/CollectorThread.cpp index 27b142d57b..2d511a9d7f 100644 --- a/arangod/Wal/CollectorThread.cpp +++ b/arangod/Wal/CollectorThread.cpp @@ -670,10 +670,7 @@ int CollectorThread::processCollectionOperations(CollectorCache* cache) { << collection->name() << "'"; updateDatafileStatistics(collection, cache); - document->_uncollectedLogfileEntries -= cache->totalOperationsCount; - if (document->_uncollectedLogfileEntries < 0) { - document->_uncollectedLogfileEntries = 0; - } + collection->decreaseUncollectedLogfileEntries(cache->totalOperationsCount); res = TRI_ERROR_NO_ERROR; } catch (arangodb::basics::Exception const& ex) { diff --git a/arangod/Wal/DocumentOperation.h b/arangod/Wal/DocumentOperation.h index 16c9f0fe9e..8177c04461 100644 --- a/arangod/Wal/DocumentOperation.h +++ b/arangod/Wal/DocumentOperation.h @@ -4,6 +4,7 @@ #include "Basics/Common.h" #include "VocBase/LogicalCollection.h" +#include "VocBase/MasterPointer.h" #include "VocBase/MasterPointers.h" #include "VocBase/voc-types.h" #include "Wal/Marker.h" diff --git a/arangod/Wal/Marker.h b/arangod/Wal/Marker.h index 1f343c552e..46298980be 100644 --- a/arangod/Wal/Marker.h +++ b/arangod/Wal/Marker.h @@ -30,7 +30,6 @@ #include "VocBase/voc-types.h" #include -#include namespace arangodb { namespace wal { diff --git a/arangod/Wal/RecoverState.cpp b/arangod/Wal/RecoverState.cpp index 0c7fde57d5..7535c1b2cd 100644 --- a/arangod/Wal/RecoverState.cpp +++ b/arangod/Wal/RecoverState.cpp @@ -261,8 +261,8 @@ int RecoverState::executeSingleOperation( return TRI_ERROR_ARANGO_COLLECTION_NOT_FOUND; } - TRI_voc_tick_t tickMax = collection->_collection->_tickMax; - if (marker->getTick() <= tickMax) { + TRI_voc_tick_t maxTick = collection->maxTick(); + if (marker->getTick() <= maxTick) { // already transferred this marker return TRI_ERROR_NO_ERROR; }