| @@ -1,10 +1,9 @@ | ||
| 1 | 1 | <?php |
| 2 | 2 | namespace Elementor\Core\Files; |
| 3 | 3 | |
| 4 | -use Elementor\Core\Base\Document as Document_Base; | |
| 5 | -use Elementor\Core\Base\Elements_Iteration_Actions\Assets; | |
| 6 | 4 | use Elementor\Core\Common\Modules\Ajax\Module as Ajax; |
| 5 | +use Elementor\Core\Files\CSS\Global_CSS; | |
| 7 | 6 | use Elementor\Core\Files\CSS\Post as Post_CSS; |
| 8 | 7 | use Elementor\Core\Page_Assets\Data_Managers\Base as Page_Assets_Data_Manager; |
| 9 | 8 | use Elementor\Core\Responsive\Files\Frontend; |
| 10 | 9 | use Elementor\Plugin; |
| @@ -25,20 +24,8 @@ | ||
| 25 | 24 | |
| 26 | 25 | private $files = []; |
| 27 | 26 | |
| 28 | 27 | /** |
| 29 | - * Whether `clear_cache()` already ran once during the current request. | |
| 30 | - * | |
| 31 | - * Only consulted when the `e_optimized_css_files` experiment is active, to | |
| 32 | - * collapse the multiple purges a single genuine update can trigger (e.g. | |
| 33 | - * Elementor's own DB upgrade purges at both upgrade-start and | |
| 34 | - * upgrade-complete, on top of the `upgrader_process_complete` hook). | |
| 35 | - * | |
| 36 | - * @var bool | |
| 37 | - */ | |
| 38 | - private $has_cleared_cache_this_request = false; | |
| 39 | - | |
| 40 | - /** | |
| 41 | 28 | * Files manager constructor. |
| 42 | 29 | * |
| 43 | 30 | * Initializing the Elementor files manager. |
| 44 | 31 | * |
| @@ -46,17 +33,16 @@ | ||
| 46 | 33 | * @access public |
| 47 | 34 | */ |
| 48 | 35 | public function __construct() { |
| 49 | 36 | $this->register_actions(); |
| 50 | - $this->register_site_changed_hooks(); | |
| 51 | 37 | } |
| 52 | 38 | |
| 53 | - public function get( $class_name, $args ) { | |
| 54 | - $id = $class_name . '-' . wp_json_encode( $args ); | |
| 39 | + public function get( $class, $args ) { | |
| 40 | + $id = $class . '-' . wp_json_encode( $args ); | |
| 55 | 41 | |
| 56 | 42 | if ( ! isset( $this->files[ $id ] ) ) { |
| 57 | 43 | // Create an instance from dynamic args length. |
| 58 | - $reflection_class = new \ReflectionClass( $class_name ); | |
| 44 | + $reflection_class = new \ReflectionClass( $class ); | |
| 59 | 45 | $this->files[ $id ] = $reflection_class->newInstanceArgs( $args ); |
| 60 | 46 | } |
| 61 | 47 | |
| 62 | 48 | return $this->files[ $id ]; |
| @@ -113,43 +99,22 @@ | ||
| 113 | 99 | * |
| 114 | 100 | * Delete all meta containing files data. And delete the actual |
| 115 | 101 | * files from the upload directory. |
| 116 | 102 | * |
| 117 | - * When the `e_optimized_css_files` experiment is active, repeated calls within | |
| 118 | - * the same request are collapsed into a single purge. | |
| 119 | - * | |
| 120 | 103 | * @since 1.2.0 |
| 121 | 104 | * @access public |
| 122 | 105 | */ |
| 123 | 106 | public function clear_cache() { |
| 124 | - if ( $this->is_optimized_css_files_active() ) { | |
| 125 | - if ( $this->has_cleared_cache_this_request ) { | |
| 126 | - return; | |
| 127 | - } | |
| 128 | - | |
| 129 | - $this->has_cleared_cache_this_request = true; | |
| 130 | - } | |
| 131 | - | |
| 132 | 107 | // Delete files. |
| 133 | 108 | $path = Base::get_base_uploads_dir() . Base::DEFAULT_FILES_DIR . '*'; |
| 134 | 109 | |
| 135 | - $file_paths = glob( $path ); | |
| 136 | - | |
| 137 | - if ( is_array( $file_paths ) ) { | |
| 138 | - foreach ( $file_paths as $file_path ) { | |
| 139 | - // A file that vanished between `glob()` and `unlink()` (e.g. a concurrent | |
| 140 | - // purge) is not an error, so guard with `is_file()` instead of letting | |
| 141 | - // `unlink()` emit a PHP warning. | |
| 142 | - if ( is_file( $file_path ) ) { | |
| 143 | - unlink( $file_path ); | |
| 144 | - } | |
| 145 | - } | |
| 110 | + foreach ( glob( $path ) as $file_path ) { | |
| 111 | + unlink( $file_path ); | |
| 146 | 112 | } |
| 147 | 113 | |
| 148 | 114 | delete_post_meta_by_key( Post_CSS::META_KEY ); |
| 149 | - delete_post_meta_by_key( Document_Base::CACHE_META_KEY ); | |
| 150 | - delete_post_meta_by_key( Assets::ASSETS_META_KEY ); | |
| 151 | 115 | |
| 116 | + delete_option( Global_CSS::META_KEY ); | |
| 152 | 117 | delete_option( Frontend::META_KEY ); |
| 153 | 118 | |
| 154 | 119 | $this->reset_assets_data(); |
| 155 | 120 | |
| @@ -163,12 +128,8 @@ | ||
| 163 | 128 | do_action( 'elementor/core/files/clear_cache' ); |
| 164 | 129 | } |
| 165 | 130 | |
| 166 | 131 | public function clear_custom_image_sizes() { |
| 167 | - if ( ! defined( 'BFITHUMB_UPLOAD_DIR' ) ) { | |
| 168 | - return; | |
| 169 | - } | |
| 170 | - | |
| 171 | 132 | $upload_info = wp_upload_dir(); |
| 172 | 133 | $upload_dir = $upload_info['basedir'] . '/' . BFITHUMB_UPLOAD_DIR; |
| 173 | 134 | |
| 174 | 135 | $path = $upload_dir . '/*'; |
| @@ -225,10 +186,8 @@ | ||
| 225 | 186 | |
| 226 | 187 | add_action( 'update_option_siteurl', function () { |
| 227 | 188 | $this->reset_assets_data(); |
| 228 | 189 | } ); |
| 229 | - | |
| 230 | - add_action( 'rest_api_init', [ $this, 'register_endpoints' ] ); | |
| 231 | 190 | } |
| 232 | 191 | |
| 233 | 192 | /** |
| 234 | 193 | * Reset Assets Data. |
| @@ -239,172 +198,6 @@ | ||
| 239 | 198 | * @access private |
| 240 | 199 | */ |
| 241 | 200 | private function reset_assets_data() { |
| 242 | 201 | delete_option( Page_Assets_Data_Manager::ASSETS_DATA_KEY ); |
| 243 | - } | |
| 244 | - | |
| 245 | - /** | |
| 246 | - * Register site-changed hooks. | |
| 247 | - * | |
| 248 | - * Purge the files cache whenever the site's plugins, theme or Elementor's | |
| 249 | - * own element-cache TTL setting change. Relocated here (from the | |
| 250 | - * `element-cache` module) because the module's Performance-tab setting | |
| 251 | - * does not actually govern this purge - it is a files/assets concern. | |
| 252 | - * | |
| 253 | - * Ungated: this registration is behaviour-neutral regardless of the | |
| 254 | - * `e_optimized_css_files` experiment. | |
| 255 | - * | |
| 256 | - * @since 3.33.0 | |
| 257 | - * @access private | |
| 258 | - */ | |
| 259 | - private function register_site_changed_hooks() { | |
| 260 | - add_action( 'activated_plugin', [ $this, 'clear_cache' ] ); | |
| 261 | - add_action( 'deactivated_plugin', [ $this, 'clear_cache' ] ); | |
| 262 | - add_action( 'switch_theme', [ $this, 'clear_cache' ] ); | |
| 263 | - add_action( 'upgrader_process_complete', [ $this, 'on_upgrader_process_complete' ], 10, 2 ); | |
| 264 | - | |
| 265 | - add_action( 'update_option_elementor_element_cache_ttl', [ $this, 'clear_cache' ] ); | |
| 266 | - } | |
| 267 | - | |
| 268 | - /** | |
| 269 | - * On upgrader process complete. | |
| 270 | - * | |
| 271 | - * Fired by the `upgrader_process_complete` action, which WordPress also fires on | |
| 272 | - * mere update checks, translation updates, and bulk-update submissions with an | |
| 273 | - * empty item queue - none of which changed anything Elementor needs to purge for. | |
| 274 | - * | |
| 275 | - * When the `e_optimized_css_files` experiment is active, those false alarms are | |
| 276 | - * skipped. When inactive, behaviour is unchanged: always purge. | |
| 277 | - * | |
| 278 | - * WordPress passes the `hook_extra` array directly as the second argument to this | |
| 279 | - * action (see `WP_Upgrader::run()`), NOT nested under a `hook_extra` key - do not | |
| 280 | - * confuse this with `WP_Upgrader::$result['hook_extra']` accessed elsewhere. | |
| 281 | - * | |
| 282 | - * @since 3.33.0 | |
| 283 | - * @access public | |
| 284 | - * | |
| 285 | - * @param \WP_Upgrader|false $upgrader The upgrader instance, or false. | |
| 286 | - * @param array $hook_extra The upgrade payload (`action`, `type`, `plugins`/`themes`/`plugin`/`theme`, `translations`, ...). | |
| 287 | - */ | |
| 288 | - public function on_upgrader_process_complete( $upgrader, $hook_extra ) { | |
| 289 | - if ( $this->is_optimized_css_files_active() && ! $this->is_genuine_update( $hook_extra ) ) { | |
| 290 | - return; | |
| 291 | - } | |
| 292 | - | |
| 293 | - $this->clear_cache(); | |
| 294 | - } | |
| 295 | - | |
| 296 | - /** | |
| 297 | - * Whether the `upgrader_process_complete` payload represents a genuine plugin, | |
| 298 | - * theme or core update (as opposed to an update check, a translation update, or | |
| 299 | - * a bulk-update form submitted with nothing selected). | |
| 300 | - * | |
| 301 | - * @since 3.33.0 | |
| 302 | - * @access private | |
| 303 | - * | |
| 304 | - * @param array $hook_extra The upgrade payload passed as the hook's second argument. | |
| 305 | - * | |
| 306 | - * @return bool | |
| 307 | - */ | |
| 308 | - private function is_genuine_update( $hook_extra ) { | |
| 309 | - if ( empty( $hook_extra ) || ! is_array( $hook_extra ) ) { | |
| 310 | - return false; | |
| 311 | - } | |
| 312 | - | |
| 313 | - if ( 'translation' === ( $hook_extra['type'] ?? null ) || ! empty( $hook_extra['translations'] ) ) { | |
| 314 | - return false; | |
| 315 | - } | |
| 316 | - | |
| 317 | - if ( 'update' === ( $hook_extra['action'] ?? null ) && 'core' !== ( $hook_extra['type'] ?? null ) ) { | |
| 318 | - $has_queued_items = ! empty( $hook_extra['plugins'] ) | |
| 319 | - || ! empty( $hook_extra['themes'] ) | |
| 320 | - || ! empty( $hook_extra['plugin'] ) | |
| 321 | - || ! empty( $hook_extra['theme'] ); | |
| 322 | - | |
| 323 | - if ( ! $has_queued_items ) { | |
| 324 | - return false; | |
| 325 | - } | |
| 326 | - } | |
| 327 | - | |
| 328 | - return true; | |
| 329 | - } | |
| 330 | - | |
| 331 | - /** | |
| 332 | - * Whether the `e_optimized_css_files` experiment is active. | |
| 333 | - * | |
| 334 | - * @since 3.33.0 | |
| 335 | - * @access private | |
| 336 | - * | |
| 337 | - * @return bool | |
| 338 | - */ | |
| 339 | - private function is_optimized_css_files_active() { | |
| 340 | - return Plugin::$instance->experiments->is_feature_active( 'e_optimized_css_files' ); | |
| 341 | - } | |
| 342 | - | |
| 343 | - /** | |
| 344 | - * Generate CSS. | |
| 345 | - * | |
| 346 | - * Generates CSS for all posts built with Elementor. | |
| 347 | - * | |
| 348 | - * @since 3.25.0 | |
| 349 | - * @access public | |
| 350 | - */ | |
| 351 | - public function generate_css() { | |
| 352 | - $batch_size = apply_filters( 'elementor/core/files/generate_css/batch_size', 100 ); | |
| 353 | - $processed_posts = 0; | |
| 354 | - | |
| 355 | - while ( true ) { | |
| 356 | - $args = [ | |
| 357 | - 'post_type' => get_post_types(), | |
| 358 | - 'posts_per_page' => $batch_size, | |
| 359 | - 'meta_query' => [ | |
| 360 | - [ | |
| 361 | - 'key' => Document_Base::BUILT_WITH_ELEMENTOR_META_KEY, | |
| 362 | - 'compare' => 'EXISTS', | |
| 363 | - ], | |
| 364 | - ], | |
| 365 | - 'offset' => $processed_posts, | |
| 366 | - 'fields' => 'ids', | |
| 367 | - ]; | |
| 368 | - | |
| 369 | - $query = new \WP_Query( $args ); | |
| 370 | - | |
| 371 | - if ( empty( $query->posts ) ) { | |
| 372 | - break; | |
| 373 | - } | |
| 374 | - | |
| 375 | - foreach ( $query->posts as $post_id ) { | |
| 376 | - $document = Plugin::$instance->documents->get_doc_for_frontend( $post_id ); | |
| 377 | - | |
| 378 | - if ( $document ) { | |
| 379 | - $css_file = Post_CSS::create( $post_id ); | |
| 380 | - $css_file->update(); | |
| 381 | - } | |
| 382 | - } | |
| 383 | - | |
| 384 | - $processed_posts += $batch_size; | |
| 385 | - } | |
| 386 | - | |
| 387 | - /** | |
| 388 | - * Elementor Generate CSS files. | |
| 389 | - * | |
| 390 | - * Fires after Elementor generates new CSS files | |
| 391 | - * | |
| 392 | - * @since 3.25.0 | |
| 393 | - */ | |
| 394 | - do_action( 'elementor/core/files/after_generate_css' ); | |
| 395 | - } | |
| 396 | - | |
| 397 | - public function register_endpoints() { | |
| 398 | - register_rest_route( | |
| 399 | - 'elementor/v1', | |
| 400 | - '/cache', | |
| 401 | - [ | |
| 402 | - 'methods' => \WP_REST_Server::DELETABLE, | |
| 403 | - 'callback' => [ $this, 'clear_cache' ], | |
| 404 | - 'permission_callback' => function() { | |
| 405 | - return current_user_can( 'manage_options' ); | |
| 406 | - }, | |
| 407 | - ] | |
| 408 | - ); | |
| 409 | 202 | } |
| 410 | 203 | } |