tutorial net create collection c#-4.0 mongodb mongodb-.net-driver dynamicobject

c#-4.0 - create - mongodb net core



¿Hay mongodb C#driver support System.Dynamic.DynamicObject en.NET 4? (5)

Estoy trabajando en un proyecto que usa .NET Razor y mongodb. Me gustaría hacer algo como esto:

@{ var feeds = DP.Database.GetCollection("feeds").FindAll(); } <ul> @foreach (dynamic feed in feeds) { <li>@feed.message - @feed.from.name</li> } </ul>

Sin embargo, el controlador mongodb C # actual FindAll () devuelve la colección de BsonDocument que no admite objetos dinámicos. ¿Alguien sabe un controlador mongodb C # compatible con .NET 4 dynamic?

Muchas gracias


A pesar de que este es un tema antiguo, todavía es tan relevante hoy como cuando se hizo la publicación, y aún no he visto ninguna solución que brinde una solución simple para el soporte bidireccional, he modificado el código de @Maximilian Scherer para que permita convierte a objetos dinámicos que le permiten guardar fácilmente su documento nuevamente.

public static class MongoDynamic { /// <summary> /// deserializes this bson doc to a .net dynamic object /// </summary> /// <param name="bson">bson doc to convert to dynamic</param> public static dynamic ToDynamic(this BsonDocument bson) { var json = bson.ToJson(new MongoDB.Bson.IO.JsonWriterSettings { OutputMode = JsonOutputMode.Strict }); dynamic e = Newtonsoft.Json.JsonConvert.DeserializeObject<ExpandoObject>(json); BsonValue id; if (bson.TryGetValue("_id", out id)) { // Lets set _id again so that its possible to save document. e._id = new ObjectId(id.ToString()); } return e; } }

Ejemplo de uso:

// Get BsonDocument from db here BsonDocument doc = ... // Convert to dynamic. var d = doc.ToDynamic(); // Lets add a none existant property. d.Name = "test"; // Assuming you already have your collection set up collection.Save(new BsonDocument(d));


Actualmente, no hay soporte para dinámica en el controlador MongoDB. Esto se debe a que está basado en .NET 3.5. Sin embargo, dado que un ensamblado .NET 4.0 puede hacer referencia a un ensamblado .NET 3.5, es posible que escriba un proveedor de IBsonSerialization y un IBsonSerializer en .NET 4.0 para admitir la dinámica.

Nosotros, 10gen, estamos buscando hacer esto en el futuro. He añadido algún soporte en https://github.com/craiggwilson/mongo-csharp-driver/tree/dynamic si quieres echar un vistazo. Definitivamente hay errores, pero muestra que es posible.


Creé una extensión directa al controlador MongoDB que vuelve a serializar el documento BSON usando Json.NET y lo deserializa como dinámico. Al incluir la siguiente clase, simplemente puede convertir sus consultas de MongoDB a dinámicas como esta

dynamic obj = collection.FindOneByIdAs<BsonDocument>(someObjectId).ToDynamic();

Clase de extensión:

public static class MongoDynamic { private static System.Text.RegularExpressions.Regex objectIdReplace = new System.Text.RegularExpressions.Regex(@"ObjectId/((.[a-f0-9]{24}.)/)", System.Text.RegularExpressions.RegexOptions.Compiled); /// <summary> /// deserializes this bson doc to a .net dynamic object /// </summary> /// <param name="bson">bson doc to convert to dynamic</param> public static dynamic ToDynamic(this BsonDocument bson) { var json = objectIdReplace.Replace(bson.ToJson(), (s) => s.Groups[1].Value); return Newtonsoft.Json.JsonConvert.DeserializeObject<dynamic>(json); } }

Asegúrese de consultar Newtonsoft.Json.dll ( http://james.newtonking.com/projects/json-net.aspx )


Solo para construir sobre la respuesta de Maximiliano. Esto devolverá una lista de dinámicas de cualquier consulta.

/// <summary> /// deserializes this BsonDocument cursor result to a list of .net dynamic objects /// </summary> /// <param name="cursor">cursor result to convert to dynamic</param> /// <returns></returns> public static List<dynamic> ToDynamicList(this MongoCursor<BsonDocument> cursor) { var dynamicList = new List<dynamic>(); var list = cursor.ToList(); for (int i = 0, l = list.Count; i < l; i++) dynamicList.Add(list[i].ToDynamic()); return dynamicList; }


Tengo una solución limpia utilizando IBsonSerializer y Newtonsoft.Json personalizados.

Configure su serializador personalizado en BsonClassMap

map.MapProperty(member => member.Data) .SetElementName("Data") .SetSerializer(new DynamicSerializer());

o en la propiedad

[BsonSerializer(typeof(DynamicSerializer))] public dynamic Data { get; set; }

Y solo incluye la siguiente clase

public class DynamicSerializer : IBsonSerializer { #region Implementation of IBsonSerializer public object Deserialize(BsonReader bsonReader, Type nominalType, IBsonSerializationOptions options) { return Deserialize(bsonReader, nominalType, null, options); } public object Deserialize(BsonReader bsonReader, Type nominalType, Type actualType, IBsonSerializationOptions options) { if (bsonReader.GetCurrentBsonType() != BsonType.Document) throw new Exception("Not document"); var bsonDocument = BsonSerializer.Deserialize(bsonReader, typeof(BsonDocument), options) as BsonDocument; return JsonConvert.DeserializeObject<dynamic>(bsonDocument.ToJson()); } public IBsonSerializationOptions GetDefaultSerializationOptions() { return new DocumentSerializationOptions(); } public void Serialize(BsonWriter bsonWriter, Type nominalType, object value, IBsonSerializationOptions options) { var json = (value == null) ? "{}": JsonConvert.SerializeObject(value); BsonDocument document = BsonDocument.Parse(json); BsonSerializer.Serialize(bsonWriter, typeof(BsonDocument), document,options); } #endregion }

InfoSlips - GlobalKinetic