// Copyright Vespa.ai. Licensed under the terms of the Apache 2.0 license. See LICENSE in the project root. #include #include #include #include #include #include #include #include #include #include #include #include #include #include LOG_SETUP("attributes_state_explorer_test"); using namespace proton; using namespace proton::test; using search::AttributeVector; using search::DictionaryConfig; using vespalib::ForegroundThreadExecutor; using vespalib::ISequencedTaskExecutor; using vespalib::SequencedTaskExecutor; using vespalib::Slime; using search::TuneFileAttributes; using search::index::DummyFileHeaderContext; using search::test::DirectoryHandler; using vespalib::HwInfo; const vespalib::string TEST_DIR = "test_output"; namespace { VESPA_THREAD_STACK_TAG(test_executor) } struct AttributesStateExplorerTest : public ::testing::Test { DirectoryHandler _dirHandler; DummyFileHeaderContext _fileHeaderContext; std::unique_ptr _attribute_field_writer; ForegroundThreadExecutor _shared; HwInfo _hwInfo; AttributeManager::SP _mgr; AttributeManagerExplorer _explorer; AttributesStateExplorerTest() : _dirHandler(TEST_DIR), _fileHeaderContext(), _attribute_field_writer(SequencedTaskExecutor::create(test_executor, 1)), _shared(), _hwInfo(), _mgr(new AttributeManager(TEST_DIR, "test.subdb", TuneFileAttributes(), _fileHeaderContext, std::make_shared(), *_attribute_field_writer, _shared, _hwInfo)), _explorer(_mgr) { addAttribute("regular"); addExtraAttribute("extra"); add_fast_search_attribute("btree", DictionaryConfig::Type::BTREE); add_fast_search_attribute("hybrid", DictionaryConfig::Type::BTREE_AND_HASH); add_fast_search_attribute("hash", DictionaryConfig::Type::HASH); } void addAttribute(const vespalib::string &name) { _mgr->addAttribute({name, AttributeUtils::getInt32Config()}, 1); } void add_fast_search_attribute(const vespalib::string &name, DictionaryConfig::Type dictionary_type) { search::attribute::Config cfg = AttributeUtils::getInt32Config(); cfg.setFastSearch(true); cfg.set_dictionary_config(search::DictionaryConfig(dictionary_type)); _mgr->addAttribute({name, cfg}, 1); } void addExtraAttribute(const vespalib::string &name) { _mgr->addExtraAttribute(createInt32Attribute(name)); } Slime explore_attribute(const vespalib::string &name) { Slime result; vespalib::slime::SlimeInserter inserter(result); _explorer.get_child(name)->get_state(inserter, true); return result; } }; using StringVector = std::vector; TEST_F(AttributesStateExplorerTest, require_that_attributes_are_exposed_as_children_names) { StringVector children = _explorer.get_children_names(); std::sort(children.begin(), children.end()); EXPECT_EQ(StringVector({"btree", "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("not").get() == nullptr); } TEST_F(AttributesStateExplorerTest, require_that_dictionary_memory_usage_is_reported) { { auto slime = explore_attribute("btree"); auto& dictionary = slime.get()["enumStore"]["dictionary"]; EXPECT_LT(0, dictionary["btreeMemoryUsage"]["used"].asLong()); EXPECT_EQ(0, dictionary["hashMemoryUsage"]["used"].asLong()); } { auto slime = explore_attribute("hash"); auto& dictionary = slime.get()["enumStore"]["dictionary"]; EXPECT_EQ(0, dictionary["btreeMemoryUsage"]["used"].asLong()); EXPECT_LT(0, dictionary["hashMemoryUsage"]["used"].asLong()); } { auto slime = explore_attribute("hybrid"); auto& dictionary = slime.get()["enumStore"]["dictionary"]; EXPECT_LT(0, dictionary["btreeMemoryUsage"]["used"].asLong()); EXPECT_LT(0, dictionary["hashMemoryUsage"]["used"].asLong()); } } GTEST_MAIN_RUN_ALL_TESTS()