Skip to content
Projects
Groups
Snippets
Help
This project
Loading...
Sign in / Register
Toggle navigation
W
wecloud_im_server
Overview
Overview
Details
Activity
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
Collapse sidebar
Close sidebar
Activity
Graph
Charts
Create a new issue
Jobs
Commits
Issue Boards
Open sidebar
hewei
wecloud_im_server
Commits
143e98a2
Commit
143e98a2
authored
Apr 06, 2022
by
14759289890
Browse files
Options
Browse Files
Download
Email Patches
Plain Diff
1、增加ActionExceptionResolver兼容GlobalExceptionHandler,统一处理异常
parent
e47d5b0f
Hide whitespace changes
Inline
Side-by-side
Showing
1 changed file
with
190 additions
and
0 deletions
+190
-0
core/src/main/java/com/wecloud/dispatch/exception/ActionExceptionResolver.java
+190
-0
No files found.
core/src/main/java/com/wecloud/dispatch/exception/ActionExceptionResolver.java
0 → 100644
View file @
143e98a2
package
com
.
wecloud
.
dispatch
.
exception
;
import
lombok.extern.slf4j.Slf4j
;
import
org.springframework.aop.support.AopUtils
;
import
org.springframework.beans.BeansException
;
import
org.springframework.beans.factory.InitializingBean
;
import
org.springframework.context.ApplicationContext
;
import
org.springframework.context.ApplicationContextAware
;
import
org.springframework.http.HttpStatus
;
import
org.springframework.lang.Nullable
;
import
org.springframework.ui.ModelMap
;
import
org.springframework.web.context.request.ServletWebRequest
;
import
org.springframework.web.method.ControllerAdviceBean
;
import
org.springframework.web.method.HandlerMethod
;
import
org.springframework.web.method.annotation.ExceptionHandlerMethodResolver
;
import
org.springframework.web.method.support.ModelAndViewContainer
;
import
org.springframework.web.servlet.ModelAndView
;
import
org.springframework.web.servlet.View
;
import
org.springframework.web.servlet.mvc.method.annotation.ResponseBodyAdvice
;
import
org.springframework.web.servlet.mvc.method.annotation.ServletInvocableHandlerMethod
;
import
org.springframework.web.servlet.mvc.support.RedirectAttributes
;
import
org.springframework.web.servlet.support.RequestContextUtils
;
import
javax.servlet.http.HttpServletRequest
;
import
javax.servlet.http.HttpServletResponse
;
import
java.lang.reflect.Method
;
import
java.lang.reflect.Proxy
;
import
java.util.ArrayList
;
import
java.util.LinkedHashMap
;
import
java.util.List
;
import
java.util.Map
;
import
java.util.concurrent.ConcurrentHashMap
;
/**
* @author luozh
*/
@Slf4j
public
class
ActionExceptionResolver
implements
ApplicationContextAware
,
InitializingBean
{
private
ApplicationContext
applicationContext
;
private
final
List
<
Object
>
responseBodyAdvice
=
new
ArrayList
<>();
private
final
Map
<
Class
<?>,
ExceptionHandlerMethodResolver
>
exceptionHandlerCache
=
new
ConcurrentHashMap
<>(
64
);
private
final
Map
<
ControllerAdviceBean
,
ExceptionHandlerMethodResolver
>
exceptionHandlerAdviceCache
=
new
LinkedHashMap
<>();
@Override
public
void
afterPropertiesSet
()
{
// Do this first, it may add ResponseBodyAdvice beans
initExceptionHandlerAdviceCache
();
}
@Override
public
void
setApplicationContext
(
ApplicationContext
applicationContext
)
throws
BeansException
{
this
.
applicationContext
=
applicationContext
;
}
@Nullable
public
ApplicationContext
getApplicationContext
()
{
return
this
.
applicationContext
;
}
private
void
initExceptionHandlerAdviceCache
()
{
if
(
getApplicationContext
()
==
null
)
{
return
;
}
List
<
ControllerAdviceBean
>
adviceBeans
=
ControllerAdviceBean
.
findAnnotatedBeans
(
getApplicationContext
());
for
(
ControllerAdviceBean
adviceBean
:
adviceBeans
)
{
Class
<?>
beanType
=
adviceBean
.
getBeanType
();
if
(
beanType
==
null
)
{
throw
new
IllegalStateException
(
"Unresolvable type for ControllerAdviceBean: "
+
adviceBean
);
}
ExceptionHandlerMethodResolver
resolver
=
new
ExceptionHandlerMethodResolver
(
beanType
);
if
(
resolver
.
hasExceptionMappings
())
{
this
.
exceptionHandlerAdviceCache
.
put
(
adviceBean
,
resolver
);
}
if
(
ResponseBodyAdvice
.
class
.
isAssignableFrom
(
beanType
))
{
this
.
responseBodyAdvice
.
add
(
adviceBean
);
}
}
if
(
log
.
isDebugEnabled
())
{
int
handlerSize
=
this
.
exceptionHandlerAdviceCache
.
size
();
int
adviceSize
=
this
.
responseBodyAdvice
.
size
();
if
(
handlerSize
==
0
&&
adviceSize
==
0
)
{
log
.
debug
(
"ControllerAdvice beans: none"
);
}
else
{
log
.
debug
(
"ControllerAdvice beans: "
+
handlerSize
+
" @ExceptionHandler, "
+
adviceSize
+
" ResponseBodyAdvice"
);
}
}
}
@Nullable
protected
ModelAndView
doResolveHandlerMethodException
(
HttpServletRequest
request
,
HttpServletResponse
response
,
@Nullable
HandlerMethod
handlerMethod
,
Exception
exception
)
{
ServletInvocableHandlerMethod
exceptionHandlerMethod
=
getExceptionHandlerMethod
(
handlerMethod
,
exception
);
if
(
exceptionHandlerMethod
==
null
)
{
return
null
;
}
ServletWebRequest
webRequest
=
new
ServletWebRequest
(
request
,
response
);
ModelAndViewContainer
mavContainer
=
new
ModelAndViewContainer
();
try
{
if
(
log
.
isDebugEnabled
())
{
log
.
debug
(
"Using @ExceptionHandler "
+
exceptionHandlerMethod
);
}
Throwable
cause
=
exception
.
getCause
();
if
(
cause
!=
null
)
{
// Expose cause as provided argument as well
exceptionHandlerMethod
.
invokeAndHandle
(
webRequest
,
mavContainer
,
exception
,
cause
,
handlerMethod
);
}
else
{
// Otherwise, just the given exception as-is
exceptionHandlerMethod
.
invokeAndHandle
(
webRequest
,
mavContainer
,
exception
,
handlerMethod
);
}
}
catch
(
Throwable
invocationEx
)
{
// Any other than the original exception (or its cause) is unintended here,
// probably an accident (e.g. failed assertion or the like).
if
(
invocationEx
!=
exception
&&
invocationEx
!=
exception
.
getCause
()
&&
log
.
isWarnEnabled
())
{
log
.
warn
(
"Failure in @ExceptionHandler "
+
exceptionHandlerMethod
,
invocationEx
);
}
// Continue with default processing of the original exception...
return
null
;
}
if
(
mavContainer
.
isRequestHandled
())
{
return
new
ModelAndView
();
}
else
{
ModelMap
model
=
mavContainer
.
getModel
();
HttpStatus
status
=
mavContainer
.
getStatus
();
ModelAndView
mav
=
new
ModelAndView
(
mavContainer
.
getViewName
(),
model
,
status
);
mav
.
setViewName
(
mavContainer
.
getViewName
());
if
(!
mavContainer
.
isViewReference
())
{
mav
.
setView
((
View
)
mavContainer
.
getView
());
}
if
(
model
instanceof
RedirectAttributes
)
{
Map
<
String
,
?>
flashAttributes
=
((
RedirectAttributes
)
model
).
getFlashAttributes
();
RequestContextUtils
.
getOutputFlashMap
(
request
).
putAll
(
flashAttributes
);
}
return
mav
;
}
}
@Nullable
protected
ServletInvocableHandlerMethod
getExceptionHandlerMethod
(
@Nullable
HandlerMethod
handlerMethod
,
Exception
exception
)
{
Class
<?>
handlerType
=
null
;
if
(
handlerMethod
!=
null
)
{
// Local exception handler methods on the controller class itself.
// To be invoked through the proxy, even in case of an interface-based proxy.
handlerType
=
handlerMethod
.
getBeanType
();
ExceptionHandlerMethodResolver
resolver
=
this
.
exceptionHandlerCache
.
get
(
handlerType
);
if
(
resolver
==
null
)
{
resolver
=
new
ExceptionHandlerMethodResolver
(
handlerType
);
this
.
exceptionHandlerCache
.
put
(
handlerType
,
resolver
);
}
Method
method
=
resolver
.
resolveMethod
(
exception
);
if
(
method
!=
null
)
{
return
new
ServletInvocableHandlerMethod
(
handlerMethod
.
getBean
(),
method
);
}
// For advice applicability check below (involving base packages, assignable types
// and annotation presence), use target class instead of interface-based proxy.
if
(
Proxy
.
isProxyClass
(
handlerType
))
{
handlerType
=
AopUtils
.
getTargetClass
(
handlerMethod
.
getBean
());
}
}
for
(
Map
.
Entry
<
ControllerAdviceBean
,
ExceptionHandlerMethodResolver
>
entry
:
this
.
exceptionHandlerAdviceCache
.
entrySet
())
{
ControllerAdviceBean
advice
=
entry
.
getKey
();
if
(
advice
.
isApplicableToBeanType
(
handlerType
))
{
ExceptionHandlerMethodResolver
resolver
=
entry
.
getValue
();
Method
method
=
resolver
.
resolveMethod
(
exception
);
if
(
method
!=
null
)
{
return
new
ServletInvocableHandlerMethod
(
advice
.
resolveBean
(),
method
);
}
}
}
return
null
;
}
}
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