pushed api files

pushed middlewares
This commit is contained in:
ElenitaMLG
2024-04-07 02:49:34 +03:00
parent 55eaa0d53a
commit 2ccec617a5
11 changed files with 390 additions and 54 deletions
-4
View File
@@ -10,10 +10,6 @@
<PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" /> <PackageReference Include="Swashbuckle.AspNetCore" Version="6.5.0" />
</ItemGroup> </ItemGroup>
<ItemGroup>
<Folder Include="Middlewares\" />
</ItemGroup>
<ItemGroup> <ItemGroup>
<ProjectReference Include="..\Application\Application.csproj" /> <ProjectReference Include="..\Application\Application.csproj" />
<ProjectReference Include="..\Infrastructure\Infrastructure.csproj" /> <ProjectReference Include="..\Infrastructure\Infrastructure.csproj" />
+5 -6
View File
@@ -1,10 +1,9 @@
using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc;
namespace HealthcareManager.API.Controllers namespace HealthcareManager.API.Controllers;
[Route("api/v1/[controller]")]
[ApiController]
public abstract class BaseApiController : ControllerBase
{ {
[Route("api/v1/[controller]")]
[ApiController]
public abstract class BaseApiController : ControllerBase
{
}
} }
+8 -10
View File
@@ -1,16 +1,14 @@
using Infrastructure.Services.MongoDB; using Infrastructure.Services.MongoDB;
using Microsoft.AspNetCore.Mvc;
namespace HealthcareManager.API.Controllers namespace HealthcareManager.API.Controllers;
public class ChatController : BaseApiController
{ {
public class ChatController : BaseApiController private readonly MongoDbService _mongoDbService;
public ChatController(MongoDbService mongoDbService)
{ {
private readonly MongoDbService _mongoDbService; _mongoDbService = mongoDbService;
public ChatController(MongoDbService mongoDbService)
{
_mongoDbService = mongoDbService;
}
} }
} }
+90 -24
View File
@@ -2,50 +2,116 @@
using Core.Entities; using Core.Entities;
using Application.Endpoints.Doctors.Login; using Application.Endpoints.Doctors.Login;
using Application.Services.Database; using Application.Services.Database;
using Application.Endpoints.Doctors.Registration;
using Application.Endpoints.Doctors.ResetPassword;
using Application.Endpoints.Doctors.Profile;
namespace HealthcareManager.API.Controllers namespace HealthcareManager.API.Controllers;
[ApiController]
[Route("api/[controller]")]
public class DoctorsController : ControllerBase
{ {
[ApiController] private readonly IDoctorRepository _database;
[Route("api/[controller]")]
public class DoctorsController : ControllerBase public DoctorsController(IDoctorRepository database)
{ {
private readonly IDoctorRepository _database; _database = database ?? throw new ArgumentNullException(nameof(database));
}
public DoctorsController(IDoctorRepository database) [HttpGet]
public async Task<ActionResult<Doctor>> GetAllDoctors()
{
var handler = new DoctorProfileHandler(_database);
var response = await handler.HandleGetAll();
if (!response.Success)
{ {
_database = database ?? throw new ArgumentNullException(nameof(database)); return BadRequest(response);
} }
[HttpGet("{id}")] return Ok(response.Data);
public async Task<ActionResult<Doctor>> GetDoctor(int id) }
[HttpGet("{id}")]
public async Task<ActionResult<Doctor>> GetDoctor(Guid id)
{
var handler = new DoctorProfileHandler(_database);
var response = await handler.HandleGet(id);
if (!response.Success)
{ {
return NotFound(); return BadRequest(response);
} }
[HttpPost] return Ok(response.Data);
public async Task<ActionResult<Doctor>> Login(DoctorLoginDTO doctor) }
[HttpPost("login")]
public async Task<ActionResult<Doctor>> Login(DoctorLoginDTO doctor)
{
var handler = new DoctorLoginHandler(_database);
var response = await handler.Handle(doctor).ConfigureAwait(false);
if(!response.Success)
{ {
var handler = new DoctorLoginHandler(_database); return Unauthorized(response);
var response = handler.Handle(doctor).Result; }
if(!response.Success) return Ok(response);
{ }
return Unauthorized(response);
}
[HttpPost("register")]
public async Task<ActionResult<Doctor>> Register(DoctorRegistrationDto doctor)
{
var handler = new DoctorRegistrationHandler(_database);
var response = await handler.Handle(doctor).ConfigureAwait(false);
if (!response.Success)
{
return Unauthorized(response);
}
return Ok(response);
}
[HttpPost("resetPassword")]
public async Task<IActionResult> ResetPassword(DoctorLoginDTO resetDoctorDto)
{
var handler = new DoctorResetPasswordHandler(_database);
var response = await handler.Handle(resetDoctorDto).ConfigureAwait(false);
if (response.Success)
{
return Ok(response); return Ok(response);
} }
[HttpPut("{id}")] return BadRequest(response);
public async Task<IActionResult> PutDoctor(int id, Doctor doctor) }
[HttpPut("{id}/profile")]
public async Task<IActionResult> UpdateDoctorProfile(Guid id, [FromBody]DoctorProfileDTO doctorDto)
{
var handler = new DoctorProfileHandler(_database);
var response = await handler.HandleUpdate(id, doctorDto).ConfigureAwait(false);
if (response.Success)
{ {
return NotFound(); return Ok(response);
} }
[HttpDelete("{id}")] return BadRequest(response);
public async Task<IActionResult> DeleteDoctor(int id) }
[HttpDelete("{id}/profile")]
public async Task<IActionResult> DeleteDoctorProfile(Guid id)
{
var handler = new DoctorProfileHandler(_database);
var response = await handler.HandleDelete(id).ConfigureAwait(false);
if (response.Success)
{ {
return NotFound(); return NoContent();
} }
return BadRequest(response);
} }
} }
@@ -1,9 +1,67 @@
using Microsoft.AspNetCore.Mvc; using Application.Endpoints.MedicalHistories;
using Application.Services.Database;
using Core.Entities;
using Microsoft.AspNetCore.Mvc;
namespace HealthcareManager.API.Controllers namespace HealthcareManager.API.Controllers;
[ApiController]
[Route("api/[controller]")]
public class MedicalHistoryController : ControllerBase
{ {
public class MedicalHistoryController : BaseApiController private readonly IMedicalHistoryRepository _medicalHistoryRepository;
{ private readonly IPacientRepository _pacientRepository;
public MedicalHistoryController(IMedicalHistoryRepository medicalHistoryRepository, IPacientRepository pacientRepository)
{
_medicalHistoryRepository = medicalHistoryRepository ?? throw new ArgumentNullException(nameof(medicalHistoryRepository));
_pacientRepository = pacientRepository ?? throw new ArgumentNullException(nameof(pacientRepository));
}
[HttpGet("{id}")]
public async Task<ActionResult<MedicalHistory>> GetAsync(Guid id)
{
var handler = new MedicalHistoryHandler(_medicalHistoryRepository, _pacientRepository);
var response = await handler.HandleGet(id);
if (!response.Success)
{
return BadRequest(response);
}
return Ok(response.Data);
}
[HttpPost("{id}")]
public async Task<ActionResult<MedicalHistory>> PostAsync(Guid id, [FromBody] byte[] description)
{
var handler = new MedicalHistoryHandler(_medicalHistoryRepository, _pacientRepository);
var response = await handler.HandleCreate(id, description).ConfigureAwait(false);
if (!response.Success)
{
return Unauthorized(response);
}
return Ok(response);
}
[HttpPut("{id}")]
public async Task<IActionResult> UpdateAsync(Guid id, [FromBody] MedicalHistoryDTO medicalHistoryDTO)
{
var handler = new MedicalHistoryHandler(_medicalHistoryRepository, _pacientRepository);
var response = await handler.HandleUpdate(id, medicalHistoryDTO).ConfigureAwait(false);
if (response.Success)
{
return Ok(response);
}
return BadRequest(response);
}
[HttpPut("grant_access")]
public async Task<IActionResult> GrantAccessToMedicalHistory(Guid id)
{
return NotFound();
} }
} }
+111 -3
View File
@@ -1,9 +1,117 @@
using Microsoft.AspNetCore.Mvc; using Microsoft.AspNetCore.Mvc;
using Core.Entities;
using Application.Endpoints.Pacients.Login;
using Application.Services.Database;
using Application.Endpoints.Pacients.Registration;
using Application.Endpoints.Pacients.ResetPassword;
using Application.Endpoints.Pacients.Profile;
namespace HealthcareManager.API.Controllers namespace HealthcareManager.API.Controllers;
[ApiController]
[Route("api/[controller]")]
public class PacientsController : ControllerBase
{ {
public class PacientsController : BaseApiController private readonly IPacientRepository _database;
{
public PacientsController(IPacientRepository database)
{
_database = database ?? throw new ArgumentNullException(nameof(database));
}
[HttpGet]
public async Task<ActionResult<Pacient>> GetAllPacients()
{
var handler = new PacientProfileHandler(_database);
var response = await handler.HandleGetAll();
if (!response.Success)
{
return BadRequest(response);
}
return Ok(response.Data);
}
[HttpGet("{id}")]
public async Task<ActionResult<Pacient>> GetPacient(Guid id)
{
var handler = new PacientProfileHandler(_database);
var response = await handler.HandleGet(id);
if (!response.Success)
{
return BadRequest(response);
}
return Ok(response.Data);
}
[HttpPost("login")]
public async Task<ActionResult<Pacient>> Login(PacientLoginDTO pacient)
{
var handler = new PacientLoginHandler(_database);
var response = await handler.Handle(pacient).ConfigureAwait(false);
if (!response.Success)
{
return Unauthorized(response);
}
return Ok(response);
}
[HttpPost("register")]
public async Task<ActionResult<Pacient>> Register(PacientRegistrationDto pacient)
{
var handler = new PacientRegistrationHandler(_database);
var response = await handler.Handle(pacient).ConfigureAwait(false);
if (!response.Success)
{
return Unauthorized(response);
}
return Ok(response);
}
[HttpPost("resetPassword")]
public async Task<IActionResult> ResetPassword(PacientLoginDTO resetPacientDto)
{
var handler = new PacientResetPasswordHandler(_database);
var response = await handler.Handle(resetPacientDto).ConfigureAwait(false);
if (response.Success)
{
return Ok(response);
}
return BadRequest(response);
}
[HttpPut("{id}/profile")]
public async Task<IActionResult> UpdatePacientProfile(Guid id, [FromBody] PacientProfileDTO pacientDto)
{
var handler = new PacientProfileHandler(_database);
var response = await handler.HandleUpdate(id, pacientDto).ConfigureAwait(false);
if (response.Success)
{
return Ok(response);
}
return BadRequest(response);
}
[HttpDelete("{id}/profile")]
public async Task<IActionResult> DeletePacientProfile(Guid id)
{
var handler = new PacientProfileHandler(_database);
var response = await handler.HandleDelete(id).ConfigureAwait(false);
if (response.Success)
{
return NoContent();
}
return BadRequest(response);
} }
} }
@@ -0,0 +1,42 @@
namespace API.Middlewares;
public class ApiKeyValidationMiddleware
{
private readonly RequestDelegate _next;
private const string APIKEYNAME = "ApiKey";
public ApiKeyValidationMiddleware(RequestDelegate next)
{
_next = next;
}
public async Task InvokeAsync(HttpContext context)
{
if (!context.Request.Headers.TryGetValue(APIKEYNAME, out var extractedApiKey))
{
context.Response.StatusCode = 401;
await context.Response.WriteAsync("API Key was not provided.");
return;
}
var appSettings = context.RequestServices.GetRequiredService<IConfiguration>();
var apiKey = appSettings.GetValue<string>("ApiKey");
if (string.IsNullOrEmpty(apiKey))
{
context.Response.StatusCode = 400;
await context.Response.WriteAsync("Unable to retrieve API key.");
return;
}
if (!apiKey.Equals(extractedApiKey))
{
context.Response.StatusCode = 401;
await context.Response.WriteAsync("Unauthorized client.");
return;
}
await _next(context);
}
}
@@ -0,0 +1,35 @@
using System.Net;
using System.Text;
namespace API.Middlewares;
public class BodyCheckMiddleware(RequestDelegate next)
{
private readonly RequestDelegate _next = next;
public async Task InvokeAsync(HttpContext context)
{
// Only check the body for POST and PUT requests
if (context.Request.Method == HttpMethods.Post || context.Request.Method == HttpMethods.Put)
{
// Enable buffering so we can read the stream without issues downstream
context.Request.EnableBuffering();
var buffer = new byte[Convert.ToInt32(context.Request.ContentLength)];
await context.Request.Body.ReadAsync(buffer, 0, buffer.Length);
string requestBody = Encoding.UTF8.GetString(buffer);
context.Request.Body.Seek(0, SeekOrigin.Begin); // Reset the stream for next middleware
// Check if the body is empty
if (string.IsNullOrEmpty(requestBody))
{
context.Response.StatusCode = (int)HttpStatusCode.BadRequest;
await context.Response.WriteAsync("Request body cannot be empty.");
return;
}
}
await _next(context);
}
}
+31 -2
View File
@@ -1,7 +1,8 @@
using API.Middlewares;
using Infrastructure; using Infrastructure;
using Infrastructure.Data; using Infrastructure.Data;
using Microsoft.EntityFrameworkCore; using Microsoft.EntityFrameworkCore;
using Microsoft.Extensions.DependencyInjection; using Microsoft.OpenApi.Models;
var builder = WebApplication.CreateBuilder(args); var builder = WebApplication.CreateBuilder(args);
@@ -9,7 +10,31 @@ builder.Services.AddControllers();
builder.Services.AddInfrastructureServices(builder.Configuration); builder.Services.AddInfrastructureServices(builder.Configuration);
builder.Services.AddEndpointsApiExplorer(); builder.Services.AddEndpointsApiExplorer();
builder.Services.AddSwaggerGen(); builder.Services.AddSwaggerGen(c =>
{
c.AddSecurityDefinition("ApiKey", new OpenApiSecurityScheme
{
Description = "ApiKey must appear in header",
Type = SecuritySchemeType.ApiKey,
Name = "ApiKey",
In = ParameterLocation.Header,
Scheme = "ApiKeyScheme"
});
var key = new OpenApiSecurityScheme()
{
Reference = new OpenApiReference
{
Type = ReferenceType.SecurityScheme,
Id = "ApiKey"
},
In = ParameterLocation.Header
};
var requirement = new OpenApiSecurityRequirement
{
{ key, new List<string>() }
};
c.AddSecurityRequirement(requirement);
});
var app = builder.Build(); var app = builder.Build();
@@ -25,6 +50,10 @@ app.UseAuthorization();
app.MapControllers(); app.MapControllers();
// Middlewares
app.UseMiddleware<ApiKeyValidationMiddleware>();
app.UseMiddleware<BodyCheckMiddleware>();
using (var scope = app.Services.CreateScope()) using (var scope = app.Services.CreateScope())
{ {
var services = scope.ServiceProvider; var services = scope.ServiceProvider;
+2 -1
View File
@@ -10,5 +10,6 @@
"MongoDBDatabase": "mongodb+srv://andrei_cerbu:andrei_cerbu@cluster0.v80skg6.mongodb.net/?retryWrites=true&w=majority&appName=Cluster0" "MongoDBDatabase": "mongodb+srv://andrei_cerbu:andrei_cerbu@cluster0.v80skg6.mongodb.net/?retryWrites=true&w=majority&appName=Cluster0"
}, },
"AllowedHosts": "*" "AllowedHosts": "*",
"ApiKey": "testapikey"
} }
+4
View File
@@ -10,4 +10,8 @@
<PackageReference Include="FluentValidation" Version="11.9.0" /> <PackageReference Include="FluentValidation" Version="11.9.0" />
</ItemGroup> </ItemGroup>
<ItemGroup>
<ProjectReference Include="..\Core\Core.csproj" />
</ItemGroup>
</Project> </Project>