我正在尝试了解监视应用程序的最佳模型。
我有一个监视应用程序,它将每30分钟运行一次,以从目标系统获取统计信息并将详细信息存储在MongoDB中。
用例:
产品,公司
大约有2000种产品。将添加/删除产品,但每个月的增长率不会超过10%。因此,我预计未来1年不会超过3000。
公司是每种产品的消费者。每个使用该产品的公司将有1到10家公司。消费者人数也将上升或下降。
因此,在每次运行中,我们将获得产品列表以及相应的公司。产品详细信息如下:
产品:
产品的样品数据:
{
"productName" : "Small Box",
"total" : NumberLong(1000),
"weight" : "1.5",
"durability" : "20",
"companies" : [
{
"name" : "Nike",
"taken" : NumberLong(10)
},
{
"name" : "Reebok",
"taken" : NumberLong(20)
}
]
}
在这里,每次投票的计数都会不断变化。
网络应用程序:
将有3个屏幕显示详细信息。
产品-列表视图(要查看完整列表)-在选择任何产品时将显示产品的详细信息
在这里,我将必须显示产品详细信息,并必须列出所有消费的公司。
公司-列表视图(要查看完整列表)-将显示每个选择任何公司的公司详细信息
在这里,我将必须显示公司详细信息及其正在使用的所有产品。
我正在存储的方式。
仪表板集合-显示统计信息,例如产品总数,公司总数...
{ “时间” : “ totalProducts”:NumberLong(1000), “ totalCompanies”:“ 1.5”, }
产品集合-将具有以下详细信息。
{ "productName" : "Small Box", "total" : NumberLong(1000), "weight" : "1.5", "durability" : "20", "companies" : [ { "name" : "Nike", "taken" : NumberLong(10) }, { "name" : "Reebok", "taken" : NumberLong(20) } ] }
{ "companyName" : "Nike", "products" : [ { "name" : "Small Box", "taken" : NumberLong(10) }, { "name" : "Medium Box", "taken" : NumberLong(20) } ] }
因此,在每次运行中,我都会生成唯一的ID,并将此ID添加到要存储的所有数据中。我仅将这些集合中的最后两周的数据保留下来。每天都会清理2周以上的数据。
因此,当用户来到Dashboard时,请进行排序以获取最新记录并显示详细信息。 Dashboard集合中每次运行将只有一条记录,并且将有最近2周的记录。
当用户进入“产品”屏幕时,Still将不得不从仪表板获取最新记录以获取UniqueId,并转到Products集合以获取该UniqueId的所有记录,因为每次运行大约有2000条记录。公司集合也一样。
在这里,我将必须始终显示最新数据。当用户转到“产品或公司”屏幕时,我将转到2个不同的收藏集。
还有更好的方法吗?
答案 0 :(得分:3)
请检查其可帮助您准备模式 注意:Mongo版本:3.6.5
产品组合
/* 1 */
{
"_id" : ObjectId("5bb1e270269004e06093e178"),
"productName" : "Small Box",
"total" : NumberLong(1000),
"weight" : "1.5",
"durability" : "20",
"companies" : [
ObjectId("5bb1e2d2269004e06093e17b"),
ObjectId("5bb1e2d8269004e06093e17c")
],
"date" : ISODate("2018-10-01T09:28:40.502Z")
}
/* 2 */
{
"_id" : ObjectId("5bb1e293269004e06093e179"),
"productName" : "Large Box",
"total" : 1000.0,
"weight" : "1.2",
"durability" : "20",
"companies" : [
ObjectId("5bb1e2d8269004e06093e17c"),
ObjectId("5bb1e2de269004e06093e17d")
],
"date" : ISODate("2018-10-01T09:28:40.502Z")
}
/* 3 */
{
"_id" : ObjectId("5bb1e29d269004e06093e17a"),
"productName" : "Medium Box",
"total" : 1000.0,
"weight" : "1.2",
"durability" : "20",
"companies" : [
ObjectId("5bb1e2d2269004e06093e17b"),
ObjectId("5bb1e2d8269004e06093e17c"),
ObjectId("5bb1e2de269004e06093e17d")
],
"date" : ISODate("2018-07-01T09:28:40.502Z")
}
公司收藏
/* 1 */
{
"_id" : ObjectId("5bb1e2d2269004e06093e17b"),
"companyName" : "Nike"
}
/* 2 */
{
"_id" : ObjectId("5bb1e2d8269004e06093e17c"),
"companyName" : "Reebok"
}
/* 3 */
{
"_id" : ObjectId("5bb1e2de269004e06093e17d"),
"companyName" : "PUMA"
}
使用comapny获取单个产品
db.getCollection('products').aggregate([{
$match : { "_id" : ObjectId("5bb1e270269004e06093e178") } },
{ $lookup : {
from : 'company',
foreignField : '_id',
localField : 'companies',
as : 'companies'
}
}
])
所有带有公司列表的产品
db.getCollection('products').aggregate([
{ $lookup : {
from : 'company',
foreignField : '_id',
localField : 'companies',
as : 'companies'
}
}
])
公司ID和二手产品
db.getCollection('company').aggregate([{
$match : { "_id" : ObjectId("5bb1e2d2269004e06093e17b") } },
{ $lookup : {
from : 'products',
foreignField : 'companies',
localField : '_id',
as : 'products'
}
}
])
还可以通过在每个产品中添加日期字段来获得上周数据
db.getCollection('products').aggregate([{
$match : {
date: {
$gte: new Date(new Date() - 7 * 60 * 60 * 24 * 1000)
} } },
{ $lookup : {
from : 'products',
foreignField : 'companies',
localField : '_id',
as : 'products'
}
}
])
获取公司的最新产品
db.getCollection('products').aggregate([
{ $sort : { date : -1} },
{ $limit : 1},
{ $lookup : {
from : 'company',
foreignField : '_id',
localField : 'companies',
as : 'companies'
}
}
])
答案 1 :(得分:0)
因此,每次运行时,我都会生成唯一的ID,并将此ID添加到所有要存储的数据中。我仅将这些集合中的最后两周的数据保留下来。每天都会清理2周以上的数据。
我不会那样做。我会使用_id,mongodb自动给您。并制作一个runobject来收集所有这些对象id。因为每个对象拥有1个键比336个键(48(每天30分钟)x 14(2周内的天数))更好。
我将创建一个运行对象,其中包含company_id,product_id和时间戳的数组。如果30分钟内未发生任何变化,我将只使用一个运行对象_id(与第一个相同)和一个时间戳。这样就节省了很多空间。
希望我能正确理解您,因为这对我来说很难读。