【问题标题】:How to use @Inject in Spring MVC Controller?如何在 Spring MVC 控制器中使用 @Inject?
【发布时间】:2014-06-10 23:21:36
【问题描述】:

我正在使用 Spring MVC 控制器。我的控制器之一是DataController

我正在考虑使用@InjectDataController 类的顶部添加HttpServletRequest 作为可注入对象。

@Controller
public class DataController {

    @Inject
    HttpServletRequest request;

    // .. some code here

    @RequestMapping(value = "process", method = RequestMethod.GET)
    public @ResponseBody
    DataResponse processTask(@RequestParam("workflow") final String workflow) {

        String ipAddress = request.getRemoteAddr();
        System.out.println(ipAddress);

}

所以我的问题是 - 这是使用 @Inject 的正确方法吗?我以前从未使用过@Inject,所以试图了解我这样做的方式是否正确?由于每次调用processTask 方法的人,我都需要获取调用processTask 方法的人的ipAddress。

【问题讨论】:

  • 你可以试试...
  • 该控制器在其生命周期内是否需要一个 HttpServletRequest?请记住,控制器本质上只是另一个对象。请求通常应作为方法参数传入,因为每个请求都会调用一次该方法。
  • @chrylis 这将是一个请求范围的bean,每个请求的值不同。
  • @SotiriosDelimanolis 你说的“那个”是什么意思?提供的代码是默认的单例范围的。 (无论如何,就测试和模块化而言,方法注入是正确的。)
  • @chrylis Spring 将注入HttpServletRequest 的代理,其中将包含一个ObjectFactory,它将在请求时检索实际 HttpServletRequest(例如:方法调用)。这只能在该请求可用的上下文中工作(如这里)。它会在其他任何地方失败。

标签: java spring spring-mvc


【解决方案1】:

在获取HttpServletRequest方面:从语义上来说肯定是错误的。

原因HttpServletRequest 是一个对象,仅在用户发送请求时创建,并在请求的用户操作完成后销毁。您可以简单地以这种方式存储它(从语法角度),但您不应该(从语义角度)。您需要意识到 Web 应用程序的工作方式与桌面应用程序的工作方式并不完全相同(并且不要从相同的角度观察它们)。

建议

@RequestMapping(value = "process", method = RequestMethod.GET)
public @ResponseBody
DataResponse processTask(@RequestParam("workflow") final String workflow, HttpServletRequest request) {...}

这样每次调用processTask方法都会得到对应的请求。 (HttpServletRequest对象由@RequestMapping注入。)

(如果您想在会话中保留某些内容,请考虑使用

建议
@Inject private UserService userService;
(假设我们注册了一个名为 UserService 的类。)

【讨论】:

  • 两种说法You simply can't store it that way and you shouldn't. 都是错误的。你可以这样存储它。将它存储在那里没有意义的唯一原因是如果只有一些请求处理程序使用它。如果他们都需要它,您应该使用像 OP 所示的实例字段。
  • 所以是:If you are using Spring, then you really should be using @Autowired rather than @Inject。任何一个都可以。由于@Inject 来自标准的 Java EE 组件,您可以更轻松地使您的应用程序模块不依赖于 Spring,并且可以与其他 IoC 容器重用。
  • @SotiriosDelimanolis 感谢您的更正,我同意您的意见。但是对于那个你根本不能那样存储它,你不应该。语句,这是从语义角度。从语义上讲,我仍然认为他不应该那样存储。
【解决方案2】:

据我所知,您不能“注入” HttpServletRequest 唯一的使用方法是将其添加为方法成员。像这样:

@Controller
public class DataController {



    // .. some code here

    @RequestMapping(value = "process", method = RequestMethod.GET)
    public @ResponseBody
    DataResponse processTask(@RequestParam("workflow") final String workflow,HttpServletRequest request) {

        String ipAddress = request.getRemoteAddr();
        System.out.println(ipAddress);

}

看看Spring MVC @AutoWired response not working

【讨论】:

  • 正是 OP 的方式。
  • 如果请求本身包含参数,为什么我们要同时传递参数和请求?
  • @xwid 在这种情况下,@RequestParam 将为您执行null 检查。
猜你喜欢
  • 1970-01-01
  • 2014-10-16
  • 2019-03-29
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2013-05-25
  • 2015-06-05
  • 1970-01-01
相关资源
最近更新 更多