From c7b0e6802652b155209105855541c403f3ec1a0b Mon Sep 17 00:00:00 2001 From: Jan Date: Thu, 12 Sep 2019 15:42:56 +0200 Subject: [PATCH] disable the creation of TTL indexes on sub-attributes (#9995) * disable the creation of TTL indexes on sub-attributes * updated CHANGELOG --- CHANGELOG | 6 ++++++ arangod/Indexes/IndexFactory.cpp | 18 +++++++++++++----- arangod/Indexes/IndexFactory.h | 5 +++-- tests/js/common/shell/shell-ttl.js | 10 ++++++++++ 4 files changed, 32 insertions(+), 7 deletions(-) diff --git a/CHANGELOG b/CHANGELOG index 037d9a5881..a1c17afd18 100644 --- a/CHANGELOG +++ b/CHANGELOG @@ -1,6 +1,12 @@ v3.5.1 (XXXX-XX-XX) ------------------- +* Disallow creation of TTL indexes on sub-attributes. + + Creation of such indexes was not caught before, but the resulting + indexes were defunct. From now on the creation of TTL indexes on sub- + attributes is disallowed. + * Added HotBackup feature. * Improved database creation within the cluster. In the case of diff --git a/arangod/Indexes/IndexFactory.cpp b/arangod/Indexes/IndexFactory.cpp index c779a5a073..2cb57be07f 100644 --- a/arangod/Indexes/IndexFactory.cpp +++ b/arangod/Indexes/IndexFactory.cpp @@ -333,7 +333,9 @@ TRI_idx_iid_t IndexFactory::validateSlice(arangodb::velocypack::Slice info, return iid; } -Result IndexFactory::validateFieldsDefinition(VPackSlice definition, size_t minFields, size_t maxFields) { +Result IndexFactory::validateFieldsDefinition(VPackSlice definition, + size_t minFields, size_t maxFields, + bool allowSubAttributes) { if (basics::VelocyPackHelper::getBooleanValue(definition, StaticStrings::Error, false)) { // We have an error here. return Result(TRI_ERROR_BAD_PARAMETER); @@ -364,7 +366,12 @@ Result IndexFactory::validateFieldsDefinition(VPackSlice definition, size_t minF return Result(TRI_ERROR_BAD_PARAMETER, "duplicate attribute name in index fields list"); } - + + if (!allowSubAttributes && f.find('.') != std::string::npos) { + return Result(TRI_ERROR_BAD_PARAMETER, + "cannot index a sub-attribute in this type of index"); + } + if (std::regex_match(f.toString(), idRegex)) { return Result(TRI_ERROR_BAD_PARAMETER, "_id attribute cannot be indexed"); @@ -386,10 +393,11 @@ Result IndexFactory::validateFieldsDefinition(VPackSlice definition, size_t minF /// @brief process the fields list, deduplicate it, and add it to the json Result IndexFactory::processIndexFields(VPackSlice definition, VPackBuilder& builder, size_t minFields, size_t maxFields, - bool create, bool allowExpansion) { + bool create, bool allowExpansion, + bool allowSubAttributes) { TRI_ASSERT(builder.isOpenObject()); - Result res = validateFieldsDefinition(definition, minFields, maxFields); + Result res = validateFieldsDefinition(definition, minFields, maxFields, allowSubAttributes); if (res.fail()) { return res; } @@ -477,7 +485,7 @@ Result IndexFactory::enhanceJsonIndexGeneric(VPackSlice definition, /// @brief enhances the json of a ttl index Result IndexFactory::enhanceJsonIndexTtl(VPackSlice definition, VPackBuilder& builder, bool create) { - Result res = processIndexFields(definition, builder, 1, 1, create, false); + Result res = processIndexFields(definition, builder, 1, 1, create, false, false); auto value = definition.get(arangodb::StaticStrings::IndexUnique); if (value.isBoolean() && value.getBoolean()) { diff --git a/arangod/Indexes/IndexFactory.h b/arangod/Indexes/IndexFactory.h index 8afffc1bc0..7d5d94f783 100644 --- a/arangod/Indexes/IndexFactory.h +++ b/arangod/Indexes/IndexFactory.h @@ -111,13 +111,14 @@ class IndexFactory { std::vector>& indexes) const = 0; static Result validateFieldsDefinition(arangodb::velocypack::Slice definition, - size_t minFields, size_t maxFields); + size_t minFields, size_t maxFields, + bool allowSubAttributes = true); /// @brief process the fields list, deduplicate it, and add it to the json static Result processIndexFields(arangodb::velocypack::Slice definition, arangodb::velocypack::Builder& builder, size_t minFields, size_t maxFields, bool create, - bool allowExpansion); + bool allowExpansion, bool allowSubAttributes = true); /// @brief process the unique flag and add it to the json static void processIndexUniqueFlag(arangodb::velocypack::Slice definition, diff --git a/tests/js/common/shell/shell-ttl.js b/tests/js/common/shell/shell-ttl.js index b7da45db07..3fdbf29e72 100644 --- a/tests/js/common/shell/shell-ttl.js +++ b/tests/js/common/shell/shell-ttl.js @@ -204,6 +204,16 @@ function TtlSuite () { // number of runs must not have changed assertEqual(stats.runs, oldRuns); }, + + testCreateIndexSubAttribute : function () { + let c = db._create(cn, { numberOfShards: 2 }); + try { + c.ensureIndex({ type: "ttl", fields: ["date.created"], expireAfter: 10, unique: true }); + fail(); + } catch (err) { + assertEqual(ERRORS.ERROR_BAD_PARAMETER.code, err.errorNum); + } + }, testCreateIndexUnique : function () { let c = db._create(cn, { numberOfShards: 2 });