summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--src/mongo/db/commands/create_indexes.cpp4
-rw-r--r--src/mongo/db/commands/dbcommands.cpp2
-rw-r--r--src/mongo/db/commands/drop_indexes.cpp2
-rw-r--r--src/mongo/db/commands/list_indexes.cpp47
-rw-r--r--src/mongo/db/timeseries/timeseries_field_names.h3
-rw-r--r--src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.cpp34
-rw-r--r--src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.h29
-rw-r--r--src/mongo/db/timeseries/timeseries_index_schema_conversion_functions_test.cpp9
8 files changed, 68 insertions, 62 deletions
diff --git a/src/mongo/db/commands/create_indexes.cpp b/src/mongo/db/commands/create_indexes.cpp
index bb75219b9b8..36e1596459e 100644
--- a/src/mongo/db/commands/create_indexes.cpp
+++ b/src/mongo/db/commands/create_indexes.cpp
@@ -638,8 +638,8 @@ std::unique_ptr<CreateIndexesCommand> makeTimeseriesCreateIndexesCommand(
for (const auto& elem : origIndex) {
if (elem.fieldNameStringData() == NewIndexSpec::kKeyFieldName) {
auto bucketsIndexSpecWithStatus =
- timeseries::convertTimeseriesIndexSpecToBucketsIndexSpec(*timeseriesOptions,
- elem.Obj());
+ timeseries::createBucketsIndexSpecFromTimeseriesIndexSpec(*timeseriesOptions,
+ elem.Obj());
uassert(ErrorCodes::CannotCreateIndex,
str::stream() << bucketsIndexSpecWithStatus.getStatus().toString()
<< " Command request: " << redact(origCmd.toBSON({})),
diff --git a/src/mongo/db/commands/dbcommands.cpp b/src/mongo/db/commands/dbcommands.cpp
index 85c1d0b5e01..ca3768c8698 100644
--- a/src/mongo/db/commands/dbcommands.cpp
+++ b/src/mongo/db/commands/dbcommands.cpp
@@ -122,7 +122,7 @@ std::unique_ptr<CollMod> makeTimeseriesCollModCommand(OperationContext* opCtx,
auto index = origCmd.getIndex();
if (index && index->getKeyPattern()) {
- auto bucketsIndexSpecWithStatus = timeseries::convertTimeseriesIndexSpecToBucketsIndexSpec(
+ auto bucketsIndexSpecWithStatus = timeseries::createBucketsIndexSpecFromTimeseriesIndexSpec(
*timeseriesOptions, *index->getKeyPattern());
uassert(ErrorCodes::IndexNotFound,
diff --git a/src/mongo/db/commands/drop_indexes.cpp b/src/mongo/db/commands/drop_indexes.cpp
index 85d1c56b929..a2a5be13db7 100644
--- a/src/mongo/db/commands/drop_indexes.cpp
+++ b/src/mongo/db/commands/drop_indexes.cpp
@@ -90,7 +90,7 @@ std::unique_ptr<DropIndexes> makeTimeseriesDropIndexesCommand(OperationContext*
const auto& origIndex = origCmd.getIndex();
if (auto keyPtr = stdx::get_if<BSONObj>(&origIndex)) {
auto bucketsIndexSpecWithStatus =
- timeseries::convertTimeseriesIndexSpecToBucketsIndexSpec(*timeseriesOptions, *keyPtr);
+ timeseries::createBucketsIndexSpecFromTimeseriesIndexSpec(*timeseriesOptions, *keyPtr);
uassert(ErrorCodes::IndexNotFound,
str::stream() << bucketsIndexSpecWithStatus.getStatus().toString()
diff --git a/src/mongo/db/commands/list_indexes.cpp b/src/mongo/db/commands/list_indexes.cpp
index 5d207392b6a..ee927bb7dd6 100644
--- a/src/mongo/db/commands/list_indexes.cpp
+++ b/src/mongo/db/commands/list_indexes.cpp
@@ -63,51 +63,6 @@ namespace mongo {
namespace {
/**
- * Converts buckets collection index specs to the time-series collection schema.
- * Returns a list of index specs mapped from the bucket collection schema.
- */
-std::list<BSONObj> makeTimeseriesIndexSpecs(const TimeseriesOptions& timeseriesOptions,
- const std::list<BSONObj>& bucketsIndexSpecs) {
- std::list<BSONObj> indexSpecs;
- for (const auto& bucketsIndexSpec : bucketsIndexSpecs) {
- // TODO(SERVER-54639): Map index specs from bucket collection using helper function.
- BSONObjBuilder builder;
- bool skip = false;
- for (const auto& elem : bucketsIndexSpec) {
- if (elem.fieldNameStringData() == ListIndexesReplyItem::kKeyFieldName) {
- auto key = timeseries::convertBucketsIndexSpecToTimeseriesIndexSpec(
- timeseriesOptions, elem.Obj());
- if (key.isEmpty()) {
- // Skip index spec due to failed conversion.
- skip = true;
- break;
- }
- builder.append(ListIndexesReplyItem::kKeyFieldName, key);
- continue;
- }
- // Besides 'key', fields such as 'v' and 'name' commonly appear in the spec.
- // Depending on the index options, other fields that may be appended here
- // include 'sparse', 'hidden', 'collation'.
- // {
- // v: 2,
- // name: 'mm_1',
- // ...
- // sparse: true,
- // ...
- // }
- // For a complete list, refer to:
- // https://docs.mongodb.com/manual/reference/method/db.collection.createIndex/#options-for-all-index-types
- builder.append(elem);
- }
- if (skip) {
- continue;
- }
- indexSpecs.push_back(builder.obj());
- }
- return indexSpecs;
-}
-
-/**
* Returns index specs, with resolved namespace, from the catalog for this listIndexes request.
*/
using IndexSpecsWithNamespaceString = std::pair<std::list<BSONObj>, NamespaceString>;
@@ -128,7 +83,7 @@ IndexSpecsWithNamespaceString getIndexSpecsWithNamespaceString(OperationContext*
coll);
return std::make_pair(
- makeTimeseriesIndexSpecs(
+ timeseries::createTimeseriesIndexesFromBucketsIndexes(
*timeseriesOptions,
listIndexesInLock(opCtx, coll, bucketsNss, cmd.getIncludeBuildUUIDs())),
*origNss);
diff --git a/src/mongo/db/timeseries/timeseries_field_names.h b/src/mongo/db/timeseries/timeseries_field_names.h
index fdbd89240b4..7bc3a3c0417 100644
--- a/src/mongo/db/timeseries/timeseries_field_names.h
+++ b/src/mongo/db/timeseries/timeseries_field_names.h
@@ -41,5 +41,8 @@ static constexpr StringData kControlMinFieldNamePrefix = "control.min."_sd;
static constexpr StringData kTimeFieldName = "timeField"_sd;
static constexpr StringData kMetaFieldName = "metaField"_sd;
+// These are hard-coded field names in index specs.
+static constexpr StringData kKeyFieldName = "key"_sd;
+
} // namespace timeseries
} // namespace mongo
diff --git a/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.cpp b/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.cpp
index 49b9a15d3a7..2a14169b28f 100644
--- a/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.cpp
+++ b/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.cpp
@@ -57,7 +57,7 @@ boost::optional<TimeseriesOptions> getTimeseriesOptions(OperationContext* opCtx,
return view->timeseries();
}
-StatusWith<BSONObj> convertTimeseriesIndexSpecToBucketsIndexSpec(
+StatusWith<BSONObj> createBucketsIndexSpecFromTimeseriesIndexSpec(
const TimeseriesOptions& timeseriesOptions, const BSONObj& timeseriesIndexSpecBSON) {
auto timeField = timeseriesOptions.getTimeField();
auto metaField = timeseriesOptions.getMetaField();
@@ -127,8 +127,8 @@ StatusWith<BSONObj> convertTimeseriesIndexSpecToBucketsIndexSpec(
return builder.obj();
}
-BSONObj convertBucketsIndexSpecToTimeseriesIndexSpec(const TimeseriesOptions& timeseriesOptions,
- const BSONObj& bucketsIndexSpecBSON) {
+boost::optional<BSONObj> createTimeseriesIndexSpecFromBucketsIndexSpec(
+ const TimeseriesOptions& timeseriesOptions, const BSONObj& bucketsIndexSpecBSON) {
auto timeField = timeseriesOptions.getTimeField();
auto metaField = timeseriesOptions.getMetaField();
@@ -183,5 +183,33 @@ BSONObj convertBucketsIndexSpecToTimeseriesIndexSpec(const TimeseriesOptions& ti
return builder.obj();
}
+boost::optional<BSONObj> createTimeseriesIndexFromBucketsIndex(
+ const TimeseriesOptions& timeseriesOptions, const BSONObj& bucketsIndex) {
+ if (bucketsIndex.hasField(kKeyFieldName)) {
+ auto timeseriesKeyValue = createTimeseriesIndexSpecFromBucketsIndexSpec(
+ timeseriesOptions, bucketsIndex.getField(kKeyFieldName).Obj());
+ if (timeseriesKeyValue) {
+ // This creates a bsonobj copy with a modified kKeyFieldName field set to
+ // timeseriesKeyValue.
+ return bucketsIndex.addFields(BSON(kKeyFieldName << timeseriesKeyValue.get()),
+ StringDataSet{kKeyFieldName});
+ }
+ }
+ return boost::none;
+}
+
+std::list<BSONObj> createTimeseriesIndexesFromBucketsIndexes(
+ const TimeseriesOptions& timeseriesOptions, const std::list<BSONObj>& bucketsIndexes) {
+ std::list<BSONObj> indexSpecs;
+ for (const auto& bucketsIndex : bucketsIndexes) {
+ auto timeseriesIndex =
+ createTimeseriesIndexFromBucketsIndex(timeseriesOptions, bucketsIndex);
+ if (timeseriesIndex) {
+ indexSpecs.push_back(timeseriesIndex->getOwned());
+ }
+ }
+ return indexSpecs;
+}
+
} // namespace timeseries
} // namespace mongo
diff --git a/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.h b/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.h
index aec7cda44c7..a387a1022d7 100644
--- a/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.h
+++ b/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions.h
@@ -55,15 +55,15 @@ boost::optional<TimeseriesOptions> getTimeseriesOptions(OperationContext* opCtx,
*
* Returns an error if the specified 'timeseriesKeyBSON' is invalid for the time-series collection.
*/
-StatusWith<BSONObj> convertTimeseriesIndexSpecToBucketsIndexSpec(
+StatusWith<BSONObj> createBucketsIndexSpecFromTimeseriesIndexSpec(
const TimeseriesOptions& timeseriesOptions, const BSONObj& timeseriesIndexSpecBSON);
/**
* Maps the buckets collection index spec 'bucketsIndexSpecBSON' to the index schema of the
* time-series collection using the information provided in 'timeseriesOptions'.
*
- * If 'bucketsIndexSpecBSON' does not match a valid time-series index format, then an empty BSONObj
- * is returned.
+ * If 'bucketsIndexSpecBSON' does not match a valid time-series index format, then boost::none is
+ * returned.
*
* Conversion Example:
* On a time-series collection with 'tm' time field and 'mm' metadata field,
@@ -79,8 +79,27 @@ StatusWith<BSONObj> convertTimeseriesIndexSpecToBucketsIndexSpec(
* 'tm': 1
* }
*/
-BSONObj convertBucketsIndexSpecToTimeseriesIndexSpec(const TimeseriesOptions& timeseriesOptions,
- const BSONObj& bucketsIndexSpecBSON);
+boost::optional<BSONObj> createTimeseriesIndexSpecFromBucketsIndexSpec(
+ const TimeseriesOptions& timeseriesOptions, const BSONObj& bucketsIndexSpecBSON);
+
+/**
+ * Returns a time-series collection index spec equivalent to the given 'bucketsIndex' using the
+ * time-series specifications provided in 'timeseriesOptions'. Returns boost::none if the
+ * buckets index is not supported on a time-series collection.
+ *
+ * Copies and modifies the 'key' field of the buckets index, but otherwises copies all of the fields
+ * over unaltered.
+ */
+boost::optional<BSONObj> createTimeseriesIndexFromBucketsIndex(
+ const TimeseriesOptions& timeseriesOptions, const BSONObj& bucketsIndex);
+
+/**
+ * Returns a list of time-series collection index specs equivalent to the given 'bucketsIndexSpecs'
+ * using the time-series specifications provided in 'timeseriesOptions'. If any of the buckets
+ * indexes is not supported on a time-series collection, it will be ommitted from the results.
+ */
+std::list<BSONObj> createTimeseriesIndexesFromBucketsIndexes(
+ const TimeseriesOptions& timeseriesOptions, const std::list<BSONObj>& bucketsIndexes);
} // namespace timeseries
} // namespace mongo
diff --git a/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions_test.cpp b/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions_test.cpp
index 8da8db97f2a..6c5320c9fd3 100644
--- a/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions_test.cpp
+++ b/src/mongo/db/timeseries/timeseries_index_schema_conversion_functions_test.cpp
@@ -70,7 +70,7 @@ void testBothWaysIndexSpecConversion(const TimeseriesOptions& timeseriesOptions,
bool testShouldSucceed = true) {
// Test time-series => buckets schema conversion.
- auto swBucketsIndexSpecs = timeseries::convertTimeseriesIndexSpecToBucketsIndexSpec(
+ auto swBucketsIndexSpecs = timeseries::createBucketsIndexSpecFromTimeseriesIndexSpec(
timeseriesOptions, timeseriesIndexSpec);
if (testShouldSucceed) {
@@ -82,15 +82,16 @@ void testBothWaysIndexSpecConversion(const TimeseriesOptions& timeseriesOptions,
// Test buckets => time-series schema conversion.
- auto timeseriesIndexSpecResult = timeseries::convertBucketsIndexSpecToTimeseriesIndexSpec(
+ auto timeseriesIndexSpecResult = timeseries::createTimeseriesIndexSpecFromBucketsIndexSpec(
timeseriesOptions, bucketsIndexSpec);
if (testShouldSucceed) {
- ASSERT_BSONOBJ_EQ(timeseriesIndexSpec, timeseriesIndexSpecResult);
+ ASSERT(timeseriesIndexSpecResult);
+ ASSERT_BSONOBJ_EQ(timeseriesIndexSpec, timeseriesIndexSpecResult.get());
} else {
// A buckets collection index spec that does not conform to the supported time-series index
// spec schema should be converted to an empty time-series index spec result.
- ASSERT(timeseriesIndexSpecResult.isEmpty());
+ ASSERT(!timeseriesIndexSpecResult);
}
}