目录
1 大概思路... 1
2 Nginx集群之基于Redis的WebApi身份验证... 1
3 Redis数据库... 2
4 Visualbox虚拟机ubuntu下的redis部署... 3
5 编写.NET WebApi的OnAuthorization身份验证... 6
6 编写.NET WebApi的ActionFilterAttribute令牌验证... 8
7 编写.NET WebApi的服务端... 10
8 编写.NET WebApi的客户端... 11
9 部署WebApi到本机... 17
10 Nginx集群配置搭建... 18
11 运行结果... 19
12 总结... 20
1 大概思路
l Nginx集群之基于Redis的WebApi身份验证
l Redis数据库
l Visualbox虚拟机ubuntu下的redis部署
l 编写.NET WebApi的OnAuthorization身份验证
l 编写.NET WebApi的ActionFilterAttribute令牌验证
l 编写.NET WebApi的服务端
l 编写.NET WebApi的客户端
l 部署WebApi到本机
l Nginx集群配置搭建
l 运行结果
l 总结
2 Nginx集群之基于Redis的WebApi身份验证
Nginx在集群上使用Redis数据库进行身份验证,达到了支持集群、分布式。在此基础上能够实现单点登录、时效性的访问,结合WebApi最大限度地发挥了后台身份验证的管理。
基于Redis的原因有几个:第一点是Redis是基于内存的数据库访问起来比较快,能够设置数据库存储的时效性;第二点,Redis数据库的语法比较简单、轻巧,在Linux、Windows服务器均可以一键安装完成;第三点,Redis支持数据的备份,即master-slave模式的数据备份。
以下是本文讲述的主要结构图:
客户端输入用户名密码服务器,通过了用户名密码验证,其中一台WebApi服务器生成一个Token并返回https的响应。客户端收到Token保存在本地,带上token发出ajax请求、WebRequest请求,经过Action过滤器的检验,访问Action并返回数据。
Token令牌身份验证机制:
Nginx集群之基于Redis的WebApi身份验证,如下图所示:
3 Redis数据库
Redis是一个开源的使用ANSI C语言编写、支持网络、可基于内存亦可持久化的日志型、Key-Value数据库,并提供多种语言的API。它通常被称为数据结构服务器,因为值(value)可以是 字符串(String), 哈希(Map), 列表(list), 集合(sets) 和 有序集合(sorted sets)等类型。
具体可以在以下网址进行学习:
http://www.runoob.com/redis/redis-tutorial.html
4 Visualbox虚拟机ubuntu下的redis部署
(已安装Oracle VM VirtualBox、ubuntu-17.10-desktop-amd64.iso)
Redis安装可参考:http://www.runoob.com/redis/redis-install.html
- 虚拟机
因网络的限制,本文采取的是“网络地址转换(NAT)”方式,进行redis数据库连接访问。有条件的可以采用“桥接网上”的方式,便可以使多台PC机在同一redis数据库进行访问,达到集群的效果。
Linux的ubuntu打开6379端口:
sudo iptables -I INPUT -p tcp --dport 6379 -j ACCEPT
具体如下所示:
登录Redis服务器,设置密码:
redis-cli
config set requirepass 123456
- 主机
Windows安装Telnet客户端,进行测试连接成功与否
运行CMD,输入命令行如下:
Microsoft Windows [版本 6.1.7601] 版权所有 (c) 2009 Microsoft Corporation。保留所有权利。 C:\Users\zhyongfeng>telnet 10.93.85.66 6379
测试成功
5 编写.NET WebApi的OnAuthorization身份验证
CustomAuthorizeAttribute.cs
using System.Web.Http; using System.Web.Http.Controllers; namespace SSLWebApi.Controllers { public class CustomAuthorizeAttribute : AuthorizeAttribute { public override void OnAuthorization(HttpActionContext actionContext) { //判断用户是否登录 if (actionContext.Request.Headers.Authorization != null) { string userInfo = System.Text.Encoding.Default.GetString(System.Convert.FromBase64String(actionContext.Request.Headers.Authorization.Parameter)); //用户验证逻辑 if (string.Equals(userInfo, string.Format("{0}:{1}", "zhyongfeng", "123456"))) { IsAuthorized(actionContext); } else { HandleUnauthorizedRequest(actionContext); } } else { HandleUnauthorizedRequest(actionContext); } } protected override void HandleUnauthorizedRequest(System.Web.Http.Controllers.HttpActionContext actionContext) { var challengeMessage = new System.Net.Http.HttpResponseMessage(System.Net.HttpStatusCode.Unauthorized); challengeMessage.Headers.Add("WWW-Authenticate", "Basic"); throw new System.Web.Http.HttpResponseException(challengeMessage); } } }
生成Token
BaseController.cs