Skip to content
Projects
Groups
Snippets
Help
Loading...
Help
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
I
ioc_sixiang_license
Project
Project
Details
Activity
Releases
Cycle Analytics
Repository
Repository
Files
Commits
Branches
Tags
Contributors
Graph
Compare
Charts
Issues
0
Issues
0
List
Board
Labels
Milestones
Merge Requests
0
Merge Requests
0
CI / CD
CI / CD
Pipelines
Jobs
Schedules
Charts
Wiki
Wiki
Snippets
Snippets
Members
Members
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
zengtianlai3
ioc_sixiang_license
Commits
869793d3
Commit
869793d3
authored
Jul 16, 2022
by
zengtianlai3
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
测试存储型XSS是否解决
parent
905a535b
Changes
6
Hide whitespace changes
Inline
Side-by-side
Showing
6 changed files
with
243 additions
and
8 deletions
+243
-8
OperateController.java
...ava/iot/sixiang/license/controller/OperateController.java
+3
-6
Alarm.java
license/src/main/java/iot/sixiang/license/entity/Alarm.java
+5
-0
AlarmReadServiceImpl.java
...ot/sixiang/license/service/impl/AlarmReadServiceImpl.java
+5
-1
ResultSetInterceptor.java
...in/java/iot/sixiang/license/xss/ResultSetInterceptor.java
+176
-0
XssHttpServletRequestWrapper.java
...iot/sixiang/license/xss/XssHttpServletRequestWrapper.java
+1
-1
XssUtil.java
license/src/main/java/iot/sixiang/license/xss/XssUtil.java
+53
-0
No files found.
license/src/main/java/iot/sixiang/license/controller/OperateController.java
View file @
869793d3
...
...
@@ -104,9 +104,6 @@ public class OperateController {
String
user
=
UserUtils
.
getLoginUserId
();
int
userI
=
Integer
.
valueOf
(
user
);
List
<
AlarmVo
>
alarmList
=
alarmService
.
getAlarmList
(
userI
);
for
(
AlarmVo
alarmVo
:
alarmList
)
{
alarmVo
.
setLevelDescribe
(
ESAPI
.
encoder
().
encodeForHTML
(
alarmVo
.
getLevelDescribe
()));
}
return
ResResult
.
success
().
goRecord
(
alarmList
);
}
...
...
@@ -114,9 +111,9 @@ public class OperateController {
@PostMapping
(
"alarm/read"
)
@MyLog
(
title
=
"将告警信息状态设为已读"
,
businessType
=
BusinessType
.
OTHER
)
public
BaseResult
readAlarm
()
{
String
i
d
=
UserUtils
.
getLoginUserId
();
int
u
serId
=
Integer
.
valueOf
(
id
);
boolean
res
=
alarmReadService
.
readAlarm
(
u
serId
);
String
i
=
UserUtils
.
getLoginUserId
();
int
u
I
=
Integer
.
valueOf
(
i
);
boolean
res
=
alarmReadService
.
readAlarm
(
u
I
);
if
(
res
)
{
return
BaseResult
.
success
();
}
else
{
...
...
license/src/main/java/iot/sixiang/license/entity/Alarm.java
View file @
869793d3
...
...
@@ -34,4 +34,9 @@ public class Alarm {
@DateTimeFormat
(
pattern
=
"yyyy-MM-dd HH:mm:ss"
)
@ApiModelProperty
(
"告警创建时间"
)
private
Date
createTime
;
public
Integer
getI
()
{
return
this
.
id
;
}
}
license/src/main/java/iot/sixiang/license/service/impl/AlarmReadServiceImpl.java
View file @
869793d3
...
...
@@ -8,9 +8,11 @@ import iot.sixiang.license.mapper.AlarmMapper;
import
iot.sixiang.license.mapper.AlarmReadMapper
;
import
iot.sixiang.license.model.vo.AlarmVo
;
import
iot.sixiang.license.service.AlarmReadService
;
import
org.apache.poi.ss.formula.functions.T
;
import
org.springframework.stereotype.Service
;
import
javax.annotation.Resource
;
import
java.util.HashMap
;
import
java.util.List
;
/**
...
...
@@ -29,15 +31,17 @@ public class AlarmReadServiceImpl extends ServiceImpl<AlarmReadMapper, AlarmRead
@Resource
AlarmReadMapper
alarmReadMapper
;
@Override
public
boolean
readAlarm
(
int
userId
)
{
if
(
userId
==
0
)
{
throw
new
IotLicenseException
(
ResultCode
.
VALIDATE_FAILED
.
getCode
(),
ResultCode
.
VALIDATE_FAILED
.
getMsg
());
}
List
<
AlarmVo
>
alarmList
=
alarmMapper
.
getAlarmList
(
userId
);
for
(
AlarmVo
alarm:
alarmList
)
{
if
(
alarm
.
getReadFlag
()
==
0
)
{
int
alarmId
=
alarm
.
getI
d
();
int
alarmId
=
alarm
.
getI
();
int
typeId
=
alarm
.
getTypeId
();
String
title
=
alarm
.
getTitle
();
String
content
=
alarm
.
getContent
();
...
...
license/src/main/java/iot/sixiang/license/xss/ResultSetInterceptor.java
0 → 100644
View file @
869793d3
package
iot
.
sixiang
.
license
.
xss
;
import
iot.sixiang.license.model.vo.AlarmVo
;
import
lombok.extern.slf4j.Slf4j
;
import
org.apache.ibatis.executor.resultset.ResultSetHandler
;
import
org.apache.ibatis.plugin.*
;
import
org.springframework.stereotype.Component
;
import
org.springframework.util.CollectionUtils
;
import
java.lang.reflect.Field
;
import
java.lang.reflect.Method
;
import
java.sql.Statement
;
import
java.util.*
;
/**
* @Author m33
* @Date 2022/7/15 19:52
* @Description: 对mybaits返回的结果集进行拦截,再做防XSS攻击处理 此处仅根据Mapper接口的返回类型做处理,其他未处理类型需要自行拓展
*/
@Slf4j
@Component
@Intercepts
({
@Signature
(
type
=
ResultSetHandler
.
class
,
method
=
"handleResultSets"
,
args
=
{
Statement
.
class
})})
public
class
ResultSetInterceptor
implements
Interceptor
{
@Override
public
Object
intercept
(
Invocation
invocation
)
throws
Throwable
{
//取出查询的结果
final
Object
resultObject
=
invocation
.
proceed
();
if
(
Objects
.
isNull
(
resultObject
))
{
return
resultObject
;
}
//针对ArrayList进行过滤
if
(
resultObject
instanceof
ArrayList
)
{
ArrayList
resultList
=
(
ArrayList
)
resultObject
;
if
(
CollectionUtils
.
isEmpty
(
resultList
))
{
return
resultList
;
}
//遍历List里面所有对象
resultList
.
stream
().
forEach
(
value
->
{
Field
[]
fields
=
value
.
getClass
().
getDeclaredFields
();
Class
<?>
clazz
=
value
.
getClass
();
Field
[]
field
=
null
;
// for (; clazz != Object.class; clazz = clazz.getSuperclass()) {//向上循环 遍历父类
// field = clazz.getDeclaredFields();
// for (Field f : field) {
// f.setAccessible(true);
// try {
// System.out.println("属性:"+f.getName()+" 值:"+f.get(value).toString());
// } catch (IllegalAccessException e) {
// e.printStackTrace();
// }
//
// }
// }
// System.out.println(field);
//定义一个HashMap存取当前遍历的Map的k-v值
HashMap
<
String
,
Object
>
store
=
new
HashMap
<>();
//
// if (value instanceof AlarmVo) {
// System.out.println("=========================");
// for (Field field1 : fields) {
// try {
// System.out.println(field1.get(value).toString());
// } catch (IllegalAccessException e) {
// e.printStackTrace();
// }
// }
// System.out.println("=========================");
// }
//如果是List<Map> 则value为Map
if
(
value
instanceof
HashMap
)
{
System
.
out
.
println
(
"Map ==>"
+
value
);
//遍历Map的所有属性
Arrays
.
stream
(
fields
).
forEach
(
v1
->
{
//开启属性访问
v1
.
setAccessible
(
true
);
try
{
//声明一个java.util.HashMap$Node的Class 用于获取Node的key,value,next的值
Class
clsHashMap$Node
=
Class
.
forName
(
"java.util.HashMap$Node"
);
//遍历属性,获取Map的table属性 ,Node[] table
if
(
v1
.
getName
()
==
"table"
)
{
Object
[]
nodes
=
(
Object
[])
v1
.
get
(
value
);
//遍历所有非空节点
for
(
Object
node
:
nodes
)
{
if
(
node
!=
null
)
{
//节点递归获取节点k-v值存入hashmap中
forEachGetNodeKV
(
node
,
clsHashMap$Node
,
store
);
}
}
}
}
catch
(
Exception
e
)
{
e
.
printStackTrace
();
}
});
//打印取出来的k-v结果
// for (Map.Entry entry : store.entrySet()) {
// System.out.println("key==>" + entry.getKey() + " value==>" + entry.getValue());
// }
}
//如果是List<String> 则value为String
if
(
value
instanceof
String
)
{
}
});
}
return
resultObject
;
}
/**
* 节点递归获取节点k-v值存入hashmap中
*
* @param node
* @param clsHashMap$Node
* @param hashMap
* @throws IllegalArgumentException
* @throws IllegalAccessException
* @throws NoSuchFieldException
* @throws SecurityException
*/
private
void
forEachGetNodeKV
(
Object
node
,
Class
clsHashMap$Node
,
HashMap
<
String
,
Object
>
hashMap
)
throws
Exception
{
//获取node类里面的key属性
Field
f_key
=
clsHashMap$Node
.
getDeclaredField
(
"key"
);
//获取node类里面value属性
Field
f_value
=
clsHashMap$Node
.
getDeclaredField
(
"value"
);
//获取node类里面next属性,指向下一个节点
Field
f_next
=
clsHashMap$Node
.
getDeclaredField
(
"next"
);
//开启属性的私有属性访问
f_key
.
setAccessible
(
true
);
f_value
.
setAccessible
(
true
);
f_next
.
setAccessible
(
true
);
//获取key,value,next属性的属性值
String
key
=
f_key
.
get
(
node
).
toString
();
Object
value
=
f_value
.
get
(
node
);
Object
next
=
f_next
.
get
(
node
);
//进行XSS攻击过滤
if
(
value
instanceof
String
)
{
String
val
=
(
String
)
value
;
value
=
XssUtil
.
stripXSS
(
val
);
//将过滤后的数据放入原节点
Method
[]
methods
=
node
.
getClass
().
getMethods
();
for
(
Method
method
:
methods
)
{
if
(
method
.
getName
().
equals
(
"setValue"
))
{
method
.
setAccessible
(
true
);
method
.
invoke
(
node
,
value
);
}
}
}
//保存当前节点的k-v值
hashMap
.
put
(
key
,
value
);
//判断next是否为空,不为空则递归
if
(
null
!=
next
)
{
forEachGetNodeKV
(
next
,
clsHashMap$Node
,
hashMap
);
}
}
@Override
public
Object
plugin
(
Object
target
)
{
// 读取@Signature中的配置,判断是否需要生成代理类
if
(
target
instanceof
ResultSetHandler
)
{
return
Plugin
.
wrap
(
target
,
this
);
}
else
{
return
target
;
}
}
@Override
public
void
setProperties
(
Properties
properties
)
{
log
.
info
(
"setProperties"
);
}
}
license/src/main/java/iot/sixiang/license/xss/XssHttpServletRequestWrapper.java
View file @
869793d3
...
...
@@ -56,7 +56,7 @@ public class XssHttpServletRequestWrapper extends HttpServletRequestWrapper {
if
(
isMultipartContent
||
isMultipart
)
{
fileUpload
=
true
;
}
try
(
BufferedReader
isr
=
new
BufferedReader
(
new
InputStreamReader
(
ins
,
StandardCharsets
.
UTF_8
))
;
)
{
try
(
BufferedReader
isr
=
new
BufferedReader
(
new
InputStreamReader
(
ins
,
StandardCharsets
.
UTF_8
)))
{
String
line
=
""
;
while
((
line
=
isr
.
readLine
())
!=
null
)
{
sb
.
append
(
line
);
...
...
license/src/main/java/iot/sixiang/license/xss/XssUtil.java
0 → 100644
View file @
869793d3
package
iot
.
sixiang
.
license
.
xss
;
import
org.apache.commons.lang3.StringUtils
;
import
java.util.regex.Pattern
;
/**
* @Author m33
* @Date 2022/7/15 20:00
* @Description
*/
public
class
XssUtil
{
private
final
static
Pattern
SCRIPT_PATTERN
=
Pattern
.
compile
(
"<script>(.*?)</script>"
,
Pattern
.
CASE_INSENSITIVE
);
private
final
static
Pattern
SRC_PATTERN_ONE
=
Pattern
.
compile
(
"src[\r\n]*=[\r\n]*\\\'(.*?)\\\'"
,
Pattern
.
CASE_INSENSITIVE
|
Pattern
.
MULTILINE
|
Pattern
.
DOTALL
);
private
final
static
Pattern
SRC_PATTERN_TWO
=
Pattern
.
compile
(
"src[\r\n]*=[\r\n]*\\\"(.*?)\\\""
,
Pattern
.
CASE_INSENSITIVE
|
Pattern
.
MULTILINE
|
Pattern
.
DOTALL
);
private
final
static
Pattern
SCRIPT_PATTERN_ONE
=
Pattern
.
compile
(
"</script>"
,
Pattern
.
CASE_INSENSITIVE
);
private
final
static
Pattern
SCRIPT_PATTERN_TWO
=
Pattern
.
compile
(
"<script(.*?)>"
,
Pattern
.
CASE_INSENSITIVE
|
Pattern
.
MULTILINE
|
Pattern
.
DOTALL
);
private
final
static
Pattern
EVAL_PATTERN
=
Pattern
.
compile
(
"eval\\((.*?)\\)"
,
Pattern
.
CASE_INSENSITIVE
|
Pattern
.
MULTILINE
|
Pattern
.
DOTALL
);
private
final
static
Pattern
EXPRESSION_PATTERN
=
Pattern
.
compile
(
"expression\\((.*?)\\)"
,
Pattern
.
CASE_INSENSITIVE
|
Pattern
.
MULTILINE
|
Pattern
.
DOTALL
);
private
final
static
Pattern
JAVASCRIPT_PATTERN
=
Pattern
.
compile
(
"javascript:"
,
Pattern
.
CASE_INSENSITIVE
);
private
final
static
Pattern
VB_SCRIPT_PATTERN
=
Pattern
.
compile
(
"vbscript:"
,
Pattern
.
CASE_INSENSITIVE
);
private
final
static
Pattern
ON_LOAD_PATTERN
=
Pattern
.
compile
(
"onload(.*?)="
,
Pattern
.
CASE_INSENSITIVE
|
Pattern
.
MULTILINE
|
Pattern
.
DOTALL
);
private
XssUtil
()
{
}
/**
* 过滤xss
* @param value 值
* @return 过滤置空
*/
public
static
String
stripXSS
(
String
value
)
{
if
(
StringUtils
.
isNotBlank
(
value
))
{
value
=
SCRIPT_PATTERN
.
matcher
(
value
).
replaceAll
(
""
);
value
=
SRC_PATTERN_ONE
.
matcher
(
value
).
replaceAll
(
""
);
value
=
SRC_PATTERN_TWO
.
matcher
(
value
).
replaceAll
(
""
);
value
=
SCRIPT_PATTERN_ONE
.
matcher
(
value
).
replaceAll
(
""
);
value
=
SCRIPT_PATTERN_TWO
.
matcher
(
value
).
replaceAll
(
""
);
value
=
EVAL_PATTERN
.
matcher
(
value
).
replaceAll
(
""
);
value
=
EXPRESSION_PATTERN
.
matcher
(
value
).
replaceAll
(
""
);
value
=
JAVASCRIPT_PATTERN
.
matcher
(
value
).
replaceAll
(
""
);
value
=
VB_SCRIPT_PATTERN
.
matcher
(
value
).
replaceAll
(
""
);
value
=
ON_LOAD_PATTERN
.
matcher
(
value
).
replaceAll
(
""
);
}
return
value
;
}
}
\ No newline at end of file
Write
Preview
Markdown
is supported
0%
Try again
or
attach a new file
Attach a file
Cancel
You are about to add
0
people
to the discussion. Proceed with caution.
Finish editing this message first!
Cancel
Please
register
or
sign in
to comment