From a8c5345a7010e03d6af8a1176f75a1aac8b58df8 Mon Sep 17 00:00:00 2001 From: Henning Baldersheim Date: Tue, 28 Mar 2023 21:05:11 +0200 Subject: Revert "Explore attribute vector in writer thread." --- searchcore/CMakeLists.txt | 1 + .../attribute_manager/attribute_manager_test.cpp | 10 ++++ .../attributes_state_explorer_test.cpp | 4 +- .../exclusive_attribute_read_accessor/.gitignore | 1 + .../CMakeLists.txt | 9 ++++ .../exclusive_attribute_read_accessor_test.cpp | 55 ++++++++++++++++++++ .../searchcore/proton/attribute/CMakeLists.txt | 2 +- .../proton/attribute/attribute_executor.cpp | 34 ------------ .../proton/attribute/attribute_executor.h | 32 ------------ .../attribute/attribute_manager_explorer.cpp | 15 +++--- .../proton/attribute/attribute_vector_explorer.cpp | 15 ++---- .../proton/attribute/attribute_vector_explorer.h | 10 ++-- .../proton/attribute/attributemanager.cpp | 10 ++++ .../searchcore/proton/attribute/attributemanager.h | 2 + .../exclusive_attribute_read_accessor.cpp | 60 ++++++++++++++++++++++ .../attribute/exclusive_attribute_read_accessor.h | 53 +++++++++++++++++++ .../proton/attribute/filter_attribute_manager.cpp | 6 +++ .../proton/attribute/filter_attribute_manager.h | 1 + .../proton/attribute/i_attribute_manager.h | 3 ++ .../proton/test/mock_attribute_manager.h | 3 ++ 20 files changed, 230 insertions(+), 96 deletions(-) create mode 100644 searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/.gitignore create mode 100644 searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/CMakeLists.txt create mode 100644 searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/exclusive_attribute_read_accessor_test.cpp delete mode 100644 searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.cpp delete mode 100644 searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.h create mode 100644 searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.cpp create mode 100644 searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.h (limited to 'searchcore') diff --git a/searchcore/CMakeLists.txt b/searchcore/CMakeLists.txt index 426e577b2d2..131460b0384 100644 --- a/searchcore/CMakeLists.txt +++ b/searchcore/CMakeLists.txt @@ -64,6 +64,7 @@ vespa_define_module( src/tests/proton/attribute/attributes_state_explorer src/tests/proton/attribute/document_field_extractor src/tests/proton/attribute/document_field_populator + src/tests/proton/attribute/exclusive_attribute_read_accessor src/tests/proton/attribute/imported_attributes_context src/tests/proton/attribute/imported_attributes_repo src/tests/proton/bucketdb/bucketdb diff --git a/searchcore/src/tests/proton/attribute/attribute_manager/attribute_manager_test.cpp b/searchcore/src/tests/proton/attribute/attribute_manager/attribute_manager_test.cpp index 140012624c2..c9f3a1c1de8 100644 --- a/searchcore/src/tests/proton/attribute/attribute_manager/attribute_manager_test.cpp +++ b/searchcore/src/tests/proton/attribute/attribute_manager/attribute_manager_test.cpp @@ -5,6 +5,7 @@ #include #include #include +#include #include #include #include @@ -754,6 +755,15 @@ TEST_F("require that we can call functions on all attributes via functor", EXPECT_EQUAL("a1,a2,a3", functor->getSortedNames()); } +TEST_F("require that we can acquire exclusive read access to attribute", Fixture) +{ + f.addAttribute("attr"); + ExclusiveAttributeReadAccessor::UP attrAccessor = f._m.getExclusiveReadAccessor("attr"); + ExclusiveAttributeReadAccessor::UP noneAccessor = f._m.getExclusiveReadAccessor("none"); + EXPECT_TRUE(attrAccessor.get() != nullptr); + EXPECT_TRUE(noneAccessor.get() == nullptr); +} + TEST_F("require that imported attributes are exposed via attribute context together with regular attributes", Fixture) { f.addAttribute("attr"); diff --git a/searchcore/src/tests/proton/attribute/attributes_state_explorer/attributes_state_explorer_test.cpp b/searchcore/src/tests/proton/attribute/attributes_state_explorer/attributes_state_explorer_test.cpp index aa4871d3a12..bcd200cfd2f 100644 --- a/searchcore/src/tests/proton/attribute/attributes_state_explorer/attributes_state_explorer_test.cpp +++ b/searchcore/src/tests/proton/attribute/attributes_state_explorer/attributes_state_explorer_test.cpp @@ -92,13 +92,13 @@ TEST_F(AttributesStateExplorerTest, require_that_attributes_are_exposed_as_child { StringVector children = _explorer.get_children_names(); std::sort(children.begin(), children.end()); - EXPECT_EQ(StringVector({"btree", "hash", "hybrid", "regular"}), children); + EXPECT_EQ(StringVector({"btree", "extra", "hash", "hybrid", "regular"}), children); } TEST_F(AttributesStateExplorerTest, require_that_attributes_are_explorable) { EXPECT_TRUE(_explorer.get_child("regular").get() != nullptr); - EXPECT_TRUE(_explorer.get_child("extra").get() == nullptr); + EXPECT_TRUE(_explorer.get_child("extra").get() != nullptr); EXPECT_TRUE(_explorer.get_child("not").get() == nullptr); } diff --git a/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/.gitignore b/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/.gitignore new file mode 100644 index 00000000000..f3666eecb6e --- /dev/null +++ b/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/.gitignore @@ -0,0 +1 @@ +searchcore_exclusive_attribute_read_accessor_test_app diff --git a/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/CMakeLists.txt b/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/CMakeLists.txt new file mode 100644 index 00000000000..981d2acd7c5 --- /dev/null +++ b/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/CMakeLists.txt @@ -0,0 +1,9 @@ +# Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +vespa_add_executable(searchcore_exclusive_attribute_read_accessor_test_app TEST + SOURCES + exclusive_attribute_read_accessor_test.cpp + DEPENDS + searchcore_attribute + searchcore_pcommon +) +vespa_add_test(NAME searchcore_exclusive_attribute_read_accessor_test_app COMMAND searchcore_exclusive_attribute_read_accessor_test_app) diff --git a/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/exclusive_attribute_read_accessor_test.cpp b/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/exclusive_attribute_read_accessor_test.cpp new file mode 100644 index 00000000000..8b093be08b7 --- /dev/null +++ b/searchcore/src/tests/proton/attribute/exclusive_attribute_read_accessor/exclusive_attribute_read_accessor_test.cpp @@ -0,0 +1,55 @@ +// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. +#include + +#include +#include +#include +#include +#include +#include + +using namespace proton; +using namespace search; +using namespace vespalib; + +using ReadGuard = ExclusiveAttributeReadAccessor::Guard; +VESPA_THREAD_STACK_TAG(test_executor) + +AttributeVector::SP +createAttribute() +{ + attribute::Config cfg(attribute::BasicType::INT32, attribute::CollectionType::SINGLE); + return search::AttributeFactory::createAttribute("myattr", cfg); +} + +struct Fixture +{ + AttributeVector::SP attribute; + std::unique_ptr writer; + ExclusiveAttributeReadAccessor accessor; + + Fixture() + : attribute(createAttribute()), + writer(SequencedTaskExecutor::create(test_executor, 1)), + accessor(attribute, *writer) + {} +}; + +TEST_F("require that attribute write thread is blocked while guard is held", Fixture) +{ + ReadGuard::UP guard = f.accessor.takeGuard(); + Gate gate; + f.writer->execute(f.writer->getExecutorIdFromName(f.attribute->getNamePrefix()), [&gate]() { gate.countDown(); }); + bool reachedZero = gate.await(100ms); + EXPECT_FALSE(reachedZero); + EXPECT_EQUAL(1u, gate.getCount()); + + guard.reset(); + gate.await(); + EXPECT_EQUAL(0u, gate.getCount()); +} + +TEST_MAIN() +{ + TEST_RUN_ALL(); +} diff --git a/searchcore/src/vespa/searchcore/proton/attribute/CMakeLists.txt b/searchcore/src/vespa/searchcore/proton/attribute/CMakeLists.txt index 70a91b418a9..82bb188870f 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/CMakeLists.txt +++ b/searchcore/src/vespa/searchcore/proton/attribute/CMakeLists.txt @@ -7,7 +7,6 @@ vespa_add_library(searchcore_attribute STATIC attribute_collection_spec.cpp attribute_config_inspector.cpp attribute_directory.cpp - attribute_executor.cpp attribute_factory.cpp attribute_initializer.cpp attribute_initializer_result.cpp @@ -31,6 +30,7 @@ vespa_add_library(searchcore_attribute STATIC document_field_extractor.cpp document_field_populator.cpp document_field_retriever.cpp + exclusive_attribute_read_accessor.cpp filter_attribute_manager.cpp flushableattribute.cpp imported_attributes_context.cpp diff --git a/searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.cpp b/searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.cpp deleted file mode 100644 index 4d854bfdca1..00000000000 --- a/searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.cpp +++ /dev/null @@ -1,34 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#include "attribute_executor.h" -#include "i_attribute_manager.h" -#include -#include -#include - -using search::AttributeVector; - -namespace proton { - -AttributeExecutor::AttributeExecutor(std::shared_ptr mgr, - std::shared_ptr attr) - : _mgr(std::move(mgr)), - _attr(std::move(attr)) -{ -} - -AttributeExecutor::~AttributeExecutor() = default; - -void -AttributeExecutor::run_sync(std::function task) const -{ - vespalib::string name = _attr->getNamePrefix(); - auto& writer = _mgr->getAttributeFieldWriter(); - std::promise promise; - auto future = promise.get_future(); - auto id = writer.getExecutorIdFromName(name); - writer.execute(id, [&task, promise=std::move(promise)]() mutable { task(); promise.set_value(); }); - future.wait(); -} - -} // namespace proton diff --git a/searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.h b/searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.h deleted file mode 100644 index 4a13fe1d886..00000000000 --- a/searchcore/src/vespa/searchcore/proton/attribute/attribute_executor.h +++ /dev/null @@ -1,32 +0,0 @@ -// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. - -#pragma once - -#include -#include -#include - -namespace search { class AttributeVector; } - -namespace proton { - -struct IAttributeManager; - -/* - * Class for executing task in attribute vector write thread. - */ -class AttributeExecutor -{ -private: - std::shared_ptr _mgr; - std::shared_ptr _attr; - -public: - AttributeExecutor(std::shared_ptr mgr, - std::shared_ptr attr); - ~AttributeExecutor(); - void run_sync(std::function task) const; - const search::AttributeVector& get_attr() const noexcept { return *_attr; } -}; - -} // namespace proton diff --git a/searchcore/src/vespa/searchcore/proton/attribute/attribute_manager_explorer.cpp b/searchcore/src/vespa/searchcore/proton/attribute/attribute_manager_explorer.cpp index 1ea02c729ff..b7d6cf9e87a 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/attribute_manager_explorer.cpp +++ b/searchcore/src/vespa/searchcore/proton/attribute/attribute_manager_explorer.cpp @@ -1,11 +1,9 @@ // Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. #include "attribute_manager_explorer.h" -#include "attribute_executor.h" #include "attribute_vector_explorer.h" #include -using search::AttributeVector; using vespalib::slime::Inserter; namespace proton { @@ -27,7 +25,8 @@ AttributeManagerExplorer::get_state(const Inserter &inserter, bool full) const std::vector AttributeManagerExplorer::get_children_names() const { - auto& attributes = _mgr->getWritableAttributes(); + std::vector attributes; + _mgr->getAttributeListAll(attributes); std::vector names; for (const auto &attr : attributes) { names.push_back(attr->getName()); @@ -38,13 +37,11 @@ AttributeManagerExplorer::get_children_names() const std::unique_ptr AttributeManagerExplorer::get_child(vespalib::stringref name) const { - auto guard = _mgr->getAttribute(name); - auto attr = guard ? guard->getSP() : std::shared_ptr(); - if (attr && _mgr->getWritableAttribute(name) != nullptr) { - auto executor = std::make_unique(_mgr, std::move(attr)); - return std::make_unique(std::move(executor)); + auto attr = _mgr->getExclusiveReadAccessor(name); + if (attr.get() != nullptr) { + return std::make_unique(std::move(attr)); } - return {}; + return std::unique_ptr(); } } // namespace proton diff --git a/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.cpp b/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.cpp index 2deabeda797..c153f873480 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.cpp +++ b/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.cpp @@ -1,7 +1,6 @@ // Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. #include "attribute_vector_explorer.h" -#include "attribute_executor.h" #include #include #include @@ -18,7 +17,6 @@ using search::IEnumStore; using vespalib::AddressSpace; using vespalib::MemoryUsage; using search::attribute::MultiValueMappingBase; -using search::attribute::IAttributeVector; using search::attribute::IPostingListAttributeBase; using namespace vespalib::slime; @@ -118,21 +116,16 @@ convertPostingBaseToSlime(const IPostingListAttributeBase &postingBase, Cursor & } -AttributeVectorExplorer::AttributeVectorExplorer(std::unique_ptr executor) - : _executor(std::move(executor)) +AttributeVectorExplorer::AttributeVectorExplorer(ExclusiveAttributeReadAccessor::UP attribute) + : _attribute(std::move(attribute)) { } void AttributeVectorExplorer::get_state(const vespalib::slime::Inserter &inserter, bool full) const { - auto& attr = _executor->get_attr(); - _executor->run_sync([this, &attr, &inserter, full] { get_state_helper(attr, inserter, full); }); -} - -void -AttributeVectorExplorer::get_state_helper(const AttributeVector& attr, const vespalib::slime::Inserter &inserter, bool full) const -{ + ExclusiveAttributeReadAccessor::Guard::UP readGuard = _attribute->takeGuard(); + const AttributeVector &attr = readGuard->get(); const Status &status = attr.getStatus(); Cursor &object = inserter.insertObject(); if (full) { diff --git a/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.h b/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.h index f7bcc98d321..204a81ed629 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.h +++ b/searchcore/src/vespa/searchcore/proton/attribute/attribute_vector_explorer.h @@ -2,25 +2,21 @@ #pragma once +#include "exclusive_attribute_read_accessor.h" #include -namespace search { class AttributeVector; } - namespace proton { -class AttributeExecutor; - /** * Class used to explore the state of an attribute vector. */ class AttributeVectorExplorer : public vespalib::StateExplorer { private: - std::unique_ptr _executor; + ExclusiveAttributeReadAccessor::UP _attribute; - void get_state_helper(const search::AttributeVector& attr, const vespalib::slime::Inserter &inserter, bool full) const; public: - AttributeVectorExplorer(std::unique_ptr executor); + AttributeVectorExplorer(ExclusiveAttributeReadAccessor::UP attribute); // Implements vespalib::StateExplorer void get_state(const vespalib::slime::Inserter &inserter, bool full) const override; diff --git a/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.cpp b/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.cpp index ee04f17d378..161a4294908 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.cpp +++ b/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.cpp @@ -638,6 +638,16 @@ AttributeManager::asyncForAttribute(const vespalib::string &name, std::unique_pt [attr=std::move(attrsp), func=std::move(func)]() { (*func)(*attr); }); } +ExclusiveAttributeReadAccessor::UP +AttributeManager::getExclusiveReadAccessor(const vespalib::string &name) const +{ + AttributeVector::SP attribute = findAttribute(name); + if (attribute) { + return std::make_unique(attribute, _attributeFieldWriter); + } + return {}; +} + void AttributeManager::setImportedAttributes(std::unique_ptr attributes) { diff --git a/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.h b/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.h index d6d0964f97e..c924c1c5b20 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.h +++ b/searchcore/src/vespa/searchcore/proton/attribute/attributemanager.h @@ -182,6 +182,8 @@ public: void asyncForEachAttribute(std::shared_ptr func, OnDone onDone) const override; void asyncForAttribute(const vespalib::string &name, std::unique_ptr func) const override; + ExclusiveAttributeReadAccessor::UP getExclusiveReadAccessor(const vespalib::string &name) const override; + void setImportedAttributes(std::unique_ptr attributes) override; const ImportedAttributesRepo *getImportedAttributes() const override { return _importedAttributes.get(); } diff --git a/searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.cpp b/searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.cpp new file mode 100644 index 00000000000..ed72418ced4 --- /dev/null +++ b/searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.cpp @@ -0,0 +1,60 @@ +// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. + +#include "exclusive_attribute_read_accessor.h" +#include +#include +#include + +namespace proton { + +using search::AttributeVector; +using vespalib::ISequencedTaskExecutor; +using vespalib::Executor; +using vespalib::Gate; + +using GateSP = std::shared_ptr; + +ExclusiveAttributeReadAccessor::Guard::Guard(const AttributeVector &attribute, + const GateSP &exitGate) + : _attribute(attribute), + _exitGate(exitGate) +{ +} + +ExclusiveAttributeReadAccessor::Guard::~Guard() +{ + _exitGate->countDown(); +} + +ExclusiveAttributeReadAccessor:: +ExclusiveAttributeReadAccessor(const AttributeVector::SP &attribute, + ISequencedTaskExecutor &attributeFieldWriter) + : _attribute(attribute), + _attributeFieldWriter(attributeFieldWriter) +{ +} + +namespace { + +void +attributeWriteBlockingTask(AttributeVector::SP attribute, GateSP entranceGate, GateSP exitGate) +{ + attribute->commit(true); + entranceGate->countDown(); + exitGate->await(); +} + +} + +ExclusiveAttributeReadAccessor::Guard::UP +ExclusiveAttributeReadAccessor::takeGuard() +{ + GateSP entranceGate = std::make_shared(); + GateSP exitGate = std::make_shared(); + _attributeFieldWriter.execute(_attributeFieldWriter.getExecutorIdFromName(_attribute->getNamePrefix()), + [this, entranceGate, exitGate]() { attributeWriteBlockingTask(_attribute, entranceGate, exitGate); }); + entranceGate->await(); + return std::make_unique(*_attribute, exitGate); +} + +} // namespace proton diff --git a/searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.h b/searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.h new file mode 100644 index 00000000000..aa756764b1a --- /dev/null +++ b/searchcore/src/vespa/searchcore/proton/attribute/exclusive_attribute_read_accessor.h @@ -0,0 +1,53 @@ +// Copyright Yahoo. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. + +#pragma once + +#include + +namespace search { + class AttributeVector; +} +namespace vespalib { + class Gate; + class ISequencedTaskExecutor; +} + +namespace proton { + +/** + * Class that provides exclusive read access to an attribute vector + * while the write thread for that attribute is blocked. + * + * The attribute write thread is blocked while a guard is held. + */ +class ExclusiveAttributeReadAccessor +{ +public: + class Guard + { + private: + const search::AttributeVector &_attribute; + std::shared_ptr _exitGate; + + public: + using UP = std::unique_ptr; + Guard(const search::AttributeVector &attribute, + const std::shared_ptr &exitGate); + ~Guard(); + const search::AttributeVector &get() const { return _attribute; } + }; + +private: + using AttributeVectorSP = std::shared_ptr; + AttributeVectorSP _attribute; + vespalib::ISequencedTaskExecutor &_attributeFieldWriter; + +public: + using UP = std::unique_ptr; + + ExclusiveAttributeReadAccessor(const AttributeVectorSP &attribute, + vespalib::ISequencedTaskExecutor &attributeFieldWriter); + Guard::UP takeGuard(); +}; + +} // namespace proton diff --git a/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.cpp b/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.cpp index 6329c633727..6f6cd01b4a4 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.cpp +++ b/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.cpp @@ -232,6 +232,12 @@ FilterAttributeManager::asyncForAttribute(const vespalib::string &name, std::uni } +ExclusiveAttributeReadAccessor::UP +FilterAttributeManager::getExclusiveReadAccessor(const vespalib::string &name) const +{ + return (acceptAttribute(name)) ? _mgr->getExclusiveReadAccessor(name) : ExclusiveAttributeReadAccessor::UP(); +} + void FilterAttributeManager::setImportedAttributes(std::unique_ptr) { diff --git a/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.h b/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.h index 6d5ff682ca1..dff18290330 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.h +++ b/searchcore/src/vespa/searchcore/proton/attribute/filter_attribute_manager.h @@ -52,6 +52,7 @@ public: const std::vector & getWritableAttributes() const override; void asyncForEachAttribute(std::shared_ptr func) const override; void asyncForEachAttribute(std::shared_ptr func, OnDone onDone) const override; + ExclusiveAttributeReadAccessor::UP getExclusiveReadAccessor(const vespalib::string &name) const override; void setImportedAttributes(std::unique_ptr attributes) override; const ImportedAttributesRepo *getImportedAttributes() const override; std::shared_ptr readable_attribute_vector(const string& name) const override; diff --git a/searchcore/src/vespa/searchcore/proton/attribute/i_attribute_manager.h b/searchcore/src/vespa/searchcore/proton/attribute/i_attribute_manager.h index 5e60e950cc4..437e7bd0208 100644 --- a/searchcore/src/vespa/searchcore/proton/attribute/i_attribute_manager.h +++ b/searchcore/src/vespa/searchcore/proton/attribute/i_attribute_manager.h @@ -2,6 +2,7 @@ #pragma once +#include "exclusive_attribute_read_accessor.h" #include "i_attribute_factory.h" #include #include @@ -101,6 +102,8 @@ struct IAttributeManager : public search::IAttributeManager virtual void asyncForEachAttribute(std::shared_ptr func) const = 0; virtual void asyncForEachAttribute(std::shared_ptr func, OnDone onDone) const = 0; + virtual ExclusiveAttributeReadAccessor::UP getExclusiveReadAccessor(const vespalib::string &name) const = 0; + virtual void setImportedAttributes(std::unique_ptr attributes) = 0; virtual const ImportedAttributesRepo *getImportedAttributes() const = 0; diff --git a/searchcore/src/vespa/searchcore/proton/test/mock_attribute_manager.h b/searchcore/src/vespa/searchcore/proton/test/mock_attribute_manager.h index babecb6a77d..f85baa8c0ac 100644 --- a/searchcore/src/vespa/searchcore/proton/test/mock_attribute_manager.h +++ b/searchcore/src/vespa/searchcore/proton/test/mock_attribute_manager.h @@ -91,6 +91,9 @@ public: void asyncForEachAttribute(std::shared_ptr) const override { } void asyncForEachAttribute(std::shared_ptr, OnDone) const override { } + ExclusiveAttributeReadAccessor::UP getExclusiveReadAccessor(const vespalib::string &) const override { + return ExclusiveAttributeReadAccessor::UP(); + } void setImportedAttributes(std::unique_ptr importedAttributes) override { _importedAttributes = std::move(importedAttributes); } -- cgit v1.2.3