Skip to content
GitLab
Menu
Projects
Groups
Snippets
Help
Help
Support
Community forum
Keyboard shortcuts
?
Submit feedback
Contribute to GitLab
Sign in / Register
Toggle navigation
Menu
Open sidebar
jinli gu
Springboot Plus
Commits
b973b56c
"...src/main/resources/template/admin/ServiceImpl.ftl" did not exist on "bf7c1eebf08e362b478d00d0ef399d7a16f89ffc"
Commit
b973b56c
authored
Sep 10, 2019
by
trumansdo
Browse files
自定义注解RequestBodyPlus 将json类型请求可以用json path的形式注入单个参数
parent
3c546fca
Changes
2
Hide whitespace changes
Inline
Side-by-side
plus-admin/admin-core/src/main/java/com/ibeetl/admin/core/conf/MVCConf.java
View file @
b973b56c
package
com.ibeetl.admin.core.conf
;
package
com.ibeetl.admin.core.conf
;
import
cn.hutool.core.bean.BeanUtil
;
import
cn.hutool.core.collection.CollUtil
;
import
cn.hutool.core.convert.Convert
;
import
cn.hutool.core.convert.Convert
;
import
cn.hutool.core.map.MapUtil
;
import
cn.hutool.core.util.CharsetUtil
;
import
cn.hutool.http.Header
;
import
cn.hutool.core.util.ObjectUtil
;
import
cn.hutool.core.util.ReflectUtil
;
import
cn.hutool.core.util.StrUtil
;
import
cn.hutool.core.util.TypeUtil
;
import
cn.hutool.core.util.URLUtil
;
import
cn.hutool.json.JSON
;
import
cn.hutool.json.JSONUtil
;
import
com.ibeetl.admin.core.annotation.RequestBodyPlus
;
import
com.ibeetl.admin.core.entity.CoreOrg
;
import
com.ibeetl.admin.core.entity.CoreOrg
;
import
com.ibeetl.admin.core.entity.CoreUser
;
import
com.ibeetl.admin.core.entity.CoreUser
;
import
com.ibeetl.admin.core.service.CorePlatformService
;
import
com.ibeetl.admin.core.service.CorePlatformService
;
import
com.ibeetl.admin.core.service.CoreUserService
;
import
com.ibeetl.admin.core.service.CoreUserService
;
import
com.ibeetl.admin.core.util.ConvertUtil
;
import
com.ibeetl.admin.core.util.HttpRequestLocal
;
import
com.ibeetl.admin.core.util.HttpRequestLocal
;
import
com.ibeetl.admin.core.util.JoseJwtUtil
;
import
com.ibeetl.admin.core.util.JoseJwtUtil
;
import
java.io.IOException
;
import
java.io.InputStream
;
import
java.lang.reflect.Type
;
import
java.lang.reflect.TypeVariable
;
import
java.util.HashMap
;
import
java.util.HashMap
;
import
java.util.List
;
import
java.util.List
;
import
java.util.Map
;
import
java.util.Map
;
import
java.util.Optional
;
import
javax.servlet.http.HttpServletRequest
;
import
javax.servlet.http.HttpServletRequest
;
import
javax.servlet.http.HttpServletResponse
;
import
javax.servlet.http.HttpServletResponse
;
import
javax.servlet.http.HttpSession
;
import
javax.servlet.http.HttpSession
;
import
jdk.nashorn.internal.ir.ReturnNode
;
import
org.beetl.core.GroupTemplate
;
import
org.beetl.core.GroupTemplate
;
import
org.beetl.ext.spring.BeetlGroupUtilConfiguration
;
import
org.beetl.ext.spring.BeetlGroupUtilConfiguration
;
import
org.springframework.beans.BeanUtils
;
import
org.springframework.beans.factory.InitializingBean
;
import
org.springframework.beans.factory.InitializingBean
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.context.annotation.Configuration
;
import
org.springframework.context.annotation.Configuration
;
import
org.springframework.core.Conventions
;
import
org.springframework.core.MethodParameter
;
import
org.springframework.core.env.Environment
;
import
org.springframework.core.env.Environment
;
import
org.springframework.format.FormatterRegistry
;
import
org.springframework.format.FormatterRegistry
;
import
org.springframework.format.datetime.DateFormatter
;
import
org.springframework.format.datetime.DateFormatter
;
import
org.springframework.http.HttpHeaders
;
import
org.springframework.http.HttpHeaders
;
import
org.springframework.http.MediaType
;
import
org.springframework.http.converter.HttpMessageConverter
;
import
org.springframework.http.converter.HttpMessageNotReadableException
;
import
org.springframework.http.converter.StringHttpMessageConverter
;
import
org.springframework.http.server.ServletServerHttpRequest
;
import
org.springframework.util.Assert
;
import
org.springframework.validation.BindingResult
;
import
org.springframework.web.HttpMediaTypeNotSupportedException
;
import
org.springframework.web.accept.ContentNegotiationManager
;
import
org.springframework.web.bind.MethodArgumentNotValidException
;
import
org.springframework.web.bind.WebDataBinder
;
import
org.springframework.web.bind.annotation.RequestBody
;
import
org.springframework.web.bind.support.WebDataBinderFactory
;
import
org.springframework.web.context.request.NativeWebRequest
;
import
org.springframework.web.method.support.HandlerMethodArgumentResolver
;
import
org.springframework.web.method.support.ModelAndViewContainer
;
import
org.springframework.web.servlet.HandlerInterceptor
;
import
org.springframework.web.servlet.HandlerInterceptor
;
import
org.springframework.web.servlet.ModelAndView
;
import
org.springframework.web.servlet.ModelAndView
;
import
org.springframework.web.servlet.config.annotation.CorsRegistry
;
import
org.springframework.web.servlet.config.annotation.CorsRegistry
;
import
org.springframework.web.servlet.config.annotation.InterceptorRegistry
;
import
org.springframework.web.servlet.config.annotation.InterceptorRegistry
;
import
org.springframework.web.servlet.config.annotation.WebMvcConfigurer
;
import
org.springframework.web.servlet.config.annotation.WebMvcConfigurer
;
import
org.springframework.web.servlet.mvc.method.annotation.AbstractMessageConverterMethodProcessor
;
import
org.springframework.web.servlet.mvc.method.annotation.RequestMappingHandlerAdapter
;
import
sun.plugin2.util.ColorUtil
;
@Configuration
@Configuration
public
class
MVCConf
implements
WebMvcConfigurer
,
InitializingBean
{
public
class
MVCConf
implements
WebMvcConfigurer
,
InitializingBean
{
...
@@ -40,29 +76,27 @@ public class MVCConf implements WebMvcConfigurer, InitializingBean {
...
@@ -40,29 +76,27 @@ public class MVCConf implements WebMvcConfigurer, InitializingBean {
// @Value("${app.name}")
// @Value("${app.name}")
// String appName;
// String appName;
// 开发用的模拟当前用户和机构
private
String
mvcTestPath
;
Long
useId
;
Long
orgId
;
@Autowired
private
Environment
env
;
String
mvcTestPath
;
@Autowired
private
CoreUserService
userService
;
@Autowired
Environment
env
;
@Autowired
private
BeetlGroupUtilConfiguration
beetlGroupUtilConfiguration
;
@Autowired
CoreUserService
userService
;
@Autowired
private
HttpRequestLocal
httpRequestLocal
;
@Autowired
BeetlGroupUtilConfiguration
beetlGroupUtilConfiguration
;
@Autowired
private
GroupTemplate
groupTemplate
;
@Autowired
HttpRequestLocal
httpRequestLocal
;
@Autowired
private
RequestMappingHandlerAdapter
adapter
;
@Autowired
GroupTemplate
groupTemplate
;
@Override
@Override
public
void
addInterceptors
(
InterceptorRegistry
registry
)
{
public
void
addInterceptors
(
InterceptorRegistry
registry
)
{
registry
registry
.
addInterceptor
(
new
SessionInterceptor
(
httpRequestLocal
,
this
)).
addPathPatterns
(
"/**"
);
.
addInterceptor
(
new
SessionInterceptor
(
httpRequestLocal
,
userService
))
.
addPathPatterns
(
"/**"
)
.
excludePathPatterns
(
"/user/login"
,
"/error"
,
"/logout"
);
// super.addInterceptors(registry);
// super.addInterceptors(registry);
}
}
@Override
@Override
...
@@ -77,29 +111,31 @@ public class MVCConf implements WebMvcConfigurer, InitializingBean {
...
@@ -77,29 +111,31 @@ public class MVCConf implements WebMvcConfigurer, InitializingBean {
}
}
@Override
@Override
public
void
afterPropertiesSet
()
throws
Exception
{
public
void
afterPropertiesSet
()
{
this
.
useId
=
env
.
getProperty
(
"user.id"
,
Long
.
class
);
this
.
orgId
=
env
.
getProperty
(
"user.orgId"
,
Long
.
class
);
this
.
mvcTestPath
=
env
.
getProperty
(
"mvc.test.path"
);
this
.
mvcTestPath
=
env
.
getProperty
(
"mvc.test.path"
);
Map
<
String
,
Object
>
var
=
new
HashMap
<>(
5
);
Map
<
String
,
Object
>
var
=
new
HashMap
<>(
5
);
String
appName
=
env
.
getProperty
(
"app.name"
);
String
appName
=
env
.
getProperty
(
"app.name"
);
if
(
appName
==
null
)
{
if
(
appName
==
null
)
{
var
.
put
(
"appName"
,
DEFAULT_APP_NAME
);
var
.
put
(
"appName"
,
DEFAULT_APP_NAME
);
}
}
var
.
put
(
"jsVer"
,
System
.
currentTimeMillis
());
var
.
put
(
"jsVer"
,
System
.
currentTimeMillis
());
groupTemplate
.
setSharedVars
(
var
);
groupTemplate
.
setSharedVars
(
var
);
/*自定义参数解析器配置,自定义应该优先级最高*/
List
<
HandlerMethodArgumentResolver
>
argumentResolvers
=
CollUtil
.
newArrayList
();
argumentResolvers
.
add
(
new
RequestBodyPlusProcessor
(
adapter
.
getMessageConverters
()));
argumentResolvers
.
addAll
(
adapter
.
getArgumentResolvers
());
adapter
.
setArgumentResolvers
(
argumentResolvers
);
}
}
}
}
class
SessionInterceptor
implements
HandlerInterceptor
{
class
SessionInterceptor
implements
HandlerInterceptor
{
MVCConf
conf
;
CoreUserService
userService
;
HttpRequestLocal
httpRequestLocal
;
HttpRequestLocal
httpRequestLocal
;
public
SessionInterceptor
(
HttpRequestLocal
httpRequestLocal
,
MVCConf
conf
)
{
public
SessionInterceptor
(
HttpRequestLocal
httpRequestLocal
,
CoreUserService
userService
)
{
this
.
conf
=
conf
;
this
.
userService
=
userService
;
this
.
httpRequestLocal
=
httpRequestLocal
;
this
.
httpRequestLocal
=
httpRequestLocal
;
}
}
...
@@ -116,10 +152,10 @@ class SessionInterceptor implements HandlerInterceptor {
...
@@ -116,10 +152,10 @@ class SessionInterceptor implements HandlerInterceptor {
HttpSession
requestSession
=
request
.
getSession
(
true
);
HttpSession
requestSession
=
request
.
getSession
(
true
);
if
(
requestSession
.
getAttribute
(
CorePlatformService
.
ACCESS_CURRENT_USER
)
==
null
)
{
if
(
requestSession
.
getAttribute
(
CorePlatformService
.
ACCESS_CURRENT_USER
)
==
null
)
{
// 模拟用户登录,用于快速开发,未来用rember么代替?
// 模拟用户登录,用于快速开发,未来用rember么代替?
CoreUser
user
=
conf
.
userService
.
getUserById
(
uid
);
CoreUser
user
=
userService
.
getUserById
(
uid
);
Long
orgId
=
user
.
getOrgId
();
Long
orgId
=
user
.
getOrgId
();
CoreOrg
org
=
conf
.
userService
.
getOrgById
(
orgId
);
CoreOrg
org
=
userService
.
getOrgById
(
orgId
);
List
<
CoreOrg
>
orgs
=
conf
.
userService
.
getUserOrg
(
uid
,
org
.
getId
());
List
<
CoreOrg
>
orgs
=
userService
.
getUserOrg
(
uid
,
org
.
getId
());
requestSession
.
setAttribute
(
CorePlatformService
.
ACCESS_CURRENT_USER
,
user
);
requestSession
.
setAttribute
(
CorePlatformService
.
ACCESS_CURRENT_USER
,
user
);
requestSession
.
setAttribute
(
CorePlatformService
.
ACCESS_CURRENT_ORG
,
org
);
requestSession
.
setAttribute
(
CorePlatformService
.
ACCESS_CURRENT_ORG
,
org
);
requestSession
.
setAttribute
(
CorePlatformService
.
ACCESS_USER_ORGS
,
orgs
);
requestSession
.
setAttribute
(
CorePlatformService
.
ACCESS_USER_ORGS
,
orgs
);
...
@@ -134,15 +170,79 @@ class SessionInterceptor implements HandlerInterceptor {
...
@@ -134,15 +170,79 @@ class SessionInterceptor implements HandlerInterceptor {
HttpServletRequest
request
,
HttpServletRequest
request
,
HttpServletResponse
response
,
HttpServletResponse
response
,
Object
handler
,
Object
handler
,
ModelAndView
modelAndView
)
ModelAndView
modelAndView
)
{
throws
Exception
{
/* do nothing */
// do nothing
}
}
@Override
@Override
public
void
afterCompletion
(
public
void
afterCompletion
(
HttpServletRequest
request
,
HttpServletResponse
response
,
Object
handler
,
Exception
ex
)
HttpServletRequest
request
,
HttpServletResponse
response
,
Object
handler
,
Exception
ex
)
{
/* do nothing */
}
}
/** 自定义注解,用json path 的方式注入json类型的参数 */
class
RequestBodyPlusProcessor
extends
AbstractMessageConverterMethodProcessor
{
private
static
final
ThreadLocal
<
String
>
bodyLocal
=
ThreadLocal
.
withInitial
(()
->
null
);
protected
RequestBodyPlusProcessor
(
List
<
HttpMessageConverter
<?>>
converters
)
{
super
(
converters
);
}
@Override
public
boolean
supportsParameter
(
MethodParameter
parameter
)
{
return
parameter
.
hasParameterAnnotation
(
RequestBodyPlus
.
class
);
}
@Override
public
Object
resolveArgument
(
MethodParameter
parameter
,
ModelAndViewContainer
mavContainer
,
NativeWebRequest
webRequest
,
WebDataBinderFactory
binderFactory
)
throws
Exception
{
throws
Exception
{
// do nothing
parameter
=
parameter
.
nestedIfOptional
();
/*非json请求过滤*/
Class
<?>
parameterType
=
parameter
.
getNestedParameterType
();
if
(!
StrUtil
.
containsAny
(
webRequest
.
getHeader
(
HttpHeaders
.
CONTENT_TYPE
),
MediaType
.
APPLICATION_JSON_VALUE
))
{
return
ReflectUtil
.
newInstanceIfPossible
(
parameterType
);
}
HttpServletRequest
servletRequest
=
webRequest
.
getNativeRequest
(
HttpServletRequest
.
class
);
Assert
.
state
(
servletRequest
!=
null
,
"No HttpServletRequest"
);
ServletServerHttpRequest
inputMessage
=
new
ServletServerHttpRequest
(
servletRequest
);
StringHttpMessageConverter
stringHttpMessageConverter
=
new
StringHttpMessageConverter
();
String
jsonBody
=
Optional
.
ofNullable
(
bodyLocal
.
get
())
.
orElseGet
(
()
->
{
try
{
bodyLocal
.
set
(
stringHttpMessageConverter
.
read
(
String
.
class
,
inputMessage
));
}
catch
(
IOException
e
)
{
logger
.
error
(
"can't read request body by input stream : {}"
,
e
);
}
return
bodyLocal
.
get
();
});
RequestBodyPlus
requestBodyPlus
=
parameter
.
getParameterAnnotation
(
RequestBodyPlus
.
class
);
JSON
json
=
JSONUtil
.
parse
(
jsonBody
);
Object
parseVal
=
json
.
getByPath
(
requestBodyPlus
.
value
(),
parameterType
);
/*TODO 待将json转成对象*/
System
.
out
.
println
(
JSONUtil
.
parse
(
"{'users':[ {'user':{'name':'lisi'}} ]}"
).
getByPath
(
"users"
));
return
parseVal
;
}
@Override
public
boolean
supportsReturnType
(
MethodParameter
returnType
)
{
return
false
;
}
}
@Override
public
void
handleReturnValue
(
Object
returnValue
,
MethodParameter
returnType
,
ModelAndViewContainer
mavContainer
,
NativeWebRequest
webRequest
)
{}
}
}
plus-admin/admin-core/src/main/java/com/ibeetl/admin/core/web/IndexController.java
View file @
b973b56c
package
com.ibeetl.admin.core.web
;
package
com.ibeetl.admin.core.web
;
import
com.ibeetl.admin.core.annotation.RequestBodyPlus
;
import
java.util.Enumeration
;
import
java.util.Enumeration
;
import
java.util.List
;
import
java.util.Map
;
import
javax.servlet.http.HttpServletRequest
;
import
javax.servlet.http.HttpServletRequest
;
import
javax.servlet.http.HttpSession
;
import
javax.servlet.http.HttpSession
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.beans.factory.annotation.Autowired
;
import
org.springframework.stereotype.Controller
;
import
org.springframework.stereotype.Controller
;
import
org.springframework.web.bind.annotation.CrossOrigin
;
import
org.springframework.web.bind.annotation.PostMapping
;
import
org.springframework.web.bind.annotation.PostMapping
;
import
org.springframework.web.bind.annotation.RequestBody
;
import
org.springframework.web.bind.annotation.RequestMapping
;
import
org.springframework.web.bind.annotation.RequestMapping
;
import
org.springframework.web.bind.annotation.RequestParam
;
import
org.springframework.web.servlet.ModelAndView
;
import
org.springframework.web.servlet.ModelAndView
;
import
com.ibeetl.admin.core.entity.CoreOrg
;
import
com.ibeetl.admin.core.entity.CoreOrg
;
...
@@ -57,9 +63,12 @@ public class IndexController {
...
@@ -57,9 +63,12 @@ public class IndexController {
return view;
return view;
}*/
}*/
@CrossOrigin
@PostMapping
(
"/user/login"
)
@PostMapping
(
"/user/login"
)
public
Object
login
(
String
username
,
String
password
)
{
public
Object
login
(
@RequestBodyPlus
(
"username"
)
String
username
,
String
password
,
@RequestBodyPlus
Map
params
)
{
UserLoginInfo
info
=
userService
.
login
(
username
,
password
);
UserLoginInfo
info
=
userService
.
login
(
username
,
password
);
System
.
out
.
println
(
params
);
if
(
info
==
null
)
{
if
(
info
==
null
)
{
throw
new
PlatformException
(
"用户名密码错误"
);
throw
new
PlatformException
(
"用户名密码错误"
);
}
}
...
...
Write
Preview
Supports
Markdown
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