简体   繁体   English

Web.Api上的基本令牌认证和授权

[英]Basic Token authentification and authorization on Web.Api

So I have an MVC Application that calls WebApi method. 因此,我有一个调用WebApi方法的MVC应用程序。

My Authorization on MVC App is done like this 我在MVC App上的授权是这样完成的

  public class CustomAuthorizeAttribute : AuthorizeAttribute {

        private RolesEnum _role;

        public CustomAuthorizeAttribute() {
            _role = RolesEnum.User;
        }

        public CustomAuthorizeAttribute(RolesEnum role) {
            _role = role;
        }

        protected override bool AuthorizeCore(HttpContextBase httpContext) {

            User currentUser = (User)httpContext.Session["CurrentUser"];

            if (currentUser == null) {
                return false;
            }

            if (currentUser.Role == RolesEnum.User && _role == RolesEnum.Admin) {
                return false;
            }

            return true;
        }

The authentification is done calling a WebApi method 调用WebApi方法完成身份验证

[HttpPost]
    public ActionResult Login(string username, string password)
    {

        User acc = new User();
        acc.Username = username;
        acc.Password = password;
        acc = accBL.Login(acc);

        if (acc != null) {
            Session.Add("CurrentUser", acc);
            return  RedirectToAction("Index", "Project", null);
        } else {
            return View();
        }


    }

Login method looks like this 登录方法如下所示

  public User LogIn(User acc) {
            try {
                HttpClient client = new HttpClient();
                client.BaseAddress = new Uri(BASE_URL);
                client.DefaultRequestHeaders.Accept.Add(
                   new MediaTypeWithQualityHeaderValue("application/json"));
                HttpResponseMessage response = client.PostAsJsonAsync("api/Account/Login", acc).Result;

                if (response.IsSuccessStatusCode) {
                    return response.Content.ReadAsAsync<User>().Result;
                } else {
                    return null;
                }

            } catch {
                return null;
            }
        }

And WebApi method looks like this WebApi方法看起来像这样

 [Route("api/Account/Login")]
        [HttpPost]
        public IHttpActionResult Login(User userModel) {
            User user = db.Users.Where(p => p.Username == userModel.Username && p.Password == userModel.Password).FirstOrDefault();

            if (user != null) {
                return Ok(user);
            } else {
                throw new HttpResponseException(HttpStatusCode.Unauthorized);
            }

        }

How can I make a connection between the MVC App and the WebApi Services. 如何在MVC应用程序和WebApi服务之间建立连接。 My authorization and authentification works on MVC part, but my WebApi Services can be called without this any authorization/authenification. 我的授权和身份验证在MVC上起作用,但是无需任何授权/身份验证就可以调用我的WebApi Services。 How can I secure my WebApi too based on my example? 我也可以基于示例如何保护WebApi? I've been working for about 3 weeks with MVC and WebApi and many things are not very clear too me. 我已经在MVC和WebApi上工作了大约3周,但我对很多事情也不太清楚。

Should I just create a GUID in public IHttpActionResult Login(User userModel) and check for it everytime ia method is called? 我应该只在公共IHttpActionResult Login(User userModel)中创建一个GUID并在每次调用ia方法时检查它吗? How do i pass this GUID to MVC App and from MVC to WebApi? 我如何将此GUID传递给MVC App以及从MVC传递给WebApi?

What you can do is create some sort of a token (eg. JWT) in the WebAPI Login() method and return with the Ok() response (to the MVC app). 您可以做的是在WebAPI Login()方法中创建某种令牌(例如JWT),然后返回Ok()响应(返回到MVC应用)。 Users calling your API endpoints have to send this token back (eg. in a custom "Token" header). 调用您的API端点的用户必须将此令牌发回(例如,在自定义“令牌”标头中)。 You can validate the token inside a custom WebAPI authorize attribute that you use in your API endpoints. 您可以在API端点中使用的自定义WebAPI授权属性中验证令牌。

eg. 例如。

Login endpoint 登录端点

[Route("api/Account/Login")]
[HttpPost]
public object Login(User userModel) {
    User user = ...;
    string token = CreateTokenForUser(user);

    if (user != null) {
        // return user and token back 
        return new {User = user, Token = token};
    } else {
        throw new HttpResponseException(HttpStatusCode.Unauthorized);
    }
}

Custom authentication filter 自定义身份验证过滤器

public class UserAuthAttribute : ActionFilterAttribute, IAuthenticationFilter
{

    public async Task AuthenticateAsync(HttpAuthenticationContext context, CancellationToken cancellationToken)
    {
        string token = null;
        IEnumerable<string> tokenHeader;
        if (context.Request.Headers.TryGetValues("Token", out tokenHeader))
            token = tokenHeader.FirstOrDefault();

        if (token != null && IsTokenValid(token)
        {
            // user has been authenticated i.e. send us a token we sent back earlier
        }
        else 
        {
            // set ErrorResult - this will result in sending a 401 Unauthorized
            context.ErrorResult = new AuthenticationFailureResult(Invalid token", context.Request);
        }
    }

}

Other endpoint which only authenticated users should be allowed access 仅允许经过身份验证的用户访问的其他端点

[Route("api/Values")]
[HttpGet]
[UserAuth]
public object GetValues() {

    // only requests with a valid token will be able to call this because of the [UserAuth] attribute
}

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM