diff --git a/.gitignore b/.gitignore index 48597ec..5273f55 100644 --- a/.gitignore +++ b/.gitignore @@ -2,6 +2,7 @@ # Edit at https://www.toptal.com/developers/gitignore?templates=dotnetcore,visualstudio,visualstudiocode log.txt +cat_cafe/log.txt ### DotnetCore ### # .NET Core build folders @@ -427,3 +428,4 @@ FodyWeavers.xsd # Additional files built by Visual Studio # End of https://www.toptal.com/developers/gitignore/api/dotnetcore,visualstudio,visualstudiocode +/Tests/Tests - Backup.csproj diff --git a/Tests/Controllers/CatsControllerTest.cs b/Tests/Controllers/CatsControllerTest.cs new file mode 100644 index 0000000..796fca7 --- /dev/null +++ b/Tests/Controllers/CatsControllerTest.cs @@ -0,0 +1,127 @@ +using AutoMapper; +using Castle.Core.Logging; +using cat_cafe.Controllers; +using cat_cafe.Dto; +using cat_cafe.Entities; +using cat_cafe.Mappers; +using cat_cafe.Repositories; +using Microsoft.AspNetCore.Http; +using Microsoft.AspNetCore.Mvc; +using Microsoft.EntityFrameworkCore; +using Microsoft.Extensions.Logging; +using Microsoft.Extensions.Logging.Abstractions; +using Microsoft.Extensions.Options; +using Newtonsoft.Json.Linq; +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using FluentAssertions; + + +namespace cat_cafe.Controllers.Tests +{ + + [TestClass()] + public class CatsControllerTest + { + + private readonly ILogger logger = new NullLogger(); + + private readonly MapperConfiguration mapperConf = new(mapper => mapper.AddProfile(typeof(CatMapper))); + + private readonly DbContextOptions options = new DbContextOptionsBuilder() + .UseInMemoryDatabase(databaseName: "CatCafeTests") + .Options; + + private readonly IMapper mapper; + + private readonly CatCafeContext context; + + private readonly CatsController controller; + + public CatsControllerTest() + { + mapper = mapperConf.CreateMapper(); + context = new CatCafeContext(options); + controller = new CatsController(context, mapper, logger); + } + + + [TestInitialize] + public void BeforeEach() + { + context.Database.EnsureCreated(); + context.Cats.AddRange( + new Cat + { + Id = 1, + Name = "Alice", + Age = 5 + }, + new Cat + { + Id = 2, + Name = "Bob", + Age = 3 + }); + context.SaveChanges(); + } + + [TestCleanup] + public void AfterEach() + { + context.Database.EnsureDeleted(); + } + + [TestMethod()] + public async Task GetCatsTest() + { + var actual = await controller.GetCats(); + + actual.Result.Should().BeOfType(); + + var actualResult = actual.Result as OkObjectResult; + + actualResult.Should().NotBeNull(); + actualResult!.Value.Should().BeEquivalentTo(new List() + { + new CatDto + { + Id = 1, + Name = "Alice", + }, + new CatDto + { + Id = 2, + Name = "Bob", + } + }.AsEnumerable()); + } + + [TestMethod()] + public void GetCatTest() + { + Assert.IsTrue(true); + } + + [TestMethod()] + public void PutCatTest() + { + Assert.IsTrue(true); + } + + [TestMethod()] + public void PostCatTest() + { + Assert.IsTrue(true); + } + + [TestMethod()] + public void DeleteCatTest() + { + Assert.IsTrue(true); + } + } +} \ No newline at end of file diff --git a/Tests/Tests.csproj b/Tests/Tests.csproj index fd2e07d..92027b6 100644 --- a/Tests/Tests.csproj +++ b/Tests/Tests.csproj @@ -9,24 +9,16 @@ + - - - runtime; build; native; contentfiles; analyzers; buildtransitive - all - - - runtime; build; native; contentfiles; analyzers; buildtransitive - all - - + + + + - - - diff --git a/Tests/UnitTest1.cs b/Tests/UnitTest1.cs deleted file mode 100644 index d834b5f..0000000 --- a/Tests/UnitTest1.cs +++ /dev/null @@ -1,23 +0,0 @@ -using cat_cafe.Entities; - -namespace Tests -{ - public class UnitTest1 - { - [Fact] - public void Test1() - { - String name = "Margot"; - int id = 1337; - - Cat cat = new() - { - Id = id, - Name = name - }; - - Assert.Equal(name, cat.Name); - Assert.Equal(id, cat.Id); - } - } -} \ No newline at end of file diff --git a/Tests/Usings.cs b/Tests/Usings.cs index 8c927eb..ab67c7e 100644 --- a/Tests/Usings.cs +++ b/Tests/Usings.cs @@ -1 +1 @@ -global using Xunit; \ No newline at end of file +global using Microsoft.VisualStudio.TestTools.UnitTesting; \ No newline at end of file diff --git a/cat_cafe/Controllers/BarsController.cs b/cat_cafe/Controllers/BarsController.cs index 1a8b202..6f58943 100644 --- a/cat_cafe/Controllers/BarsController.cs +++ b/cat_cafe/Controllers/BarsController.cs @@ -7,6 +7,10 @@ using Microsoft.AspNetCore.Mvc; using Microsoft.EntityFrameworkCore; using cat_cafe.Entities; using cat_cafe.Repositories; +using AutoMapper; +using cat_cafe.Dto; +using System.Collections; +using System.Xml.Linq; namespace cat_cafe.Controllers { @@ -15,43 +19,65 @@ namespace cat_cafe.Controllers public class BarsController : ControllerBase { private readonly CatCafeDbContext _context; + private readonly IMapper _mapper; + private readonly ILogger _logger; - public BarsController(CatCafeDbContext context) + public BarsController(CatCafeDbContext context,IMapper mapper, ILogger logger) { _context = context; + _mapper = mapper; + _logger = logger; } // GET: api/Bars [HttpGet] - public async Task>> GetBars() + public async Task>> GetBars() { - return await _context.bars.ToListAsync(); + //return await _context.bars.ToListAsync(); + var bars = _context.bars + .Include(a => a.cats) + .Select(a => new Bar + { + Id = a.Id, + Name = a.Name, + cats = a.cats.Select(p => new Cat { Name = p.Name, Age = p.Age, Id= p.Id}).ToList() + }) + .ToListAsync(); + return _mapper.Map>(bars); } // GET: api/Bars/5 [HttpGet("{id}")] - public async Task> GetBar(long id) + public async Task> GetBar(long id) { - var bar = await _context.bars.FindAsync(id); + //var bar = await _context.bars.FindAsync(id); + var bar = _context.bars.Include(p => p.cats) + .Select(a => new Bar + { + Id = a.Id, + Name = a.Name, + cats = a.cats.Select(p => new Cat { Name = p.Name, Age = p.Age, Id = p.Id }).ToList() + + }).FirstOrDefaultAsync(p => p.Id == id); if (bar == null) { return NotFound(); } - return bar; + return _mapper.Map(bar.Result); } // PUT: api/Bars/5 // To protect from overposting attacks, see https://go.microsoft.com/fwlink/?linkid=2123754 [HttpPut("{id}")] - public async Task PutBar(long id, Bar bar) + public async Task PutBar(long id, BarDto barDto) { - if (id != bar.Id) + if (id != barDto.Id) { return BadRequest(); } - + Bar bar = _mapper.Map(barDto); _context.Entry(bar).State = EntityState.Modified; try @@ -76,12 +102,12 @@ namespace cat_cafe.Controllers // POST: api/Bars // To protect from overposting attacks, see https://go.microsoft.com/fwlink/?linkid=2123754 [HttpPost] - public async Task> PostBar(Bar bar) + public async Task> PostBar(BarDto barDto) { - _context.bars.Add(bar); + _context.bars.Add(_mapper.Map(barDto)) ; await _context.SaveChangesAsync(); - return CreatedAtAction("GetBar", new { id = bar.Id }, bar); + return CreatedAtAction("GetBar", new { id = barDto.Id }, _mapper.Map(barDto)); } // DELETE: api/Bars/5 diff --git a/cat_cafe/Controllers/CatsController.cs b/cat_cafe/Controllers/CatsController.cs index be013cb..39832f7 100644 --- a/cat_cafe/Controllers/CatsController.cs +++ b/cat_cafe/Controllers/CatsController.cs @@ -9,6 +9,9 @@ using cat_cafe.Entities; using cat_cafe.Repositories; using AutoMapper; using cat_cafe.Dto; +using Serilog; +using Newtonsoft.Json; +using Microsoft.Extensions.Logging.Abstractions; namespace cat_cafe.Controllers { @@ -18,11 +21,13 @@ namespace cat_cafe.Controllers { private readonly CatCafeDbContext _context; private readonly IMapper _mapper; + private readonly ILogger _logger; - public CatsController(CatCafeDbContext context, IMapper mapper) + public CatsController(CatCafeDbContext context, IMapper mapper, ILogger logger) { _mapper = mapper; _context = context; + _logger = logger; } // GET: api/Cats @@ -32,6 +37,7 @@ namespace cat_cafe.Controllers var cats = await _context.cats.ToListAsync(); return _mapper.Map>(cats); + return Ok(_mapper.Map>(cats)); } // GET: api/Cats/5 @@ -45,7 +51,7 @@ namespace cat_cafe.Controllers return NotFound(); } - return _mapper.Map(cat); + return Ok(_mapper.Map(cat)); } // PUT: api/Cats/5 diff --git a/cat_cafe/Dto/BarDto.cs b/cat_cafe/Dto/BarDto.cs new file mode 100644 index 0000000..85173dd --- /dev/null +++ b/cat_cafe/Dto/BarDto.cs @@ -0,0 +1,13 @@ +using System; +using cat_cafe.Entities; + +namespace cat_cafe.Dto +{ + public class BarDto + { + public long Id { get; set; } + public string? Name { get; set; } + public List cats { get; set; } = new List(); + } +} + diff --git a/cat_cafe/EFCatCafe.db b/cat_cafe/EFCatCafe.db index 5174413..ee3a5ea 100644 Binary files a/cat_cafe/EFCatCafe.db and b/cat_cafe/EFCatCafe.db differ diff --git a/cat_cafe/Entities/Cat.cs b/cat_cafe/Entities/Cat.cs index 25999eb..d16b49d 100644 --- a/cat_cafe/Entities/Cat.cs +++ b/cat_cafe/Entities/Cat.cs @@ -1,9 +1,12 @@ -namespace cat_cafe.Entities +using System.ComponentModel.DataAnnotations; + +namespace cat_cafe.Entities { public class Cat { public long Id { get; set; } public string? Name { get; set; } + [Required] public int Age { get; set; } = 0; public string Meow() { return "meow"; } diff --git a/cat_cafe/Mappers/BarMapper.cs b/cat_cafe/Mappers/BarMapper.cs new file mode 100644 index 0000000..cb89d24 --- /dev/null +++ b/cat_cafe/Mappers/BarMapper.cs @@ -0,0 +1,18 @@ +using System; +using AutoMapper; +using cat_cafe.Dto; +using cat_cafe.Entities; + +namespace cat_cafe.Mappers +{ + public class BarMapper:Profile + { + public BarMapper() + { + + // var mapper = config.CreateMapper(); + CreateMap().ReverseMap(); + } + } +} + diff --git a/cat_cafe/Program.cs b/cat_cafe/Program.cs index fb61f53..8051079 100644 --- a/cat_cafe/Program.cs +++ b/cat_cafe/Program.cs @@ -8,11 +8,6 @@ using cat_cafe.Entities; var builder = WebApplication.CreateBuilder(args); -/* -ILoggerFactory loggerFactory=new LoggerFactory(); -loggerFactory.AddFile($@"{Directory.GetCurrentDirectory}\Logs\logs.txt"); -*/ - Log.Logger = new LoggerConfiguration().MinimumLevel.Information().WriteTo.File("log.txt").CreateLogger(); // Add services to the container. @@ -41,18 +36,13 @@ catch (Exception ex) { Console.WriteLine($"{ex.Message}\n... Couldn't use the da // Learn more about configuring Swagger/OpenAPI at https://aka.ms/aspnetcore/swashbuckle builder.Services.AddEndpointsApiExplorer(); builder.Services.AddSwaggerGen(); - builder.Services.AddAutoMapper(typeof(Program)); builder.Services.AddControllersWithViews(); var app = builder.Build(); -/*var loggerFactory = app.Services.GetService(); -loggerFactory.AddFile(builder.Configuration["Logging:LogFilePath"].ToString()); - -app.Services.GetService().AddFile(builder.Configuration["Logging:LogFilePath"].ToString());*/ - app.UseHttpLogging(); + // Configure the HTTP request pipeline. if (app.Environment.IsDevelopment()) { @@ -67,4 +57,5 @@ app.UseAuthorization(); app.MapControllers(); Log.Information("program start"); + app.Run(); diff --git a/cat_cafe/cat_cafe.sln b/cat_cafe/cat_cafe.sln index aa8e7c0..86b7799 100644 --- a/cat_cafe/cat_cafe.sln +++ b/cat_cafe/cat_cafe.sln @@ -5,7 +5,7 @@ VisualStudioVersion = 17.2.32616.157 MinimumVisualStudioVersion = 10.0.40219.1 Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "cat_cafe", "cat_cafe.csproj", "{CC02D05A-3817-4D0A-8766-3FEE0C90941B}" EndProject -Project("{9A19103F-16F7-4668-BE54-9A1E7A4F7556}") = "Tests", "..\Tests\Tests.csproj", "{674DDACC-DB0E-473B-81E2-E3CABB8CB65B}" +Project("{FAE04EC0-301F-11D3-BF4B-00C04F79EFBC}") = "Tests", "..\Tests\Tests.csproj", "{039A9A95-25ED-4632-9C4B-0AB4E5B5A7B4}" EndProject Global GlobalSection(SolutionConfigurationPlatforms) = preSolution @@ -17,10 +17,10 @@ Global {CC02D05A-3817-4D0A-8766-3FEE0C90941B}.Debug|Any CPU.Build.0 = Debug|Any CPU {CC02D05A-3817-4D0A-8766-3FEE0C90941B}.Release|Any CPU.ActiveCfg = Release|Any CPU {CC02D05A-3817-4D0A-8766-3FEE0C90941B}.Release|Any CPU.Build.0 = Release|Any CPU - {674DDACC-DB0E-473B-81E2-E3CABB8CB65B}.Debug|Any CPU.ActiveCfg = Debug|Any CPU - {674DDACC-DB0E-473B-81E2-E3CABB8CB65B}.Debug|Any CPU.Build.0 = Debug|Any CPU - {674DDACC-DB0E-473B-81E2-E3CABB8CB65B}.Release|Any CPU.ActiveCfg = Release|Any CPU - {674DDACC-DB0E-473B-81E2-E3CABB8CB65B}.Release|Any CPU.Build.0 = Release|Any CPU + {039A9A95-25ED-4632-9C4B-0AB4E5B5A7B4}.Debug|Any CPU.ActiveCfg = Debug|Any CPU + {039A9A95-25ED-4632-9C4B-0AB4E5B5A7B4}.Debug|Any CPU.Build.0 = Debug|Any CPU + {039A9A95-25ED-4632-9C4B-0AB4E5B5A7B4}.Release|Any CPU.ActiveCfg = Release|Any CPU + {039A9A95-25ED-4632-9C4B-0AB4E5B5A7B4}.Release|Any CPU.Build.0 = Release|Any CPU EndGlobalSection GlobalSection(SolutionProperties) = preSolution HideSolutionNode = FALSE diff --git a/cat_cafe/log.txt b/cat_cafe/log.txt index b5765e5..2fc4e6c 100644 --- a/cat_cafe/log.txt +++ b/cat_cafe/log.txt @@ -137,3 +137,15 @@ 2023-02-04 09:53:40.756 +01:00 [INF] program start 2023-02-04 09:53:50.214 +01:00 [INF] GET => get All customers 2023-02-04 09:53:50.290 +01:00 [INF] GET => 200 System.Collections.Generic.List`1[cat_cafe.Entities.Customer] length[3] +2023-02-04 11:47:11.896 +01:00 [INF] program start +2023-02-04 11:47:24.495 +01:00 [INF] GET => get All customers +2023-02-04 11:47:24.570 +01:00 [INF] GET => 200 System.Collections.Generic.List`1[cat_cafe.Entities.Customer] length[3] +2023-02-04 11:47:45.623 +01:00 [INF] POST => post customer +2023-02-04 11:47:45.710 +01:00 [INF] POST => 201 cat_cafe.Entities.Customer {"Id":4,"FullName":"string","Age":0} +2023-02-04 11:47:47.622 +01:00 [INF] POST => post customer +2023-02-04 11:47:47.627 +01:00 [INF] POST => 201 cat_cafe.Entities.Customer {"Id":5,"FullName":"string","Age":0} +2023-02-04 11:47:57.417 +01:00 [INF] GET => get All customers +2023-02-04 11:47:57.421 +01:00 [INF] GET => 200 System.Collections.Generic.List`1[cat_cafe.Entities.Customer] length[5] +2023-02-04 11:48:05.671 +01:00 [INF] program start +2023-02-04 11:48:15.442 +01:00 [INF] GET => get All customers +2023-02-04 11:48:15.516 +01:00 [INF] GET => 200 System.Collections.Generic.List`1[cat_cafe.Entities.Customer] length[5]