Warning: file_get_contents(/data/phpspider/zhask/data//catemap/6/mongodb/13.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Php 如何在mongodb中更改集合结构?_Php_Mongodb_Collections_Alter Table - Fatal编程技术网

Php 如何在mongodb中更改集合结构?

Php 如何在mongodb中更改集合结构?,php,mongodb,collections,alter-table,Php,Mongodb,Collections,Alter Table,我有一个mongodb系列,如 { "_id" : 57, "value" : { "user" : [ { "fk_status_id" : "0", "firstname" : "Ajith", "lastname" : "S", "city" : "known", "State" :"kerala"

我有一个mongodb系列,如

{
"_id" : 57,
"value" : {
    "user" : [ 
     {
            "fk_status_id"  : "0",
            "firstname"     : "Ajith",
            "lastname"      : "S",
            "city"          : "known",
            "State"         :"kerala",          
            "location" : {
                "lat" : 34.123456,
                "lon" : -95.123456
            },
     }

    ],
}}
拥有数百万文档

{
"_id" : 58,
    "user" : [ 
     {
            "fk_status_id"  : "0",
            "firstname"     : "Ajith",
            "lastname"      : "S",
            "city"          : "known",
            "State"         :"kerala",          
            "location" : {
                "lat" : 34.123456,
                "lon" : -95.123456
            },
     }

    ]}
我想像这样修改表结构

{
"_id" : 58,
    "user" : [ 
     {
            "fk_status_id"  : "0",
            "firstname"     : "Ajith",
            "lastname"      : "S",
            "city"          : "known",
            "State"         :"kerala",          
            "location" : {
                "lat" : 34.123456,
                "lon" : -95.123456
            },
     }

    ]}
我的意思是,我想从这个结构中省略'value{}'。

  • 数据应该在“值”之外。 请解决我的问题

您没有回答给出的评论,但重要的是要说明原因

所以,如果你真的有“数以百万计的文档”,你现在必须修改并迅速完成,那么你就有一个明确的问题要面对。由于没有“原子”操作可以通过“引用”现有字段中的值来作用于文档,从而应用于更新,因此唯一的方法是实际循环结果:

db.collection.find().forEach(function(doc) {
    var user = doc.value.user;

    delete doc.value;

   db.collection.update(
       { "_id": doc._id },
       { "$set": { "user": user } }
   );

})
这是基本的过程,对于大型数据集来说有点可怕

但是对于“一次性”转换,有一种方法可以做到这一点,尽管这不是一种很好的方法,它被称为
db.eval()
方法。但请注意文档(手册页面的大翻页):

警告

  • 默认情况下,db.eval()在计算JavaScript函数之前接受全局写锁。因此,在运行db.eval()操作时,db.eval()会阻止对数据库的所有其他读写操作。在eval命令上将nolock设置为true,以防止eval命令在评估JavaScript之前获取全局写锁。nolock不影响JavaScript代码本身中的操作是否具有写锁

  • 不要将db.eval()用于长时间运行的操作,因为db.eval()会阻止所有其他操作。考虑使用.< /P>
  • 不能对数据使用db.eval()。通常,应该避免在中使用db.eval();不过,可以将db.eval()用于存储在数据库中的非分片集合和数据库

  • 启用身份验证后,如果您没有执行指定任务的权限,db.eval()将在操作期间失败

在版本2.4中更改:您必须具有完全管理员权限才能运行

这样一来,如果这真的符合您的情况,那么我们就不需要成为鸵鸟(将我们的头埋在“神话”的沙子中),而需要实际做一些可以在服务器上运行的事情来实现这一点:

db.eval(function() {

    db.collection.find().forEach(function(doc) {
        var user = doc.value.user;

        delete doc.value;

        db.collection.update(
            { "_id": doc._id },
            { "$set": { "user": user } }
        );

    });

});
当然,正如所建议的那样,还有其他方法来实现这一点

  • mapReduce可以在某种程度上做到这一点,而不存在锁定问题,但是输出仍然需要大量的重塑,以及集合重命名和替换

  • 在服务器上实际运行(或在网络中最接近),这可能是最好的选择。通过这种方式,您可以安全地编码并避免扩展锁定问题


但是,如果您真的像以前那样“陷入困境”,那么服务器上的JavaScript执行将修复您需要的特定问题。

您已经切分了吗?你能在数据库节点上直接连接到shell吗?不,它不是分片的