【问题标题】:Spring MVC Singleton Controller - Multiple Download RequestsSpring MVC Singleton Controller - 多个下载请求
【发布时间】:2023-03-30 09:20:01
【问题描述】:

我知道 Spring MVC 控制器是单例的。

因此,使用控制器的字段来存储数据可能会导致安全问题。

问题是,假设它有一个允许用户下载文件的映射 -

@RequestMapping(value = "downloadReport", method=RequestMethod.GET)
public void downloadReport(@RequestParam("reportStoreId") String reportStoreId,
            HttpServletResponse response, HttpServletRequest request) {
    // use reportStoreId to fetch a report from file system and pass it to user using PrintWriter, response.getWriter(), etc...
}

那么如果多个用户同时请求下载不同ID的文件,是否会导致一个用户获取另一个用户请求的文件?

【问题讨论】:

  • 您认为为什么以及如何会发生这种情况?

标签: java session spring-mvc singleton-methods


【解决方案1】:

如果您的downloadReport 实现是Thread Safe,那么您不必担心这一点。

在您描述的情况下,多个线程将执行downloadReport。如果执行中使用的所有变量都在每个线程的堆栈上,它们就不会发生冲突。下面是一个简单的例子来说明:

@RequestMapping(value = "downloadReport", method=RequestMethod.GET)
public void downloadReport(@RequestParam("reportStoreId") String reportStoreId,
            HttpServletResponse response, HttpServletRequest request) {
    response.getWriter().print(getReportText(reportStoreId));
}

您需要实现getReportText 来返回命名报告的文本——或类似的东西。如您所见,getReportText 根据其参数返回文本。这个参数在线程的调用栈上,对于每个请求都会不同(当然,除非两个请求是针对同一个文件的)。

【讨论】:

    【解决方案2】:

    简短的回答是否定的。

    下面的答案不是那么简短。 对于每个请求,spring 将调用控制器的方法,并将传递从 HTTP 请求解析的自己的 id 值。堆栈变量与类字段非常不同。它的生命周期不同,它在方法启动时创建,在方法完成时销毁。此外,其他并发运行的线程也无法访问它,因此不会发生干扰。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2011-02-17
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2011-06-08
      • 1970-01-01
      • 1970-01-01
      • 2023-03-23
      相关资源
      最近更新 更多