Лучшее место для проверки аутентификации и авторизации в ActionFilter, вы можете проверить политику аутентификации на стороне базы данных, а также с помощью JWT.
Если вы хотите авторизовать свой контроллер, вы должны использовать промежуточное программное обеспечение ( ActionFilterAttribute ), которое будет обнаруживать http-запрос пользователя и проверять его путем декодирования токена пользователя.Вы можете отфильтровать все методы http (GET, POST, PUT, DELETE ... и т. д.) и реализовать собственную логику авторизации для конкретного метода http.
AuthorizationRequiredAttribute.cs
Примечание: здесь все коды не имеют отношения к вашей проблеме.но надеюсь, вы поймете, как на самом деле я фильтрую запрос на получение / публикацию с условием.
[AttributeUsage(AttributeTargets.Method | AttributeTargets.Class)]
public class AuthorizationRequiredAttribute : ActionFilterAttribute
{
private readonly IAccessTokenServices _accessTokenServices;
private readonly IPermissionServices _permissionServices;
private readonly IAuditLogServices _auditLogServices;
private IConfiguration _config;
public AuthorizationRequiredAttribute(IAccessTokenServices accessTokenServices, IPermissionServices permissionServices,
IAuditLogServices auditLogServices,IConfiguration config)
{
_accessTokenServices = accessTokenServices;
_config = config;
_permissionServices = permissionServices;
_auditLogServices = auditLogServices;
}
public override void OnActionExecuting(ActionExecutingContext context)
{
try
{
if (context.HttpContext.Request.Headers.ContainsKey(Constants.HttpHeaders.Token))
{
var handler = new JwtSecurityTokenHandler();
var token = handler.ReadToken(context.HttpContext.Request.Headers[Constants.HttpHeaders.Token])
as JwtSecurityToken;
var expireDate = Convert.ToDateTime(token.Claims.First(claim => claim.Type == Constants.JwtClaims.ExpiresOn).Value);
if (context.HttpContext.Request.Method == WebRequestMethods.Http.Get)
{
if (expireDate < DateTime.Now)
{
context.Result = new UnauthorizedResult();
}
}
else
{
var accessToken = _accessTokenServices
.Details(x => x.Token == context.HttpContext.Request.Headers[Constants.HttpHeaders.Token]);
if (accessToken != null)
{
if (accessToken.ExpiresOn < DateTime.Now)
{
_accessTokenServices.Delete(accessToken);
context.Result = new UnauthorizedResult();
}
else
{
var userId = Convert.ToInt32(token.Claims.First(claim => claim.Type == Constants.JwtClaims.UserId).Value);
var userTypeId = Convert.ToInt32(token.Claims.First(claim => claim.Type == Constants.JwtClaims.UserTypeId).Value);
if (accessToken == null)
{
context.Result = new UnauthorizedResult();
}
else if (!_permissionServices.IsPermissionExist(context.HttpContext.Request.Path.ToString(), userTypeId))
{
context.Result = new StatusCodeResult((int)HttpStatusCode.NotAcceptable);
}
else
{
_auditLogServices.Save(context.HttpContext.Request.Path.ToString(), userId);
accessToken.ExpiresOn = DateTime.Now.AddMinutes(Convert.ToInt16(_config["Jwt:ExpiresOn"]));
_accessTokenServices.UpdateExpireTime(accessToken);
}
}
}
else
{
context.Result = new UnauthorizedResult();
}
}
}
else
{
context.Result = new NotFoundResult();
}
}
catch (Exception ex)
{
context.Result = new BadRequestResult();
}
base.OnActionExecuting(context);
}
}
}
HomeController.cs
Теперь вы можете использовать AuthorizationRequiredAttribute в качестве службы фильтрации API / контроллера.я изменил ваш контроллер и вижу метод сообщения
using System;
using System.Collections.Generic;
using System.Linq;
using System.Threading.Tasks;
using Microsoft.AspNetCore.Mvc;
namespace Chat.Controllers
{
[Route("api/home")]
public class HomeController : Controller
{
public IActionResult Index()
{
return View();
}
[HttpGet("message"), ServiceFilter(typeof(AuthorizationRequiredAttribute))]
public IActionResult Message()
{
return Ok("Hello World!");
}
}
}