首页 > 解决方案 > Jetty ResourceCache 与 CachedContentFactory

问题描述

我正在从码头迁移9.0.x9.4.x

org.eclipse.jetty.server.ResourceCache从 Jetty 中移除9.4.x

问题:

1)这个类的替代品是什么9.4.x

2)我发现CachedContentFactory是这个类的最接近的等价物,但是这个类的构造函数需要一个额外的参数CompressedContentFormat[] precompressedFormats。如果这是一个正确的替换,那么我不确定我应该为这个参数传递什么?它可以是空数组吗?抱歉,javadocs 也没有太大帮助。

标签: jettyembedded-jettyjetty-9

解决方案


首先是一些历史。

回到主要版本 Jetty 9.0.0 期间,有两种主要的方法来处理静态内容:( DefaultHandler和次要的ResourceHandler)。

当主要版本 Jetty 9.4.0 推出时(这是 Jetty 之后的 4 个主要版本版本,然后是 Jetty 9.0.0),努力使这两个组件都使用一个通用的代码库,因此ResourceService创建它是为了标准化静态服务内容在一个地方。现在 和 之间的差异DefaultHandler大大ResourceHandler减少了。(注意:DefaultHandler仍然支持自己的更多特性和各种 HTTP 规范的更多特性

接下来,解决了问题 #539,以允许ResourceHandler(现在DefaultHandler)拥有自定义目录列表。为此HttpOutput.ContentFactory,引入了界面。

newHttpOutput.ContentFactory负责返回HttpContent表示提供的路径(以及可选的最大缓冲区大小配置选项)。

所以这意味着,在这一点上,我们有......

  1. 一个DefaultServlet(或ResourceHandler
  2. 其中有一个ResourceService
  3. 它的内容来自HttpOutput.ContentFactory
  4. 返回的HttpContent可以是静态资源、目录列表或欢迎文件。

当需要发送一段静态内容时,所采取的步骤是......

  1. 请求HttpContent对象HttpOutput.ContentFactory.getContent(path, maxBufferSize)
  2. 请求表示HttpContent可用于发送引用的内容,以下之一(按此顺序):
    1. 如果HttpChannel配置为使用“直接缓冲区”,则要求HttpContent.getDirectBuffer()表示整个内容。(这可能是使用可忽略的堆内存量的内存映射文件)
    2. 要求HttpContent.getIndirectBuffer()代表整个内容。(这可能是使用可忽略的堆内存量的内存映射文件)
    3. 要求HttpContent.getReadableByteChannel()发送内容。
    4. 要求HttpContent.getInputStream()发送内容。
  3. 返回错误指示“未知内容”

HttpOutput.ContentFactoryJetty 9.4.0+ 中有 2 个主要的 present 实现

  • ResourceContentFactory处理瞬态内容(未缓存) - 如果内容超过,则不会返回maxBufferSize原始版本。ByteBuffer
  • CachedContentFactory这将缓存ByteBuffer以前HttpOutput使用返回的各种值。

CachedContentFactory一个isCacheable(Resource)方法被询问以了解提供的资源是否应该进入内存缓存。

关于构造函数CompressedContentFormat[] precompressedFormats中的参数,指的是 .和.CachedContentFactoryResourceServiceCachedContentFactory

典型的,默认的,设置是...

CompressedContentFormat[] precompressedFormats = {
    CompressedContentFormat.GZIP, // gzip compressed
    CompressedContentFormat.BR, // brotli compressed
    new CompressedContentFormat("bzip", ".bz") // bzip compressed
};
CachedContentFactory cachedContentFactory = new CachedContentFactory(parentContentFactory,
   resourceFactory, mimeTypes, useFileMappedBuffers,
   useEtags, precompressedFormats);
resourceService.setContentFactory(cachedContentFactory);

这些precompressedFormats是指在服务器启动之前已预压缩的静态(和不可变)内容。

这允许客户端发送请求说...

GET /css/main.css HTTP/1.1
Host: example.hostname.com
Accept-Encoding: gzip, deflate

并且如果“基本资源”目录有一个${resource.basedir}/css/main.css AND a${resource.basedir}/css/main.css.gz那么响应将从main.css.gz(而不是main.css)提供,从而产生一个 HTTP 响应,如...

HTTP/1.1 200 OK
Date: Wed, 15 May 2019 20:17:22 GMT
Vary: Accept-Encoding
Last-Modified: Wed, 15 May 2019 20:17:22 GMT
Content-Type: text/css
ETag: W/"H/6qTDwA8vsH/6rJoEknqc"
Accept-Ranges: bytes
Content-Length: 11222

推荐阅读