将网站配置存储为Mongoose模型

8

我可以帮您进行翻译。以下是需要翻译的内容:

我有一个网站配置(目前存储为JSON文件),我想将其移动到MongoDB,并可能使用Mongoose来处理读写操作并通过模式执行验证。

配置是一个具有有限键数的对象,类似于以下内容:

{
  siteOffline: false,
  storeOffline: false,
  priceMultipliers: {
    a1: 0.96
    a2: 0.85
  },
  ...
}

是否应该创建一个具有键值条目的集合?不确定如何在这种情况下强制执行Mongoose模式。

是否应该创建一个只有单个文档的集合?不确定如何保证一次只有一个文档。

还有其他选项吗?


那么你只需要一次存储一个文档吗?我不确定你是否需要一个数据库。Mongo模式用于存储相同数据结构(也称为结构化数据)的多个实例。 - nadavvadan
是的,一次只能处理一个。我可以使用静态JSON文件进行只读访问,但由于配置应该从后端实时修改,并且已经使用了Mongoose,因此我想使用它进行验证、并发访问和缓存插件等。 - Estus Flask
2个回答

7

好的,一次只做一件事:

如果您想使用mongoose,您应该将完整的配置作为一个文档:

var siteConfig = new Schema({
  siteOffline: Boolean,
  storeOffline: Boolean,
  priceMultipliers: {
    a1: Number
    a2: Number
  } 
});

如果您需要仅包含一个文档的集合,可以使用MongoDB封顶集合

我建议您查看Mongoose允许的多个选项,在这里

适用于您的单文档集合的模式应该类似于:

   var config = new Schema({
      siteOffline: Boolean,
      storeOffline: Boolean,
      priceMultipliers: {
        a1: Number
        a2: Number
      } 
    }, { 
      collection:'config',
      capped: { size: 1024, max: 1} 
    });

只有一个文档的“集合”确实有些讽刺 :)

另一种可能更适合您的“黑客”解决方案是使用安全字段(您无法更改其值),并在该字段上添加唯一索引。 阅读此处以获取更多信息 该字段可以存在于文档中但不在模型中(虚拟)。再次强调,这是hacky的,但是您的用例也有点奇怪 :)


封顶集合看起来像一个不错的技巧。然而,让我担心的是更新文档。通常情况下,做类似于“查找并插入”的操作会很好,但封顶集合似乎只限于插入操作。 - Estus Flask
这很简洁,但肯定是非常hacky的。我会尝试提供替代方案。 - xShirase
谢谢,我最终得到了一个具有默认值的唯一字段,并且这个默认值也是该字段允许的唯一值。但是使用限制方法也可以。 - Estus Flask

4

使用截断法是可行的,但它不允许更新字段。有一个更好的解决方案:使用immutable字段属性(>= mongoose v5.6)。

此外,你可以在模式中添加collection选项来防止mongoose对集合名称进行复数处理。

let configSchema = new Schema(
    {
        _immutable: {
            type: Boolean,
            default: true,
            required: true,
            unique : true,
            immutable: true,
        },

        siteOffline: Boolean,
        storeOffline: Boolean,
        priceMultipliers: {
            a1: Number
            a2: Number
        },
    },
    {
        collection:'config',
    }
);

var Config = mongoose.model( 'config', configSchema );
Config.updateOne( {}, { siteOffline: false });

我希望这能有所帮助。


谢谢,这看起来很有前途。我还没有使用不可变字段。_immutable是一个随机的内部名称,它强制执行了一些限制,对吗?您能否在答案中添加如何更新它的说明? - Estus Flask
1
我刚刚更新了答案。更新时没有什么特别的要做的。您可以将“_immutable”替换为任何其他字段名。 - Raphael Deiana

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接