public void TestBookmark() { var json = "{ \"x\" : 1, \"y\" : 2 }"; using (bsonReader = BsonReader.Create(json)) { // do everything twice returning to bookmark in between var bookmark = bsonReader.GetBookmark(); Assert.AreEqual(BsonType.Document, bsonReader.ReadBsonType()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual(BsonType.Document, bsonReader.ReadBsonType()); bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); bsonReader.ReturnToBookmark(bookmark); bsonReader.ReadStartDocument(); bookmark = bsonReader.GetBookmark(); Assert.AreEqual(BsonType.Int32, bsonReader.ReadBsonType()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual(BsonType.Int32, bsonReader.ReadBsonType()); bookmark = bsonReader.GetBookmark(); Assert.AreEqual("x", bsonReader.ReadName()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual("x", bsonReader.ReadName()); bookmark = bsonReader.GetBookmark(); Assert.AreEqual(1, bsonReader.ReadInt32()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual(1, bsonReader.ReadInt32()); bookmark = bsonReader.GetBookmark(); Assert.AreEqual(BsonType.Int32, bsonReader.ReadBsonType()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual(BsonType.Int32, bsonReader.ReadBsonType()); bookmark = bsonReader.GetBookmark(); Assert.AreEqual("y", bsonReader.ReadName()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual("y", bsonReader.ReadName()); bookmark = bsonReader.GetBookmark(); Assert.AreEqual(2, bsonReader.ReadInt32()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual(2, bsonReader.ReadInt32()); bookmark = bsonReader.GetBookmark(); Assert.AreEqual(BsonType.EndOfDocument, bsonReader.ReadBsonType()); bsonReader.ReturnToBookmark(bookmark); Assert.AreEqual(BsonType.EndOfDocument, bsonReader.ReadBsonType()); bookmark = bsonReader.GetBookmark(); bsonReader.ReadEndDocument(); bsonReader.ReturnToBookmark(bookmark); bsonReader.ReadEndDocument(); Assert.AreEqual(BsonReaderState.Done, bsonReader.State); } Assert.AreEqual(json, BsonSerializer.Deserialize <BsonDocument>(new StringReader(json)).ToJson()); }
// public methods /// <summary> /// Gets the actual type of an object by reading the discriminator from a BsonReader. /// </summary> /// <param name="bsonReader">The reader.</param> /// <param name="nominalType">The nominal type.</param> /// <returns>The actual type.</returns> public Type GetActualType(BsonReader bsonReader, Type nominalType) { // the BsonReader is sitting at the value whose actual type needs to be found var bsonType = bsonReader.GetCurrentBsonType(); if (bsonType == BsonType.Document) { // ensure KnownTypes of nominalType are registered (so IsTypeDiscriminated returns correct answer) BsonSerializer.EnsureKnownTypesAreRegistered(nominalType); // we can skip looking for a discriminator if nominalType has no discriminated sub types if (BsonSerializer.IsTypeDiscriminated(nominalType)) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var actualType = nominalType; if (bsonReader.FindElement(_elementName)) { var context = BsonDeserializationContext.CreateRoot <BsonValue>(bsonReader); var discriminator = BsonValueSerializer.Instance.Deserialize(context); if (discriminator.IsBsonArray) { discriminator = discriminator.AsBsonArray.Last(); // last item is leaf class discriminator } actualType = BsonSerializer.LookupActualType(nominalType, discriminator); } bsonReader.ReturnToBookmark(bookmark); return(actualType); } } return(nominalType); }
public Type GetActualType( BsonReader bsonReader, Type nominalType ) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var actualType = nominalType; while (bsonReader.ReadBsonType() != BsonType.EndOfDocument) { var name = bsonReader.ReadName(); if (name == "OnlyInB") { actualType = typeof(B); break; } else if (name == "OnlyInC") { actualType = typeof(C); break; } bsonReader.SkipValue(); } bsonReader.ReturnToBookmark(bookmark); return(actualType); }
// private methods private Type GetActualType(BsonReader bsonReader) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); if (bsonReader.FindElement("type")) { var type = bsonReader.ReadString(); bsonReader.ReturnToBookmark(bookmark); switch (type) { case "link": return(typeof(GeoJsonLinkedCoordinateReferenceSystem)); case "name": return(typeof(GeoJsonNamedCoordinateReferenceSystem)); default: var message = string.Format("The type field of the GeoJsonCoordinateReferenceSystem is not valid: '{0}'.", type); throw new FormatException(message); } } else { throw new FormatException("GeoJsonCoordinateReferenceSystem object is missing the type field."); } }
public Type GetActualType(BsonReader bsonReader, Type nominalType) { //Edit: added additional check for list if (nominalType != typeof(IRestriction) && nominalType != typeof(List <IRestriction>)) { throw new Exception("Cannot use IRestrictionDiscriminatorConvention for type " + nominalType); } var ret = nominalType; var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); if (bsonReader.FindElement(ElementName)) { var value = bsonReader.ReadString(); ret = Type.GetType(value); if (ret == null) { throw new Exception("Could not find type from " + value); } //Edit: doing the checking a little different if (!typeof(IRestriction).IsAssignableFrom(ret) && !ret.IsSubclassOf(typeof(IRestriction))) { throw new Exception("type is not an IRestriction"); } } bsonReader.ReturnToBookmark(bookmark); return(ret); }
// private methods private bool IsCSharpNullRepresentation(BsonReader bsonReader) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var bsonType = bsonReader.ReadBsonType(); if (bsonType == BsonType.Boolean) { var name = bsonReader.ReadName(); if (name == "_csharpnull" || name == "$csharpnull") { var value = bsonReader.ReadBoolean(); if (value) { bsonType = bsonReader.ReadBsonType(); if (bsonType == BsonType.EndOfDocument) { bsonReader.ReadEndDocument(); return(true); } } } } bsonReader.ReturnToBookmark(bookmark); return(false); }
public Type GetActualType(BsonReader bsonReader, Type nominalType) { BsonReaderBookmark bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); Type actualType = nominalType; if (bsonReader.FindElement("Type")) { BsonValue discriminator = BsonSerializer.Deserialize <BsonValue>(bsonReader); actualType = BsonSerializer.LookupActualType(nominalType, discriminator); } bsonReader.ReturnToBookmark(bookmark); return(actualType); }
public Type GetActualType(BsonReader bsonReader, Type nominalType) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var actualType = nominalType; if (bsonReader.FindElement(ElementName)) { var discriminator = (BsonValue)BsonValueSerializer.Instance.Deserialize(bsonReader, typeof(BsonValue), null); actualType = BsonSerializer.LookupActualType(nominalType, discriminator); } bsonReader.ReturnToBookmark(bookmark); return(actualType); }
/// <summary> /// Deserializes an object from a BsonReader. /// </summary> /// <param name="bsonReader">The BsonReader.</param> /// <param name="nominalType">The nominal type of the object.</param> /// <param name="options">The serialization options.</param> /// <returns>An object.</returns> public object Deserialize( BsonReader bsonReader, Type nominalType, IBsonSerializationOptions options ) { if (nominalType != typeof(object)) { var message = string.Format("ObjectSerializer can only be used with nominal type System.Object, not type {1}.", nominalType.FullName); throw new InvalidOperationException(message); } var bsonType = bsonReader.CurrentBsonType; if (bsonType == BsonType.Null) { bsonReader.ReadNull(); return(null); } else if (bsonType == BsonType.Document) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); if (bsonReader.ReadBsonType() == BsonType.EndOfDocument) { bsonReader.ReadEndDocument(); return(new object()); } else { bsonReader.ReturnToBookmark(bookmark); } } var discriminatorConvention = BsonDefaultSerializer.LookupDiscriminatorConvention(typeof(object)); var actualType = discriminatorConvention.GetActualType(bsonReader, typeof(object)); if (actualType == typeof(object)) { var message = string.Format("Unable to determine actual type of object to deserialize. NominalType is System.Object and BsonType is {0}.", bsonType); throw new FileFormatException(message); } var serializer = BsonSerializer.LookupSerializer(actualType); return(serializer.Deserialize(bsonReader, nominalType, actualType, options)); }
public Type GetActualType(BsonReader bsonReader, System.Type nominalType) { var currentBsonType = bsonReader.GetCurrentBsonType(); if (bsonReader.State == BsonReaderState.Value) { if (currentBsonType == BsonType.Document) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var type = nominalType; if (bsonReader.FindElement(ElementName)) { var discriminator = BsonValue.ReadFrom(bsonReader).AsString; try { if (discriminator == "Typed") { type = typeof(TypedSettings <>); bsonReader.ReturnToBookmark(bookmark); bsonReader.ReadStartDocument(); bsonReader.FindElement("Name"); var stringType = BsonValue.ReadFrom(bsonReader).AsString; type = type.MakeGenericType(Type.GetType(stringType)); } else if (discriminator == "Setting") { type = typeof(Setting); } } catch (Exception ex) { type = typeof(Setting); } } bsonReader.ReturnToBookmark(bookmark); return(type); } } return(nominalType); }
// public methods /// <summary> /// Deserializes an object from a BsonReader. /// </summary> /// <param name="bsonReader">The BsonReader.</param> /// <param name="nominalType">The nominal type of the object.</param> /// <param name="options">The serialization options.</param> /// <returns>An object.</returns> public object Deserialize(BsonReader bsonReader, Type nominalType, IBsonSerializationOptions options) { if (nominalType != typeof(object)) { var message = string.Format("ObjectSerializer can only be used with nominal type System.Object, not type {0}.", nominalType.FullName); throw new InvalidOperationException(message); } var bsonType = bsonReader.GetCurrentBsonType(); if (bsonType == BsonType.Null) { bsonReader.ReadNull(); return null; } else if (bsonType == BsonType.Document) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); if (bsonReader.ReadBsonType() == BsonType.EndOfDocument) { bsonReader.ReadEndDocument(); return new object(); } else { bsonReader.ReturnToBookmark(bookmark); } } var discriminatorConvention = BsonSerializer.LookupDiscriminatorConvention(typeof(object)); var actualType = discriminatorConvention.GetActualType(bsonReader, typeof(object)); if (actualType == typeof(object)) { var message = string.Format("Unable to determine actual type of object to deserialize. NominalType is System.Object and BsonType is {0}.", bsonType); throw new FileFormatException(message); } var serializer = BsonSerializer.LookupSerializer(actualType); return serializer.Deserialize(bsonReader, nominalType, actualType, options); }
private Type GetActualType(BsonReader bsonReader) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); if (bsonReader.FindElement("type")) { var type = bsonReader.ReadString(); bsonReader.ReturnToBookmark(bookmark); switch (type) { case "Feature": return(typeof(GeoJsonFeature <TCoordinates>)); case "FeatureCollection": return(typeof(GeoJsonFeatureCollection <TCoordinates>)); case "GeometryCollection": return(typeof(GeoJsonGeometryCollection <TCoordinates>)); case "LineString": return(typeof(GeoJsonLineString <TCoordinates>)); case "MultiLineString": return(typeof(GeoJsonMultiLineString <TCoordinates>)); case "MultiPoint": return(typeof(GeoJsonMultiPoint <TCoordinates>)); case "MultiPolygon": return(typeof(GeoJsonMultiPolygon <TCoordinates>)); case "Point": return(typeof(GeoJsonPoint <TCoordinates>)); case "Polygon": return(typeof(GeoJsonPolygon <TCoordinates>)); default: var message = string.Format("The type field of the GeoJosnGeometry is not valid: '{0}'.", type); throw new FormatException(message); } } else { throw new FormatException("GeoJson object is missing the type field."); } }
// public methods /// <summary> /// Gets the actual type of an object by reading the discriminator from a BsonReader. /// </summary> /// <param name="bsonReader">The reader.</param> /// <param name="nominalType">The nominal type.</param> /// <returns>The actual type.</returns> public Type GetActualType(BsonReader bsonReader, Type nominalType) { // the BsonReader is sitting at the value whose actual type needs to be found var bsonType = bsonReader.GetCurrentBsonType(); if (bsonReader.State == BsonReaderState.Value) { Type primitiveType = null; switch (bsonType) { case BsonType.Boolean: primitiveType = typeof(bool); break; case BsonType.Binary: var bookmark = bsonReader.GetBookmark(); var binaryData = bsonReader.ReadBinaryData(); var subType = binaryData.SubType; if (subType == BsonBinarySubType.UuidStandard || subType == BsonBinarySubType.UuidLegacy) { primitiveType = typeof(Guid); } bsonReader.ReturnToBookmark(bookmark); break; case BsonType.DateTime: primitiveType = typeof(DateTime); break; case BsonType.Double: primitiveType = typeof(double); break; case BsonType.Int32: primitiveType = typeof(int); break; case BsonType.Int64: primitiveType = typeof(long); break; case BsonType.ObjectId: primitiveType = typeof(ObjectId); break; case BsonType.String: primitiveType = typeof(string); break; } // Type.IsAssignableFrom is extremely expensive, always perform a direct type check before calling Type.IsAssignableFrom if (primitiveType != null && (primitiveType == nominalType || nominalType.IsAssignableFrom(primitiveType))) { return(primitiveType); } } if (bsonType == BsonType.Document) { // ensure KnownTypes of nominalType are registered (so IsTypeDiscriminated returns correct answer) BsonSerializer.EnsureKnownTypesAreRegistered(nominalType); // we can skip looking for a discriminator if nominalType has no discriminated sub types if (BsonSerializer.IsTypeDiscriminated(nominalType)) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var actualType = nominalType; if (bsonReader.FindElement(_elementName)) { var discriminator = (BsonValue)BsonValueSerializer.Instance.Deserialize(bsonReader, typeof(BsonValue), null); if (discriminator.IsBsonArray) { discriminator = discriminator.AsBsonArray.Last(); // last item is leaf class discriminator } actualType = BsonSerializer.LookupActualType(nominalType, discriminator); } bsonReader.ReturnToBookmark(bookmark); return(actualType); } } return(nominalType); }
/// <summary> /// Gets the actual type of an object by reading the discriminator from a BsonReader. /// </summary> /// <param name="bsonReader">The reader.</param> /// <param name="nominalType">The nominal type.</param> /// <returns>The actual type.</returns> public Type GetActualType( BsonReader bsonReader, Type nominalType ) { // the BsonReader is sitting at the value whose actual type needs to be found var bsonType = bsonReader.CurrentBsonType; if (bsonReader.State == BsonReaderState.Value) { Type primitiveType = null; switch (bsonType) { case BsonType.Boolean: primitiveType = typeof(bool); break; case BsonType.Binary: var bookmark = bsonReader.GetBookmark(); byte[] bytes; BsonBinarySubType subType; bsonReader.ReadBinaryData(out bytes, out subType); if (subType == BsonBinarySubType.Uuid && bytes.Length == 16) { primitiveType = typeof(Guid); } bsonReader.ReturnToBookmark(bookmark); break; case BsonType.DateTime: primitiveType = typeof(DateTime); break; case BsonType.Double: primitiveType = typeof(double); break; case BsonType.Int32: primitiveType = typeof(int); break; case BsonType.Int64: primitiveType = typeof(long); break; case BsonType.ObjectId: primitiveType = typeof(ObjectId); break; case BsonType.String: primitiveType = typeof(string); break; } if (primitiveType != null && nominalType.IsAssignableFrom(primitiveType)) { return(primitiveType); } } if (bsonType == BsonType.Document) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var actualType = nominalType; if (bsonReader.FindElement(elementName)) { var discriminator = BsonValue.ReadFrom(bsonReader); if (discriminator.IsBsonArray) { discriminator = discriminator.AsBsonArray.Last(); // last item is leaf class discriminator } actualType = BsonDefaultSerializer.LookupActualType(nominalType, discriminator); } bsonReader.ReturnToBookmark(bookmark); return(actualType); } return(nominalType); }
// public methods /// <summary> /// Gets the actual type of an object by reading the discriminator from a BsonReader. /// </summary> /// <param name="bsonReader">The reader.</param> /// <param name="nominalType">The nominal type.</param> /// <returns>The actual type.</returns> public Type GetActualType(BsonReader bsonReader, Type nominalType) { // the BsonReader is sitting at the value whose actual type needs to be found var bsonType = bsonReader.GetCurrentBsonType(); if (bsonReader.State == BsonReaderState.Value) { Type primitiveType = null; switch (bsonType) { case BsonType.Boolean: primitiveType = typeof(bool); break; case BsonType.Binary: var bookmark = bsonReader.GetBookmark(); byte[] bytes; BsonBinarySubType subType; bsonReader.ReadBinaryData(out bytes, out subType); if (subType == BsonBinarySubType.UuidStandard || subType == BsonBinarySubType.UuidLegacy) { primitiveType = typeof(Guid); } bsonReader.ReturnToBookmark(bookmark); break; case BsonType.DateTime: primitiveType = typeof(DateTime); break; case BsonType.Double: primitiveType = typeof(double); break; case BsonType.Int32: primitiveType = typeof(int); break; case BsonType.Int64: primitiveType = typeof(long); break; case BsonType.ObjectId: primitiveType = typeof(ObjectId); break; case BsonType.String: primitiveType = typeof(string); break; } // Type.IsAssignableFrom is extremely expensive, always perform a direct type check before calling Type.IsAssignableFrom if (primitiveType != null && (primitiveType == nominalType || nominalType.IsAssignableFrom(primitiveType))) { return primitiveType; } } if (bsonType == BsonType.Document) { // ensure KnownTypes of nominalType are registered (so IsTypeDiscriminated returns correct answer) BsonSerializer.EnsureKnownTypesAreRegistered(nominalType); // we can skip looking for a discriminator if nominalType has no discriminated sub types if (BsonSerializer.IsTypeDiscriminated(nominalType)) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var actualType = nominalType; if (bsonReader.FindElement(_elementName)) { var discriminator = BsonValue.ReadFrom(bsonReader); if (discriminator.IsBsonArray) { discriminator = discriminator.AsBsonArray.Last(); // last item is leaf class discriminator } actualType = BsonSerializer.LookupActualType(nominalType, discriminator); } bsonReader.ReturnToBookmark(bookmark); return actualType; } } return nominalType; }
public PBBsonReaderBookmark GetBookmark() { return(new PBBsonReaderBookmark { Bookmark = _reader.GetBookmark(), Type = _type, Name = _name, BsonType = _bsonType, Value = _value, Indent = _indent, IndentString = _indentString }); }
// private methods private bool IsCSharpNullRepresentation(BsonReader bsonReader) { var bookmark = bsonReader.GetBookmark(); bsonReader.ReadStartDocument(); var bsonType = bsonReader.ReadBsonType(); if (bsonType == BsonType.Boolean) { var name = bsonReader.ReadName(); if (name == "_csharpnull" || name == "$csharpnull") { var value = bsonReader.ReadBoolean(); if (value) { bsonType = bsonReader.ReadBsonType(); if (bsonType == BsonType.EndOfDocument) { bsonReader.ReadEndDocument(); return true; } } } } bsonReader.ReturnToBookmark(bookmark); return false; }
public override object Deserialize(BsonReader bsonReader, Type nominalType, IBsonSerializationOptions options) { var bsonType = bsonReader.CurrentBsonType; if (bsonType == BsonType.Null) { bsonReader.ReadNull(); return(null); } else if (bsonType == BsonType.Document) { var os = new ObjectSerializer(); MongoDynamic md = new MongoDynamic(); bsonReader.ReadStartDocument(); Dictionary <string, Type> typeMap = null; // scan document first to find interfaces { var bookMark = bsonReader.GetBookmark(); if (bsonReader.FindElement(MongoDynamic.InterfacesField)) { md[MongoDynamic.InterfacesField] = BsonSerializer.Deserialize <BsonValue>(bsonReader).AsBsonArray.Select(x => x.AsString); typeMap = md.GetTypeMap(); } else { throw new FormatException("No interfaces defined for this dynamic object - can't deserialize it"); } bsonReader.ReturnToBookmark(bookMark); } while (bsonReader.ReadBsonType() != BsonType.EndOfDocument) { var name = bsonReader.ReadName(); if (name == "_id") { //md[name] = BsonValue.ReadFrom(bsonReader).AsObjectId; md[name] = BsonSerializer.Deserialize <ObjectId>(bsonReader); } else if (name == MongoDynamic.InterfacesField) { // Read it and ignore it, we already have it //BsonValue.ReadFrom(bsonReader); BsonSerializer.Deserialize <ObjectId>(bsonReader); } else { if (typeMap == null) { throw new FormatException("No interfaces define for this dynamic object - can't deserialize"); } // lookup the type for this element according to the interfaces Type elementType; if (typeMap.TryGetValue(name, out elementType)) { var value = BsonSerializer.Deserialize(bsonReader, elementType); md[name] = value; } else { // This is a value that is no longer in the interface, maybe a column you removed // not really much we can do with it ... but we need to read it and move on var value = BsonSerializer.Deserialize(bsonReader, typeof(object)); md[name] = value; // As with all databases, removing elements from the schema is always going to cause problems ... } } } bsonReader.ReadEndDocument(); return(md); } else { var message = string.Format("Can't deserialize a {0} from BsonType {1}.", nominalType.FullName, bsonType); throw new FormatException(message); } }