1: <?php
2:
3: /**
4: * This file is part of the Nette Framework (http://nette.org)
5: *
6: * Copyright (c) 2004 David Grudl (http://davidgrudl.com)
7: *
8: * For the full copyright and license information, please view
9: * the file license.txt that was distributed with this source code.
10: */
11:
12: namespace Nette\Http;
13:
14: use Nette;
15:
16:
17: /**
18: * HTTP-specific tasks.
19: *
20: * @author David Grudl
21: *
22: * @property-read bool $modified
23: * @property-read IRequest $request
24: * @property-read IResponse $response
25: */
26: class Context extends Nette\Object
27: {
28: /** @var IRequest */
29: private $request;
30:
31: /** @var IResponse */
32: private $response;
33:
34:
35: public function __construct(IRequest $request, IResponse $response)
36: {
37: $this->request = $request;
38: $this->response = $response;
39: }
40:
41:
42: /**
43: * Attempts to cache the sent entity by its last modification date.
44: * @param string|int|DateTime last modified time
45: * @param string strong entity tag validator
46: * @return bool
47: */
48: public function isModified($lastModified = NULL, $etag = NULL)
49: {
50: if ($lastModified) {
51: $this->response->setHeader('Last-Modified', $this->response->date($lastModified));
52: }
53: if ($etag) {
54: $this->response->setHeader('ETag', '"' . addslashes($etag) . '"');
55: }
56:
57: $ifNoneMatch = $this->request->getHeader('If-None-Match');
58: if ($ifNoneMatch === '*') {
59: $match = TRUE; // match, check if-modified-since
60:
61: } elseif ($ifNoneMatch !== NULL) {
62: $etag = $this->response->getHeader('ETag');
63:
64: if ($etag == NULL || strpos(' ' . strtr($ifNoneMatch, ",\t", ' '), ' ' . $etag) === FALSE) {
65: return TRUE;
66:
67: } else {
68: $match = TRUE; // match, check if-modified-since
69: }
70: }
71:
72: $ifModifiedSince = $this->request->getHeader('If-Modified-Since');
73: if ($ifModifiedSince !== NULL) {
74: $lastModified = $this->response->getHeader('Last-Modified');
75: if ($lastModified != NULL && strtotime($lastModified) <= strtotime($ifModifiedSince)) {
76: $match = TRUE;
77:
78: } else {
79: return TRUE;
80: }
81: }
82:
83: if (empty($match)) {
84: return TRUE;
85: }
86:
87: $this->response->setCode(IResponse::S304_NOT_MODIFIED);
88: return FALSE;
89: }
90:
91:
92: /**
93: * @return IRequest
94: */
95: public function getRequest()
96: {
97: return $this->request;
98: }
99:
100:
101: /**
102: * @return IResponse
103: */
104: public function getResponse()
105: {
106: return $this->response;
107: }
108:
109: }
110: