扫码领资料
获网安教程
本文由掌控安全学院 - Track 投稿
来Track安全社区投稿~
千元稿费!还有保底奖励~(https://bbs.zkaq.cn)
mitmproxy前端加解密测试基础(windows为例)
环境安装
所需的环境:mitmproxy / yakit /phpstudy / python
1,mitmproxy 下载:https://mitmproxy.org/ (windows)
下载后选择目录安装好,然后直接双击运行mitmweb.exe,运行起mitmproxy:
浏览器挂上mitmproxy代理后(默认启动后是运行在8080端口,web界面是运行在8081端口),然后访问:http://mitm.it/ ,下载mitmproxy证书
下载好证书后,直接双击证书安装证书:
密码直接留空,下一步:
将证书存储在“受信任的根证书颁发机构”,然后直到安装完成即可。
接着运行pip install mitmproxy给python安装mitmproxy模块就可以了。
测试基础
这里直接借用了先知大牛的文章,跟着做一遍复现即可,主要体会其中过程,理解上下游代理是如何运转以及其中的原理。
上下游代理
一般上下游代理是数据传输从服务端到客户端而言,也就是说服务端为 上游,客户端为 下游,而 burp/yakit 则是位于服务端和客户端之间的代理,因此burp的流量走向上,上边就是上游代理,下边,就是下游代理。
上游代理:服务器-> 上游代理 -> burp/yakit -> 客户端
下游代理:服务器 -> burp/yakit -> 下游代理 -> 客户端
我们今天要实现的效果:服务器 -> 上游代理 -> burp/yakit -> 下游代理 -> 客户端
为啥要上 上下游代理 ,因为如果说 服务器和客户端 两端传输的数据都是加密的话,一般客户端这边是JS代码解密,而我们直接使用burp/yakit 抓包的话,看到的都是加密数据,无从下手,因此需要上下游代理,实现传输中的加解密,实现burp/yakit上抓到的数据是解密后的结果,而传输到服务器和客户端又正好是加密后的结果,保证正常“走数据包”的同时又能对数据包进行测试分析。
前后端测试环境搭建
搭建的话,就用phpstudy起一个web网站就行了,这个是最基本的了,在此不赘述。
前后端代码文件:index.html
<!DOCTYPE html>
<htmllang="en">
<head>
<metacharset="UTF-8">
<metaname="viewport"content="width=device-width, initial-scale=1.0">
<title>Base64编码示例</title>
</head>
<body>
<formid="myForm">
<labelfor="userInput">输入文本:</label>
<inputtype="text"id="userInput"name="userInput"required>
<buttontype="button"onclick="encodeAndSend()">提交</button>
</form>
<!-- 添加用于显示服务端返回的数据的元素 -->
<divid="responseDataContainer"></div>
<script>
function encodeAndSend(){
var userInput = document.getElementById("userInput").value;
var encodedData = btoa(userInput);
var jsonData ={
encodedData: encodedData
};
fetch('d.php',{
method:'POST',
headers:{
'Content-Type':'application/json'
},
body: JSON.stringify(jsonData)
})
.then(response => response.text())// 修改部分:使用 response.text() 获取字符串
.then(data =>{
// 修改部分:将服务端返回的字符串显示在页面上
var responseDataContainer = document.getElementById("responseDataContainer");
responseDataContainer.innerHTML ='服务端返回的数据:'+ data;
})
.catch(error =>{
console.error('Error:', error);
});
}
</script>
</body>
</html>
后端代码文件:d.php
<?php
header('Content-Type: application/json');
// 获取 POST 参数
$postData = json_decode(file_get_contents("php://input"),true);
// 检查是否接收到有效数据
if(isset($postData['encodedData'])){
// 获取 Base64 编码的数据
$encodedData = $postData['encodedData'];
// 判断是否以等号("=")结尾,以此判断传过来的数据是否做了base64加密
if(substr($encodedData,-1)==='='){
// 如果以等号结尾,解码并再次进行加密传递给客户端
$decodedData = base64_decode($encodedData);
$decodedData = base64_encode($decodedData);
}else{
// 如果不是 Base64 编码,直接对原始数据进行 Base64 编码
$decodedData = base64_encode($encodedData);
}
// 返回继续加密后的数据
$response = array('reencodedData'=> $decodedData);
echo json_encode($response);
}else{
// 返回错误信息
$errorResponse = array('error'=>'Invalid data received');
echo json_encode($errorResponse);
}
?>
访问后,加密aaadsdsada1 yakit抓包效果
代码简介:输入数据,如果数据不是以 = 结尾,则加密一次base64后,再加密一次base64后返回加密数据,如果以 = 号结尾,则直接返回base64结果(这里应该问题不大,只要找一串加密后带等于号的字符串测试即可)。
上下游代理测试
实际上在调试的时候,感觉容易搞混乱,后面想清楚了,我们要沿着一个思路主线去进行:那就是,将原本yakit上抓的 请求/响应 中的加密数据,最终呈现效果为 请求/响应 中的数据被解密以明文的方式展示出来!
处理请求和响应基本的python代码框架如下:
from mitmproxy import flowfilter,ctx
from mitmproxy.http importHTTPFlow
from mitmproxy import flowfilter
from mitmproxy.http importHTTPFlow
classMimit():
def request(self,flow):
def response(self,flow):
addons =[Mimit(),]
下游代理调试
downstrem.py
from mitmproxy import flowfilter,ctx
from mitmproxy.http importHTTPFlow
from mitmproxy import flowfilter
from mitmproxy.http importHTTPFlow
import base64
import json
classMimit():
def request(self,flow):
if flow.request.host=="192.168.10.32":
req = json.loads(flow.request.get_text())
ctx.log.info("浏览器请求数据 => "+req['encodedData'])
data = base64.b64decode(str(req['encodedData']).encode()).decode()
req['encodedData']= data
ctx.log.info("下游代理解密请求数据 => "+ req['encodedData'])
flow.request.set_text((json.dumps(req)))
def response(self,flow):
if flow.request.host=="192.168.10.32":
rep = json.loads(flow.response.get_text())
ctx.log.info("响应数据 => "+rep['reencodedData'])
data = base64.b64encode(str(rep['reencodedData']).encode()).decode()
rep['reencodedData']= data
ctx.log.info("下游代理加密响应数据 => "+ rep['reencodedData'])
flow.response.set_text(json.dumps(rep))
addons =[Mimit(),]
流量走向:服务器 -> burp/yakit -> 下游代理(mitmproxy - downstream.py) -> 客户端
启动mitmproxy,打开cmd窗口,输入命令:将mitmproxy设置为yakit的上游代理,8083是我yakit的代理端口
mitmdump -p 7070-s downstream.py --mode upstream:http://127.0.0.1:8083 --ssl-insecure
浏览器挂7070端口mitmproxy代理,将流量转发到mitmproxy上面。
此时,因为只设置了下游代理,下游代理会对客户端给到的加密数据进行解密,然后再丢给yakit,因此yakit中抓的包中,请求包中的数据是明文的,然后yakit 将带有明文的请求包丢给服务器,因为这时还没有设置上游代理,因此服务端拿到的数据是:aaadsdsada1
,然后对 aaadsdsada1
进行base64加密,返回结果YWFhZHNkc2FkYTE=
丢给yakit,因此yakit中响应包中的内容是密文YWFhZHNkc2FkYTE=
,yakit再将密文丢给mimtproxy,因为如果按正常逻辑来说,客户端也要接收到的是密文嘛,因此在下游代理脚本里面要写一个加密逻辑,将数据加密后返回,又因为从yakit那里接收到的是经过一次编码的密文,加密逻辑又会对密文再加密base64编码一次,因此客户端最终得到的结果就是 WVdGaFpITmtjMkZrWVRFPQ==。
上游代理调试(burp演示)
下面把yakit换成burp,没用习惯,不知道在哪设置yakit的上游代理… …
upstream.py
from mitmproxy import flowfilter,ctx
from mitmproxy.http importHTTPFlow
from mitmproxy import flowfilter
from mitmproxy.http importHTTPFlow
import base64
import json
classMimit():
def request(self,flow):
if flow.request.host=="192.168.10.32":
req = json.loads(flow.request.get_text())
ctx.log.info("浏览器请求数据 => "+req['encodedData'])
data = base64.b64encode(str(req['encodedData']).encode()).decode()
req['encodedData']= data
ctx.log.info("上游代理加密请求数据 => "+ req['encodedData'])
flow.request.set_text((json.dumps(req)))
def response(self,flow):
if flow.request.host=="192.168.10.32":
rep = json.loads(flow.response.get_text())
ctx.log.info("响应数据 => "+rep['reencodedData'])
data = base64.b64decode(str(rep['reencodedData']).encode()).decode()
rep['reencodedData']= data
ctx.log.info("上游代理解密响应数据 => "+ rep['reencodedData'])
flow.response.set_text(json.dumps(rep))
addons =[Mimit(),]
流量走向:服务器 -> 上游代理(mitmproxy - upstream.py) ->burp/yakit -> 客户端
burp设置上游代理
mitmproxy命令:
mitmdump -p 9091-s upstream.py --ssl-insecure
这个的过程直接看图即可,文字描述就有点多了:
上下游代理联动
流量走向:服务器 -> mitmproxy上游代理(upstream.py) -> burp/yakit -> mitmproxy下游代理(downstream.py) -> 客户端
上游代理:mitmdump -p 9091-s upstream.py --ssl-insecure
下游代理:mitmdump -p 7070-s downstream.py --mode upstream:http://127.0.0.1:8083 --ssl-insecure
图解如下:
上下游代理debug
上游脚本
import sys
import os
from mitmproxy.tools.main import mitmdump
sys.path.append(os.path.dirname(os.path.abspath(__file__)))
print(os.path.dirname(os.path.abspath(__file__)))
# 使用 mitmdump 启动并指定端口
mitmdump(['-s','enc.py','-p', str(9091)])
下游脚本
import sys
import os
from mitmproxy.tools.main import mitmdump
sys.path.append(os.path.dirname(os.path.abspath(__file__)))
print(os.path.dirname(os.path.abspath(__file__)))
# 启动 mitmdump
mitmdump(['-s','dec.py','-p', str(7071),'--mode',"upstream:http://127.0.0.1:8080"])
这里就不作演示了,用到的时候调试即可。
参考资料
https://xz.aliyun.com/news/12664
https://docs.mitmproxy.org/stable/#features
https://learn.microsoft.com/en-us/windows/wsl/install(可安装可不安装,只是改善界面显示用的)
申明:本公众号所分享内容仅用于网络安全技术讨论,切勿用于违法途径,
所有渗透都需获取授权,违者后果自行承担,与本号及作者无关,请谨记守法.
原文始发于微信公众号(掌控安全EDU):mitmproxy前端加解密测试
- 左青龙
- 微信扫一扫
-
- 右白虎
- 微信扫一扫
-
评论