Ordem de campo do MongoDB e alteração da posição do documento após a atualização

Estou aprendendo MongoDB e notei que sempre que eu faço uma atualização em um documento, o campo que está sendo atualizado é empurrado para o final do pedido, então se eu tivesse algo como:

db.collection.save({field1: value1, field2: value2, ..., field 10: value10}); db.collection.update({field1: value1}, {$set: {field2: new_value}}); 

então se você fizer:

 db.collection.find(); 

Ele irá mostrar:

 { "field1":"value1", ..., "field10":"value10", "field2":"new_value"} 

Você pode ver como a ordem de campo muda onde o campo atualizado está sendo empurrado para o final do documento. Além disso, o documento em si está sendo empurrado para o final da coleta. Eu sei que é um DB “sem esquema” e pode não ser um grande problema, mas não parece “bonito” :). Existe uma maneira de fazer uma atualização no local sem alterar o pedido?

O MongoDB aloca espaço para um novo documento com base em um determinado fator de preenchimento. Se a sua atualização aumentar o tamanho do documento além do tamanho originalmente alocado, o documento será movido para o final da coleção. O mesmo conceito se aplica a campos em um documento.

FYI, no MongoDB, as atualizações 2.6 preservarão a ordem dos campos, com as seguintes exceções:

  1. O campo _id é sempre o primeiro campo no documento.
  2. Atualizações que incluem a renomeação de nomes de campos podem resultar na reordenação de campos no documento.

Tanto a estrutura do documento quanto a estrutura da coleção no MongoDB com base nos princípios do JSON. JSON é um conjunto de pares chave / valor (em particular fieldName / fieldValue para documento e índice / documento para coleção). Deste ponto de vista, não parece que você pode confiar na ordem.

No caso dos documentos, se o tamanho do campo for alterado, ele gravará um novo documento com os campos classificados por nome de campo. Esse comportamento pode ser visto com as seguintes declarações

Caso 1: Nenhuma alteração no tamanho do campo, portanto, nenhuma alteração na ordem de campo

 > db.testcol.find() > db.testcol.save({a:1,c:3,b:2}) > db.testcol.find() { "_id" : ObjectId("4d5efc3bec5855af36834f5a"), "a" : 1, "c" : 3, "b" : 2 } > db.testcol.update({a:1},{$set:{c:22}}) > db.testcol.find() { "_id" : ObjectId("4d5efc3bec5855af36834f5a"), "a" : 1, "c" : 22, "b" : 2 } 

Caso 2: Alterações no tamanho do campo e os campos são refocados

 > db.testcol.find() > db.testcol.save({a:1,c:"foo",b:2,d:4}) > db.testcol.find() { "_id" : ObjectId("4d5efdceec5855af36834f5e"), "a" : 1, "c" : "foo", "b" : 2, "d" : 4 } > db.testcol.update({a:1},{$set:{c:"foobar"}}) > db.testcol.find() { "_id" : ObjectId("4d5efdceec5855af36834f5e"), "a" : 1, "b" : 2, "c" : "foobar", "d" : 4 } 

Existe uma razão específica pela qual você não deseja que os campos sejam reordenados? O acima foi usando 1.8.0_rc0 no OS X

Eu criei um projeto que cria um mongorc.js personalizado que classifica as chaves do documento por padrão para você. Chama-se Mongo Hacker

Raman, está certo, não podemos classificar um dictionary, mas podemos ordenar a visualização do dictionary, por isso não podemos classificar a ordem arquivada de uma documentação, mas posso vê-la ordenada.

Por exemplo, em perl to_json tem opção canônica

 print to_json( $data, { utf8 => 1, pretty => 1, convert_blessed => 1, canonical => 1 } ); 

(opção canônica) produzirá objects JSON classificando suas chaves. Isso está adicionando uma sobrecarga comparativamente alta. (claro, fazemos mais uma operação de sorting …)