了解Etags HTTP标头

时间:2011-02-22 19:19:50

标签: php http outputcache cache-control

我正在使用具有以下功能的缓存库。它试图从第5行的请求中获取eTags,但eTags从未设置过。

REQUEST什么时候会有eTags?你怎么设置它们?

感谢。

public function isNotModified(Request $request)
{
    $lastModified = $request->headers->get('If-Modified-Since');

    $notModified = false;
    if ($etags = $request->getEtags()) {
        $notModified = (in_array($this->getEtag(), $etags) || in_array('*', $etags)) && (!$lastModified || $this->headers->get('Last-Modified') == $lastModified);
    } elseif ($lastModified) {
        $notModified = $lastModified == $this->headers->get('Last-Modified');
    }

    if ($notModified) {
        $this->setNotModified();
    }

    return $notModified;
}

1 个答案:

答案 0 :(得分:2)

ETag header field仅用于回复:

  

ETag 响应标头字段提供所请求变体的实体标签的当前值。

getEtags方法可能是If-None-Match header field

中的标记
  

如果任何实体标签与该资源上对类似GET请求(没有 If-None-Match 标头)的响应中返回的实体的实体标签匹配,或者如果给出“*”且该资源存在任何当前实体,则服务器不得执行所请求的方法,除非需要这样做,因为资源的修改日期与中提供的修改日期不匹配请求中的If-Modified-Since 标头字段。相反,如果请求方法是GET或HEAD,服务器应该响应304(未修改)响应,包括匹配的其中一个实体的缓存相关头字段(特别是 ETag )。对于所有其他请求方法,服务器必须以状态412响应(前提条件失败)。

这似乎与给定代码完全匹配(我重新排列了第一句符合代码):

//   the server MUST NOT perform the requested method
$notModified = (
    //   if any of the entity tags match the entity tag of the entity that
    //   would have been returned in the response to a similar GET request
    //   (without the If-None-Match header) on that resource
    in_array($this->getEtag(), $etags)
    //   or if "*" is given and any current entity exists for that resource
    || in_array('*', $etags))
    //   unless required to do so because the resource's modification
    //   date fails to match that supplied in an If-Modified-Since header
    //   field in the request.
    && (!$lastModified || $this->headers->get('Last-Modified') == $lastModified);

最后一个表达式(!$lastModified || $this->headers->get('Last-Modified') == $lastModified)相当于!($lastModified && $this->headers->get('Last-Modified') != $lastModified)更适合最后一句话部分。