diff --git a/Application/CommentDTO.cs b/Application/CommentDTO.cs
new file mode 100644
index 0000000..341bf33
--- /dev/null
+++ b/Application/CommentDTO.cs
@@ -0,0 +1,12 @@
+using System;
+
+namespace Application
+{
+ public class CommentDTO
+ {
+ public Guid Id { get; set; }
+ public string Content { get; set; }
+ public int UpvotesCount { get; set; }
+ public int DownvotesCount { get; set; }
+ }
+}
\ No newline at end of file
diff --git a/Application/CommentService.cs b/Application/CommentService.cs
new file mode 100644
index 0000000..87130e1
--- /dev/null
+++ b/Application/CommentService.cs
@@ -0,0 +1,43 @@
+using System;
+using System.Linq;
+using Domain;
+
+namespace Application
+{
+ public class CommentService
+ {
+ private readonly ILinkRepository _linkRepository;
+ private readonly ICommentRepository _commentRepository;
+ private readonly IData _data;
+
+ public CommentService(ILinkRepository linkRepository, ICommentRepository commentRepository, IData data)
+ {
+ _linkRepository = linkRepository;
+ _commentRepository = commentRepository;
+ _data = data;
+ }
+
+ public void PublishComment(PublishCommentCommand cmd)
+ {
+ var link = _linkRepository.GetById(cmd.LinkId);
+ var comment = link.AddComment(cmd.Content);
+
+ _commentRepository.Add(comment);
+ }
+
+ public CommentDTO[] GetAllLinkComments(Guid linkId)
+ {
+ return _data.Comments
+ .OrderByDescending(comment => comment.CreatedAt)
+ .Where(comment => comment.LinkId == linkId)
+ .Select(comment => new CommentDTO
+ {
+ Id = comment.Id,
+ Content = comment.Content,
+ UpvotesCount = 0,
+ DownvotesCount = 0,
+ })
+ .ToArray();
+ }
+ }
+}
\ No newline at end of file
diff --git a/Application/IData.cs b/Application/IData.cs
index 8613972..a4e063a 100644
--- a/Application/IData.cs
+++ b/Application/IData.cs
@@ -9,5 +9,6 @@ namespace Application
public interface IData
{
IQueryable Links { get; }
+ IQueryable Comments { get; }
}
}
\ No newline at end of file
diff --git a/Application/LinkService.cs b/Application/LinkService.cs
index 5d080bf..015a607 100644
--- a/Application/LinkService.cs
+++ b/Application/LinkService.cs
@@ -38,18 +38,6 @@ namespace Application
///
public LinkDTO[] GetAllLinks()
{
- // return (from link in _data.Links
- // orderby link.CreatedAt descending
- // select new LinkDTO
- // {
- // Id = link.Id,
- // Url = link.Url,
- // CreatedAt = link.CreatedAt,
- // UpvotesCount = 2,
- // DownvotesCount = 4,
- // CommentsCount = 54,
- // }).ToArray();
-
return LinksDTO().ToArray();
}
@@ -60,18 +48,30 @@ namespace Application
private IQueryable LinksDTO()
{
- return _data.Links
- .Select(link => new LinkDTO
- {
- Id = link.Id,
- Url = link.Url,
- CreatedAt = link.CreatedAt,
- UpvotesCount = 2,
- DownvotesCount = 4,
- CommentsCount = 54,
- })
- // .Where(linkDto => linkDto.UpvotesCount > 5)
- .OrderByDescending(linkDto => linkDto.CreatedAt);
+ return (from link in _data.Links
+ join comment in _data.Comments on link.Id equals comment.LinkId into comments
+ orderby link.CreatedAt descending
+ select new LinkDTO
+ {
+ Id = link.Id,
+ Url = link.Url,
+ CreatedAt = link.CreatedAt,
+ UpvotesCount = 2,
+ DownvotesCount = 4,
+ CommentsCount = comments.Count(),
+ });
+
+ // return _data.Links
+ // .Select(link => new LinkDTO
+ // {
+ // Id = link.Id,
+ // Url = link.Url,
+ // CreatedAt = link.CreatedAt,
+ // UpvotesCount = 2,
+ // DownvotesCount = 4,
+ // CommentsCount = _data.Comments.Count(comment => comment.LinkId == link.Id),
+ // })
+ // .OrderByDescending(linkDto => linkDto.CreatedAt);
}
}
}
diff --git a/Application/PublishCommentCommand.cs b/Application/PublishCommentCommand.cs
new file mode 100644
index 0000000..6feea60
--- /dev/null
+++ b/Application/PublishCommentCommand.cs
@@ -0,0 +1,14 @@
+using System;
+using System.ComponentModel.DataAnnotations;
+
+namespace Application
+{
+ public class PublishCommentCommand
+ {
+ [Required]
+ public Guid LinkId { get; set; }
+
+ [Required]
+ public string Content { get; set; }
+ }
+}
\ No newline at end of file
diff --git a/Domain/Comment.cs b/Domain/Comment.cs
new file mode 100644
index 0000000..518a113
--- /dev/null
+++ b/Domain/Comment.cs
@@ -0,0 +1,20 @@
+using System;
+
+namespace Domain
+{
+ public class Comment
+ {
+ public Guid Id { get; }
+ public Guid LinkId { get; }
+ public string Content { get; }
+ public DateTime CreatedAt { get; }
+
+ internal Comment(Guid linkId, string content)
+ {
+ Id = Guid.NewGuid();
+ LinkId = linkId;
+ Content = content;
+ CreatedAt = DateTime.UtcNow;
+ }
+ }
+}
\ No newline at end of file
diff --git a/Domain/ICommentRepository.cs b/Domain/ICommentRepository.cs
new file mode 100644
index 0000000..d510113
--- /dev/null
+++ b/Domain/ICommentRepository.cs
@@ -0,0 +1,7 @@
+namespace Domain
+{
+ public interface ICommentRepository
+ {
+ void Add(Comment comment);
+ }
+}
\ No newline at end of file
diff --git a/Domain/ILinkRepository.cs b/Domain/ILinkRepository.cs
index 08d0f4e..cb52d1a 100644
--- a/Domain/ILinkRepository.cs
+++ b/Domain/ILinkRepository.cs
@@ -1,7 +1,10 @@
+using System;
+
namespace Domain
{
public interface ILinkRepository
{
void Add(Link link);
+ Link GetById(Guid id);
}
}
\ No newline at end of file
diff --git a/Domain/Link.cs b/Domain/Link.cs
index 4c62f92..dd5cb04 100644
--- a/Domain/Link.cs
+++ b/Domain/Link.cs
@@ -17,5 +17,16 @@ namespace Domain
CreatedAt = DateTime.UtcNow;
Url = url;
}
+
+ ///
+ /// Crée un commentaire pour ce lien. Permet de valider l'existence du lien et
+ /// potentiellement des règles métier de création plus complexes.
+ ///
+ ///
+ ///
+ public Comment AddComment(string content)
+ {
+ return new Comment(this.Id, content);
+ }
}
}
diff --git a/Infrastructure/Repositories/Memory/CommentRepository.cs b/Infrastructure/Repositories/Memory/CommentRepository.cs
new file mode 100644
index 0000000..159b8b9
--- /dev/null
+++ b/Infrastructure/Repositories/Memory/CommentRepository.cs
@@ -0,0 +1,21 @@
+using System.Collections.Generic;
+using System.Linq;
+using Domain;
+
+namespace Infrastructure.Repositories.Memory
+{
+ public class CommentRepository : ICommentRepository
+ {
+ public List Comments { get; }
+
+ public CommentRepository(params Comment[] comments)
+ {
+ Comments = comments.ToList();
+ }
+
+ public void Add(Comment comment)
+ {
+ Comments.Add(comment);
+ }
+ }
+}
\ No newline at end of file
diff --git a/Infrastructure/Repositories/Memory/Data.cs b/Infrastructure/Repositories/Memory/Data.cs
index 7e9a4e0..3050981 100644
--- a/Infrastructure/Repositories/Memory/Data.cs
+++ b/Infrastructure/Repositories/Memory/Data.cs
@@ -7,12 +7,16 @@ namespace Infrastructure.Repositories.Memory
public class Data : IData
{
private readonly LinkRepository _linkRepository;
+ private readonly CommentRepository _commentRepository;
public IQueryable Links => _linkRepository.Links.AsQueryable();
- public Data(LinkRepository linkRepository)
+ public IQueryable Comments => _commentRepository.Comments.AsQueryable();
+
+ public Data(LinkRepository linkRepository, CommentRepository commentRepository)
{
_linkRepository = linkRepository;
+ _commentRepository = commentRepository;
}
}
}
\ No newline at end of file
diff --git a/Infrastructure/Repositories/Memory/LinkRepository.cs b/Infrastructure/Repositories/Memory/LinkRepository.cs
index 3fec1ee..cb6da80 100644
--- a/Infrastructure/Repositories/Memory/LinkRepository.cs
+++ b/Infrastructure/Repositories/Memory/LinkRepository.cs
@@ -1,3 +1,4 @@
+using System;
using System.Collections.Generic;
using System.Linq;
using Domain;
@@ -17,5 +18,10 @@ namespace Infrastructure.Repositories.Memory
{
Links.Add(link);
}
+
+ public Link GetById(Guid id)
+ {
+ return Links.Single(link => link.Id == id);
+ }
}
}
\ No newline at end of file