缓存servlet提供的图像

时间:2010-05-20 09:53:45

标签: java http image servlets caching

我正在从我的servlet提供图像。响应内容类型是image / jpeg。我发现从我的servlet请求的图像没有被缓存。如何通过文件图像请求缓存它们?我尝试设置Cache-Control:public但无济于事。

4 个答案:

答案 0 :(得分:23)

在Tomcat等容器中提供静态内容的默认servlet不设置任何缓存控制头。您不需要为此编写servlet。只需创建一个这样的过滤器,

public void doFilter(ServletRequest request,
        ServletResponse response,
        FilterChain chain) 
    throws IOException, ServletException {

    long expiry = new Date().getTime() + cacheAge*1000;

    HttpServletResponse httpResponse = (HttpServletResponse)response;
    httpResponse.setDateHeader("Expires", expiry);
    httpResponse.setHeader("Cache-Control", "max-age="+ cacheAge);

    chain.doFilter(request, response);

 }

每当您想要添加缓存控制时,只需将过滤器添加到web.xml中的资源即可。例如,

<filter>
    <filter-name>CacheControl</filter-name>
    <filter-class>filters.CacheControlFilter</filter-class>
</filter>

<filter-mapping>
    <filter-name>CacheControl</filter-name>
    <url-pattern>/images/*</url-pattern>
</filter-mapping>

答案 1 :(得分:3)

您需要在回复中发送ETagLast-ModifiedExpires标头。 ETag表示文件的唯一标识符(通常基于filename,filesize和lastmodified timestamp的组合组成)。 Last-Modified表示文件的上次修改时间戳。 Expires标头表示允许客户端将文件保留在缓存中的时间。如果缓存已过期并且ETagLast-Modified可用,则客户端将发送HEAD请求以检查是否需要续订该文件。如果没有,那么Expires将会相应地再次推迟。

你可以在这里找到一个处理这一切的servlet示例(并下载简历和自动GZIP):FileServlet supporting resume and GZIP

答案 2 :(得分:2)

例如,如果要将它们缓存1个月:

Calendar inOneMonth = Calendar.getInstance();
inOneMonth.add(Calendar.MONTH, 1);

response.setDateHeader("Expires", inOneMonth.getTimeInMillis());

(例如,它位于处理Filter模式的*.jpg中)

但是默认情况下应该缓存图像 - 检查过滤器和配置,看看是否有什么东西没有错误地设置缓存参数。

答案 3 :(得分:-8)

好的..看起来默认的头字段应该启用缓存。我在另一个论坛找到了解决方案。显然,您需要在响应中明确设置内容长度。不知道为什么。我认为HttpServletResponse会为我们做到这一点。无论如何,它的工作就像一个魅力,图像很好地缓存。