文档菜单
文档首页
/
MongoDB 手册
/ /

创建和查询时间序列集合

本页内容

  • 创建时间序列集合
  • 向时间序列集合中插入测量值
  • 查询时间序列集合
  • 在时间序列集合上运行聚合

本页展示了如何创建和查询时间序列集合,并提供了代码示例。

重要

功能兼容性版本要求

您只能在将featureCompatibilityVersion 设置为 5.0 或更高版本的系统上创建时间序列集合。

1

定义timeField 为包含时间数据的字段,以及 metaField 为包含元数据的字段

{
timeField: "timestamp",
metaField: "metadata"
}

在此示例中,timestamptimeField 的名称,而 metadatametaField 的名称。 timestamp 字段的值必须是 日期 类型。

重要

选择适合您集合的正确的 metaField 可以优化存储和查询性能。有关 metaField 选择和最佳实践的更多信息,请参阅 元字段。

2

使用以下两种方法之一为每个数据桶定义时间间隔

重要

更改时间序列间隔

创建后,您可以使用 collMod 方法修改粒度或桶定义。但是,您只能增加每个桶覆盖的时间跨度。您不能减少它。

  1. 定义一个 granularity 字段

    {
    granularity: "seconds"
    }

    有关选择 granularity 值的更多信息,请参阅 粒度注意事项。

或者

  1. 在 MongoDB 6.3 及更高版本中,您可以定义 bucketMaxSpanSecondsbucketRoundingSeconds 字段。这两个值必须相同

    {
    bucketMaxSpanSeconds: "300",
    bucketRoundingSeconds: "300"
    }
3

可选地,设置 expireAfterSeconds 以在 timeField 的值至少那么旧时过期文档

{
expireAfterSeconds: 86400
}
4

使用 db.createCollection() 方法或 create 命令创建集合。以下示例使用 db.createCollection() 方法创建一个 weather 时间序列集合

db.createCollection(
"weather",
{
timeseries: {
timeField: "timestamp",
metaField: "metadata",
granularity: "seconds"
},
expireAfterSeconds: 86400
}
)

时间序列集合包含以下字段

字段
类型
描述
timeseries.timeField
字符串

必需。包含每个时间序列文档中日期的字段名称。时间序列集合中的文档必须使用有效的 BSON 日期作为 timeField 的值。

timeseries.metaField
字符串

可选。包含每个时间序列文档中元数据的字段名称。指定字段中的元数据应该是用于标记唯一文档序列的数据。元数据很少或几乎不改变。指定字段的名称不能是 _id 或与 timeseries.timeField 相同。该字段可以是任何数据类型。

虽然 metaField 字段是可选的,但使用元数据可以提高查询优化。例如,MongoDB 自动为新集合在 metaFieldtimeField 字段上创建组合索引。如果您不提供此字段的值,数据将仅基于时间进行分桶。

timeseries.granularity
整数

可选。如果设置了 bucketRoundingSecondsbucketMaxSpanSeconds,则不要使用。

可能的值是 seconds(默认值)、minuteshours

granularity 设置为与连续传入的时间戳之间的时间最接近的值。这通过优化 MongoDB 在集合中存储数据的方式来提高性能。

有关粒度和分桶间隔的更多信息,请参阅 为时间序列数据设置粒度。

timeseries.bucketMaxSpanSeconds
整数

可选。与 bucketRoundingSeconds 一起使用,作为 granularity 的替代方案。设置同一桶中时间戳之间的最大时间。

可能的值是 1-31536000。

在版本6.3.

timeseries.bucketRoundingSeconds
整数

可选。与 bucketMaxSpanSeconds 一起使用,作为 granularity 的替代方案。必须等于 bucketMaxSpanSeconds

当文档需要一个新桶时,MongoDB 会将文档的时间戳值向下舍入此间隔,以设置桶的最小时间。

在版本6.3.

expireAfterSeconds
整数
可选。通过指定文档过期的秒数,启用时间序列集合中文档的自动删除。MongoDB会自动删除过期的文档。有关更多信息,请参阅设置时间序列集合的自动删除(TTL)

其他允许的选项(非时间序列集合特定)包括

  • storageEngine

  • indexOptionDefaults

  • collation

  • writeConcern

  • comment

提示

请参阅

您插入的每个文档应包含一个单独的测量值。要一次性插入多个文档,请执行以下命令

db.weather.insertMany( [
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-18T00:00:00.000Z"),
temp: 12
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-18T04:00:00.000Z"),
temp: 11
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-18T08:00:00.000Z"),
temp: 11
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-18T12:00:00.000Z"),
temp: 12
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-18T16:00:00.000Z"),
temp: 16
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-18T20:00:00.000Z"),
temp: 15
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-19T00:00:00.000Z"),
temp: 13
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-19T04:00:00.000Z"),
temp: 12
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-19T08:00:00.000Z"),
temp: 11
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-19T12:00:00.000Z"),
temp: 12
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-19T16:00:00.000Z"),
temp: 17
},
{
metadata: { sensorId: 5578, type: "temperature" },
timestamp: ISODate("2021-05-19T20:00:00.000Z"),
temp: 12
}
] )

要插入单个文档,请使用db.collection.insertOne()方法。

提示

优化插入性能

有关如何优化大量操作的插入,请参阅插入最佳实践。

您可以通过与查询标准MongoDB集合相同的方式查询时间序列集合。

要从时间序列集合返回一个文档,请运行

db.weather.findOne( {
timestamp: ISODate("2021-05-18T00:00:00.000Z")
} )

示例输出

{
timestamp: ISODate("2021-05-18T00:00:00.000Z"),
metadata: { sensorId: 5578, type: 'temperature' },
temp: 12,
_id: ObjectId("62f11bbf1e52f124b84479ad")
}

有关时间序列查询的更多信息,请参阅查询最佳实践。

为了增加查询功能,请使用聚合管道,例如

db.weather.aggregate( [
{
$project: {
date: {
$dateToParts: { date: "$timestamp" }
},
temp: 1
}
},
{
$group: {
_id: {
date: {
year: "$date.year",
month: "$date.month",
day: "$date.day"
}
},
avgTmp: { $avg: "$temp" }
}
}
] )

示例聚合管道将所有文档按测量日期分组,然后返回该日所有温度测量的平均值

{
"_id" : {
"date" : {
"year" : 2021,
"month" : 5,
"day" : 18
}
},
"avgTmp" : 12.714285714285714
}
{
"_id" : {
"date" : {
"year" : 2021,
"month" : 5,
"day" : 19
}
},
"avgTmp" : 13
}

返回

创建和配置