spring secuirty简单项目创建及基于wireshark抓包的浏览器端和服务器端之间的通讯交互的分析
1.环境
Spring tool suite :Version: 4.1.2.RELEASE 集成开发工具
Maven:3.5.4 依赖管理工具
Springboot:2.1.4.RELEASE
Wireshark:Version 2.4.5 通信协议抓包分析工具
HTTP Request Editor: V1.0 HTTP请求模拟工具
Google Chrome: 74.0.3729.169(正式版本) (32 位) google浏览器
Microsoft Edge :44.18362.329.0 微软浏览器
2.创建一个简单的spring security项目
2.1.向导创建工程
备注:这步骤请选择2.1.4,否则可能pom.xml会出现第一行报错。
点击后状态栏会显示下载模板,生成项目骨架的进度
查看pom.xml,看到自动引入了以下依赖:
其中secuirty相关的2个依赖是:
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-security</artifactId>
</dependency>
<dependency>
<groupId>org.springframework.security</groupId>
<artifactId>spring-security-test</artifactId>
<scope>test</scope>
</dependency>
2.2创建简单的控制器方法
@RestController
@SpringBootApplication
public class Springsecuritytest001Application {
@GetMapping("/")
public String hello(){
return "hello, spring security";
}
public static void main(String[] args) {
SpringApplication.run(Springsecuritytest001Application.class, args);
}
}
在自动创建的Springsecuritytest001Application类中添加rest api
@GetMapping("/")
public String hello(){
return "hello, spring security";
}
并在类级别添加注释
@RestController
2.3.测试运行
控制台将生成http的默认用户(user)的密码
使用浏览器访问 127.0.0.1:8080,将会跳到登录页面,
使用用户名user,及前面控制台打印的随机密码进行填写,并点击登录
2.4通过配置文件配置HTTP认证用户名和密码
application.properties文件添加
spring.security.user.name=test
spring.security.user.password=123456
再次运行,此时控制台不再生成随机密码。
浏览器访问:
3 wireshark抓包分析
可以看到,有4个回合的请求和应答
3.1.回合1 客户端请求、服务端重定向登录
客户端请求(http://127.0.0.1:8080):
GET / HTTP/1.1
Host: 127.0.0.1:8080
Connection: keep-alive
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3
Accept-Encoding: gzip, deflate, br
Accept-Language: zh-CN,zh;q=0.9,en;q=0.8
服务端应答重定向指示(http://127.0.0.1:8080/login,设置JSESSIONID请求头字段):
HTTP/1.1 302
Set-Cookie: JSESSIONID=D87025D753F0BF55732C58988D54F6D5; Path=/; HttpOnly
X-Content-Type-Options: nosniff
X-XSS-Protection: 1; mode=block
Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Pragma: no-cache
Expires: 0
X-Frame-Options: DENY
Location: http://127.0.0.1:8080/login
Content-Length: 0
Date: Mon, 23 Sep 2019 03:31:48 GMT
3.2.回合2客户端重定向请求、服务端应答登录页面
客户端请求(http://127.0.0.1:8080/login):
GET /login HTTP/1.1
Host: 127.0.0.1:8080
Connection: keep-alive
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3
Accept-Encoding: gzip, deflate, br
Accept-Language: zh-CN,zh;q=0.9,en;q=0.8
Cookie: JSESSIONID=D87025D753F0BF55732C58988D54F6D5
服务端应答(认证表单填写页面):
HTTP/1.1 200
X-Content-Type-Options: nosniff
X-XSS-Protection: 1; mode=block
Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Pragma: no-cache
Expires: 0
X-Frame-Options: DENY
Content-Type: text/html;charset=UTF-8
Content-Length: 1406
Date: Mon, 23 Sep 2019 03:31:48 GMT
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="utf-8">
<meta name="viewport" content="width=device-width, initial-scale=1, shrink-to-fit=no">
<meta name="description" content="">
<meta name="author" content="">
<title>Please sign in</title>
<link href="https://maxcdn.bootstrapcdn.com/bootstrap/4.0.0-beta/css/bootstrap.min.css" rel="stylesheet" integrity="sha384-/Y6pD6FV/Vv2HJnA6t+vslU6fwYXjCFtcEpHbNJ0lyAFsXTsjBbfaDjzALeQsN6M" crossorigin="anonymous">
<link href="https://getbootstrap.com/docs/4.0/examples/signin/signin.css" rel="stylesheet" crossorigin="anonymous"/>
</head>
<body>
<div class="container">
<form class="form-signin" method="post" action="/login">
<h2 class="form-signin-heading">Please sign in</h2>
<p>
<label for="username" class="sr-only">Username</label>
<input type="text" id="username" name="username" class="form-control" placeholder="Username" required autofocus>
</p>
<p>
<label for="password" class="sr-only">Password</label>
<input type="password" id="password" name="password" class="form-control" placeholder="Password" required>
</p>
<input name="_csrf" type="hidden" value="2a565ff3-f23f-441c-835c-668603d2e806" />
<button class="btn btn-lg btn-primary btn-block" type="submit">Sign in</button>
</form>
</div>
</body></html>
3.3 回合3客户端客户端填写登录、服务端认证
当我们填入用户名和密码后,点击登录按钮后
客户端请求(访问:http://127.0.0.1:8080/login,请求参数中携带填入的用户名、密码字段,以及客户端生成的_csrf随机字符串)
POST /login HTTP/1.1
Host: 127.0.0.1:8080
Connection: keep-alive
Content-Length: 72
Cache-Control: max-age=0
Origin: http://127.0.0.1:8080
Upgrade-Insecure-Requests: 1
Content-Type: application/x-www-form-urlencoded
User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3
Referer: http://127.0.0.1:8080/login
Accept-Encoding: gzip, deflate, br
Accept-Language: zh-CN,zh;q=0.9,en;q=0.8
Cookie: JSESSIONID=D87025D753F0BF55732C58988D54F6D5
username=test&password=123456&_csrf=2a565ff3-f23f-441c-835c-668603d2e806
服务器应答(继续重定向到http://127.0.0.1:8080/,并更新请求头JSESSIONID字段):
HTTP/1.1 302
Set-Cookie: JSESSIONID=D11354A13F7D0706F85900B7017F42B4; Path=/; HttpOnly
X-Content-Type-Options: nosniff
X-XSS-Protection: 1; mode=block
Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Pragma: no-cache
Expires: 0
X-Frame-Options: DENY
Location: http://127.0.0.1:8080/
Content-Length: 0
Date: Mon, 23 Sep 2019 03:32:05 GMT
3.4.回合4客户端重定向请求(cookie携带已认证信息)、服务端应答内容
客户端请求( 127.0.0.1:8080,携带Cookie: JSESSIONID)
GET / HTTP/1.1
Host: 127.0.0.1:8080
Connection: keep-alive
Cache-Control: max-age=0
Upgrade-Insecure-Requests: 1
User-Agent: Mozilla/5.0 (Windows NT 10.0; WOW64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/74.0.3729.169 Safari/537.36
Accept: text/html,application/xhtml+xml,application/xml;q=0.9,image/webp,image/apng,*/*;q=0.8,application/signed-exchange;v=b3
Referer: http://127.0.0.1:8080/login
Accept-Encoding: gzip, deflate, br
Accept-Language: zh-CN,zh;q=0.9,en;q=0.8
Cookie: JSESSIONID=D11354A13F7D0706F85900B7017F42B4
服务器应答(127.0.0.1:8080的内容):
HTTP/1.1 200
X-Content-Type-Options: nosniff
X-XSS-Protection: 1; mode=block
Cache-Control: no-cache, no-store, max-age=0, must-revalidate
Pragma: no-cache
Expires: 0
X-Frame-Options: DENY
Content-Type: text/html;charset=UTF-8
Content-Length: 22
Date: Mon, 23 Sep 2019 03:32:05 GMT
hello, spring security
4 后记
1、这里提供了一种通过通讯交互视角来学习理解一些框架功能的逻辑行为,不得不说wireshark真的是一个通讯分析利器。
2、spring security5与之前版本有些调整。 在看一些书过程中,可能书中使用的是5.0之前的用法,在使用高版本时可能会报各种异常,需要针对性做一些调整。