Skip to content

Commit b07d3c8

Browse files
authored
Merge pull request #195 from tresoldigiorgio/develop
Update entity in MongoDb now works. Added configuration for ssl connection to MongoDb. Simple refactor.
2 parents 6078d9a + 7ef99a8 commit b07d3c8

10 files changed

Lines changed: 107 additions & 96 deletions

File tree

SharpRepository.MongoDbRepository/MongoDbConfigRepositoryFactory.cs

Lines changed: 7 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
using System;
2+
using System.Security.Authentication;
3+
using MongoDB.Driver;
24
using SharpRepository.Repository;
35
using SharpRepository.Repository.Configuration;
46

@@ -24,7 +26,11 @@ public override IRepository<T, TKey> GetInstance<T, TKey>()
2426
throw new ConfigurationErrorsException("The connectionString attribute is required in order to use the MongoDbRepository via the configuration file.");
2527
}
2628

27-
return new MongoDbRepository<T, TKey>(RepositoryConfiguration["connectionString"]);
29+
SslSettings sslSettings = null;
30+
if (Boolean.Parse(RepositoryConfiguration["sslEnabled"]))
31+
sslSettings = new SslSettings() { EnabledSslProtocols = (SslProtocols)Enum.Parse(typeof(SslProtocols), RepositoryConfiguration["sslProtocol"]) };
32+
33+
return new MongoDbRepository<T, TKey>(RepositoryConfiguration["connectionString"], sslSettings);
2834
}
2935

3036
public override ICompoundKeyRepository<T, TKey, TKey2> GetInstance<T, TKey, TKey2>()

SharpRepository.MongoDbRepository/MongoDbRepository.cs

Lines changed: 26 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
using System;
2+
using MongoDB.Driver;
23
using SharpRepository.Repository.Caching;
34

45
namespace SharpRepository.MongoDbRepository
@@ -24,7 +25,19 @@ public MongoDbRepository(ICachingStrategy<T, TKey> cachingStrategy = null) : bas
2425
/// <param name="connectionString">The connectionString of the MongoDb instance.</param>
2526
/// <param name="cachingStrategy">The caching strategy. Defaults to <see cref="NoCachingStrategy&lt;T, TKey&gt;" />.</param>
2627
public MongoDbRepository(string connectionString, ICachingStrategy<T, TKey> cachingStrategy = null)
27-
: base(connectionString, cachingStrategy)
28+
: base(connectionString, cachingStrategy, null)
29+
{
30+
if (String.IsNullOrEmpty(connectionString)) throw new ArgumentNullException("connectionString");
31+
}
32+
33+
/// <summary>
34+
/// Initializes a new instance of the <see cref="MongoDbRepository&lt;T, TKey&gt;"/> class.
35+
/// </summary>
36+
/// <param name="connectionString">The connectionString of the MongoDb instance.</param>
37+
/// <param name="sslSettings">Ssl Settings for mongo connection</param>
38+
/// <param name="cachingStrategy">The caching strategy. Defaults to <see cref="NoCachingStrategy&lt;T, TKey&gt;" />.</param>
39+
public MongoDbRepository(string connectionString, SslSettings sslSettings, ICachingStrategy<T, TKey> cachingStrategy = null)
40+
: base(connectionString, cachingStrategy, sslSettings)
2841
{
2942
if (String.IsNullOrEmpty(connectionString)) throw new ArgumentNullException("connectionString");
3043
}
@@ -51,7 +64,18 @@ public MongoDbRepository(ICachingStrategy<T, string> cachingStrategy = null)
5164
/// <param name="connectionString">The connectionString of the MongoDb instance.</param>
5265
/// <param name="cachingStrategy">The caching strategy. Defaults to <see cref="NoCachingStrategy&lt;T&gt;" />.</param>
5366
public MongoDbRepository(string connectionString, ICachingStrategy<T, string> cachingStrategy = null)
54-
: base(connectionString, cachingStrategy)
67+
: base(connectionString, cachingStrategy, null)
68+
{
69+
if (String.IsNullOrEmpty(connectionString)) throw new ArgumentNullException("connectionString");
70+
}
71+
72+
/// <summary>
73+
/// Initializes a new instance of the <see cref="MongoDbRepository&lt;T&gt;"/> class.
74+
/// </summary>
75+
/// <param name="connectionString">The connectionString of the MongoDb instance.</param>
76+
/// <param name="cachingStrategy">The caching strategy. Defaults to <see cref="NoCachingStrategy&lt;T&gt;" />.</param>
77+
public MongoDbRepository(string connectionString, SslSettings sslSettings, ICachingStrategy<T, string> cachingStrategy = null)
78+
: base(connectionString, cachingStrategy, sslSettings)
5579
{
5680
if (String.IsNullOrEmpty(connectionString)) throw new ArgumentNullException("connectionString");
5781
}

SharpRepository.MongoDbRepository/MongoDbRepositoryBase.cs

Lines changed: 34 additions & 75 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ namespace SharpRepository.MongoDbRepository
2424
private readonly string _databaseName;
2525
protected IMongoDatabase Database;
2626

27-
private readonly Dictionary<Type, BsonType> _keyTypeToBsonType =
27+
private readonly Dictionary<Type, BsonType> _keyTypeToBsonType =
2828
new Dictionary<Type, BsonType>
2929
{
3030
{typeof(string), BsonType.String},
@@ -33,7 +33,7 @@ namespace SharpRepository.MongoDbRepository
3333
{typeof(byte[]), BsonType.ObjectId}
3434
};
3535

36-
private readonly Dictionary<Type, IIdGenerator> _keyTypeToBsonGenerator =
36+
private readonly Dictionary<Type, IIdGenerator> _keyTypeToBsonGenerator =
3737
new Dictionary<Type, IIdGenerator>
3838
{
3939
{typeof (string), new StringObjectIdGenerator() },
@@ -42,17 +42,29 @@ namespace SharpRepository.MongoDbRepository
4242
{typeof(byte[]), new BsonBinaryDataGuidGenerator(GuidRepresentation.Standard)}
4343
};
4444

45+
#region Constructors
46+
4547
internal MongoDbRepositoryBase(ICachingStrategy<T, TKey> cachingStrategy = null)
4648
: base(cachingStrategy)
4749
{
4850
Initialize();
4951
}
5052

51-
internal MongoDbRepositoryBase(string connectionString, ICachingStrategy<T, TKey> cachingStrategy = null)
53+
internal MongoDbRepositoryBase(string connectionString, ICachingStrategy<T, TKey> cachingStrategy, SslSettings sslSettings)
5254
: base(cachingStrategy)
5355
{
5456
_databaseName = MongoUrl.Create(connectionString).DatabaseName;
55-
var cli = new MongoClient(connectionString);
57+
58+
MongoClient cli;
59+
if (sslSettings != null)
60+
{
61+
var settings = MongoClientSettings.FromUrl(new MongoUrl(connectionString));
62+
settings.SslSettings = sslSettings;
63+
cli = new MongoClient(settings);
64+
}
65+
else
66+
cli = new MongoClient(connectionString);
67+
5668
Initialize(cli.GetDatabase(_databaseName));
5769
}
5870

@@ -62,16 +74,13 @@ internal MongoDbRepositoryBase(IMongoDatabase mongoDatabase, ICachingStrategy<T,
6274
Initialize(mongoDatabase);
6375
}
6476

65-
private string DatabaseName
66-
{
67-
get { return string.IsNullOrEmpty(_databaseName) ? TypeName : _databaseName; }
68-
}
77+
#endregion
6978

7079
private void Initialize(IMongoDatabase mongoDatabase = null)
7180
{
7281
Database = mongoDatabase ?? new MongoClient("mongodb://localhost/default").GetDatabase(MongoUrl.Create("mongodb://localhost/default").DatabaseName);
7382

74-
if (!BsonClassMap.IsClassMapRegistered(typeof (T)))
83+
if (!BsonClassMap.IsClassMapRegistered(typeof(T)))
7584
{
7685
var primaryKeyPropInfo = GetPrimaryKeyPropertyInfo();
7786
var primaryKeyName = primaryKeyPropInfo.Name;
@@ -87,7 +96,7 @@ private void Initialize(IMongoDatabase mongoDatabase = null)
8796
{
8897
cm.IdMemberMap.SetSerializer(new StringSerializer(_keyTypeToBsonType[typeof(TKey)]));
8998
cm.IdMemberMap.SetIdGenerator(_keyTypeToBsonGenerator[typeof(TKey)]);
90-
}
99+
}
91100
}
92101

93102
cm.Freeze();
@@ -110,13 +119,16 @@ protected override T GetQuery(TKey key, IFetchStrategy<T> fetchStrategy)
110119
{
111120
var keyBsonType = ((StringSerializer)BsonClassMap.LookupClassMap(typeof(T)).IdMemberMap.GetSerializer()).Representation;
112121
var keyMemberName = BsonClassMap.LookupClassMap(typeof(T)).IdMemberMap.MemberName;
113-
if (IsValidKey(key)) {
122+
if (IsValidKey(key))
123+
{
114124
var keyBsonValue = BsonTypeMapper.MapToBsonValue(key, keyBsonType);
115125
var filter = Builders<T>.Filter.Eq(keyMemberName, keyBsonValue);
116126
return BaseCollection().Find(filter).FirstOrDefault();
117-
} else return default(T);
127+
}
128+
else return default(T);
118129
}
119130

131+
#region Math
120132
public override int Sum(ISpecification<T> criteria, Expression<Func<T, int>> selector)
121133
{
122134
return QueryManager.ExecuteSum(
@@ -297,89 +309,36 @@ public override double Average(ISpecification<T> criteria, Expression<Func<T, lo
297309
);
298310
}
299311

312+
#endregion
313+
300314
protected override void AddItem(T entity)
301315
{
302316
BaseCollection().InsertOne(entity);
303317
}
304318

305319
protected override void DeleteItem(T entity)
306320
{
307-
TKey pkValue;
308-
GetPrimaryKey(entity, out pkValue);
321+
GetPrimaryKey(entity, out var pkValue);
309322

310323
if (IsValidKey(pkValue))
311324
{
312-
var keyPropertyName = BsonClassMap.LookupClassMap(typeof(T)).IdMemberMap.MemberName;
313-
var keyPair = GetMongoProperty(entity, keyPropertyName);
314-
var filter = Builders<T>.Filter.Eq(keyPair.Key, keyPair.Value);
315-
325+
var pkName = GetPrimaryKeyPropertyInfo().Name;
326+
var filter = Builders<T>.Filter.Eq(pkName, pkValue);
316327
BaseCollection().DeleteOne(filter);
317328
}
318329
}
319330

320331
protected override void UpdateItem(T entity)
321332
{
322-
TKey pkValue;
323-
GetPrimaryKey(entity, out pkValue);
333+
GetPrimaryKey(entity, out var pkValue);
324334
if (IsValidKey(pkValue))
325335
{
326-
var keyMap = BsonClassMap.LookupClassMap(typeof(T)).IdMemberMap;
327-
var keyPropertyName = keyMap.MemberName;
328-
var keyBsonType = ((StringSerializer)keyMap.GetSerializer()).Representation;
329-
var keyBsonPropertyValue = BsonTypeMapper.MapToBsonValue(pkValue, keyBsonType);
330-
var keyPair = new KeyValuePair<string, BsonValue>(keyPropertyName, keyBsonPropertyValue);
331-
var filter = Builders<T>.Filter.Eq(keyPair.Key, keyPair.Value);
332-
333-
334-
var bsonMembers = BsonClassMap.LookupClassMap(typeof(T)).AllMemberMaps.Where(m => m.MemberName != keyPropertyName);
335-
var updates = new List<UpdateDefinition<T>>();
336-
foreach (var members in bsonMembers)
337-
{
338-
var propPair = GetMongoProperty(entity, members.MemberName);
339-
updates.Add(Builders<T>.Update.Set(propPair.Key, propPair.Value));
340-
}
341-
342-
BaseCollection().UpdateOne(filter, Builders<T>.Update.Combine(updates));
343-
}
344-
345-
}
346-
347-
public static KeyValuePair<string, BsonValue> GetMongoProperty(T entity, string propertyName)
348-
{
349-
var value = typeof(T).GetProperty(propertyName).GetValue(entity);
350-
var memberMap = BsonClassMap.LookupClassMap(typeof(T)).GetMemberMap(propertyName);
351-
var memberBsonType = GetBsonType(value, memberMap);
352-
353-
// some "non-string types are mapped to string"
354-
if (memberBsonType == BsonType.String)
355-
{
356-
value = value.ToString();
336+
var pkName = GetPrimaryKeyPropertyInfo().Name;
337+
var filter = Builders<T>.Filter.Eq(pkName, pkValue);
338+
BaseCollection().ReplaceOne(filter, entity);
357339
}
358-
359-
var bsonPropertyValue = BsonTypeMapper.MapToBsonValue(value, memberBsonType);
360-
return new KeyValuePair<string, BsonValue>(propertyName, bsonPropertyValue);
361340
}
362-
363-
protected static BsonType GetBsonType(object value, BsonMemberMap memberMap)
364-
{
365-
BsonType keyBsonType;
366-
367-
if (value == null) {
368-
keyBsonType = BsonType.Null;
369-
} else {
370-
var propertyInfo = memberMap.GetSerializer().GetType().GetProperty("Representation");
371-
if (propertyInfo != null)
372-
{
373-
keyBsonType = (BsonType)propertyInfo.GetValue(memberMap.GetSerializer());
374-
} else
375-
{
376-
keyBsonType = BsonType.Array;
377-
}
378-
}
379-
380-
return keyBsonType;
381-
}
382-
341+
383342
protected override void SaveChanges()
384343
{
385344
}

SharpRepository.MongoDbRepository/MongoDbRepositoryManager.cs

Lines changed: 26 additions & 8 deletions
Original file line numberDiff line numberDiff line change
@@ -20,23 +20,41 @@ public static bool ServerIsRunning(IMongoDatabase db)
2020
return true;
2121
}
2222

23-
public static bool ServerIsRunning(string connectionString)
23+
public static bool ServerIsRunning(string connectionString, SslSettings sslSettings = null)
2424
{
25-
var db_name = MongoUrl.Create(connectionString).DatabaseName;
26-
var cli = new MongoClient(connectionString);
27-
return ServerIsRunning(cli.GetDatabase(db_name));
25+
MongoClient cli;
26+
if (sslSettings != null)
27+
{
28+
var settings = MongoClientSettings.FromUrl(new MongoUrl(connectionString));
29+
settings.SslSettings = sslSettings;
30+
cli = new MongoClient(settings);
31+
}
32+
else
33+
cli = new MongoClient(connectionString);
34+
35+
var dbName = DatabaseName(connectionString);
36+
return ServerIsRunning(cli.GetDatabase(dbName));
2837
}
2938

3039
public static string DatabaseName(string connectionString)
3140
{
3241
return MongoUrl.Create(connectionString).DatabaseName;
3342
}
3443

35-
public static void DropDatabase(string connectionString)
44+
public static void DropDatabase(string connectionString, SslSettings sslSettings = null)
3645
{
37-
var cli = new MongoClient(connectionString);
38-
var db_name = MongoUrl.Create(connectionString).DatabaseName;
39-
cli.DropDatabase(db_name);
46+
MongoClient cli;
47+
if (sslSettings != null)
48+
{
49+
var settings = MongoClientSettings.FromUrl(new MongoUrl(connectionString));
50+
settings.SslSettings = sslSettings;
51+
cli = new MongoClient(settings);
52+
}
53+
else
54+
cli = new MongoClient(connectionString);
55+
56+
var dbName = DatabaseName(connectionString);
57+
cli.DropDatabase(dbName);
4058
}
4159
}
4260
}

SharpRepository.Samples.CoreMvc/Controllers/EmailsController.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,6 +3,7 @@
33
using SharpRepository.Repository;
44
using SharpRepository.Samples.CoreMvc.CustomRepositories;
55
using System.Collections.Generic;
6+
using System.Linq;
67

78
namespace SharpRepository.CoreMvc.Controllers
89
{
@@ -20,7 +21,7 @@ public EmailsController(EmailRepository repository, IRepository<Contact, string>
2021
// GET: Mails
2122
public ActionResult Index()
2223
{
23-
var mails = repository.GetMails();
24+
var mails = repository.GetMails().ToArray();
2425

2526
return View(mails);
2627
}

SharpRepository.Samples.CoreMvc/CustomRepositories/EmailRepository.cs

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -16,7 +16,8 @@ public EmailRepository(ISharpRepositoryConfiguration configuration, string repos
1616

1717
public IEnumerable<string> GetMails()
1818
{
19-
return this.GetAll().SelectMany(c => c.Emails).Select(m => m.EmailAddress).Distinct();
19+
return this.AsQueryable().Where(c => c.Emails != null & c.Emails.Any()).SelectMany(c => c.Emails).Select(m => m.EmailAddress)
20+
.Distinct();
2021
}
2122
}
2223
}

SharpRepository.Samples.CoreMvc/Models/Email.cs

Lines changed: 0 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -4,10 +4,8 @@ namespace SharpRepository.CoreMvc.Models
44
{
55
public class Email
66
{
7-
public int Id { get; set; }
87

98
public string EmailAddress { get; set; }
109

11-
public Contact Contact;
1210
}
1311
}

SharpRepository.Samples.CoreMvc/Startup.cs

Lines changed: 6 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,8 @@
77
using SharpRepository.Repository;
88
using SharpRepository.Samples.CoreMvc.CustomRepositories;
99
using System;
10+
using MongoDB.Bson.Serialization;
11+
using SharpRepository.CoreMvc.Models;
1012

1113
namespace SharpRepository.CoreMvc
1214
{
@@ -24,15 +26,15 @@ public IServiceProvider ConfigureServices(IServiceCollection services)
2426
{
2527
services.AddMvc();
2628

27-
services.AddDbContext<ContactContext>(options => options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")), ServiceLifetime.Transient);
29+
//services.AddDbContext<ContactContext>(options => options.UseSqlServer(Configuration.GetConnectionString("DefaultConnection")), ServiceLifetime.Transient);
2830

2931
// services.AddTransient<DbContext, ContactContext>(); // needed if you don't write dbContextClass on json configuration
3032

31-
services.AddTransient<EmailRepository>(r => new EmailRepository(RepositoryFactory.BuildSharpRepositoryConfiguation(Configuration.GetSection("sharpRepository"))));
33+
services.AddTransient<EmailRepository>(r => new EmailRepository(RepositoryFactory.BuildSharpRepositoryConfiguation(Configuration.GetSection("sharpRepository")), "mongoDb"));
3234

3335
// return services.UseSharpRepository(Configuration.GetSection("sharpRepository")); //default InMemory
34-
// return services.UseSharpRepository(Configuration.GetSection("sharpRepository"), "mongoDb"); // for Mongo Db
35-
return services.UseSharpRepository(Configuration.GetSection("sharpRepository"), "efCore"); // for Ef Core
36+
return services.UseSharpRepository(Configuration.GetSection("sharpRepository"), "mongoDb"); // for Mongo Db
37+
//return services.UseSharpRepository(Configuration.GetSection("sharpRepository"), "efCore"); // for Ef Core
3638
}
3739

3840
// This method gets called by the runtime. Use this method to configure the HTTP request pipeline.

SharpRepository.Samples.CoreMvc/Views/Emails/Index.cshtml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -21,7 +21,7 @@
2121
{
2222
<tr>
2323
<td>
24-
item
24+
@item
2525
</td>
2626
</tr>
2727
}

0 commit comments

Comments
 (0)