defined('WPINC') || exit();
const CONF_FILE = '.litespeed_conf.dat';
private static $_instances;
private static $_options = array();
private static $_const_options = array();
private static $_primary_options = array();
private static $_network_options = array();
* Check if need to separate ccss for mobile
protected function _separate_mobile() {
return (wp_is_mobile() || apply_filters('litespeed_is_mobile', false)) && $this->conf(Base::O_CACHE_MOBILE);
public static function debugErr( $msg, $backtrace_limit = false ) {
self::debug($msg, $backtrace_limit);
public static function debug( $msg, $backtrace_limit = false ) {
if (!defined('LSCWP_LOG')) {
if (defined('static::LOG_TAG')) {
$msg = static::LOG_TAG . ' ' . $msg;
Debug2::debug($msg, $backtrace_limit);
* Log an advanced debug message.
public static function debug2( $msg, $backtrace_limit = false ) {
if (!defined('LSCWP_LOG_MORE')) {
if (defined('static::LOG_TAG')) {
$msg = static::LOG_TAG . ' ' . $msg;
Debug2::debug2($msg, $backtrace_limit);
* Check if there is cache folder for that type
public function has_cache_folder( $type ) {
$subsite_id = is_multisite() && !is_network_admin() ? get_current_blog_id() : '';
if (file_exists(LITESPEED_STATIC_DIR . '/' . $type . '/' . $subsite_id)) {
* Maybe make the cache folder if not existed
protected function _maybe_mk_cache_folder( $type ) {
if (!$this->has_cache_folder($type)) {
$subsite_id = is_multisite() && !is_network_admin() ? get_current_blog_id() : '';
$path = LITESPEED_STATIC_DIR . '/' . $type . '/' . $subsite_id;
mkdir($path, 0755, true);
* Delete file-based cache folder for that type
public function rm_cache_folder( $type ) {
if (!$this->has_cache_folder($type)) {
$subsite_id = is_multisite() && !is_network_admin() ? get_current_blog_id() : '';
File::rrmdir(LITESPEED_STATIC_DIR . '/' . $type . '/' . $subsite_id);
// Clear All summary data
self::save_summary(false, false, true);
if ($type == 'ccss' || $type == 'ucss') {
Debug2::debug('[CSS] Cleared ' . $type . ' queue');
} elseif ($type == 'avatar') {
Debug2::debug('[Avatar] Cleared ' . $type . ' queue');
} elseif ($type == 'css' || $type == 'js') {
Debug2::debug('[' . strtoupper($type) . '] Cleared ' . $type . ' queue');
* Build the static filepath
protected function _build_filepath_prefix( $type ) {
$filepath_prefix = '/' . $type . '/';
$filepath_prefix .= get_current_blog_id() . '/';
* Load current queues from data file
* @since 4.3 Elevated to root.cls
public function load_queue( $type ) {
$filepath_prefix = $this->_build_filepath_prefix($type);
$static_path = LITESPEED_STATIC_DIR . $filepath_prefix . '.litespeed_conf.dat';
if (file_exists($static_path)) {
$queue = \json_decode(file_get_contents($static_path), true) ?: array();
* Save current queues to data file
* @since 4.3 Elevated to root.cls
public function save_queue( $type, $list ) {
$filepath_prefix = $this->_build_filepath_prefix($type);
$static_path = LITESPEED_STATIC_DIR . $filepath_prefix . '.litespeed_conf.dat';
$data = \json_encode($list);
File::save($static_path, $data, true);
* Clear all waiting queues
* @since 4.3 Elevated to root.cls
public function clear_q( $type, $silent = false ) {
$filepath_prefix = $this->_build_filepath_prefix($type);
$static_path = LITESPEED_STATIC_DIR . $filepath_prefix . '.litespeed_conf.dat';
if (file_exists($static_path)) {
$msg = __('All QUIC.cloud service queues have been cleared.', 'litespeed-cache');
Admin_Display::success($msg);
* Load an instance or create it if not existed
public static function cls( $cls = false, $unset = false, $data = false ) {
$cls = __NAMESPACE__ . '\\' . $cls;
$cls_tag = strtolower($cls);
if (!isset(self::$_instances[$cls_tag])) {
self::$_instances[$cls_tag] = new $cls($data);
unset(self::$_instances[$cls_tag]);
return self::$_instances[$cls_tag];
public function set_conf( $id, $val = null ) {
foreach ($id as $k => $v) {
self::$_options[$id] = $val;
* Set one primary conf or confs
public function set_primary_conf( $id, $val = null ) {
foreach ($id as $k => $v) {
$this->set_primary_conf($k, $v);
self::$_primary_options[$id] = $val;
public function set_network_conf( $id, $val = null ) {
foreach ($id as $k => $v) {
$this->set_network_conf($k, $v);
self::$_network_options[$id] = $val;
public function set_const_conf( $id, $val ) {
self::$_const_options[$id] = $val;
* Check if is overwritten by const
public function const_overwritten( $id ) {
if (!isset(self::$_const_options[$id]) || self::$_const_options[$id] == self::$_options[$id]) {
return self::$_const_options[$id];
* Check if is overwritten by primary site
public function primary_overwritten( $id ) {
if (!isset(self::$_primary_options[$id]) || self::$_primary_options[$id] == self::$_options[$id]) {
// Network admin settings is impossible to be overwritten by primary
if (is_network_admin()) {
return self::$_primary_options[$id];
* Check if is overwritten by filter.
public function filter_overwritten( $id ) {
$val_setting = $this->conf($id, true);
if( null === $val_setting ){
$filter_name = 'litespeed_conf_load_option_' . $id;
$val_filter = apply_filters($filter_name, $val_setting );
if ($val_setting === $val_filter) {
// If the value is the same, return null.
* Check if is overwritten by code filter
* @deprecated 7.7 Use general filter_overwritten()
public function deprecated_filter_overwritten( $id ) {
$cls_admin_display = Admin_Display::$settings_filters;
// Check if filter name is set.
if(!isset($cls_admin_display[$id]) || !isset($cls_admin_display[$id]['filter']) || is_array($cls_admin_display[$id]['filter']) ){
$val_setting = $this->conf($id, true);
if( null === $val_setting ){
$val_filter = apply_filters($cls_admin_display[$id]['filter'], $val_setting );
if ($val_setting === $val_filter) {
// If the value is the same, return null.
* Check if is overwritten by $SERVER variable
public function server_overwritten( $id ) {
$cls_admin_display = Admin_Display::$settings_filters;
if(!isset($cls_admin_display[$id]['filter'])){
if(!is_array($cls_admin_display[$id]['filter'])) {
$cls_admin_display[$id]['filter'] = array( $cls_admin_display[$id]['filter'] );
foreach( $cls_admin_display[$id]['filter'] as $variable ){
if(isset($_SERVER[$variable])) {
return [ $variable , $_SERVER[$variable] ] ;
* Get the list of configured options for the blog.
public function get_options( $ori = false ) {
return array_merge(self::$_options, self::$_primary_options, self::$_network_options, self::$_const_options);
public function has_conf( $id ) {
return array_key_exists($id, self::$_options);
* If has a primary conf or not
public function has_primary_conf( $id ) {
return array_key_exists($id, self::$_primary_options);
* If has a network conf or not
public function has_network_conf( $id ) {
return array_key_exists($id, self::$_network_options);
public function conf( $id, $ori = false ) {
if (isset(self::$_options[$id])) {
$val = $this->const_overwritten($id);
defined('LSCWP_LOG') && Debug2::debug('[Conf] 🏛️ const option ' . $id . '=' . var_export($val, true));
$val = $this->primary_overwritten($id); // Network Use primary site settings
$val = $this->filter_overwritten($id);
// Network original value will be in _network_options
if (!is_network_admin() || !$this->has_network_conf($id)) {
return self::$_options[$id];
if ($this->has_network_conf($id)) {
$val = $this->const_overwritten($id);
defined('LSCWP_LOG') && Debug2::debug('[Conf] 🏛️ const option ' . $id . '=' . var_export($val, true));
return $this->network_conf($id);
defined('LSCWP_LOG') && Debug2::debug('[Conf] Invalid option ID ' . $id);
public function primary_conf( $id ) {
return self::$_primary_options[$id];
public function network_conf( $id ) {
if (!$this->has_network_conf($id)) {
return self::$_network_options[$id];
* Get called class short name
public static function ori_cls() {
$cls = new \ReflectionClass(get_called_class());
$shortname = $cls->getShortName();
$namespace = str_replace(__NAMESPACE__ . '\\', '', $cls->getNamespaceName() . '\\');
// the left namespace after dropped LiteSpeed
$shortname = $namespace . $shortname;
* Generate conf name for wp_options record
public static function name( $id ) {