2012-07-06 12 views
15

Używam wersji 2.06 Mongodb i wersji (1.5) sterownika C# dostarczonego przez 10Gen.Z mongodb i guids dla Id dokumentów, co jest skutecznym sposobem przechowywania Guids, aby łatwo odzyskać faktyczne Guid?

Każdy z moich jednostek ma konfigurację właściwości ID jako takie ...

[BsonId(IdGenerator = typeof(GuidGenerator))] 
public Guid Id { get; set; } 

pole id jest przechowywana jako Binary - 3: UuidLegacy. Ze względu na to, jak jest przechowywany, gdy wywołuję ToJson() na obiekcie, zwraca następujący obiekt javascript dla identyfikatora.

_id : Object 
$binary: "some values here" 
$type: "03" 

Dzieje się tak oczywiście dlatego, że dane są zapisywane jako Binary = 3: UuidLegacy. To ma sens.

Chcę użyć rzeczywistego Guida w moim kodzie JavaScript. Jak wydajne byłoby MongoDB, gdyby moje właściwości Id wyglądały następująco?

[BsonId(IdGenerator = typeof(GuidGenerator)),MongoDB.Bson.Serialization.Attributes.BsonRepresentation(BsonType.String)] 
public Guid Id { get; set; } 

To sprawia, że ​​mongodb przechowuje mój Id jako ciąg. Ale jak skuteczny jest to naprawdę? Zgaduję, że format binarny dla mojego Id jest lepszy, ale naprawdę potrzebuję Guida.

Jak mogę przejść z Binary - 3: uuidLegacy do Guida, którego potrzebuję w moim jsonie?

Przypuszczam, że inna myśl mogłaby bym po prostu użyć wartości binarnej $, która została mi wysłana? Używam identyfikatora do wykonywania wyszukiwań i takich, jak część moich ciągów zapytań.

Dzięki,

Odpowiedz

25

Praca z GUID ma kilka pułapek, głównie związanych z jak pracować z binarnej reprezentacji w powłoce Mongo, a także do wypadków historycznych, które doprowadziły do ​​przechowywania różnych sterowników GUID za pomocą różnych zleceń bajtów.

Użyłem poniższy kod do zilustrowania zagadnienia:

var document = new BsonDocument { { "_id", Guid.NewGuid() }, { "x", 1 } }; 
collection.Drop(); 
collection.Insert(document); 
Console.WriteLine("Inserted GUID: {0}", document["_id"].AsGuid); 

który kiedy prowadził ją wyjściowe:

Inserted GUID: 2d25b9c6-6d30-4441-a360-47e7804c62be 

kiedy wyświetlać tego w powłoce Mongo uzyskać:

> var doc = db.test.findOne() 
> doc 
{ "_id" : BinData(3,"xrklLTBtQUSjYEfngExivg=="), "x" : 1 } 
> doc._id.hex() 
c6b9252d306d4144a36047e7804c62be 
> 

Należy zauważyć, że nawet w przypadku wyświetlania w postaci szesnastkowej kolejność bajtów nie jest zgodna z oryginalnym identyfikatorem GUID. To historyczny wypadek, o którym mówiłem. Wszystkie bajty są tam, są w nietypowej kolejności dzięki implementacji Guid.ToByteArray() przez Microsoft.

Aby ułatwić pracę z GUID w Mongo shell można skopiować poniższy plik funkcji pomocniczych do katalogu, w którym jest przechowywany mongo.exe:

https://github.com/rstam/mongo-csharp-driver/blob/master/uuidhelpers.js

plik ma kilka krótkich uwag w dokumentacji górny, który może ci się przydać. Aby udostępnić te funkcje w powłoce Mongo, musisz powiedzieć powłoce Mongo, aby przeczytała ten plik podczas uruchamiania.Zobacz następujący sesji próbkowania:

C:\mongodb\mongodb-win32-x86_64-2.0.6\bin>mongo --shell uuidhelpers.js 
MongoDB shell version: 2.0.6 
connecting to: test 
type "help" for help 
> var doc = db.test.findOne() 
> doc 
{ "_id" : BinData(3,"xrklLTBtQUSjYEfngExivg=="), "x" : 1 } 
> doc._id.hex() 
c6b9252d306d4144a36047e7804c62be 
> doc._id.toCSUUID() 
CSUUID("2d25b9c6-6d30-4441-a360-47e7804c62be") 
> 

Można również użyć innej funkcji pomocniczych do kwerendy dla GUID:

> db.test.find({_id : CSUUID("2d25b9c6-6d30-4441-a360-47e7804c62be")}) 
{ "_id" : BinData(3,"xrklLTBtQUSjYEfngExivg=="), "x" : 1 } 
> 

Jeśli chodzi o przechowywanie GUID jako ciągi, że nie jest to niespotykane rzeczy to zrobić i zdecydowanie ułatwia przeglądanie i wysyłanie zapytań do danych w powłoce Mongo i pozwala uniknąć wszystkich problemów związanych z kolejnymi bajtami. Jedyną wadą jest to, że wykorzystuje więcej miejsca (mniej więcej dwukrotnie).

+0

Witaj Robert! Dziękuję za odpowiedź, bardzo doceniona. Podwojenie wymagań dotyczących przestrzeni jest dla mnie problemem. – RDotLee

+1

Inną wadą, jaką słyszałem z przechowywaniem identyfikatorów GUID jako ciągów, jest to, że nie można używać struktury agregacji mongodb. –

+0

"Podwajanie" jest przerażającym słowem, ale dotyczy tylko pola GUID, które ma tylko 17 (?) Bajtów w BSON. Łańcuch zajmie 36 bajtów, co * jest * w przybliżeniu podwójne, ale wciąż tylko dodatkowe 19 bajtów na GUID. Jeśli 19 dodatkowych bajtów na GUID jest problemem dla ciebie, BSON prawdopodobnie nie jest formatem dla ciebie. – meustrus

Powiązane problemy