everyone!
I am creating a open source social network (I don't know if I can post the URL here) using .net core 2.1, mongo atlas using the driver v2.9.2
I am migrating from MS SQL (wich I know how to do stuff on it) to mongo (wicth I am still learning).
I have two entities, UserContent and UserContentComment, both inheriting from Entity:
public class Entity
{
public Guid Id { get; set; }
public Guid UserId { get; set; }
public DateTime CreateDate { get; set; }
public Entity()
{
CreateDate = DateTime.Now;
}
}
public class UserContent : Entity
{
public string AuthorName { get; set; }
public string Content { get; set; }
public virtual List<UserContentComment> Comments { get; set; }
}
public class UserContentComment : Entity
{
public Guid UserContentId { get; set; }
public string AuthorName { get; set; }
public string Text { get; set; }
}
I will probably clean some properties since I won't need them anymore like UserContentId, for example, because I will add UserContentComments as a nested array "Comments" of UserContent like this:
{
"_id" : UUID("ff6e86cc-bddf-419d-e049-08d6b903e6db"),
"_t" : [
"Entity",
"UserContent"
],
"userId" : UUID("9d6e26ca-5bc7-4121-9b03-ed7f9a442cf6"),
"createDate" : ISODate("2019-04-04T16:38:23.740-03:00"),
"authorName" : "User Full Name",
"content" : "content main text",
"comments" : [
{
"_t" : [
"Entity",
"UserContentComment"
],
"_id" : UUID("d7dc1328-b1bc-4f1f-a9a5-08d6bf05b672"),
"userId" : UUID("5f9eeb34-22e2-43bf-9130-034a7997d2af"),
"createDate" : ISODate("2019-04-12T05:15:20.636-03:00"),
"userContentId" : UUID("ff6e86cc-bddf-419d-e049-08d6b903e6db"),
"authorName" : "User Full Name",
"text" : "Hello from Russia!"
}
]
}
My problem is I need to:
- Count comments BY UserId;
- Get comments BY UserId;
- Get single comment BY Id;
- Update single comment BY Id;
- Update all comments BY UserId;
How can I achieve that using the mongodb driver for C#?
Thank you very much for the help!
UPDATE - What I got so far
To count comments, I got this three ways:
var count = DbSet.Aggregate()
.Match(x => x.Comments.Any(y => y.UserId == userId))
.Project(new BsonDocument("count", new BsonDocument("$size", "$comments"))).ToList();
var q = Builders<UserContent>.Filter.ElemMatch(x => x.Comments, d => d.UserId == userId);
var p = Builders<UserContent>.Projection.ElemMatch(x => x.Comments, d => d.UserId == userId);
var data = DbSet.Find(q).Project(p).ToList();
var data2 = DbSet.Find(q).ToList();
These three different queries, return 28, because the user really commented on 28 posts, but there are a total of 31 comments on the database because the user commented multiple times on some posts. What am I missing here?
UPDATE now the COUNT works
I got the count working using this code:
DbSet.AsQueryable().SelectMany(x => x.Comments).Where(where).Count();
I got 31 using the above code, now is correct!
The question now is: will this run on memory or on DB?