Last active
February 8, 2024 01:45
-
-
Save mahizsas/de6d44a91af7848d8017 to your computer and use it in GitHub Desktop.
Serilize dynamic data with mongodb
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
using System; | |
using System.Collections; | |
using System.Linq; | |
using MongoDB.Bson; | |
using MongoDB.Bson.IO; | |
using MongoDB.Bson.Serialization; | |
using MongoDB.Bson.Serialization.Attributes; | |
using MongoDB.Bson.Serialization.Options; | |
using MongoDB.Driver; | |
using MongoDB.Driver.Linq; | |
using Newtonsoft.Json; | |
using Newtonsoft.Json.Linq; | |
namespace TestMongo | |
{ | |
internal class Program | |
{ | |
private static void Main(string[] args) | |
{ | |
var store = new Store("mongodb://localhost:27017/Test__"); | |
var ticket1 = new Ticket | |
{ | |
CreatedAt = DateTime.Now, | |
Id = Guid.NewGuid(), | |
Name = "Test", | |
Payload = JObject.Parse(JsonHolder.Sample1) | |
}; | |
var ticket2 = new Ticket | |
{ | |
CreatedAt = DateTime.Now, | |
Id = Guid.NewGuid(), | |
Name = "Test", | |
Payload = JArray.Parse(JsonHolder.Sample2) | |
}; | |
var demo = store.Db.GetCollection("DEMO"); | |
demo.Drop(); | |
demo.Insert(ticket1); | |
demo.Insert(ticket2); | |
var tickets = demo.AsQueryable<Ticket>(); | |
var one = tickets.First(); | |
Console.WriteLine(one.Payload.ToString()); | |
foreach (var item in tickets) | |
{ | |
Console.WriteLine(item.Name); | |
} | |
} | |
} | |
public class Ticket | |
{ | |
public Guid Id { get; set; } | |
public string Name { get; set; } | |
public DateTime CreatedAt { get; set; } | |
[BsonSerializer(typeof (DynamicSerializer))] | |
public dynamic Payload { get; set; } | |
} | |
public class Store | |
{ | |
public readonly MongoDatabase Db; | |
public readonly MongoUrl Url; | |
public Store(string url) | |
{ | |
Url = new MongoUrl(url); | |
Db = new MongoClient(Url).GetServer().GetDatabase(Url.DatabaseName); | |
} | |
} | |
public class DynamicSerializer : 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) | |
{ | |
object document; | |
dynamic output; | |
Type type; | |
var currentBsonType = bsonReader.GetCurrentBsonType(); | |
switch (currentBsonType) | |
{ | |
case BsonType.Document: | |
type = typeof (BsonDocument); | |
document = BsonSerializer.Deserialize(bsonReader, type, options) as BsonDocument; | |
output = JObject.Parse(document.ToJson(type)); | |
break; | |
case BsonType.Array: | |
type = typeof(BsonArray); | |
document = BsonSerializer.Deserialize(bsonReader, type, options) as BsonArray; | |
output = JArray.Parse(document.ToJson(type)); | |
break; | |
default: | |
throw new ApplicationException(string.Format("Invalid type {0}", currentBsonType)); | |
} | |
return output; | |
} | |
public IBsonSerializationOptions GetDefaultSerializationOptions() | |
{ | |
return new DocumentSerializationOptions {AllowDuplicateNames = true}; | |
} | |
public void Serialize(BsonWriter bsonWriter, Type nominalType, object value, IBsonSerializationOptions options) | |
{ | |
var json = (value == null) ? "{}" : JsonConvert.SerializeObject(value).Trim(); | |
if (StartsAndEnds(json, "[", "]")) | |
{ | |
var array = BsonSerializer.Deserialize<BsonArray>(json); | |
BsonSerializer.Serialize(bsonWriter, typeof(BsonArray), array, options); | |
return; | |
} | |
var document = BsonDocument.Parse(json); | |
BsonSerializer.Serialize(bsonWriter, typeof(BsonDocument), document, options); | |
} | |
private static bool StartsAndEnds(string value, string start, string end) | |
{ | |
return value.StartsWith(start, StringComparison.InvariantCultureIgnoreCase) && | |
value.EndsWith(end, StringComparison.InvariantCultureIgnoreCase); | |
} | |
} | |
internal static class JsonHolder | |
{ | |
public static string Sample1 = "{\"autoExpand\":true,\"batchSize\":50,\"connections\":[{\"connectionName\":\"localhost\",\"credentials\":[{\"databaseName\":\"admin\",\"enabled\":false,\"userName\":\"root\",\"userPassword\":\"root\"}],\"defaultDatabase\":\"\",\"serverHost\":\"127.0.0.1\",\"serverPort\":27017,\"sshAuthMethod\":0,\"sshHost\":\"\",\"sshPassphrase\":\"\",\"sshPort\":0,\"sshPrivateKey\":\"\",\"sshPublicKey\":\"\",\"sshUserName\":\"\",\"sshUserPassword\":\"\",\"sslEnabled\":false,\"sslPemKeyFile\":\"\"}],\"disableConnectionShortcuts\":false,\"loadMongoRcJs\":false,\"style\":\"Native\",\"timeZone\":0,\"uuidEncoding\":0,\"version\":\"1.0\",\"viewMode\":1}"; | |
public static string Sample2 = "[{\"autoExpand\":true,\"batchSize\":50,\"connections\":[{\"connectionName\":\"localhost\",\"credentials\":[{\"databaseName\":\"admin\",\"enabled\":false,\"userName\":\"root\",\"userPassword\":\"root\"}],\"defaultDatabase\":\"\",\"serverHost\":\"127.0.0.1\",\"serverPort\":27017,\"sshAuthMethod\":0,\"sshHost\":\"\",\"sshPassphrase\":\"\",\"sshPort\":0,\"sshPrivateKey\":\"\",\"sshPublicKey\":\"\",\"sshUserName\":\"\",\"sshUserPassword\":\"\",\"sslEnabled\":false,\"sslPemKeyFile\":\"\"}],\"disableConnectionShortcuts\":false,\"loadMongoRcJs\":false,\"style\":\"Native\",\"timeZone\":0,\"uuidEncoding\":0,\"version\":\"1.0\",\"viewMode\":1}]"; | |
} | |
} |
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment