Use separate DTOs, entities and models

This commit is contained in:
Stanislav Mykhailenko 2023-05-18 19:42:14 +03:00
parent f29798b3e7
commit e3d4ef87c2
GPG key ID: 1E95E66A9C9D6A36
24 changed files with 249 additions and 28 deletions

View file

@ -1,4 +1,4 @@
using NG_2023_Kanban.BusinessLayer.Services;
using NG_2023_Kanban.BusinessLayer.Services;
using Microsoft.Extensions.DependencyInjection;
namespace NG_2023_Kanban.BusinessLayer.Inject
@ -8,6 +8,7 @@ namespace NG_2023_Kanban.BusinessLayer.Inject
public static void InjectBLL(
this IServiceCollection services)
{
services.AddAutoMapper(typeof(MappingProfile));
services.AddScoped<UserService>();
}
}

View file

@ -1,10 +1,10 @@
using NG_2023_Kanban.DataLayer.Entities;
using NG_2023_Kanban.BusinessLayer.Models;
namespace NG_2023_Kanban.BusinessLayer.Interfaces
{
public interface IUserService
{
Task<User> LoginAsync(User user);
Task<User> RegisterAsync(User user);
Task<UserModel?> LoginAsync(UserModel user);
Task<UserModel> RegisterAsync(UserModel user);
}
}

View file

@ -0,0 +1,27 @@
using AutoMapper;
using NG_2023_Kanban.BusinessLayer.Models;
using NG_2023_Kanban.DataLayer.Entities;
namespace NG_2023_Kanban.BusinessLayer
{
public class MappingProfile : Profile
{
public MappingProfile()
{
CreateMap<BoardModel, Board>()
.ReverseMap();
CreateMap<CardModel, Card>()
.ReverseMap();
CreateMap<ColumnModel, Column>()
.ReverseMap();
CreateMap<CommentModel, Comment>()
.ReverseMap();
CreateMap<UserModel, User>()
.ReverseMap();
}
}
}

View file

@ -0,0 +1,7 @@
namespace NG_2023_Kanban.BusinessLayer.Models
{
public abstract class BaseModel
{
public int Id { get; set; }
}
}

View file

@ -0,0 +1,11 @@
namespace NG_2023_Kanban.BusinessLayer.Models
{
public class BoardModel : BaseModel
{
public string Name { get; set; }
public virtual ICollection<UserModel>? Users { get; set; } = new HashSet<UserModel>();
public virtual ICollection<ColumnModel>? Columns { get; set; } = new HashSet<ColumnModel>();
}
}

View file

@ -0,0 +1,15 @@
namespace NG_2023_Kanban.BusinessLayer.Models
{
public class CardModel : BaseModel
{
public string Name { get; set; }
public string Description { get; set; }
public int SenderId { get; set; }
public int ColumnId { get; set; }
public virtual UserModel Sender { get; set; }
public virtual ColumnModel Column { get; set; }
public virtual ICollection<CommentModel> Comments { get; set; } = new HashSet<CommentModel>();
}
}

View file

@ -0,0 +1,12 @@
namespace NG_2023_Kanban.BusinessLayer.Models
{
public class ColumnModel : BaseModel
{
public string Name { get; set; }
public int BoardId { get; set; }
public virtual BoardModel Board { get; set; }
public virtual ICollection<CardModel>? Cards { get; set; } = new HashSet<CardModel>();
}
}

View file

@ -0,0 +1,12 @@
namespace NG_2023_Kanban.BusinessLayer.Models
{
public class CommentModel : BaseModel
{
public string Text { get; set; }
public int SenderId { get; set; }
public int CardId { get; set; }
public virtual UserModel? Sender { get; set; }
public virtual CardModel? Card { get; set; }
}
}

View file

@ -0,0 +1,16 @@
namespace NG_2023_Kanban.BusinessLayer.Models
{
public class UserModel : BaseModel
{
public string FullName { get; set; }
public string Username { get; set; }
public string Password { get; set; }
public bool IsAdmin { get; set; } = false;
public virtual ICollection<BoardModel>? Boards { get; set; } = new HashSet<BoardModel>();
public virtual ICollection<CardModel>? Cards { get; set; } = new HashSet<CardModel>();
public virtual ICollection<CommentModel>? Comments { get; set; } = new HashSet<CommentModel>();
}
}

View file

@ -10,4 +10,9 @@
<ProjectReference Include="../NG_2023_Kanban.DataLayer/NG_2023_Kanban.DataLayer.csproj" />
</ItemGroup>
<ItemGroup>
<PackageReference Include="AutoMapper" Version="12.0.1" />
<PackageReference Include="Automapper.Extensions.Microsoft.DependencyInjection" Version="12.0.1" />
</ItemGroup>
</Project>

View file

@ -1,33 +1,37 @@
using NG_2023_Kanban.BusinessLayer.Interfaces;
using AutoMapper;
using NG_2023_Kanban.BusinessLayer.Interfaces;
using NG_2023_Kanban.BusinessLayer.Models;
using NG_2023_Kanban.DataLayer.Repositories;
using NG_2023_Kanban.DataLayer.Entities;
using NG_2023_Kanban.DataLayer.Interfaces;
using Microsoft.EntityFrameworkCore;
namespace NG_2023_Kanban.BusinessLayer.Services
{
public class UserService : IUserService
{
private readonly IUserRepository _userRepository;
private readonly IMapper _mapper;
public UserService(IUserRepository userRepository)
public UserService(IUserRepository userRepository, IMapper mapper)
{
_userRepository = userRepository;
_mapper = mapper;
}
public async Task<User?> LoginAsync(User user)
public async Task<UserModel?> LoginAsync(UserModel user)
{
var data = await _userRepository.FindAsync(x => x.Username == user.Username && x.Password == user.Password);
if (data.Any())
return data.First();
return _mapper.Map<ICollection<UserModel>>(data).First();
else
return null;
}
public async Task<User> RegisterAsync(User user)
public async Task<UserModel> RegisterAsync(UserModel user)
{
await _userRepository.CreateAsync(user);
return user;
var entity = _mapper.Map<User>(user);
await _userRepository.CreateAsync(entity);
return _mapper.Map<UserModel>(entity);
}
}
}

View file

@ -1,8 +1,10 @@
using System.Diagnostics;
using Microsoft.AspNetCore.Mvc;
using NG_2023_Kanban.DataLayer.Entities;
using AutoMapper;
using NG_2023_Kanban.Models;
using NG_2023_Kanban.DTOs;
using NG_2023_Kanban.Extensions;
using NG_2023_Kanban.DataLayer.Models;
using NG_2023_Kanban.BusinessLayer.Models;
using NG_2023_Kanban.BusinessLayer.Services;
namespace NG_2023_Kanban.Controllers;
@ -11,16 +13,18 @@ public class HomeController : Controller
{
private readonly UserService _userService;
private readonly ILogger<HomeController> _logger;
private readonly IMapper _mapper;
public HomeController(ILogger<HomeController> logger, UserService userService)
public HomeController(ILogger<HomeController> logger, UserService userService, IMapper mapper)
{
_logger = logger;
_userService = userService;
_mapper = mapper;
}
public IActionResult Index()
{
User? currentAccount = HttpContext.Session.GetObject<User>("Account");
var currentAccount = HttpContext.Session.GetObject<UserDto>("Account");
if (currentAccount != null)
{
ViewData["Account"] = currentAccount;
@ -31,7 +35,7 @@ public class HomeController : Controller
public IActionResult Login()
{
User? currentAccount = HttpContext.Session.GetObject<User>("Account");
var currentAccount = HttpContext.Session.GetObject<UserDto>("Account");
if (currentAccount != null)
return Redirect("/Home/Index");
@ -39,13 +43,16 @@ public class HomeController : Controller
}
[HttpPost]
public async Task<IActionResult> Login(User user)
public async Task<IActionResult> Login(UserDto user)
{
User? currentAccount = HttpContext.Session.GetObject<User>("Account");
var currentAccount = HttpContext.Session.GetObject<UserDto>("Account");
if (currentAccount != null)
return Redirect("/Home/Index");
User? account = await _userService.LoginAsync(user);
var model = _mapper.Map<UserModel>(user);
var account = _mapper.Map<UserDto>(await _userService.LoginAsync(model));
if (account != null)
{
HttpContext.Session.SetObject("Account", account);
@ -66,7 +73,7 @@ public class HomeController : Controller
public IActionResult Register()
{
User? currentAccount = HttpContext.Session.GetObject<User>("Account");
var currentAccount = HttpContext.Session.GetObject<UserDto>("Account");
if (currentAccount != null)
return Redirect("/Home/Index");
@ -74,15 +81,16 @@ public class HomeController : Controller
}
[HttpPost]
public async Task<IActionResult> Register(User user)
public async Task<IActionResult> Register(UserDto user)
{
User? currentAccount = HttpContext.Session.GetObject<User>("Account");
var currentAccount = HttpContext.Session.GetObject<UserDto>("Account");
if (currentAccount != null)
return Redirect("/Home/Index");
try
{
User account = await _userService.RegisterAsync(user);
var model = _mapper.Map<UserModel>(user);
var account = _mapper.Map<UserDto>(await _userService.RegisterAsync(model));
HttpContext.Session.SetObject("Account", account);
return Redirect("/Home/Index");

View file

@ -0,0 +1,7 @@
namespace NG_2023_Kanban.DTOs
{
public abstract class BaseDto
{
public int Id { get; set; }
}
}

View file

@ -0,0 +1,11 @@
namespace NG_2023_Kanban.DTOs
{
public class BoardDto : BaseDto
{
public string Name { get; set; }
public virtual ICollection<UserDto>? Users { get; set; } = new HashSet<UserDto>();
public virtual ICollection<ColumnDto>? Columns { get; set; } = new HashSet<ColumnDto>();
}
}

View file

@ -0,0 +1,15 @@
namespace NG_2023_Kanban.DTOs
{
public class CardDto : BaseDto
{
public string Name { get; set; }
public string Description { get; set; }
public int SenderId { get; set; }
public int ColumnId { get; set; }
public virtual UserDto Sender { get; set; }
public virtual ColumnDto Column { get; set; }
public virtual ICollection<CommentDto> Comments { get; set; } = new HashSet<CommentDto>();
}
}

View file

@ -0,0 +1,12 @@
namespace NG_2023_Kanban.DTOs
{
public class ColumnDto : BaseDto
{
public string Name { get; set; }
public int BoardId { get; set; }
public virtual BoardDto Board { get; set; }
public virtual ICollection<CardDto>? Cards { get; set; } = new HashSet<CardDto>();
}
}

View file

@ -0,0 +1,12 @@
namespace NG_2023_Kanban.DTOs
{
public class CommentDto : BaseDto
{
public string Text { get; set; }
public int SenderId { get; set; }
public int CardId { get; set; }
public virtual UserDto? Sender { get; set; }
public virtual CardDto? Card { get; set; }
}
}

View file

@ -0,0 +1,16 @@
namespace NG_2023_Kanban.DTOs
{
public class UserDto : BaseDto
{
public string FullName { get; set; }
public string Username { get; set; }
public string Password { get; set; }
public bool IsAdmin { get; set; } = false;
public virtual ICollection<BoardDto>? Boards { get; set; } = new HashSet<BoardDto>();
public virtual ICollection<CardDto>? Cards { get; set; } = new HashSet<CardDto>();
public virtual ICollection<CommentDto>? Comments { get; set; } = new HashSet<CommentDto>();
}
}

View file

@ -0,0 +1,27 @@
using AutoMapper;
using NG_2023_Kanban.DTOs;
using NG_2023_Kanban.BusinessLayer.Models;
namespace NG_2023_Kanban
{
public class MappingProfile : Profile
{
public MappingProfile()
{
CreateMap<BoardDto, BoardModel>()
.ReverseMap();
CreateMap<CardDto, CardModel>()
.ReverseMap();
CreateMap<ColumnDto, ColumnModel>()
.ReverseMap();
CreateMap<CommentDto, CommentModel>()
.ReverseMap();
CreateMap<UserDto, UserModel>()
.ReverseMap();
}
}
}

View file

@ -1,4 +1,4 @@
namespace NG_2023_Kanban.DataLayer.Models;
namespace NG_2023_Kanban.Models;
public class ErrorViewModel
{

View file

@ -7,6 +7,7 @@
</PropertyGroup>
<ItemGroup>
<PackageReference Include="AutoMapper" Version="12.0.1" />
<PackageReference Include="Newtonsoft.Json" Version="13.0.3" />
</ItemGroup>

View file

@ -1,3 +1,4 @@
using NG_2023_Kanban;
using NG_2023_Kanban.BusinessLayer.Inject;
using NG_2023_Kanban.DataLayer.DbStartup;
@ -7,6 +8,7 @@ IConfiguration configuration = builder.Configuration;
builder.Services.InjectDAL(configuration);
builder.Services.InjectBLL();
builder.Services.AddAutoMapper(typeof(MappingProfile));
// Add services to the container.
builder.Services.AddControllersWithViews();

View file

@ -1,6 +1,6 @@
@using NG_2023_Kanban.DataLayer.Entities
@using NG_2023_Kanban.DTOs
@{
var user = ViewData["Account"] as User;
var user = ViewData["Account"] as UserDto;
}
@{

View file

@ -1,3 +1,3 @@
@using NG_2023_Kanban
@using NG_2023_Kanban.DataLayer.Models
@using NG_2023_Kanban.Models
@addTagHelper *, Microsoft.AspNetCore.Mvc.TagHelpers