2017-04-09 3 views
1

Ich versuche, Objekt in MongoDB zu speichern. Diese Objekte stammen aus dem System eines Drittanbieters und haben ein sehr spezifisches Format, d. H. Alle Objekteigenschaften sind im Wörterbuch gespeichert. Die Werte in diesem Wörterbuch können von unterschiedlicher Art und in keiner bestimmten Reihenfolge sein.

Ich glaube, um effektiv auf diesen Bereich zu suchen, muss ich sie in BSON Eigenschaften verwandeln. Und es ist machbar mit benutzerdefinierten Serializer/Deserializer, bis es zur Deserialisierung selbst kommt. Wenn die Eigenschaft ein komplexes Objekt ist, das als BSON-Dokument dargestellt wird, weiß Custom Deseriazer nicht, zu welchem ​​Typ dieses Dokument transformiert werden soll.

Wie Probleme wie diese mit MongoDB BSON richtig gelöst werden?

Ich würde neue Eigenschaft $type zu komplexen Dokument hinzufügen und dort Zieltyp während der Serialisierung speichern, aber es stört Build in MongoDB $type Eigenschaft.

Ist es möglich, standardmäßige und benutzerdefinierte $type Attribute nebeneinander zu verwenden? Was ist der Best-Practice-Ansatz für die Implementierung von Custom Deserializer in diesem Fall?

Antwort

1

nicht ohne die Spezifikation selbst zu erweitern oder einen Verweis darauf, wie es im Dokument selbst (de) serialisiert werden sollte.

PHP-Treiber hat ein ODM-Framework, das genau was Sie vorschlagen. Ich schlage vor, Sie schauen http://php.net/manual/en/class.mongodb-bson-persistable.php

Bei der Serialisierung wird der Fahrer eine __pclass Eigenschaft injizieren die PHP-Klassennamen in die Daten

So enthält, fügt es eine specifc Schlüssel „__pclass“ auf das Dokument zu speichernden. Während der Deserialisierung liest der Treiber den Schlüssel aus, um zu entscheiden, welche spezifischen Deserialisierungsschritte auszuführen sind, und entfernt den Schlüssel __pclass/value, bevor er das Dokument an den Benutzer zurückgibt (jetzt deserialisiert in die vom __pclass-Schlüssel angegebene PHP-Klasse).

Dies ist unglaublich gefährlich, wenn Sie einen Grund haben, den in mongodb gespeicherten Daten nicht zu vertrauen. Es ermöglicht im Grunde, dass Daten einen Aufruf von ausführbarem PHP-Code diktieren.

Über die Spezifikation selbst. http://bsonspec.org/spec.html

Die Typen und der zugehörige Typenindex sind in der Spezifikation fest codiert.

element  ::=  "\x01" e_name double 64-bit binary floating point 
    | "\x02" e_name string UTF-8 string 
    | "\x03" e_name document Embedded document 
    | "\x04" e_name document Array 
    | "\x05" e_name binary Binary data 
    | "\x06" e_name Undefined (value) — Deprecated 
    | "\x07" e_name (byte*12)  ObjectId 
    | "\x08" e_name "\x00" Boolean "false" 
    | "\x08" e_name "\x01" Boolean "true" 
    | "\x09" e_name int64  UTC datetime 
    | "\x0A" e_name Null value 
    | "\x0B" e_name cstring cstring Regular expression - The first cstring is the regex pattern, the second is the regex options string. Options are identified by characters, which must be stored in alphabetical order. Valid options are 'i' for case insensitive matching, 'm' for multiline matching, 'x' for verbose mode, 'l' to make \w, \W, etc. locale dependent, 's' for dotall mode ('.' matches everything), and 'u' to make \w, \W, etc. match unicode. 
    | "\x0C" e_name string (byte*12) DBPointer — Deprecated 
    | "\x0D" e_name string JavaScript code 
    | "\x0E" e_name string Symbol. Deprecated 
    | "\x0F" e_name code_w_s JavaScript code w/ scope 
    | "\x10" e_name int32  32-bit integer 
    | "\x11" e_name uint64 Timestamp 
    | "\x12" e_name int64  64-bit integer 
    | "\x13" e_name decimal128 128-bit decimal floating point 
    | "\xFF" e_name Min key 
    | "\x7F" e_name Max key 

könnten Sie Ihre eigenen Benutzer erzeugten binäre Subtyp erstellen, wenn Sie das Blob in einem binären Block gespeichert, den benutzerdefinierten Subtyp Bereich verwendet wird.

binary ::=  int32 **subtype** (byte*) Binary - The int32 is the number of bytes in the (byte*). 

subtype  ::=  "\x00" Generic binary subtype 
    | "\x01" Function 
    | "\x02" Binary (Old) 
    | "\x03" UUID (Old) 
    | "\x04" UUID 
    | "\x05" MD5 
    | **"\x80" User defined** 

Die Kehrseite ist, dass das Objekt würde in der Datenbank als binäres Blob gespeichert wird, ist es sehr schwierig macht, über Subtyp Prüfung abzufragen.

Alles darüber hinaus würde bedeuten, die Spezifikation selbst zu erweitern

Verwandte Themen