REST Web 服务/Web UI 服务的单独异常映射

发布于 2024-11-26 03:10:16 字数 416 浏览 1 评论 0 原文

我用 Jersey 编写了一个网络服务。 此 Web 服务提供通过 REST 客户端和用户 WebUI(基本上是简单的 HTML)访问的 REST 方法。

这两个方面由两个独立的“Restlet”类提供。

我注册了一个独特的异常映射器,每当发生意外异常时,它都会打印整个错误和堆栈跟踪。这些异常可以由 REST 服务或 WebUI 引发。

我希望每当异常返回到 REST 客户端时都返回一个纯文本堆栈跟踪,并在 WebUI 端发生异常时返回一个漂亮的 HTML 错误页面。

我想我可以通过探索请求的“接受”Http 标头,寻找 HTML mime 类型来做到这一点。但该请求在ExceptionMapper接口中不可用。

你会怎么做?

I have written a web service with Jersey.
This web service provides both REST methods to be accessed via a REST client, and a User WebUI (basically simple HTML).

Those two aspects are served by 2 separate"Restlet" classes.

I have registered a unique Exception mapper that prints the whole error and stack trace whenever an unexpected exception happens. Those exceptions can be thrown either by the REST service or the WebUI.

I would like to return a plain text stack trace whenever the exception is returned to a REST client, and a pretty HTML error page whenever it happens on the WebUI side.

I thought I could do that by exploring the "Accepts" Http headers of the request, looking for HTML mime type. But the request is not available in the ExceptionMapper interface.

How would you do that ?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

娇女薄笑 2024-12-03 03:10:16

这个想法怎么样:

编写一个 servlet 过滤器/侦听器,将 HTTP 请求对象存储在线程局部变量中,然后您可以从异常映射器中读取该对象。

注意:在 Spring 中,这可以使用 RequestContextFilterRequestContextListener

它将添加到 web.xml 中

<listener>
    <listener-class>org.springframework.web.context.request.RequestContextListener</listener-class>
</listener>

并像这样使用:

ServletRequestAttributes reqAttr = (ServletRequestAttributes) RequestContextHolder.currentRequestAttributes();
HttpServletRequest req = reqAttr.getRequest(); 

如果您不使用 spring,那么源代码可能会让您了解如何推出自己的。希望有帮助。

How's this for an idea:

Write a servlet filter/listener that stores the HTTP request object in a Thread Local variable which you can then read from your exception mapper.

NB: In Spring this would be the achieved using either the RequestContextFilter or the RequestContextListener

which would be added in web.xml

<listener>
    <listener-class>org.springframework.web.context.request.RequestContextListener</listener-class>
</listener>

and used like this:

ServletRequestAttributes reqAttr = (ServletRequestAttributes) RequestContextHolder.currentRequestAttributes();
HttpServletRequest req = reqAttr.getRequest(); 

If you are not using spring, then the source code may give you an idea on how to roll your own. Hope that helps.

素手挽清风 2024-12-03 03:10:16

ExceptionMapper 将异常映射到响应,然后处理响应,就好像它是由资源方法返回的一样。因此,如果响应返回一个 bean 作为其实体并且没有媒体类型,则 JAX-RS 规范第 3.8 节中的算法将生效。

总之,您可以执行以下操作:

  1. 定义一个 bean(或使用异常类型本身作为 bean)
  2. 为要返回的媒体类型(text/html、application/json、text/plain)的 bean 定义 MBW )
  3. ExceptionMapper 返回包​​含 bean 实例的响应(但没有媒体类型)

JAX-RS 运行时将使用 Accept 标头来生成正确的响应(即选择您的 MessageBodyWritter 来生成响应)。

如果映射器本身仍然需要来自请求的附加信息,我看到的唯一解决方案是创建您自己的异常,在资源类中注入 Request,并在您抛出的异常中包含对请求的引用。

希望这有帮助。

——圣地亚哥

An ExceptionMapper maps an Exception to a Response, and the Response is then processed as if it had been returned by the resource method. It follows that if the response returns a bean as its entity and no media type, the algorithm in section 3.8 of the JAX-RS spec will take affect.

In summary, what you can do is the following:

  1. Define a bean (or use the exception type itself as a bean)
  2. Define MBW for the bean for the media types you want to return (text/html, application/json, text/plain)
  3. ExceptionMapper returns Response that contains instance of bean (but no media type)

The JAX-RS runtime will then use the Accept header to produce the correct response (i.e. pick your MessageBodyWritter to produce the response).

If additional info from the request is still needed in the mapper itself, the only solution I see is to create your own exception, inject Request in your resource class, and include a reference to the request in the exception that you throw.

Hope this helps.

-- Santiago

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文