summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorHenning Baldersheim <balder@yahoo-inc.com>2021-08-12 06:21:54 +0000
committerHenning Baldersheim <balder@yahoo-inc.com>2021-08-12 06:21:54 +0000
commit96d88f5e9273060bb8d264e2988cb854048cf1d6 (patch)
treea69f1c3cf4417cc8248212c0fc6bc79b82b4d3ee
parentd7f026fdc2bbe507da717f45c0a8704291cff16f (diff)
Add swapable attribute option.
-rw-r--r--configdefinitions/src/vespa/attributes.def1
-rw-r--r--searchcommon/src/vespa/searchcommon/attribute/config.cpp3
-rw-r--r--searchcommon/src/vespa/searchcommon/attribute/config.h3
-rw-r--r--searchlib/src/tests/attribute/attributemanager/attributemanager_test.cpp110
-rw-r--r--searchlib/src/vespa/searchlib/attribute/attributevector.h16
-rw-r--r--searchlib/src/vespa/searchlib/attribute/configconverter.cpp1
6 files changed, 49 insertions, 85 deletions
diff --git a/configdefinitions/src/vespa/attributes.def b/configdefinitions/src/vespa/attributes.def
index 46e1674e9b9..7d7f417bce0 100644
--- a/configdefinitions/src/vespa/attributes.def
+++ b/configdefinitions/src/vespa/attributes.def
@@ -11,6 +11,7 @@ attribute[].removeifzero bool default=false
attribute[].createifnonexistent bool default=false
attribute[].fastsearch bool default=false
attribute[].huge bool default=false
+attribute[].swapable bool default=false
# An attribute marked mutable can be updated by a query.
attribute[].ismutable bool default=false
attribute[].sortascending bool default=true
diff --git a/searchcommon/src/vespa/searchcommon/attribute/config.cpp b/searchcommon/src/vespa/searchcommon/attribute/config.cpp
index c62d7ef0ea1..23119ac8e1f 100644
--- a/searchcommon/src/vespa/searchcommon/attribute/config.cpp
+++ b/searchcommon/src/vespa/searchcommon/attribute/config.cpp
@@ -14,6 +14,7 @@ Config::Config() noexcept :
_isFilter(false),
_fastAccess(false),
_mutable(false),
+ _swapable(false),
_match(Match::UNCASED),
_dictionary(),
_growStrategy(),
@@ -35,6 +36,7 @@ Config::Config(BasicType bt, CollectionType ct, bool fastSearch_, bool huge_) no
_isFilter(false),
_fastAccess(false),
_mutable(false),
+ _swapable(false),
_match(Match::UNCASED),
_dictionary(),
_growStrategy(),
@@ -64,6 +66,7 @@ Config::operator==(const Config &b) const
_isFilter == b._isFilter &&
_fastAccess == b._fastAccess &&
_mutable == b._mutable &&
+ _swapable == b._swapable &&
_match == b._match &&
_dictionary == b._dictionary &&
_growStrategy == b._growStrategy &&
diff --git a/searchcommon/src/vespa/searchcommon/attribute/config.h b/searchcommon/src/vespa/searchcommon/attribute/config.h
index fdf3a00ac99..36bfe711029 100644
--- a/searchcommon/src/vespa/searchcommon/attribute/config.h
+++ b/searchcommon/src/vespa/searchcommon/attribute/config.h
@@ -40,6 +40,7 @@ public:
CollectionType collectionType() const { return _type; }
bool fastSearch() const { return _fastSearch; }
bool huge() const { return _huge; }
+ bool swapable() const { return _swapable; }
const PredicateParams &predicateParams() const { return _predicateParams; }
const vespalib::eval::ValueType & tensorType() const { return _tensorType; }
DistanceMetric distance_metric() const { return _distance_metric; }
@@ -116,6 +117,7 @@ public:
*/
Config & setIsFilter(bool isFilter) { _isFilter = isFilter; return *this; }
Config & setMutable(bool isMutable) { _mutable = isMutable; return *this; }
+ Config & setSwapable(bool isSwapable) { _swapable = isSwapable; return *this; }
Config & setFastAccess(bool v) { _fastAccess = v; return *this; }
Config & setGrowStrategy(const GrowStrategy &gs) { _growStrategy = gs; return *this; }
Config & setCompactionStrategy(const CompactionStrategy &compactionStrategy) {
@@ -137,6 +139,7 @@ private:
bool _isFilter;
bool _fastAccess;
bool _mutable;
+ bool _swapable;
Match _match;
DictionaryConfig _dictionary;
GrowStrategy _growStrategy;
diff --git a/searchlib/src/tests/attribute/attributemanager/attributemanager_test.cpp b/searchlib/src/tests/attribute/attributemanager/attributemanager_test.cpp
index 721e7e1c805..729067f1c6b 100644
--- a/searchlib/src/tests/attribute/attributemanager/attributemanager_test.cpp
+++ b/searchlib/src/tests/attribute/attributemanager/attributemanager_test.cpp
@@ -20,43 +20,13 @@ using namespace search::attribute;
using std::shared_ptr;
using vespalib::stringref;
-typedef BasicType BT;
-typedef CollectionType CT;
-typedef AttributeVector::SP AVSP;
+using BT = BasicType;
+using CT = CollectionType;
+using AVSP = AttributeVector::SP;
namespace search {
-class AttributeManagerTest : public vespalib::TestApp
-{
-private:
- void verifyLoad(AttributeVector & v);
- void testLoad();
- void testGuards();
- void testConfigConvert();
- void testContext();
- void can_get_readable_attribute_vector_by_name();
-
- bool
- assertDataType(BT::Type exp,
- AttributesConfig::Attribute::Datatype in);
-
- bool
- assertCollectionType(CollectionType exp,
- AttributesConfig::Attribute::Collectiontype in,
- bool removeIfZ = false,
- bool createIfNe = false);
-
-public:
- AttributeManagerTest()
- {
- }
- int Main() override;
-};
-
-
-typedef MultiValueNumericAttribute< IntegerAttributeTemplate<int32_t>,
- multivalue::Value<int32_t> >
-TestAttributeBase;
+using TestAttributeBase = MultiValueNumericAttribute< IntegerAttributeTemplate<int32_t>, multivalue::Value<int32_t> >;
class TestAttribute : public TestAttributeBase
{
@@ -73,8 +43,7 @@ public:
};
-void
-AttributeManagerTest::testGuards()
+TEST("Test attribute guards")
{
AttributeVector::SP vec(new TestAttribute("mvint") );
TestAttribute * v = static_cast<TestAttribute *> (vec.get());
@@ -134,7 +103,7 @@ AttributeManagerTest::testGuards()
void
-AttributeManagerTest::verifyLoad(AttributeVector & v)
+verifyLoad(AttributeVector & v)
{
EXPECT_TRUE( !v.isLoaded() );
EXPECT_TRUE( v.load() );
@@ -143,8 +112,7 @@ AttributeManagerTest::verifyLoad(AttributeVector & v)
}
-void
-AttributeManagerTest::testLoad()
+TEST("Test loading of attributes")
{
{
TestAttributeBase v("mvint");
@@ -172,14 +140,14 @@ AttributeManagerTest::testLoad()
verifyLoad(v);
}
{
- AttributeVector::Config config(BT::INT32,
+ Config config(BT::INT32,
CollectionType::ARRAY);
TestAttributeBase v("mvint", config);
verifyLoad(v);
}
{
AttributeManager manager;
- AttributeVector::Config config(BT::INT32,
+ Config config(BT::INT32,
CollectionType::ARRAY);
EXPECT_TRUE(manager.addVector("mvint", config));
AttributeManager::AttributeList list;
@@ -193,7 +161,7 @@ AttributeManagerTest::testLoad()
bool
-AttributeManagerTest::assertDataType(BT::Type exp, AttributesConfig::Attribute::Datatype in)
+assertDataType(BT::Type exp, AttributesConfig::Attribute::Datatype in)
{
AttributesConfig::Attribute a;
a.datatype = in;
@@ -202,25 +170,22 @@ AttributeManagerTest::assertDataType(BT::Type exp, AttributesConfig::Attribute::
bool
-AttributeManagerTest::
assertCollectionType(CollectionType exp, AttributesConfig::Attribute::Collectiontype in,
- bool removeIfZ, bool createIfNe)
+ bool removeIfZ = false, bool createIfNe = false)
{
AttributesConfig::Attribute a;
a.collectiontype = in;
a.removeifzero = removeIfZ;
a.createifnonexistent = createIfNe;
- AttributeVector::Config out = ConfigConverter::convert(a);
+ Config out = ConfigConverter::convert(a);
return EXPECT_EQUAL(exp.type(), out.collectionType().type()) &&
EXPECT_EQUAL(exp.removeIfZero(), out.collectionType().removeIfZero()) &&
EXPECT_EQUAL(exp.createIfNonExistant(), out.collectionType().createIfNonExistant());
}
-void
-AttributeManagerTest::testConfigConvert()
+TEST("require that config can be converted")
{
- // typedef AttributeVector::Config AVC;
typedef BT AVBT;
typedef CollectionType AVCT;
using CACA = AttributesConfig::Attribute;
@@ -271,11 +236,17 @@ AttributeManagerTest::testConfigConvert()
a.ismutable = true;
EXPECT_TRUE(CC::convert(a).isMutable());
}
+ {
+ CACA a;
+ EXPECT_TRUE(!CC::convert(a).swapable());
+ a.swapable = true;
+ EXPECT_TRUE(CC::convert(a).swapable());
+ }
{ // tensor
CACA a;
a.datatype = CACAD::TENSOR;
a.tensortype = "tensor(x[5])";
- AttributeVector::Config out = ConfigConverter::convert(a);
+ Config out = ConfigConverter::convert(a);
EXPECT_EQUAL("tensor(x[5])", out.tensorType().to_spec());
}
{ // distance metric (default)
@@ -334,8 +305,7 @@ bool gt_attribute(const attribute::IAttributeVector * a, const attribute::IAttri
return a->getName() < b->getName();
}
-void
-AttributeManagerTest::testContext()
+TEST("test the attribute context")
{
std::vector<AVSP> attrs;
// create various attributes vectors
@@ -370,13 +340,13 @@ AttributeManagerTest::testContext()
}
for (uint32_t i = 0; i < 2; ++i) {
- EXPECT_TRUE(first->getAttribute("sint32") != NULL);
- EXPECT_TRUE(first->getAttribute("aint32") != NULL);
- EXPECT_TRUE(first->getAttribute("wsint32") != NULL);
- EXPECT_TRUE(first->getAttributeStableEnum("wsint32") != NULL);
+ EXPECT_TRUE(first->getAttribute("sint32") != nullptr);
+ EXPECT_TRUE(first->getAttribute("aint32") != nullptr);
+ EXPECT_TRUE(first->getAttribute("wsint32") != nullptr);
+ EXPECT_TRUE(first->getAttributeStableEnum("wsint32") != nullptr);
}
- EXPECT_TRUE(first->getAttribute("foo") == NULL);
- EXPECT_TRUE(first->getAttribute("bar") == NULL);
+ EXPECT_TRUE(first->getAttribute("foo") == nullptr);
+ EXPECT_TRUE(first->getAttribute("bar") == nullptr);
// one generation guard taken per attribute asked for
for (uint32_t i = 0; i < attrs.size(); ++i) {
@@ -388,10 +358,10 @@ AttributeManagerTest::testContext()
{
IAttributeContext::UP second = manager.createContext();
- EXPECT_TRUE(second->getAttribute("sint32") != NULL);
- EXPECT_TRUE(second->getAttribute("aint32") != NULL);
- EXPECT_TRUE(second->getAttribute("wsint32") != NULL);
- EXPECT_TRUE(second->getAttributeStableEnum("wsint32") != NULL);
+ EXPECT_TRUE(second->getAttribute("sint32") != nullptr);
+ EXPECT_TRUE(second->getAttribute("aint32") != nullptr);
+ EXPECT_TRUE(second->getAttribute("wsint32") != nullptr);
+ EXPECT_TRUE(second->getAttributeStableEnum("wsint32") != nullptr);
// two generation guards taken per attribute asked for
for (uint32_t i = 0; i < attrs.size(); ++i) {
@@ -428,8 +398,7 @@ AttributeManagerTest::testContext()
}
}
-void
-AttributeManagerTest::can_get_readable_attribute_vector_by_name()
+TEST("require that we can get readable attribute by name")
{
auto attr = AttributeFactory::createAttribute("cool_attr", Config(BT::INT32, CT::SINGLE));
// Ensure there's something to actually load, or fetching the attribute will throw.
@@ -443,20 +412,7 @@ AttributeManagerTest::can_get_readable_attribute_vector_by_name()
EXPECT_TRUE(av.get() == nullptr);
}
-int AttributeManagerTest::Main()
-{
- TEST_INIT("attributemanager_test");
-
- testLoad();
- testGuards();
- testConfigConvert();
- testContext();
- can_get_readable_attribute_vector_by_name();
-
- TEST_DONE();
-}
-
} // namespace search
-TEST_APPHOOK(search::AttributeManagerTest);
+TEST_MAIN() { TEST_RUN_ALL(); } \ No newline at end of file
diff --git a/searchlib/src/vespa/searchlib/attribute/attributevector.h b/searchlib/src/vespa/searchlib/attribute/attributevector.h
index 3c27f00a022..99b0c923c90 100644
--- a/searchlib/src/vespa/searchlib/attribute/attributevector.h
+++ b/searchlib/src/vespa/searchlib/attribute/attributevector.h
@@ -282,6 +282,14 @@ public:
virtual IExtendAttribute * getExtendInterface();
+ /**
+ * Returns the number of readers holding a generation guard.
+ * Should be called by the writer thread.
+ **/
+ uint32_t getGenerationRefCount(generation_t gen) const {
+ return _genHandler.getGenerationRefCount(gen);
+ }
+
protected:
/**
* Called when a new document has been added, but only for
@@ -291,14 +299,6 @@ protected:
**/
virtual bool onAddDoc(DocId) { return false; }
- /**
- * Returns the number of readers holding a generation guard.
- * Should be called by the writer thread.
- */
- uint32_t getGenerationRefCount(generation_t gen) const {
- return _genHandler.getGenerationRefCount(gen);
- }
-
const GenerationHandler & getGenerationHandler() const {
return _genHandler;
}
diff --git a/searchlib/src/vespa/searchlib/attribute/configconverter.cpp b/searchlib/src/vespa/searchlib/attribute/configconverter.cpp
index 6387edc588b..cff0c0b1063 100644
--- a/searchlib/src/vespa/searchlib/attribute/configconverter.cpp
+++ b/searchlib/src/vespa/searchlib/attribute/configconverter.cpp
@@ -108,6 +108,7 @@ ConfigConverter::convert(const AttributesConfig::Attribute & cfg)
retval.setIsFilter(cfg.enableonlybitvector);
retval.setFastAccess(cfg.fastaccess);
retval.setMutable(cfg.ismutable);
+ retval.setSwapable(cfg.swapable);
predicateParams.setArity(cfg.arity);
predicateParams.setBounds(cfg.lowerbound, cfg.upperbound);
predicateParams.setDensePostingListThreshold(cfg.densepostinglistthreshold);