[英]How do I change the response for a HTTP OPTIONS request in a Spring MVC 2.5 application?
This sounds like a trivial question but somehow I can't seem to figure it out. 这听起来像一个微不足道的问题但不知何故我似乎无法弄明白。
I have a Spring MVC application. 我有一个Spring MVC应用程序。 I don't support any http methods except GET and POST.
我不支持除GET和POST之外的任何http方法。 I have the following set in all my controllers beans:
我在所有控制器bean中都有以下设置:
<property name="supportedMethods" value="GET,POST"/>
However, an OPTIONS request sent to my application sends back a response that shows all http methods as allowed. 但是,发送到我的应用程序的OPTIONS请求会发回一个响应,该响应将所有 http方法显示为允许。
How do I change the OPTIONS response to show only GET and POST methods as allowed? 如何更改OPTIONS响应以仅显示允许的GET和POST方法? I know I could do this in a servlet by overriding the
doOptions
method, but I am not sure about a Spring MVC application. 我知道我可以通过覆盖
doOptions
方法在servlet中执行此操作,但我不确定Spring MVC应用程序。 Do I have to extend the DispatcherServlet
and override doOptions
? 我是否必须扩展
DispatcherServlet
并覆盖doOptions
?
The application is using Spring mvc 2.5.6 with SimpleFormController based controllers and xml based config. 该应用程序使用Spring mvc 2.5.6和基于SimpleFormController的控制器和基于xml的配置。
Caveat: I have not handled OPTIONS messages. 警告:我还没有处理OPTIONS消息。
In your request handler (annotated with @Controller) you can use RequestMethod.OPTIONS to handle an Options request. 在您的请求处理程序(使用@Controller注释)中,您可以使用RequestMethod.OPTIONS来处理Options请求。 For example you might use
例如,您可以使用
... stuff ...
@RequestMapping(RequestMethod.OPTIONS)
public String processOptions()
{
... stuff ...
}
I think you could invoke WebContentGenerator#setSupportedMethods
which receives as input parameter an array of strings containing supported methods. 我想你可以调用
WebContentGenerator#setSupportedMethods
,它接收包含支持方法的字符串数组作为输入参数。 WebContentGenerator
is the base class for spring 2.x controllers, so you just need to invoke this method during the construction of your controller that surely extends it. WebContentGenerator
是spring 2.x控制器的基类,因此您只需要在构造控制器期间调用此方法,这肯定会扩展它。 You also could use the Constructor of WebContentGenerator that receives a string varargs (supported methods) as input parameter. 您还可以使用WebContentGenerator的构造函数来接收字符串varargs(支持的方法)作为输入参数。
Unfortunately, the doOptions
method in FrameworkServlet
class invokes super.doOptions(request, response);
不幸的是,
FrameworkServlet
类中的doOptions
方法调用了super.doOptions(request, response);
of HttpServlet
class. HttpServlet
类。 The ouput of this method is based on the declared methods in the servlet, something like this: 此方法的输出基于servlet中声明的方法,如下所示:
Method[] methods = getAllDeclaredMethods(this.getClass());
for (int i = 0; i < methods.length; i++) {
Method m = methods[i];
if (m.getName().equals("doGet")) {
ALLOW_GET = true;
ALLOW_HEAD = true;
}
if (m.getName().equals("doPost"))
ALLOW_POST = true;
if (m.getName().equals("doPut"))
ALLOW_PUT = true;
if (m.getName().equals("doDelete"))
ALLOW_DELETE = true;
}
The DispatcherServlet class (and its base class FrameworkServlet) declares all these methods: doPut
, doDelete
, doGet
, doPost
etc., so the output of doOptions
is not what you desire. DispatcherServlet类(及其基类FrameworkServlet)声明了所有这些方法:
doPut
, doDelete
, doGet
, doPost
等,因此doOptions
的输出不是您想要的。 I think the only way is subclassing the DispatcherServlet. 我认为唯一的方法是继承DispatcherServlet。
I know that this is a bit old but I've found additional info on this question that I hope will help others in the future. 我知道这有点旧了,但我已经找到了关于这个问题的更多信息,我希望将来可以帮助其他人。
The @RequestMapping(RequestMethod.OPTIONS) approach won't work immediately using the DispatcherServlet out of the box since its superclass, FrameworkServlet, first delegates to its superclass, HttpServlet, as noted above which scans the servlet to see if it implements the doXXX methods and sets the Allow header accordingly. @RequestMapping(RequestMethod.OPTIONS)方法无法立即使用DispatcherServlet开箱即用,因为它的超类FrameworkServlet首先委托给它的超类HttpServlet,如上所述,它扫描servlet以查看它是否实现了doXXX方法并相应地设置Allow标头。 But following the call to super.doOptions(...) it then has these lines:
但是在调用super.doOptions(...)后,它会有以下几行:
if (this.dispatchOptionsRequest) {
processRequest(request, response);
}
And there is a setDispatchOptionsRequest(boolean) that can be used to set the dispatchOptionsRequest value to true. 并且有一个setDispatchOptionsRequest(boolean)可用于将dispatchOptionsRequest值设置为true。 Only then will the DispatcherServlet pass to the controller the OPTIONS request to an appropriately annotated method.
只有这样,DispatcherServlet才会向适当的注释方法传递OPTIONS请求给控制器。
I needed to do this to allow the OPTIONS request to return different values based upon authorizations of the current user. 我需要这样做以允许OPTIONS请求根据当前用户的授权返回不同的值。 So by subclassing DispatcherServlet and setting that parameter in its default constructor I was finally able to receive the call in my controller for http OPTIONS requests and handle it on my own.
因此,通过继承DispatcherServlet并在其默认构造函数中设置该参数,我终于能够在我的控制器中接收对http OPTIONS请求的调用并自行处理它。
And one more thought, in that controller method you can declare a parameter of type HttpServletResponse and Spring will hand the instance to you. 还有一个想法,在那个控制器方法中,你可以声明一个HttpServletResponse类型的参数,Spring将把实例交给你。 Once had you can call reset() to purge the Allow header already set and roll your own as needed.
一旦你有可以调用reset()来清除已经设置的Allow头,并根据需要滚动你自己的头。
(Note: A similar patter is had in FrameworkServlet for http TRACE support via a setDispatchTraceRequest if you plan on getting those requests through to your controller methods annotated with @RequestMapping(RequestMethod.TRACE)). (注意:如果您计划将这些请求发送到使用@RequestMapping(RequestMethod.TRACE)注释的控制器方法,则FrameworkServlet中的类似模式用于通过setDispatchTraceRequest支持http TRACE。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.