1 <?php 2 // This file is part of Moodle - http://moodle.org/ 3 // 4 // Moodle is free software: you can redistribute it and/or modify 5 // it under the terms of the GNU General Public License as published by 6 // the Free Software Foundation, either version 3 of the License, or 7 // (at your option) any later version. 8 // 9 // Moodle is distributed in the hope that it will be useful, 10 // but WITHOUT ANY WARRANTY; without even the implied warranty of 11 // MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 12 // GNU General Public License for more details. 13 // 14 // You should have received a copy of the GNU General Public License 15 // along with Moodle. If not, see <http://www.gnu.org/licenses/>. 16 17 namespace core\local\guzzle; 18 19 /** 20 * Class to define an interface for interacting with objects inside a cache. 21 * 22 * @package core 23 * @copyright 2022 safatshahin <safat.shahin@moodle.com> 24 * @license http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later 25 */ 26 class cache_item { 27 28 /** 29 * Key to be used to store and identify the cache. 30 * 31 * @var string $key cache item key. 32 */ 33 private string $key; 34 35 /** 36 * Actual data of the cache. 37 * 38 * @var mixed $value cache data. 39 */ 40 private $value; 41 42 /** 43 * The expiry of the cache item according to TTL. 44 * 45 * @var \DateTime|null $expiration TTL time for the cache item. 46 */ 47 private ?\DateTime $expiration; 48 49 /** 50 * Confirms if the cache item lookup resulted in a cache hit. 51 * 52 * @var bool $ishit determine the cache lookup. 53 */ 54 private bool $ishit = false; 55 56 /** 57 * Constructor for the cache_item to get the key and module to retrieve or set the cache item. 58 * 59 * @param string $key The key for the current cache item. 60 * @param string $module determines the location of the cache item. 61 * @param int|null $ttl Time to live for the cache item. 62 */ 63 public function __construct(string $key, string $module, ?int $ttl = null) { 64 global $CFG, $USER; 65 $this->key = $key; 66 // Set the directory for cache. 67 $dir = $CFG->cachedir . '/' . $module . '/'; 68 if (file_exists($dir)) { 69 $filename = 'u' . $USER->id . '_' . md5(serialize($key)); 70 // If the cache fine exists, set the value from the cache file. 71 if (file_exists($dir . $filename)) { 72 $this->ishit = true; 73 $this->expires_after($ttl); 74 $fp = fopen($dir . $filename, 'rb'); 75 $size = filesize($dir . $filename); 76 $content = fread($fp, $size); 77 $this->value = unserialize($content); 78 } 79 } 80 } 81 82 /** 83 * Returns the key for the current cache item. 84 * 85 * The key is loaded by the Implementing Library, but should be available to 86 * the higher level callers when needed. 87 * 88 * @return string The key string for this cache item. 89 */ 90 public function get_key(): string { 91 return $this->key; 92 } 93 94 /** 95 * Retrieves the value of the item from the cache associated with this object's key. 96 * 97 * The value returned must be identical to the value originally stored by set(). 98 * 99 * If isHit() returns false, this method MUST return null. Note that null 100 * is a legitimate cache value, so the isHit() method SHOULD be used to 101 * differentiate between "null value was found" and "no value was found." 102 * 103 * @return mixed The value corresponding to this cache item's key, or null if not found. 104 */ 105 public function get() { 106 return $this->is_hit() ? $this->value : null; 107 } 108 109 /** 110 * Confirms if the cache item lookup resulted in a cache hit. 111 * 112 * Note: This method MUST NOT have a race condition between calling isHit() 113 * and calling get(). 114 * 115 * @return bool True if the request resulted in a cache hit. False otherwise. 116 */ 117 public function is_hit():bool { 118 if (!$this->ishit) { 119 return false; 120 } 121 122 if ($this->expiration === null) { 123 return true; 124 } 125 126 return $this->current_time()->getTimestamp() < $this->expiration->getTimestamp(); 127 } 128 129 /** 130 * Sets the value represented by this cache item. 131 * 132 * The $value argument may be any item that can be serialized by PHP, 133 * although the method of serialization is left up to the Implementing 134 * Library. 135 * 136 * @param mixed $value The serializable value to be stored. 137 * @return static The invoked object. 138 */ 139 public function set($value): cache_item { 140 $this->ishit = true; 141 $this->value = $value; 142 143 return $this; 144 } 145 146 /** 147 * Sets the absolute expiration time for this cache item. 148 * 149 * @param \DateTimeInterface|null $expiration 150 * The point in time after which the item MUST be considered expired. 151 * If null is passed explicitly, a default value MAY be used. If none is set, 152 * the value should be stored permanently or for as long as the 153 * implementation allows. 154 * 155 * @return static The called object. 156 */ 157 public function expires_at($expiration): cache_item { 158 if (null === $expiration || $expiration instanceof \DateTimeInterface) { 159 $this->expiration = $expiration; 160 161 return $this; 162 } 163 164 throw new \coding_exception('Invalid argument passed'); 165 } 166 167 /** 168 * Sets the relative expiration time for this cache item. 169 * 170 * @param int|\DateInterval|null $time 171 * The period of time from the present after which the item MUST be considered 172 * expired. An integer parameter is understood to be the time in seconds until 173 * expiration. If null is passed explicitly, a default value MAY be used. 174 * If none is set, the value should be stored permanently or for as long as the 175 * implementation allows. 176 * 177 * @return static The called object. 178 */ 179 public function expires_after($time): cache_item { 180 if (is_int($time) && $time >= 0) { 181 $this->expiration = $this->current_time()->add(new \DateInterval("PT{$time}S")); 182 } else if ($time instanceof \DateInterval) { 183 $this->expiration = $this->current_time()->add($time); 184 } else { 185 $this->expiration = $time; 186 } 187 188 return $this; 189 } 190 191 /** 192 * Gets the current time in the user timezone. 193 * 194 * @return \DateTime 195 */ 196 private function current_time(): \DateTime { 197 return new \DateTime('now', new \DateTimeZone(get_user_timezone())); 198 } 199 }
title
Description
Body
title
Description
Body
title
Description
Body
title
Body