HuasoFoundries /
jpgraph
| 1 | <?php |
||
| 2 | |||
| 3 | /** |
||
| 4 | * JPGraph v4.0.3 |
||
| 5 | */ |
||
| 6 | |||
| 7 | namespace Amenadiel\JpGraph\Image; |
||
| 8 | |||
| 9 | use Amenadiel\JpGraph\Util; |
||
| 10 | |||
| 11 | /** |
||
| 12 | * @class ImgStreamCache |
||
| 13 | * // Description: Handle caching of graphs to files. All image output goes |
||
| 14 | * // through this class |
||
| 15 | */ |
||
| 16 | class ImgStreamCache |
||
| 17 | { |
||
| 18 | private $cache_dir; |
||
| 19 | private $timeout = 0; |
||
| 20 | |||
| 21 | // Infinite timeout |
||
| 22 | |||
| 23 | /** |
||
| 24 | * CONSTRUCTOR. |
||
| 25 | * |
||
| 26 | * @param mixed $aCacheDir |
||
| 27 | */ |
||
| 28 | 21 | public function __construct($aCacheDir = CACHE_DIR) |
|
| 29 | { |
||
| 30 | 21 | $this->cache_dir = $aCacheDir; |
|
| 31 | 21 | } |
|
| 32 | |||
| 33 | /** |
||
| 34 | * PUBLIC METHODS. |
||
| 35 | * |
||
| 36 | * @param mixed $aTimeout |
||
| 37 | */ |
||
| 38 | // Specify a timeout (in minutes) for the file. If the file is older then the |
||
| 39 | // timeout value it will be overwritten with a newer version. |
||
| 40 | // If timeout is set to 0 this is the same as infinite large timeout and if |
||
| 41 | // timeout is set to -1 this is the same as infinite small timeout |
||
| 42 | 21 | public function SetTimeout($aTimeout) |
|
| 43 | { |
||
| 44 | 21 | $this->timeout = $aTimeout; |
|
| 45 | 21 | } |
|
| 46 | |||
| 47 | // Output image to browser and also write it to the cache |
||
| 48 | 21 | public function PutAndStream($aImage, $aCacheFileName, $aInline, $aStrokeFileName) |
|
| 49 | { |
||
| 50 | // Check if we should always stroke the image to a file |
||
| 51 | 21 | if (_FORCE_IMGTOFILE) { |
|
| 52 | $aStrokeFileName = _FORCE_IMGDIR . Util\Helper::GenImgName(); |
||
| 53 | } |
||
| 54 | |||
| 55 | 21 | if ($aStrokeFileName != '') { |
|
| 56 | if ($aStrokeFileName == 'auto') { |
||
| 57 | $aStrokeFileName = Util\Helper::GenImgName(); |
||
| 58 | } |
||
| 59 | |||
| 60 | if (file_exists($aStrokeFileName)) { |
||
| 61 | // Wait for lock (to make sure no readers are trying to access the image) |
||
| 62 | $fd = fopen($aStrokeFileName, 'w'); |
||
| 63 | $lock = flock($fd, LOCK_EX); |
||
|
0 ignored issues
–
show
Unused Code
introduced
by
Loading history...
|
|||
| 64 | |||
| 65 | // Since the image write routines only accepts a filename which must not |
||
| 66 | // exist we need to delete the old file first |
||
| 67 | if (!@unlink($aStrokeFileName)) { |
||
| 68 | $lock = flock($fd, LOCK_UN); |
||
| 69 | Util\JpGraphError::RaiseL(25111, $aStrokeFileName); |
||
| 70 | //(" Can't delete cached image $aStrokeFileName. Permission problem?"); |
||
| 71 | } |
||
| 72 | $aImage->Stream($aStrokeFileName); |
||
| 73 | $lock = flock($fd, LOCK_UN); |
||
| 74 | fclose($fd); |
||
| 75 | } else { |
||
| 76 | $aImage->Stream($aStrokeFileName); |
||
| 77 | } |
||
| 78 | |||
| 79 | return; |
||
| 80 | } |
||
| 81 | |||
| 82 | 21 | if ($aCacheFileName != '' && USE_CACHE) { |
|
| 83 | $aCacheFileName = $this->cache_dir . $aCacheFileName; |
||
| 84 | if (file_exists($aCacheFileName)) { |
||
| 85 | if (!$aInline) { |
||
| 86 | // If we are generating image off-line (just writing to the cache) |
||
| 87 | // and the file exists and is still valid (no timeout) |
||
| 88 | // then do nothing, just return. |
||
| 89 | $diff = time() - filemtime($aCacheFileName); |
||
| 90 | if ($diff < 0) { |
||
| 91 | Util\JpGraphError::RaiseL(25112, $aCacheFileName); |
||
| 92 | //(" Cached imagefile ($aCacheFileName) has file date in the future!!"); |
||
| 93 | } |
||
| 94 | if ($this->timeout > 0 && ($diff <= $this->timeout * 60)) { |
||
| 95 | return; |
||
| 96 | } |
||
| 97 | } |
||
| 98 | |||
| 99 | // Wait for lock (to make sure no readers are trying to access the image) |
||
| 100 | $fd = fopen($aCacheFileName, 'w'); |
||
| 101 | $lock = flock($fd, LOCK_EX); |
||
| 102 | |||
| 103 | if (!@unlink($aCacheFileName)) { |
||
| 104 | $lock = flock($fd, LOCK_UN); |
||
| 105 | Util\JpGraphError::RaiseL(25113, $aStrokeFileName); |
||
| 106 | //(" Can't delete cached image $aStrokeFileName. Permission problem?"); |
||
| 107 | } |
||
| 108 | $aImage->Stream($aCacheFileName); |
||
| 109 | $lock = flock($fd, LOCK_UN); |
||
| 110 | fclose($fd); |
||
| 111 | } else { |
||
| 112 | $this->MakeDirs(dirname($aCacheFileName)); |
||
| 113 | if (!is_writeable(dirname($aCacheFileName))) { |
||
| 114 | Util\JpGraphError::RaiseL(25114, $aCacheFileName); |
||
| 115 | //('PHP has not enough permissions to write to the cache file '.$aCacheFileName.'. Please make sure that the user running PHP has write permission for this file if you wan to use the cache system with JpGraph.'); |
||
| 116 | } |
||
| 117 | $aImage->Stream($aCacheFileName); |
||
| 118 | } |
||
| 119 | |||
| 120 | $res = true; |
||
| 121 | // Set group to specified |
||
| 122 | if (CACHE_FILE_GROUP != '') { |
||
|
0 ignored issues
–
show
|
|||
| 123 | $res = @chgrp($aCacheFileName, CACHE_FILE_GROUP); |
||
| 124 | } |
||
| 125 | if (CACHE_FILE_MOD != '') { |
||
|
0 ignored issues
–
show
|
|||
| 126 | $res = @chmod($aCacheFileName, CACHE_FILE_MOD); |
||
| 127 | } |
||
| 128 | if (!$res) { |
||
| 129 | Util\JpGraphError::RaiseL(25115, $aStrokeFileName); |
||
| 130 | //(" Can't set permission for cached image $aStrokeFileName. Permission problem?"); |
||
| 131 | } |
||
| 132 | |||
| 133 | $aImage->Destroy(); |
||
| 134 | if ($aInline) { |
||
| 135 | if ($fh = @fopen($aCacheFileName, 'rb')) { |
||
| 136 | $aImage->Headers(); |
||
| 137 | fpassthru($fh); |
||
| 138 | |||
| 139 | return; |
||
| 140 | } |
||
| 141 | Util\JpGraphError::RaiseL(25116, $aFile); //(" Cant open file from cache [$aFile]"); |
||
|
0 ignored issues
–
show
Comprehensibility
Best Practice
introduced
by
|
|||
| 142 | } |
||
| 143 | 21 | } elseif ($aInline) { |
|
| 144 | 21 | $aImage->Headers(); |
|
| 145 | 21 | $aImage->Stream(); |
|
| 146 | |||
| 147 | 21 | return; |
|
| 148 | } |
||
| 149 | } |
||
| 150 | |||
| 151 | public function IsValid($aCacheFileName) |
||
| 152 | { |
||
| 153 | $aCacheFileName = $this->cache_dir . $aCacheFileName; |
||
| 154 | if (USE_CACHE && file_exists($aCacheFileName)) { |
||
| 155 | $diff = time() - filemtime($aCacheFileName); |
||
| 156 | if ($this->timeout > 0 && ($diff > $this->timeout * 60)) { |
||
| 157 | return false; |
||
| 158 | } |
||
| 159 | |||
| 160 | return true; |
||
| 161 | } |
||
| 162 | |||
| 163 | return false; |
||
| 164 | } |
||
| 165 | |||
| 166 | public function StreamImgFile($aImage, $aCacheFileName) |
||
| 167 | { |
||
| 168 | $aCacheFileName = $this->cache_dir . $aCacheFileName; |
||
| 169 | if ($fh = @fopen($aCacheFileName, 'rb')) { |
||
| 170 | $lock = flock($fh, LOCK_SH); |
||
|
0 ignored issues
–
show
|
|||
| 171 | $aImage->Headers(); |
||
| 172 | fpassthru($fh); |
||
| 173 | $lock = flock($fh, LOCK_UN); |
||
| 174 | fclose($fh); |
||
| 175 | |||
| 176 | return true; |
||
| 177 | } |
||
| 178 | Util\JpGraphError::RaiseL(25117, $aCacheFileName); //(" Can't open cached image \"$aCacheFileName\" for reading."); |
||
| 179 | } |
||
| 180 | |||
| 181 | // Check if a given image is in cache and in that case |
||
| 182 | // pass it directly on to web browser. Return false if the |
||
| 183 | // image file doesn't exist or exists but is to old |
||
| 184 | public function GetAndStream($aImage, $aCacheFileName) |
||
| 185 | { |
||
| 186 | if ($this->Isvalid($aCacheFileName)) { |
||
| 187 | return $this->StreamImgFile($aImage, $aCacheFileName); |
||
| 188 | } else { |
||
| 189 | return false; |
||
| 190 | } |
||
| 191 | } |
||
| 192 | |||
| 193 | /** |
||
| 194 | * PRIVATE METHODS. |
||
| 195 | * |
||
| 196 | * @param mixed $aFile |
||
| 197 | */ |
||
| 198 | |||
| 199 | // Create all necessary directories in a path |
||
| 200 | public function MakeDirs($aFile) |
||
| 201 | { |
||
| 202 | $dirs = []; |
||
| 203 | // In order to better work when open_basedir is enabled |
||
| 204 | // we do not create directories in the root path |
||
| 205 | while ($aFile != '/' && !(file_exists($aFile))) { |
||
| 206 | $dirs[] = $aFile . '/'; |
||
| 207 | $aFile = dirname($aFile); |
||
| 208 | } |
||
| 209 | for ($i = safe_count($dirs) - 1; $i >= 0; --$i) { |
||
| 210 | if (!@mkdir($dirs[$i], 0777)) { |
||
| 211 | Util\JpGraphError::RaiseL(25118, $aFile); //(" Can't create directory $aFile. Make sure PHP has write permission to this directory."); |
||
| 212 | } |
||
| 213 | // We also specify mode here after we have changed group. |
||
| 214 | // This is necessary if Apache user doesn't belong the |
||
| 215 | // default group and hence can't specify group permission |
||
| 216 | // in the previous mkdir() call |
||
| 217 | if (CACHE_FILE_GROUP != '') { |
||
| 218 | $res = true; |
||
|
0 ignored issues
–
show
|
|||
| 219 | $res = @chgrp($dirs[$i], CACHE_FILE_GROUP); |
||
| 220 | $res = @chmod($dirs[$i], 0777); |
||
| 221 | if (!$res) { |
||
| 222 | Util\JpGraphError::RaiseL(25119, $aFile); //(" Can't set permissions for $aFile. Permission problems?"); |
||
| 223 | } |
||
| 224 | } |
||
| 225 | } |
||
| 226 | |||
| 227 | return true; |
||
| 228 | } |
||
| 229 | } // @class Cache |
||
| 230 |