model = sl($this->modelClass); $this->dataKey = $key; $this->validPeriod = (int) $timeout; $this->callback = $callback; $this->assocJsonDecode = $assoc; $this->initLoadProcess($forceReload); } /** * wrapper for loading data process * @param bool $forceReload */ protected function initLoadProcess($forceReload = false) { if ($forceReload) { $this->updateRemoteData(); return; } $this->loadDataFromDb(); if (!$this->isDataValid()) { $this->updateRemoteData(); } } /** * loads remote data and updates to local storage */ protected function updateRemoteData() { $data = $this->loadRemoteData(); $time = \time(); $this->updateDbCache($data, $time); $this->data = $data; $this->lastDataUpdate = $time; } /** * updates data in database */ protected function updateDbCache($data, $time) { $dbData = $this->model->where('setting', $this->dataKey)->first(); if ($dbData) { $dbData->update(['value' => json_encode($data)]); } else { $this->model->create([ 'setting' => $this->dataKey, 'value' => json_encode($data) ]); } $dbDataTime = $this->model->where('setting', $this->dataKey . '_lastDataUpdate')->first(); if ($dbDataTime) { $dbDataTime->update(['value' => $time]); } else { $this->model->create([ 'setting' => $this->dataKey . '_lastDataUpdate', 'value' => $time ]); } } /** * using callback function to load data from custom source */ protected function loadRemoteData() { if (!is_callable($this->callback)) { throw new Exception(ErrorCodesLib::CORE_CDB_000001, ['callback' => $this->callback]); } $data = call_user_func_array($this->callback, []); return $data; } /** * returns loaded data */ public function getData() { return $this->data; } /** * static wrpper for creating instance and retriving data */ public static function loadData($key, $callback, $timeout = 300, $assoc = false, $forceReload = false) { $loader = new DatabaseCache($key, $callback, $timeout, $assoc, $forceReload); return $loader->getData(); } /** * loads data stored in DB */ protected function loadDataFromDb() { $dbData = $this->model->where('setting', $this->dataKey)->first(); if (!$dbData) { return false; } $this->data = json_decode($dbData->value, $this->assocJsonDecode); $lastUpdate = $this->model->where('setting', $this->dataKey . '_lastDataUpdate')->first(); if ($lastUpdate) { $this->lastDataUpdate = (int) $lastUpdate->value; } } /** * Check if data is still befeore renewal time */ protected function isDataValid() { if (!$this->data || !$this->lastDataUpdate) { return false; } if (time() > ($this->lastDataUpdate + $this->validPeriod)) { return false; } return true; } }