• Resolved mindthetrash

    (@mindthetrash)


    We’ve created a custom endpoint for API v2

    /**  * Register the WooCommerce endpoints so they will be cached.*/
    function wprc_add_wc_endpoints( $allowed_endpoints ) {
         if ( ! isset( $allowed_endpoints[ 'wc/v2' ] ) || ! in_array( 'products', $allowed_endpoints[ 'wc/v2' ] ) ) {
             $allowed_endpoints[ 'wc/v2' ][] = 'products';     }
         return $allowed_endpoints; }
    add_filter( 'wp_rest_cache/allowed_endpoints', 'wprc_add_wc_endpoints', 10, 1);
    

    set the header authorization and added “authorization” in the plugin

    function wprc_add_cacheable_request_headers( $cacheable_headers ) {
         $cacheable_headers['wc/v2/products'] = 'authorization';
         return $cacheable_headers; }
    add_filter('wp_rest_cache/cacheable_request_headers', 'wprc_add_cacheable_request_headers', 10, 1);
    

    set the object type

    function wc_determine_object_type( $type, $cache_key, $data, $uri ) {
            if ( '/wp-json/wc/v2/products' === substr( $uri, 0, 23 ) ) {
                    return 'product';
            }
    
            return $type;
    }
    add_filter( 'wp_rest_cache/determine_object_type', 'wc_determine_object_type', 10, 4 );
    

    set the cache to be flushed when a product is updated

    function wc_flush_product_caches() {
            \WP_REST_Cache_Plugin\Includes\Caching\Caching::get_instance()->delete_cache_by_endpoint( '/wp-json/wc/v2/products', \WP_REST_Cache_Plugin\Includes\Caching\Caching::FLUSH_LOOSE );
    }
    
    add_action( 'woocommerce_update_product', 'wc_flush_product_caches', 10 );
    

    Everything is working great.
    As of now, if one product is updated the whole cache is flushed. We would like the cache to only be flushed on the product that was updated, and not all the products in the cache.

    Is that somehow possible?

Viewing 1 replies (of 1 total)
  • Plugin Author Richard Korthuis

    (@rockfire)

    Hi @mindthetrash

    Thank you for using our plugin!

    Yes that is possible, some more coding. First of all you would have to process the relations within a cache. An endpoint can contain multiple records and if one of those records changes, you would want that cache to be flushed also. So you would have to use the wp_rest_cache/process_cache_relations action, for instance like this:

    /**
     * Process cache relations.
     *
     * @param int    $cache_id The row id of the current cache.
     * @param mixed  $data The data that is to be cached.
     * @param string $object_type Object type.
     * @param string $uri The requested URI.
     */
    function wprc_process_cache_relations( $cache_id, $data, $object_type, $uri ) {
    	if ( ! isset( $data['data'] ) || false === strpos( $uri, '/namespace/v2/custom_endpoint' ) ) {
    		return;
    	}
    
    	$caching = \WP_Rest_Cache_Plugin\Includes\Caching\Caching::get_instance();
    
    	if ( isset( $data['data']['id'] ) ) {
    		// Single item.
    		$caching->insert_cache_relation( $cache_id, $data['data']['id'], 'my-post-type' );
    		return;
    	}
    
    	foreach ( $data['data'] as $record ) {
    		if ( ! is_array( $record ) || ! isset( $record['id'] ) ) {
    			continue;
    		}
    		$caching->insert_cache_relation( $cache_id, $record['id'], 'my-post-type' );
    	}
    }
    
    add_action( 'wp_rest_cache/process_cache_relations', 'wprc_process_cache_relations', 10, 4 );

    Now you can change your function wc_flush_product_caches to use the function delete_related_caches(...) like this:

    \WP_REST_Cache_Plugin\Includes\Caching\Caching::get_instance()->delete_related_caches( $post_id, $object_type );

Viewing 1 replies (of 1 total)
  • The topic ‘Custom API endpoint – Clear cache only on updated product’ is closed to new replies.