newbee mall搭建&&审计
搭建:
我用的是IDEA
下载源码
链接如下:https://github.com/newbee-ltd/newbee-mall
直接在github下载即可
在phpstudy打开web环境,新建数据库,如下:(数据库名称一定要是newbee_mall_db)

然后导入sql文件(源码包里面就有)
记得先修改这个配置文件
(修改数据库名和用户名)
然后导入即可
1
\newbee-mall-master\src\main\resources\newbee_mall_schema.sql在Navicat Premium 17连接数据库

弹出即说明成功启动

直接输入
审计:
初审
先看pom.xml配置文件以及README.md
README.md中存在MyBatis,可能存在sql注入

通过搜索发现存在拦截器interceptor,可能存在越权漏洞

controller目录中也可能存在越权漏洞,下面具体审计可以跟着看一下
水平越权漏洞
- 或者在篡改相关参数(请求参数 / 表单字段 / JSON 字段)
- 要么就是修改之中存在注入点,需要替换用户
- 在url使用参数切换用户或者管理员id未校验,尝试替换 ID(+1、-1、随机大/小 ID、其它已知用户的 ID)
- 文件/图片等直接用可访问 URL,访问其它用户的文件路径或修改 URL(没有权限校验或短期 token)
- token 换取其他用户的数据
- 直接访问管理/内部接口,扫列出隐藏路由、尝试访问
/admin、/internal、/debug
sql
接上面说的,存在MyBatis,直接检索${,主要是查看${} 拼接 SQL 语句


都找不到和sql相关的东西
说明可能使用
#代替$实现sql的预编译,防止了sql注入(可能是版本问题,这个漏洞修复了emmm)查找
#{
进去分析一下
使用了直接拼接的方式向数据库进行查询(但是预编译即已修复)
所以可以查看NewBeeMallGoodsMapper.java (逆向追踪)

找到传参定义,跟近函数
跟进到getTotalNewBeeMallGoods
C:\Users\95227\Desktop\newbee-mall-master\src\main\java\ltd\newbee\mall\service\impl\NewBeeMallGoodsServiceImpl.java
1
2
3
4
5
6
7@Override public PageResult getNewBeeMallGoodsPage(PageQueryUtil pageUtil) { List<NewBeeMallGoods> goodsList = goodsMapper.findNewBeeMallGoodsList(pageUtil); int total = goodsMapper.getTotalNewBeeMallGoods(pageUtil); PageResult pageResult = new PageResult(goodsList, total, pageUtil.getLimit(), pageUtil.getPage()); return pageResult; }查看谁调用了getNewBeeMallGoodsPage 方法
跟进到NewBeeMallGoodsController
C:\Users\95227\Desktop\newbee-mall-master\src\main\java\ltd\newbee\mall\controller\admin\NewBeeMallGoodsController.java
1
2
3
4
5
6
7
8
9@RequestMapping(value = "/goods/list", method = RequestMethod.GET) @ResponseBody public Result list(@RequestParam Map<String, Object> params) { if (ObjectUtils.isEmpty(params.get("page")) || ObjectUtils.isEmpty(params.get("limit"))) { return ResultGenerator.genFailResult("参数异常!"); } PageQueryUtil pageUtil = new PageQueryUtil(params); return ResultGenerator.genSuccessResult(newBeeMallGoodsService.getNewBeeMallGoodsPage(pageUtil)); }传入了 pageUtil 参数,而该参数同样通过 PageQueryUtil 类创建一个 pageUtil 对象,传入 params 作为参数,以及 params 同样是个 Map 对象。未对其进行过滤处理
针对版本低的源码(未修复的)
直接抓包,报错注入,sqlmap跑就行了(我的漏洞已经“预编译”修复,所以我就不演示了哈)
后台权限绕过
说到后台,肯定先看admin相关文件啊,所以可以找找登录后台的文件(AdminLogin)
进入src/main/java/ltd/newbee/mall/interceptor/AdminLoginInterceptor.java

第一步:
1
String requestServletPath = request.getServletPath();使用getServletPath传入url: getRequestURI 方法返回的路径是未经过服务器端处理的原始路径,可能包含特殊字符或路径跳转,从而绕过服务器端的安全控制
第二步:
1
if (requestServletPath.startsWith("/admin") && null == request.getSession().getAttribute("loginUser")) {先判断 Uri 路径中是否以 /admin 开头,然后以及获取并判断Session 中的 loginUser 属性是否为 null
两个条件 && 在一起结果为 True 的话进入条件代码
payload:
登陆后台寻找一个后台接口(账号密码是弱密码,考考大家吧🤭)

删除cookic之后,查看回显

明显报错了
绕过

XSS漏洞(1,2)
分析
啥也不知道,先在前端进行测试(找那种可以保留的对话框,类似于评论/弹幕的那种)

搜索xss的代码没有弹窗(我觉得应该是因为存在双引号,将代码包起来了)
去源码中找找原因(源代码好找,看现在的url,在源代码文件夹寻找相关的代码就行)
(不明确的话,存在keyword传参,所以直接在项目文件里面搜索keyword即可)
存在转义

thymeleaf模版在对th:text标签进行渲染的时候,默认对特殊字符进行了转义
接着进入search.html
src\main\resources\templates\mall\search.html
找thymeleaf未作转义的输出,th:utext不会将字符转义
第一个,存在th:utext,所以这两个功能点存在XSS。
第二个,detail.html因为显示的是商品信息,商品信息使用富文本编辑器,不能简单的转义处理,需要考虑正常的html标签传输,所以作者在这里使用th:utext来显示商品详细。
xss(1):
进入商品信息,添加xss的payload

然后(提交即可弹窗)
xss(2):
进入订单管理,然后添加payload

提交即可弹窗

垂直越权
上面提到过,存在interceptor拦截器(可以寻找相关函数)

步入看一下

对url路径设置了不同的interceptor
addPathPatterns表示其中的路径会经过设置的拦截器,excludePathPatterns不过该拦截器
其中两个星**表示匹配任意字符。如果出现一个星*则表示匹配单个路径找到拦截器,下面就要看登录页面,所以可以跟进一下NewBeeMallLoginInterceptor

用 getServletPath() 来获取最后真正分发到路由地方的 path,getRequestURI() 只是获取了请求的 URl
这个意义不大
所以找一下下一个类AdminLoginInterceptor
AdminLoginInterceptor,就是第二步骤里面的类名

使用了 getRequestURI() 来获取URI来判断URI是否以 /admin 开头,如果是 /admin 开头则校验 session,不是则不用校验(其实这个和上面那个后台权限绕过的类似,都定位到这里了)
payload
进入dashboard模块
输入//admin 或 /index/..;/admin也可以成功访问到页面

成功绕过了目录访问字符限制
水平越权漏洞(1,2)
上面的分析已经提前说过了
可以看一下Controller的相关文件,直接看controller目录也行,可能存在水平越权漏洞
1
在文件里面全局搜索Controller

寻找到目标文件(初审里面总结一小部分注入点)

接着看 updateUserInfo() 的实现
src\main\java\ltd\newbee\mall\service\impl\NewBeeMallUserServiceImpl.java
发现这里从数据库查找用户并未用到 session ,而是直接以传递过来的 userId 为参数来查找并修改数据的,所以这里存在水平越权漏洞,修改 userId 便可修改其他用户的信息。
payload
注册一个用户,然后查看个人信息


使用burp抓包,修改用户 userId


ok,回显成功
2
还是根据上面的流程进入OrderController(查询订单)

跟进getOrderDetailByOrderNo() 函数
src\main\java\ltd\newbee\mall\service\impl\NewBeeMallOrderServiceImpl.java
还是id问题,输入其他id,可以查看其他人的cookic,没有绕过限制
payload
跟上面一样抓包+改数据即可
我就不演示了🤭,我相信各位大佬可以
Csrf漏洞
添加购物车功能,抓包,查看请求内容,没有任何token值来进行校验

由于是json格式的请求,不能直接使用burp Generate CSRF PoC,因为burp生成的PoC无法伪造Content-Type。burp生成的CSRF PoC请求内容如下,可以看到Content-Type: text/plain,并且post数据多出一个等号
直接在bp的插件里面生成csrf的代码就行
是一个html
payload
对上面生成csrf的poc进行抓包

然后成功写入xss的payload

查看页面,成功添加

逻辑漏洞
下订单但未支付时,访问/orders/{orderNo}/finish可直接完成交易
直接看代码

从代码中发现直接调用newBeeMallOrderService.finishOrder(orderNo, user.getUserId()),对于该订单是否支付,是否出库等过程都没有校验
put方式去请求即可(左边标黄的就是 putmapping)

payload
添加一件物品到购物车,然后提交订单

点击去支付,一系列流程下来可以购买商品
管理员查看显示 待支付

我们使用put方式去请求

查看回显成功支付商品