//只有登录的用户可以访问
1.统一返回格式
namespace webapi;/// <summary>
/// 统一数据响应格式
/// </summary>
public class Results<T>
{/// <summary>/// 自定义的响应码,可以和http响应码一致,也可以不一致/// </summary>public int Code { get; set; }/// <summary>/// 中文消息提示/// </summary>public string? Msg { get; set; }/// <summary>/// 是否成功/// </summary>public bool Success { get; set; }/// <summary>/// 响应的数据/// </summary>public T? Data { get; set; }/// <summary>/// 返回的Token: 如果有值,则前端需要此这个值替旧的token值/// </summary>public string? Token { get; set; }/// <summary>/// 设置数据的结果/// </summary>/// <param name="data">数据</param>/// <returns></returns>public static Results<T> DataResult(T data){return new Results<T> { Code = 1, Data = data, Msg = "请求成功", Success = true };}/// <summary>/// 响应成功的结果/// </summary>/// <param name="msg"></param>/// <returns></returns>public static Results<T> SuccessResult(string msg = "操作成功"){return new Results<T> { Code = 1, Data = default, Msg = msg, Success = true };}/// <summary>/// 响应失败的结果/// </summary>/// <param name="msg"></param>/// <returns></returns>public static Results<T> FailResult(string msg = "请求失败"){return new Results<T> { Code = -1, Data = default, Msg = msg, Success = false };}/// <summary>/// 参数有误/// </summary>/// <param name="msg"></param>/// <returns></returns>public static Results<T> InValidParameter(string msg = "参数有误"){return new Results<T> { Code = -1, Data = default, Msg = msg, Success = false };}/// <summary>/// 获取结果/// </summary>/// <param name="code"></param>/// <param name="msg"></param>/// <param name="data"></param>/// <param name="success"></param>/// <returns></returns>public static Results<T> GetResult(int code = 0, string? msg = null, T? data = default, bool success = true){return new Results<T> { Code = code, Data = data, Msg = msg, Success = success };}/// <summary>/// 设置token结果/// </summary>/// <param name="token"></param>/// <returns></returns>public static Results<T> TokenResult(string token){return new Results<T> { Code = 1, Data = default, Msg = "请求成功", Success = true, Token = token };}
}
2.自定义授权过滤器
using Microsoft.AspNetCore.Authorization;
using Microsoft.AspNetCore.Mvc;
usinsg Microsoft.AspNetCore.Mvc.Authorization;
using Microsoft.AspNetCore.Mvc.Filters;namespace webapi
{/// <summary>/// 授权过滤器/// </summary>[AttributeUsage(AttributeTargets.Class | AttributeTargets.Method, AllowMultiple = true, Inherited = true)]public class CustomAuthorizeAttribute : Attribute, IAuthorizationFilter, IAuthorizeData{public CustomAuthorizeAttribute(){}/// <summary>/// 策略名称/// </summary>public string? Policy { get; set; }/// <summary>/// 可支持角色/// </summary>public string? Roles { get; set; }/// <summary>/// 以逗号分隔的方案列表,从中构造用户信息/// </summary>public string? AuthenticationSchemes { get; set; }//public CustomAuthorizeAttribute(string policy) => this.Policy = policy;/// <summary>/// 授权时执行此方法/// </summary>public void OnAuthorization(AuthorizationFilterContext context){// 需要排除具有AllowAnymons 这个标签的控制器// 过滤掉带有AllowAnonymousFilterif (HasAllowAnonymous(context)){return;}// 如果用户没有登录,则给出一个友好的提示(而不是返回401给前端)if (!context.HttpContext.User.Identity.IsAuthenticated) // 判断是否登录{context.Result = new JsonResult(Results<string>.FailResult("Token无效"));}}// 判断是否含有IAllowAnonymousprivate bool HasAllowAnonymous(AuthorizationFilterContext context){if (context.Filters.Any(filter => filter is IAllowAnonymousFilter)){return true;}// 终节点:里面包含了路由方法的所有元素信息(特性等信息)var endpoint = context.HttpContext.GetEndpoint();return endpoint?.Metadata.GetMetadata<IAllowAnonymous>() != null;}}
}
在需要授权的方法上使用TypeFilter特性表示要使用授权过滤器,也可以是用 [ServiceFilter(typeof(CustomAuthorizeAttribute))]
serviceFilter要输入服务
builder.Services.AddScoped<CustomAuthorizeAttribute>();
TypeFilter和serviceFilter都是局部注入,控制范围只能在某个控制器和方法,如果想要全局注入就要注入到控制器里
builder.Services.AddControllers(opt =>{opt.Filters.Add<CustomAuthorizeAttribute>();});
不需要授权的接口可以使用
[AllowAnonymous]
[TypeFilter(typeof(CustomAuthorizeAttribute))][HttpGet(Name = "GetWeatherForecast")]public IEnumerable<WeatherForecast> Get(){return Enumerable.Range(1, 5).Select(index => new WeatherForecast{Date = DateTime.Now.AddDays(index),// Date = Convert.ToDateTime("2023-12-10 "),TemperatureC = Random.Shared.Next(-20, 55),Summary = Summaries[Random.Shared.Next(Summaries.Length)]}).ToArray();}