{"id":378251,"date":"2023-05-05T09:39:31","date_gmt":"2023-05-05T09:39:31","guid":{"rendered":"https:\/\/webkul.com\/blog\/?p=378251"},"modified":"2023-11-02T12:33:52","modified_gmt":"2023-11-02T12:33:52","slug":"how-to-use-caching-in-woocommerce-addons","status":"publish","type":"post","link":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/","title":{"rendered":"How to use Caching in WooCommerce Addons"},"content":{"rendered":"\n<div class=\"wk-index-wrap\"><div class=\"block-wrap\">\n<h3 class=\"wp-block-heading index-title\">Introduction<\/h3>\n<\/div><\/div>\n\n\n\n<p>In a WooCommerce addon, we can implement different types of caching. In this article, we\u2019ll explain majorly 3 types of caching in WooCommerce addons. These are Object caching, File caching, and Transient Caching.<\/p>\n\n\n\n<p>In our previous blog, we have already explained the basics of <a href=\"https:\/\/webkul.com\/blog\/caching-in-wordpress\/\">Caching in WordPress.<\/a><\/p>\n\n\n\n<div class=\"wk-index-wrap\"><div class=\"block-wrap\">\n<h3 class=\"wp-block-heading index-title\">1. Object Caching<\/h3>\n<\/div><\/div>\n\n\n\n<p>In <strong>object caching<\/strong> we store our data on an object of a class. As we know an object of a class persists throughout the page while the page is loading. So we can use the result of a query later on a page if we save it on the first fetch request.<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\">&lt;?php\n\/**\n * Object caching class.\n *\n * @package WK_Caching\n *\/\ndefined( &#039;ABSPATH&#039; ) || exit(); \/\/ Exit if access directly.\n\nif ( ! class_exists( &#039;WK_Caching_Object&#039; ) ) {\n\t\/**\n\t * WK_Caching_Object Class.\n\t *\/\n\tclass WK_Caching_Object {\n\t\t\/**\n\t\t * Instance variable\n\t\t *\n\t\t * @var $instance\n\t\t *\/\n\t\tprotected static $instance = null;\n\n\t\t\/**\n\t\t * Instance variable.\n\t\t *\n\t\t * @var $instance\n\t\t *\/\n\t\tprotected $cache = array();\n\n\t\t\/**\n\t\t * Constructor.\n\t\t *\/\n\t\tpublic function __construct() {\n\t\t}\n\n\t\t\/**\n\t\t * Ensures only one instance of this class is loaded or can be loaded.\n\t\t *\n\t\t * @return object\n\t\t *\/\n\t\tpublic static function get_instance() {\n\t\t\tif ( ! static::$instance ) {\n\t\t\t\tstatic::$instance = new self();\n\t\t\t}\n\t\t\treturn static::$instance;\n\t\t}\n\n\t\t\/**\n\t\t * Set the data in object cache on a key with group.\n\t\t *\n\t\t * @param string     $key The key on which data will be saved.\n\t\t * @param mixed      $data Data to save.\n\t\t * @param string|int $data_group The data group.\n\t\t *\/\n\t\tpublic function set( $key, $data, $data_group = &#039;0&#039; ) {\n\t\t\tWK_Caching::log( &quot;Set Cache key: $key, Cache group: $data_group&quot; );\n\t\t\t$this-&gt;cache&#091; $data_group ]&#091; $key ] = $data;\n\t\t}\n\n\t\t\/**\n\t\t * Get the cached data by the key or data group.\n\t\t *\n\t\t * @param string     $key Key of the data.\n\t\t * @param string|int $data_group The data group.\n\t\t *\n\t\t * @return bool|mixed\n\t\t *\/\n\t\tpublic function get( $key, $data_group = &#039;0&#039; ) {\n\t\t\tif ( isset( $this-&gt;cache&#091; $data_group ] ) &amp;&amp; isset( $this-&gt;cache&#091; $data_group ]&#091; $key ] ) &amp;&amp; ! empty( $this-&gt;cache&#091; $data_group ]&#091; $key ] ) ) {\n\t\t\t\treturn $this-&gt;cache&#091; $data_group ]&#091; $key ];\n\t\t\t}\n\n\t\t\treturn false;\n\t\t}\n\n\t\t\/**\n\t\t * Reset the cache by group or complete reset by force param.\n\t\t *\n\t\t * @param string $data_group The data group.\n\t\t * @param bool   $force Reset the complete cache object.\n\t\t *\n\t\t * @return void\n\t\t *\/\n\t\tpublic function reset( $data_group = &#039;0&#039;, $force = false ) {\n\t\t\tif ( true === $force ) {\n\t\t\t\t$this-&gt;cache = array();\n\t\t\t} elseif ( isset( $this-&gt;cache&#091; $data_group ] ) ) {\n\t\t\t\t$this-&gt;cache&#091; $data_group ] = array();\n\t\t\t}\n\t\t}\n\t}\n}<\/pre>\n\n\n\n<p>Here we have created a class &#8216;<strong>WK_Caching_Object<\/strong>&#8216; to store the query result on its object keys.  Then created a class element &#8216;$cache&#8217; of type array to save the result. Finely created 3 methods namely set, get, and reset to handle the CRUD operation.<\/p>\n\n\n\n<div class=\"wk-index-wrap\"><div class=\"block-wrap\">\n<h3 class=\"wp-block-heading index-title\">2. File Caching<\/h3>\n<\/div><\/div>\n\n\n\n<p>In file caching, we store the result of a DB query in some text\/JSON file. While querying the same result we supply the result data from the file rather than DB. And due to faster access of files over DB the Turn Around Time improves significantly.<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\">&lt;?php\n\/**\n * File caching.\n *\n * @package WK_Caching\n *\/\ndefined( &#039;ABSPATH&#039; ) || exit(); \/\/ Exit if access directly.\n\n\/**\n * Including WordPress Filesystem API\n *\/\nrequire_once ABSPATH . &#039;\/wp-admin\/includes\/file.php&#039;;\n\nif ( function_exists( &#039;WP_Filesystem&#039; ) ) {\n\tWP_Filesystem();\n}\n\nif ( class_exists( &#039;WP_Filesystem_Direct&#039; ) ) {\n\t\/**\n\t * WK_Caching_File class.\n\t *\/\n\tclass WK_Caching_File extends WP_Filesystem_Direct {\n\t\t\/**\n\t\t * Upload directory.\n\t\t *\n\t\t * @var mixed\n\t\t *\/\n\t\tprivate $upload_dir;\n\n\t\t\/**\n\t\t * Core directory name.\n\t\t *\n\t\t * @var string\n\t\t *\/\n\t\tprivate $wk_core_dir = &#039;&#039;;\n\n\t\t\/**\n\t\t * Directory name for files in Uploads folder.\n\t\t *\n\t\t * @var string\n\t\t *\/\n\t\tprivate $wk_dir = &#039;wkwc&#039;;\n\n\t\t\/**\n\t\t * Module wise directory name.\n\t\t *\n\t\t * @var string\n\t\t *\/\n\t\tprivate $module_dir_name = &#039;&#039;;\n\n\t\t\/**\n\t\t * __construct\n\t\t *\n\t\t * @param  string $module Module wise directory name.\n\t\t *\n\t\t * @return void\n\t\t *\/\n\t\tpublic function __construct( $module ) {\n\t\t\t$upload            = wp_upload_dir();\n\t\t\t$this-&gt;upload_dir  = $upload&#091;&#039;basedir&#039;];\n\t\t\t$this-&gt;wk_core_dir = $this-&gt;upload_dir . &#039;\/&#039; . $this-&gt;wk_dir;\n\t\t\t$this-&gt;set_module_dir( $module );\n\n\t\t\t$this-&gt;makedirs();\n\t\t}\n\n\t\t\/**\n\t\t * Set Module name.\n\t\t *\n\t\t * @param string $module Module name.\n\t\t *\n\t\t * @return void\n\t\t *\/\n\t\tpublic function set_module_dir( $module ) {\n\t\t\tif ( &#039;&#039; !== $module ) {\n\t\t\t\t$this-&gt;module_dir_name = $module;\n\t\t\t}\n\t\t}\n\n\t\t\/**\n\t\t * Get module directory.\n\t\t *\n\t\t * @return string\n\t\t *\/\n\t\tpublic function get_module_dir() {\n\t\t\treturn $this-&gt;wk_core_dir . &#039;\/&#039; . $this-&gt;module_dir_name;\n\t\t}\n\n\t\t\/**\n\t\t * Create file.\n\t\t *\n\t\t * @param string $file File directory.\n\t\t * @param int    $time Time stamp.\n\t\t * @param string $atime At time.\n\t\t *\n\t\t * @return string\n\t\t *\/\n\t\tpublic function touch( $file, $time = 0, $atime = 0 ) {\n\t\t\t$file = $this-&gt;file_path( $file );\n\n\t\t\treturn parent::touch( $file, $time, $atime );\n\t\t}\n\n\t\t\/**\n\t\t * Get file path.\n\t\t *\n\t\t * @param string $file File name.\n\t\t *\n\t\t * @return string\n\t\t *\/\n\t\tpublic function file_path( $file ) {\n\t\t\t$file_path = $this-&gt;wk_core_dir . &#039;\/&#039; . $this-&gt;module_dir_name . &#039;\/&#039; . $file;\n\n\t\t\treturn $file_path;\n\t\t}\n\n\t\t\/**\n\t\t * Folder path.\n\t\t *\n\t\t * @param string $folder_name Folder name.\n\t\t *\n\t\t * @return string\n\t\t *\/\n\t\tpublic function folder_path( $folder_name ) {\n\t\t\t$folder_path = $this-&gt;wk_core_dir . &#039;\/&#039; . $folder_name . &#039;\/&#039;;\n\n\t\t\treturn $folder_path;\n\t\t}\n\n\t\t\/**\n\t\t * Is readable.\n\t\t *\n\t\t * @param string $file File name.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function is_readable( $file ) {\n\t\t\t$file = $this-&gt;file_path( $file );\n\n\t\t\treturn parent::is_readable( $file );\n\t\t}\n\n\t\t\/**\n\t\t * Is writable.\n\t\t *\n\t\t * @param string $file File name.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function is_writable( $file ) {\n\t\t\t$file = $this-&gt;file_path( $file );\n\n\t\t\treturn parent::is_writable( $file );\n\t\t}\n\n\t\t\/**\n\t\t * Put contents.\n\t\t *\n\t\t * @param string $file File name.\n\t\t * @param string $contents File content.\n\t\t * @param bool   $mode File mode.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function put_contents( $file, $contents, $mode = false ) {\n\t\t\t$file = $this-&gt;file_path( $file );\n\n\t\t\treturn parent::put_contents( $file, $contents, $mode );\n\t\t}\n\n\t\t\/**\n\t\t * Delete file.\n\t\t *\n\t\t * @param string $file File name.\n\t\t * @param bool   $recursive Recursive.\n\t\t * @param string $type File type.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function delete_file( $file, $recursive = false, $type = &#039;f&#039; ) {\n\t\t\t$file = $this-&gt;file_path( $file );\n\n\t\t\treturn parent::delete( $file, $recursive, $type );\n\t\t}\n\n\t\t\/**\n\t\t * Delete all.\n\t\t *\n\t\t * @param string $folder_name Folder name.\n\t\t * @param bool   $recursive Is recursive.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function delete_all( $folder_name, $recursive = false ) {\n\t\t\t$folder_path = $this-&gt;folder_path( $folder_name );\n\n\t\t\treturn parent::rmdir( $folder_path, $recursive );\n\t\t}\n\n\t\t\/**\n\t\t * Gets details for files in a directory or a specific file.\n\t\t *\n\t\t * @since 2.5.0\n\t\t *\n\t\t * @param string $path           Path to directory or file.\n\t\t * @param bool   $include_hidden Optional. Whether to include details of hidden (&quot;.&quot; prefixed) files. Default true.\n\t\t * @param bool   $recursive      Optional. Whether to recursively include file details in nested directories. Default false.\n\t\t *\n\t\t * @return array|false {\n\t\t *     Array of files. False if unable to list directory contents.\n\t\t *\n\t\t *     @type string $name        Name of the file or directory.\n\t\t *     @type string $perms       *nix representation of permissions.\n\t\t *     @type int    $permsn      Octal representation of permissions.\n\t\t *     @type string $owner       Owner name or ID.\n\t\t *     @type int    $size        Size of file in bytes.\n\t\t *     @type int    $lastmodunix Last modified unix timestamp.\n\t\t *     @type mixed  $lastmod     Last modified month (3 letter) and day (without leading 0).\n\t\t *     @type int    $time        Last modified time.\n\t\t *     @type string $type        Type of resource. &#039;f&#039; for file, &#039;d&#039; for directory.\n\t\t *     @type mixed  $files       If a directory and $recursive is true, contains another array of files.\n\t\t * }\n\t\t *\/\n\t\tpublic function dirlist( $path, $include_hidden = true, $recursive = false ) {\n\t\t\tif ( $this-&gt;is_file( $path ) ) {\n\t\t\t\t$limit_file = basename( $path );\n\t\t\t\t$path       = dirname( $path );\n\t\t\t} else {\n\t\t\t\t$limit_file = false;\n\t\t\t}\n\t\t\tif ( ! $this-&gt;is_dir( $path ) ) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\t$dir = dir( $path );\n\t\t\tif ( ! $dir ) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\t$ret = array();\n\n\t\t\twhile ( false !== ( $entry = $dir-&gt;read() ) ) {\n\t\t\t\t$struc         = array();\n\t\t\t\t$struc&#091;&#039;name&#039;] = $entry;\n\n\t\t\t\tif ( &#039;.&#039; == $struc&#091;&#039;name&#039;] || &#039;..&#039; == $struc&#091;&#039;name&#039;] ) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tif ( ! $include_hidden &amp;&amp; &#039;.&#039; == $struc&#091;&#039;name&#039;]&#091;0] ) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\tif ( $limit_file &amp;&amp; $struc&#091;&#039;name&#039;] != $limit_file ) {\n\t\t\t\t\tcontinue;\n\t\t\t\t}\n\n\t\t\t\t$struc&#091;&#039;perms&#039;]       = $this-&gt;gethchmod( $path . &#039;\/&#039; . $entry );\n\t\t\t\t$struc&#091;&#039;permsn&#039;]      = $this-&gt;getnumchmodfromh( $struc&#091;&#039;perms&#039;] );\n\t\t\t\t$struc&#091;&#039;number&#039;]      = false;\n\t\t\t\t$struc&#091;&#039;owner&#039;]       = $this-&gt;owner( $path . &#039;\/&#039; . $entry );\n\t\t\t\t$struc&#091;&#039;group&#039;]       = $this-&gt;group( $path . &#039;\/&#039; . $entry );\n\t\t\t\t$struc&#091;&#039;size&#039;]        = $this-&gt;size( $path . &#039;\/&#039; . $entry );\n\t\t\t\t$struc&#091;&#039;lastmodunix&#039;] = $this-&gt;mtime( $path . &#039;\/&#039; . $entry );\n\t\t\t\t$struc&#091;&#039;lastmod&#039;]     = gmdate( &#039;M j&#039;, $struc&#091;&#039;lastmodunix&#039;] );\n\t\t\t\t$struc&#091;&#039;time&#039;]        = gmdate( &#039;h:i:s&#039;, $struc&#091;&#039;lastmodunix&#039;] );\n\t\t\t\t$struc&#091;&#039;type&#039;]        = $this-&gt;is_dir( $path . &#039;\/&#039; . $entry ) ? &#039;d&#039; : &#039;f&#039;;\n\n\t\t\t\tif ( &#039;d&#039; == $struc&#091;&#039;type&#039;] ) {\n\t\t\t\t\tif ( $recursive ) {\n\t\t\t\t\t\t$struc&#091;&#039;files&#039;] = $this-&gt;dirlist( $path . &#039;\/&#039; . $struc&#091;&#039;name&#039;], $include_hidden, $recursive );\n\t\t\t\t\t} else {\n\t\t\t\t\t\t$struc&#091;&#039;files&#039;] = array();\n\t\t\t\t\t}\n\t\t\t\t}\n\n\t\t\t\t$ret&#091; $struc&#091;&#039;name&#039;] ] = $struc;\n\t\t\t}\n\t\t\t$dir-&gt;close();\n\t\t\tunset( $dir );\n\t\t\treturn $ret;\n\t\t}\n\n\t\t\/**\n\t\t * Delete folder.\n\t\t *\n\t\t * @param string $folder_path Folder path.\n\t\t * @param bool   $recursive Delete recursive.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function delete_folder( $folder_path, $recursive = false ) {\n\t\t\treturn parent::rmdir( $folder_path, $recursive );\n\t\t}\n\n\t\t\/**\n\t\t * If file exists.\n\t\t *\n\t\t * @param string $file File name.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function exists( $file ) {\n\t\t\t$file = $this-&gt;file_path( $file );\n\n\t\t\treturn parent::exists( $file );\n\t\t}\n\n\t\t\/**\n\t\t * Get contents.\n\t\t *\n\t\t * @param string $file File name.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tpublic function get_contents( $file ) {\n\t\t\t$file = $this-&gt;file_path( $file );\n\n\t\t\treturn parent::get_contents( $file );\n\t\t}\n\n\t\t\/**\n\t\t * Make Dirs.\n\t\t *\n\t\t * @return void\n\t\t *\/\n\t\tpublic function makedirs() {\n\t\t\t$module = $this-&gt;module_dir_name;\n\n\t\t\tif ( parent::is_writable( $this-&gt;upload_dir ) ) {\n\t\t\t\tif ( false === $this-&gt;is_dir( $this-&gt;wk_core_dir ) ) {\n\t\t\t\t\t$this-&gt;mkdir( $this-&gt;wk_core_dir );\n\t\t\t\t\t$file_handle = @fopen( trailingslashit( $this-&gt;wk_core_dir ) . &#039;\/.htaccess&#039;, &#039;w&#039; ); \/\/ phpcs:ignore Generic.PHP.NoSilencedErrors.Discouraged, WordPress.WP.AlternativeFunctions.file_system_read_fopen\n\t\t\t\t\tif ( $file_handle ) {\n\t\t\t\t\t\tfwrite( $file_handle, &#039;deny from all&#039; ); \/\/ phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_read_fwrite\n\t\t\t\t\t\tfclose( $file_handle ); \/\/ phpcs:ignore WordPress.WP.AlternativeFunctions.file_system_read_fclose\n\t\t\t\t\t}\n\t\t\t\t}\n\t\t\t\t$dir = $this-&gt;wk_core_dir . &#039;\/&#039; . $module;\n\t\t\t\tif ( false === $this-&gt;is_dir( $dir ) ) {\n\t\t\t\t\t$this-&gt;mkdir( $dir );\n\t\t\t\t}\n\t\t\t}\n\t\t}\n\t}\n}<\/pre>\n\n\n\n<p>To implement the file caching we created a class &#8216;WK_Caching_File&#8217; and extended the WordPress File System Direct class &#8216;WP_Filesystem_Direct&#8217; to override different file-related methods. We set a folder to create inside the &#8216;wp-content\/uploads&#8217; folder.<\/p>\n\n\n\n<p>We put the result in JSON format in the file and delete the file after the result is modified or any DB data changes. In the process we retrieve the data first from the DB store it in a file and then serve it for rendering.<\/p>\n\n\n\n<div class=\"wk-index-wrap\"><div class=\"block-wrap\">\n<h3 class=\"wp-block-heading index-title\">3. Transient Caching<\/h3>\n<\/div><\/div>\n\n\n\n<p>In transient caching, we utilize the concept of transient API to store the result of the DB query in the option table with an expiration time. <\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\">&lt;?php\n\/**\n * Transient caching.\n *\n * @package WK_Caching\n *\/\ndefined( &#039;ABSPATH&#039; ) || exit(); \/\/ Exit if access directly.\n\nif ( ! class_exists( &#039;WK_Caching_Transient&#039; ) ) {\n\t\/**\n\t * WK_Caching_Transient class.\n\t *\/\n\tclass WK_Caching_Transient {\n\t\t\/**\n\t\t * Instance variable\n\t\t *\n\t\t * @var $instance\n\t\t *\/\n\t\tprotected static $instance = null;\n\n\t\t\/**\n\t\t * WKWC_Wallet_Transient_Cache constructor.\n\t\t *\/\n\t\tpublic function __construct() {\n\n\t\t}\n\n\t\t\/**\n\t\t * Ensures only one instance of this class is loaded or can be loaded.\n\t\t *\n\t\t * @return object\n\t\t *\/\n\t\tpublic static function get_instance() {\n\t\t\tif ( ! static::$instance ) {\n\t\t\t\tstatic::$instance = new self();\n\t\t\t}\n\t\t\treturn static::$instance;\n\t\t}\n\n\t\t\/**\n\t\t * Set the transient contents by key and group within page scope.\n\t\t *\n\t\t * @param string $transient_key Transient key.\n\t\t * @param mixed  $transient_value Transient value.\n\t\t * @param string $transient_group Transient group.\n\t\t * @param int    $expiry Default 1 hour.\n\t\t *\/\n\t\tpublic function set( $transient_key, $transient_value, $transient_group = &#039;wk&#039;, $expiry = 3600 ) {\n\t\t\t$option_key = &#039;_wkwc_transient_&#039; . $transient_group . &#039;_&#039; . $transient_key;\n\n\t\t\tWK_Caching::log( &quot;Set transient key: $transient_key, Option key: $option_key, Transient group: $transient_group, Expiry: $expiry&quot; );\n\n\t\t\t$transient_value = array(\n\t\t\t\t&#039;time&#039;  =&gt; time() + (int) $expiry,\n\t\t\t\t&#039;value&#039; =&gt; $transient_value,\n\t\t\t);\n\n\t\t\t$file_writing       = $this-&gt;enable_file_writing();\n\t\t\t$cache_in_transient = $this-&gt;enable_transient_caching();\n\n\t\t\tif ( class_exists( &#039;WK_Caching_File&#039; ) &amp;&amp; true === $file_writing ) {\n\t\t\t\t$file_api = new WK_Caching_File( $transient_group . &#039;-transient&#039; );\n\t\t\t\t$file_api-&gt;touch( $option_key );\n\n\t\t\t\tif ( $file_api-&gt;is_writable( $option_key ) &amp;&amp; $file_api-&gt;is_readable( $option_key ) ) {\n\t\t\t\t\t$transient_value = maybe_serialize( $transient_value );\n\t\t\t\t\t$file_api-&gt;put_contents( $option_key, $transient_value );\n\t\t\t\t\tWK_Caching::log( &quot;Data written in file, transient key: $transient_key, Option key: $option_key, Transient group: $transient_group, Expiry: $expiry&quot; );\n\t\t\t\t} elseif ( $cache_in_transient ) {\n\t\t\t\t\t\/\/ wkwc folder is not writable.\n\t\t\t\t\tWK_Caching::log( &quot;Data written in transient, transient key: $transient_key, Option key: $option_key&quot; );\n\t\t\t\t\tupdate_option( $option_key, $transient_value, false );\n\t\t\t\t}\n\t\t\t} elseif ( $cache_in_transient ) {\n\t\t\t\t\/\/ WK file API method not available.\n\t\t\t\tWK_Caching::log( &quot;Cache Data written in transient, transient key: $transient_key, Option key: $option_key&quot; );\n\t\t\t\tupdate_option( $option_key, $transient_value, false );\n\t\t\t}\n\t\t}\n\n\t\t\/**\n\t\t * Get the transient contents by the transient key or group.\n\t\t *\n\t\t * @param string $transient_key Transient Key.\n\t\t * @param string $transient_group Transient Group.\n\t\t *\n\t\t * @return bool|mixed\n\t\t *\/\n\t\tpublic function get( $transient_key, $transient_group = &#039;wk&#039; ) {\n\t\t\t$option_key = &#039;_wkwc_transient_&#039; . $transient_group . &#039;_&#039; . $transient_key;\n\n\t\t\t$file_writing       = $this-&gt;enable_file_writing();\n\t\t\t$cache_in_transient = $this-&gt;enable_transient_caching();\n\n\t\t\tWK_Caching::log( &quot;Get transient key: $transient_key, Option key: $option_key, Transient group: $transient_group, File writing: $file_writing, Transient caching enabled: $cache_in_transient&quot; );\n\n\t\t\tif ( class_exists( &#039;WK_Caching_File&#039; ) &amp;&amp; true === $file_writing ) {\n\t\t\t\t$file_api = new WK_Caching_File( $transient_group . &#039;-transient&#039; );\n\t\t\t\tif ( $file_api-&gt;is_writable( $option_key ) &amp;&amp; $file_api-&gt;is_readable( $option_key ) ) {\n\t\t\t\t\t$data  = $file_api-&gt;get_contents( $option_key );\n\t\t\t\t\t$data  = maybe_unserialize( $data );\n\t\t\t\t\t$value = $this-&gt;get_value( $option_key, $data );\n\n\t\t\t\t\tif ( false !== $value ) {\n\t\t\t\t\t\tWK_Caching::log( &quot;Data found in file, Transient key: $transient_key, Option key: $option_key&quot; );\n\t\t\t\t\t\treturn $value;\n\t\t\t\t\t}\n\n\t\t\t\t\t$file_api-&gt;delete( $option_key );\n\t\t\t\t}\n\t\t\t}\n\n\t\t\tif ( ! $cache_in_transient ) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\t\/\/ WK file api method is not available.\n\t\t\t$data = get_option( $option_key, false );\n\t\t\tif ( false === $data ) {\n\t\t\t\treturn false;\n\t\t\t}\n\n\t\t\tWK_Caching::log( &quot;Data found in Transient with key: $transient_key, Option key: $option_key&quot; );\n\n\t\t\treturn $this-&gt;get_value( $option_key, $data, true );\n\t\t}\n\n\t\t\/**\n\t\t * Get transient value.\n\t\t *\n\t\t * @param string $transient_key Transient key.\n\t\t * @param string $data JSON data.\n\t\t * @param bool   $db_call is DB call.\n\t\t *\n\t\t * @return bool|string\n\t\t *\/\n\t\tpublic function get_value( $transient_key, $data, $db_call = false ) {\n\t\t\t$current_time = time();\n\t\t\tif ( is_array( $data ) &amp;&amp; isset( $data&#091;&#039;time&#039;] ) ) {\n\t\t\t\tif ( $current_time &gt; (int) $data&#091;&#039;time&#039;] ) {\n\t\t\t\t\tif ( true === $db_call ) {\n\t\t\t\t\t\tdelete_option( $transient_key );\n\t\t\t\t\t}\n\n\t\t\t\t\treturn false;\n\t\t\t\t}\n\t\t\t\treturn $data&#091;&#039;value&#039;];\n\t\t\t}\n\n\t\t\treturn false;\n\t\t}\n\n\t\t\/**\n\t\t * Delete the transient by key.\n\t\t *\n\t\t * @param string $transient_key Transient key.\n\t\t * @param string $transient_group Transient group.\n\t\t *\/\n\t\tpublic function delete_transient( $transient_key, $transient_group = &#039;wk&#039; ) {\n\t\t\t$option_key = &#039;_wkwc_transient_&#039; . $transient_group . &#039;_&#039; . $transient_key;\n\n\t\t\t$file_writing       = $this-&gt;enable_file_writing();\n\t\t\t$cache_in_transient = $this-&gt;enable_transient_caching();\n\n\t\t\tWK_Caching::log( &quot;Deleting transient and file, Option key: $option_key, File writing: $file_writing, Cache in transient: $cache_in_transient&quot; );\n\n\t\t\tif ( class_exists( &#039;WK_Caching_File&#039; ) &amp;&amp; true === $file_writing ) {\n\t\t\t\t$file_api = new WK_Caching_File( $transient_group . &#039;-transient&#039; );\n\n\t\t\t\tif ( $file_api-&gt;exists( $option_key ) ) {\n\t\t\t\t\tWK_Caching::log( &quot;Deleting file: $option_key&quot; );\n\t\t\t\t\t$file_api-&gt;delete_file( $option_key );\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t\/\/ Removing db transient.\n\t\t\tif ( $cache_in_transient ) {\n\t\t\t\tWK_Caching::log( &quot;Deleting transient: $option_key&quot; );\n\t\t\t\tdelete_option( $option_key );\n\t\t\t}\n\t\t}\n\n\t\t\/**\n\t\t * Delete all the transients\n\t\t *\n\t\t * @param string $transient_group Transient Group.\n\t\t *\/\n\t\tpublic function delete_all_transients( $transient_group = &#039;&#039; ) {\n\t\t\tglobal $wpdb;\n\n\t\t\t\/\/ Removing files if file api exist.\n\t\t\t$file_writing       = $this-&gt;enable_file_writing();\n\t\t\t$cache_in_transient = $this-&gt;enable_transient_caching();\n\n\t\t\tWK_Caching::log( &quot;Deleting all transients and files: File writing: $file_writing, Cache in transient: $cache_in_transient&quot; );\n\n\t\t\tif ( class_exists( &#039;WK_Caching_File&#039; ) &amp;&amp; true === $file_writing ) {\n\t\t\t\t$file_api = new WK_Caching_File( $transient_group . &#039;-transient&#039; );\n\t\t\t\t$file_api-&gt;delete_all( $transient_group . &#039;-transient&#039;, true );\n\t\t\t\tWK_Caching::log( &quot;Deleting all file: $transient_group&quot; );\n\t\t\t}\n\n\t\t\tif ( $cache_in_transient ) {\n\t\t\t\t\/\/ Removing db transient.\n\t\t\t\t$query = &quot;DELETE FROM `$wpdb-&gt;options` WHERE `option_name` LIKE &#039;%_wk_transient_{$transient_group}%&#039;&quot;;\n\t\t\t\t$wpdb-&gt;query( $query ); \/\/phpcs:ignore WordPress.DB.PreparedSQL\n\n\t\t\t\tWK_Caching::log( &quot;Deleting all transient: $transient_group&quot; );\n\t\t\t}\n\t\t}\n\n\t\t\/**\n\t\t * Delete all wk plugins transients.\n\t\t *\/\n\t\tpublic function delete_force_transients() {\n\t\t\tglobal $wpdb;\n\n\t\t\t\/\/ Removing files if file api exist.\n\t\t\t$file_writing       = $this-&gt;enable_file_writing();\n\t\t\t$cache_in_transient = $this-&gt;enable_transient_caching();\n\n\t\t\tWK_Caching::log( &quot;Deleting force transients and files: File writing: $file_writing, Cache in transient: $cache_in_transient&quot; );\n\n\t\t\tif ( class_exists( &#039;WK_Caching_File&#039; ) &amp;&amp; true === $file_writing ) {\n\t\t\t\t$file_api = new WK_Caching_File( &#039;wk-transient&#039; );\n\n\t\t\t\t$upload      = wp_upload_dir();\n\t\t\t\t$folder_path = $upload&#091;&#039;basedir&#039;] . &#039;\/wk&#039;;\n\t\t\t\t$file_api-&gt;delete_folder( $folder_path, true );\n\n\t\t\t\tWK_Caching::log( &quot;Deleting force files: $folder_path&quot; );\n\t\t\t}\n\n\t\t\tif ( $cache_in_transient ) {\n\t\t\t\t\/\/ Removing db transient.\n\t\t\t\t$query = &quot;DELETE FROM `$wpdb-&gt;options` WHERE `option_name` LIKE &#039;%_wk_transient_%&#039;&quot;;\n\t\t\t\t$wpdb-&gt;query( $query ); \/\/phpcs:ignore WordPress.DB.PreparedSQL\n\n\t\t\t\tWK_Caching::log( &#039;Deleting force transient&#039; );\n\t\t\t}\n\t\t}\n\n\t\t\/**\n\t\t * Allow to stop file writing.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tprotected function enable_file_writing() {\n\t\t\treturn apply_filters( &#039;_wkwc_enable_file_writing&#039;, true );\n\t\t}\n\n\t\t\/**\n\t\t * Allow to stop file writing.\n\t\t *\n\t\t * @return bool\n\t\t *\/\n\t\tprotected function enable_transient_caching() {\n\t\t\treturn apply_filters( &#039;_wkwc_enable_transient_caching&#039;, true );\n\t\t}\n\t}\n}<\/pre>\n\n\n\n<p>We have created the class &#8216;WK_Caching_Transient&#8217; and added the method set, get, and delete methods for performing CRUD operations. Added File caching at the top and transient caching as a fallback because transient caching involves DB operations.<\/p>\n\n\n\n<div class=\"wk-index-wrap\"><div class=\"block-wrap\">\n<h3 class=\"wp-block-heading index-title\">Implementation<\/h3>\n<\/div><\/div>\n\n\n\n<p>To provide the public methods for using these 3 types of caching we have created a Core class &#8216;WK_Caching_Core&#8217; and provide set, get, and reset methods. <\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\">&lt;?php\n\/**\n * The Core cache class.\n *\n * @package WK_Caching\n *\/\ndefined( &#039;ABSPATH&#039; ) || exit(); \/\/ Exit if access directly.\n\nif ( ! class_exists( &#039;WK_Caching_Core&#039; ) ) {\n\t\/**\n\t * WK_Caching_Core Class.\n\t *\/\n\tclass WK_Caching_Core {\n\t\t\/**\n\t\t * Instance variable\n\t\t *\n\t\t * @var $instance\n\t\t *\/\n\t\tprotected static $instance = null;\n\n\t\t\/**\n\t\t * Constructor.\n\t\t *\/\n\t\tpublic function __construct() {\n\t\t}\n\n\t\t\/**\n\t\t * Ensures only one instance of this class is loaded or can be loaded.\n\t\t *\n\t\t * @return object\n\t\t *\/\n\t\tpublic static function get_instance() {\n\t\t\tif ( ! static::$instance ) {\n\t\t\t\tstatic::$instance = new self();\n\t\t\t}\n\t\t\treturn static::$instance;\n\t\t}\n\n\t\t\/**\n\t\t * Set the data in different cache on a key with group.\n\t\t *\n\t\t * @param string     $key The key on which data will be saved.\n\t\t * @param mixed      $data Data to save.\n\t\t * @param string|int $data_group The data group.\n\t\t * @param int        $expiry Expiry in seconds in case of transient.\n\t\t *\/\n\t\tpublic function set( $key, $data, $data_group, $expiry = 3600 ) {\n\t\t\tWK_Caching::log( &quot;Set Cache key: $key, Cache group: $data_group&quot; );\n\t\t\t$cache_obj = WK_Caching_Object::get_instance();\n\t\t\t$cache_obj-&gt;set( $key, $data, $data_group );\n\n\t\t\t$transient_obj = WK_Caching_Transient::get_instance();\n\t\t\t$transient_obj-&gt;set( $key, $data, $data_group, $expiry );\n\t\t}\n\n\t\t\/**\n\t\t * Get the cached data by the key or data group.\n\t\t *\n\t\t * @param string     $key Key of the data.\n\t\t * @param string|int $data_group The data group.\n\t\t *\n\t\t * @return bool|mixed\n\t\t *\/\n\t\tpublic function get( $key, $data_group ) {\n\t\t\tWK_Caching::log( &quot;Get Cache key: $key, Cache group: $data_group&quot; );\n\t\t\t$cache_obj = WK_Caching_Object::get_instance();\n\t\t\t$data      = $cache_obj-&gt;get( $key, $data_group );\n\n\t\t\tif ( ! empty( $data ) ) {\n\t\t\t\treturn $data;\n\t\t\t}\n\n\t\t\t$transient_obj = WK_Caching_Transient::get_instance();\n\t\t\treturn $transient_obj-&gt;get( $key, $data_group );\n\t\t}\n\n\t\t\/**\n\t\t * Reset the cache by group or complete reset by force param.\n\t\t *\n\t\t * @param string $key The key to reset.\n\t\t * @param string $data_group The data group to rest.\n\t\t * @param bool   $force Reset the complete cache object.\n\t\t *\n\t\t * @return void\n\t\t *\/\n\t\tpublic function reset( $key, $data_group, $force ) {\n\t\t\tWK_Caching::log( &quot;Reset Cache key: $key, Cache group: $data_group, Force: $force&quot; );\n\t\t\t$cache_obj = WK_Caching_Object::get_instance();\n\t\t\t$cache_obj-&gt;reset( $data_group, $force );\n\n\t\t\t$transient_obj = WK_Caching_Transient::get_instance();\n\n\t\t\tif ( $force ) {\n\t\t\t\t$transient_obj-&gt;delete_force_transients();\n\t\t\t} elseif ( empty( $key ) ) {\n\t\t\t\t$transient_obj-&gt;delete_all_transients( $data_group );\n\t\t\t} else {\n\t\t\t\t$transient_obj-&gt;delete_transient( $key, $data_group );\n\t\t\t}\n\t\t}\n\t}\n}<\/pre>\n\n\n\n<p>While setting data, we have set the data in object cache and file caching. If file writing is not enabled we have added transient caching in fallback and also implemented it in the same for reading the data from the cache.<\/p>\n\n\n\n<p>To implement it in our <a href=\"https:\/\/store.webkul.com\/woocommerce-wallet-plugin.html\">WooCommerce Wallet System<\/a> module for getting wallet transactions list data, we created and object of the &#8216;WK_Caching_Core&#8217; class. In the first attempt there is no data in the cache so get the data from the database using SQL queries.<\/p>\n\n\n\n<p>On getting results from SQL queries, set the cache and by default, the result is saved in the object cache followed by file or transient caching depending on whether file caching is enabled or not. Thus on subsequent requests, the result will be served from the caching API.<\/p>\n\n\n\n<pre class=\"EnlighterJSRAW\">\/**\n\t\t * Get Transaction data.\n\t\t *\n\t\t * @param array $args Transaction Data query params.\n\t\t *\n\t\t * @return array\n\t\t *\/\n\t\tpublic function get_transactions( $args ) {\n\t\t\t$wpdb_obj = $this-&gt;wpdb;\n\n\t\t\t$cache_group = empty( $args&#091;&#039;cache_group&#039;] ) ? 0 : $args&#091;&#039;cache_group&#039;];\n\t\t\t$cache_key   = empty( $args&#091;&#039;cache_key&#039;] ) ? &#039;&#039; : $args&#091;&#039;cache_key&#039;];\n\t\t\t$cache_obj   = WK_Caching_Core::get_instance();\n\n\t\t\tif ( ! empty( $cache_key ) ) {\n\t\t\t\t$result = $cache_obj-&gt;get( $cache_key, $cache_group );\n\n\t\t\t\tif ( ! empty( $result ) ) {\n\t\t\t\t\tWKWC_Wallet::log( &quot;Object Cached group: $cache_group, Cached key: $cache_key, result : &quot; . print_r( $result, true ) );\n\t\t\t\t\treturn $result;\n\t\t\t\t}\n\t\t\t}\n\n\t\t\t$sql = &#039;SELECT &#039;;\n\n\t\t\t$sql .= empty( $args&#091;&#039;fields&#039;] ) ? &#039;* &#039; : $args&#091;&#039;fields&#039;];\n\t\t\t$sql .= &quot; FROM {$wpdb_obj-&gt;prefix}wkwc_wallet_transactions WHERE 1=1&quot;;\n\n\t\t\tif ( ! empty( $args&#091;&#039;transaction_id&#039;] ) ) {\n\t\t\t\t$sql .= $wpdb_obj-&gt;prepare( &#039; AND `id`=%d&#039;, esc_sql( $args&#091;&#039;transaction_id&#039;] ) );\n\t\t\t}\n\n\t\t\tif ( ! empty( $args&#091;&#039;customer&#039;] ) ) {\n\t\t\t\t$sql .= $wpdb_obj-&gt;prepare( &#039; AND (`customer`=%d || `sender`=%d)&#039;, esc_sql( $args&#091;&#039;customer&#039;] ), esc_sql( $args&#091;&#039;customer&#039;] ) );\n\t\t\t}\n\n\t\t\tif ( ! empty( $args&#091;&#039;limit&#039;] ) ) {\n\t\t\t\t$sql .= $wpdb_obj-&gt;prepare( &#039; LIMIT %d&#039;, esc_sql( $args&#091;&#039;limit&#039;] ) );\n\t\t\t}\n\n\t\t\tif ( ! empty( $args&#091;&#039;offset&#039;] ) ) {\n\t\t\t\t$sql .= $wpdb_obj-&gt;prepare( &#039; OFFSET %d&#039;, esc_sql( $args&#091;&#039;offset&#039;] ) );\n\t\t\t}\n\n\t\t\t$result = $wpdb_obj-&gt;get_results( $sql, &#039;ARRAY_A&#039; );\n\n\t\t\t$cache_obj-&gt;set( $cache_key, $result, $cache_group );\n\n\t\t\treturn $result;\n\t\t}<\/pre>\n\n\n\n<div class=\"wk-index-wrap\"><div class=\"block-wrap\">\n<h3 class=\"wp-block-heading index-title\">Conclusion: Caching in WooCommerce Addons<\/h3>\n<\/div><\/div>\n\n\n\n<p>That&#8217;s all about the implementation of 3 popular methods of caching in WooCommerce add-ons. We have shown the flow and working of Object caching followed by File caching and Transient caching.<\/p>\n\n\n\n<p>We also saw that object caching is only available for subsequent requests for the same data during a single page loading.<\/p>\n\n\n\n<p>File and Transient caching persists till the expiry time is given or updating\/deleting the data. These caching techniques accomplish our goal to minimize database queries for similar results again and again. <\/p>\n\n\n\n<p>We are implementing these caching methods on our popular plugins like <a href=\"https:\/\/store.webkul.com\/woocommerce-multivendor-marketplace.html\">Multi Vendor Marketplace for WooCommerce<\/a> and <a href=\"https:\/\/store.webkul.com\/woocommerce-point-of-sale.html\">Point of Sale System for WooCommerce<\/a>.<\/p>\n\n\n\n<div class=\"wk-index-wrap\"><div class=\"block-wrap\">\n<h3 class=\"wp-block-heading index-title\">Support<\/h3>\n<\/div><\/div>\n\n\n\n<p>For any technical assistance, please&nbsp;<a href=\"https:\/\/webkul.uvdesk.com\/en\/customer\/create-ticket\/\">raise a ticket<\/a>&nbsp;or reach us by mail at&nbsp;<strong>support@webkul.com<\/strong><\/p>\n\n\n\n<p>Kindly visit the <a href=\"https:\/\/store.webkul.com\/woocommerce-plugins.html\">WooCommerce Addons<\/a> page to see our addons and can also explore our <a href=\"https:\/\/webkul.com\/woocommerce-development\/\">WooCommerce Development Services.<\/a><\/p>\n","protected":false},"excerpt":{"rendered":"<p>Object, File and Transient caching implementation.<\/p>\n","protected":false},"author":498,"featured_media":0,"comment_status":"open","ping_status":"open","sticky":false,"template":"","format":"standard","meta":{"footnotes":""},"categories":[13710,7966,1260],"tags":[3355,3565,7690,2316,14133,1468,1511],"class_list":["post-378251","post","type-post","status-publish","format-standard","hentry","category-caching","category-wordpress-woocommerce","category-wordpress","tag-caching","tag-file","tag-object","tag-optimization","tag-transient","tag-woocommerce","tag-woocommerce-plugins"],"yoast_head":"<!-- This site is optimized with the Yoast SEO plugin v24.5 - https:\/\/yoast.com\/wordpress\/plugins\/seo\/ -->\n<title>How to use Caching in WooCommerce Addons - Webkul Blog %<\/title>\n<meta name=\"description\" content=\"We will show the implementation of 3 types of caching in woocommerce addons: Object caching, File caching and Transient caching.\" \/>\n<meta name=\"robots\" content=\"index, follow, max-snippet:-1, max-image-preview:large, max-video-preview:-1\" \/>\n<link rel=\"canonical\" href=\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/\" \/>\n<meta property=\"og:locale\" content=\"en_US\" \/>\n<meta property=\"og:type\" content=\"article\" \/>\n<meta property=\"og:title\" content=\"How to use Caching in WooCommerce Addons - Webkul Blog %\" \/>\n<meta property=\"og:description\" content=\"We will show the implementation of 3 types of caching in woocommerce addons: Object caching, File caching and Transient caching.\" \/>\n<meta property=\"og:url\" content=\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/\" \/>\n<meta property=\"og:site_name\" content=\"Webkul Blog\" \/>\n<meta property=\"article:publisher\" content=\"https:\/\/www.facebook.com\/webkul\/\" \/>\n<meta property=\"article:published_time\" content=\"2023-05-05T09:39:31+00:00\" \/>\n<meta property=\"article:modified_time\" content=\"2023-11-02T12:33:52+00:00\" \/>\n<meta property=\"og:image\" content=\"https:\/\/cdnblog.webkul.com\/blog\/wp-content\/uploads\/2021\/08\/webkul-og.png\" \/>\n\t<meta property=\"og:image:width\" content=\"1200\" \/>\n\t<meta property=\"og:image:height\" content=\"630\" \/>\n\t<meta property=\"og:image:type\" content=\"image\/png\" \/>\n<meta name=\"author\" content=\"Dinesh Yadav\" \/>\n<meta name=\"twitter:card\" content=\"summary_large_image\" \/>\n<meta name=\"twitter:creator\" content=\"@webkul\" \/>\n<meta name=\"twitter:site\" content=\"@webkul\" \/>\n<meta name=\"twitter:label1\" content=\"Written by\" \/>\n\t<meta name=\"twitter:data1\" content=\"Dinesh Yadav\" \/>\n\t<meta name=\"twitter:label2\" content=\"Est. reading time\" \/>\n\t<meta name=\"twitter:data2\" content=\"3 minutes\" \/>\n<script type=\"application\/ld+json\" class=\"yoast-schema-graph\">{\"@context\":\"https:\/\/schema.org\",\"@graph\":[{\"@type\":\"Article\",\"@id\":\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#article\",\"isPartOf\":{\"@id\":\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/\"},\"author\":{\"name\":\"Dinesh Yadav\",\"@id\":\"https:\/\/webkul.com\/blog\/#\/schema\/person\/a2c513ba357ca0781d2ea37d9da0f076\"},\"headline\":\"How to use Caching in WooCommerce Addons\",\"datePublished\":\"2023-05-05T09:39:31+00:00\",\"dateModified\":\"2023-11-02T12:33:52+00:00\",\"mainEntityOfPage\":{\"@id\":\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/\"},\"wordCount\":668,\"commentCount\":0,\"publisher\":{\"@id\":\"https:\/\/webkul.com\/blog\/#organization\"},\"keywords\":[\"caching\",\"file\",\"object\",\"optimization\",\"transient\",\"WooCommerce\",\"woocommerce plugins\"],\"articleSection\":[\"Caching\",\"WooCommerce\",\"WordPress\"],\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"CommentAction\",\"name\":\"Comment\",\"target\":[\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#respond\"]}]},{\"@type\":\"WebPage\",\"@id\":\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/\",\"url\":\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/\",\"name\":\"How to use Caching in WooCommerce Addons - Webkul Blog %\",\"isPartOf\":{\"@id\":\"https:\/\/webkul.com\/blog\/#website\"},\"datePublished\":\"2023-05-05T09:39:31+00:00\",\"dateModified\":\"2023-11-02T12:33:52+00:00\",\"description\":\"We will show the implementation of 3 types of caching in woocommerce addons: Object caching, File caching and Transient caching.\",\"breadcrumb\":{\"@id\":\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#breadcrumb\"},\"inLanguage\":\"en-US\",\"potentialAction\":[{\"@type\":\"ReadAction\",\"target\":[\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/\"]}]},{\"@type\":\"BreadcrumbList\",\"@id\":\"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#breadcrumb\",\"itemListElement\":[{\"@type\":\"ListItem\",\"position\":1,\"name\":\"Home\",\"item\":\"https:\/\/webkul.com\/blog\/\"},{\"@type\":\"ListItem\",\"position\":2,\"name\":\"How to use Caching in WooCommerce Addons\"}]},{\"@type\":\"WebSite\",\"@id\":\"https:\/\/webkul.com\/blog\/#website\",\"url\":\"https:\/\/webkul.com\/blog\/\",\"name\":\"Webkul Blog\",\"description\":\"\",\"publisher\":{\"@id\":\"https:\/\/webkul.com\/blog\/#organization\"},\"potentialAction\":[{\"@type\":\"SearchAction\",\"target\":{\"@type\":\"EntryPoint\",\"urlTemplate\":\"https:\/\/webkul.com\/blog\/?s={search_term_string}\"},\"query-input\":{\"@type\":\"PropertyValueSpecification\",\"valueRequired\":true,\"valueName\":\"search_term_string\"}}],\"inLanguage\":\"en-US\"},{\"@type\":\"Organization\",\"@id\":\"https:\/\/webkul.com\/blog\/#organization\",\"name\":\"WebKul Software Private Limited\",\"url\":\"https:\/\/webkul.com\/blog\/\",\"logo\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/webkul.com\/blog\/#\/schema\/logo\/image\/\",\"url\":\"https:\/\/cdnblog.webkul.com\/blog\/wp-content\/uploads\/2021\/08\/webkul-logo-accent-sq.png\",\"contentUrl\":\"https:\/\/cdnblog.webkul.com\/blog\/wp-content\/uploads\/2021\/08\/webkul-logo-accent-sq.png\",\"width\":380,\"height\":380,\"caption\":\"WebKul Software Private Limited\"},\"image\":{\"@id\":\"https:\/\/webkul.com\/blog\/#\/schema\/logo\/image\/\"},\"sameAs\":[\"https:\/\/www.facebook.com\/webkul\/\",\"https:\/\/x.com\/webkul\",\"https:\/\/www.instagram.com\/webkul\/\",\"https:\/\/www.linkedin.com\/company\/webkul\",\"https:\/\/www.youtube.com\/user\/webkul\/\"]},{\"@type\":\"Person\",\"@id\":\"https:\/\/webkul.com\/blog\/#\/schema\/person\/a2c513ba357ca0781d2ea37d9da0f076\",\"name\":\"Dinesh Yadav\",\"image\":{\"@type\":\"ImageObject\",\"inLanguage\":\"en-US\",\"@id\":\"https:\/\/webkul.com\/blog\/#\/schema\/person\/image\/\",\"url\":\"https:\/\/secure.gravatar.com\/avatar\/deaa9c46b9b57fbb117ac9a9e51ff5835f9320bd26661dd55bb9a162fc24d905?s=96&d=https%3A%2F%2Fcdnblog.webkul.com%2Fblog%2Fwp-content%2Fuploads%2F2019%2F10%2Fmike.png&r=g\",\"contentUrl\":\"https:\/\/secure.gravatar.com\/avatar\/deaa9c46b9b57fbb117ac9a9e51ff5835f9320bd26661dd55bb9a162fc24d905?s=96&d=https%3A%2F%2Fcdnblog.webkul.com%2Fblog%2Fwp-content%2Fuploads%2F2019%2F10%2Fmike.png&r=g\",\"caption\":\"Dinesh Yadav\"},\"description\":\"Dinesh Yadav, a seasoned Technical Project Manager in the WordPress department, excels in Marketplace Development Services. With deep expertise in WooCommerce modules. He crafts tailored solutions, optimizing performance and ensuring seamless user experiences for complex, scalable online marketplaces.\",\"url\":\"https:\/\/webkul.com\/blog\/author\/dineshyadav-wp\/\"}]}<\/script>\n<!-- \/ Yoast SEO plugin. -->","yoast_head_json":{"title":"How to use Caching in WooCommerce Addons - Webkul Blog %","description":"We will show the implementation of 3 types of caching in woocommerce addons: Object caching, File caching and Transient caching.","robots":{"index":"index","follow":"follow","max-snippet":"max-snippet:-1","max-image-preview":"max-image-preview:large","max-video-preview":"max-video-preview:-1"},"canonical":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/","og_locale":"en_US","og_type":"article","og_title":"How to use Caching in WooCommerce Addons - Webkul Blog %","og_description":"We will show the implementation of 3 types of caching in woocommerce addons: Object caching, File caching and Transient caching.","og_url":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/","og_site_name":"Webkul Blog","article_publisher":"https:\/\/www.facebook.com\/webkul\/","article_published_time":"2023-05-05T09:39:31+00:00","article_modified_time":"2023-11-02T12:33:52+00:00","og_image":[{"width":1200,"height":630,"url":"https:\/\/cdnblog.webkul.com\/blog\/wp-content\/uploads\/2021\/08\/webkul-og.png","type":"image\/png"}],"author":"Dinesh Yadav","twitter_card":"summary_large_image","twitter_creator":"@webkul","twitter_site":"@webkul","twitter_misc":{"Written by":"Dinesh Yadav","Est. reading time":"3 minutes"},"schema":{"@context":"https:\/\/schema.org","@graph":[{"@type":"Article","@id":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#article","isPartOf":{"@id":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/"},"author":{"name":"Dinesh Yadav","@id":"https:\/\/webkul.com\/blog\/#\/schema\/person\/a2c513ba357ca0781d2ea37d9da0f076"},"headline":"How to use Caching in WooCommerce Addons","datePublished":"2023-05-05T09:39:31+00:00","dateModified":"2023-11-02T12:33:52+00:00","mainEntityOfPage":{"@id":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/"},"wordCount":668,"commentCount":0,"publisher":{"@id":"https:\/\/webkul.com\/blog\/#organization"},"keywords":["caching","file","object","optimization","transient","WooCommerce","woocommerce plugins"],"articleSection":["Caching","WooCommerce","WordPress"],"inLanguage":"en-US","potentialAction":[{"@type":"CommentAction","name":"Comment","target":["https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#respond"]}]},{"@type":"WebPage","@id":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/","url":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/","name":"How to use Caching in WooCommerce Addons - Webkul Blog %","isPartOf":{"@id":"https:\/\/webkul.com\/blog\/#website"},"datePublished":"2023-05-05T09:39:31+00:00","dateModified":"2023-11-02T12:33:52+00:00","description":"We will show the implementation of 3 types of caching in woocommerce addons: Object caching, File caching and Transient caching.","breadcrumb":{"@id":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#breadcrumb"},"inLanguage":"en-US","potentialAction":[{"@type":"ReadAction","target":["https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/"]}]},{"@type":"BreadcrumbList","@id":"https:\/\/webkul.com\/blog\/how-to-use-caching-in-woocommerce-addons\/#breadcrumb","itemListElement":[{"@type":"ListItem","position":1,"name":"Home","item":"https:\/\/webkul.com\/blog\/"},{"@type":"ListItem","position":2,"name":"How to use Caching in WooCommerce Addons"}]},{"@type":"WebSite","@id":"https:\/\/webkul.com\/blog\/#website","url":"https:\/\/webkul.com\/blog\/","name":"Webkul Blog","description":"","publisher":{"@id":"https:\/\/webkul.com\/blog\/#organization"},"potentialAction":[{"@type":"SearchAction","target":{"@type":"EntryPoint","urlTemplate":"https:\/\/webkul.com\/blog\/?s={search_term_string}"},"query-input":{"@type":"PropertyValueSpecification","valueRequired":true,"valueName":"search_term_string"}}],"inLanguage":"en-US"},{"@type":"Organization","@id":"https:\/\/webkul.com\/blog\/#organization","name":"WebKul Software Private Limited","url":"https:\/\/webkul.com\/blog\/","logo":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/webkul.com\/blog\/#\/schema\/logo\/image\/","url":"https:\/\/cdnblog.webkul.com\/blog\/wp-content\/uploads\/2021\/08\/webkul-logo-accent-sq.png","contentUrl":"https:\/\/cdnblog.webkul.com\/blog\/wp-content\/uploads\/2021\/08\/webkul-logo-accent-sq.png","width":380,"height":380,"caption":"WebKul Software Private Limited"},"image":{"@id":"https:\/\/webkul.com\/blog\/#\/schema\/logo\/image\/"},"sameAs":["https:\/\/www.facebook.com\/webkul\/","https:\/\/x.com\/webkul","https:\/\/www.instagram.com\/webkul\/","https:\/\/www.linkedin.com\/company\/webkul","https:\/\/www.youtube.com\/user\/webkul\/"]},{"@type":"Person","@id":"https:\/\/webkul.com\/blog\/#\/schema\/person\/a2c513ba357ca0781d2ea37d9da0f076","name":"Dinesh Yadav","image":{"@type":"ImageObject","inLanguage":"en-US","@id":"https:\/\/webkul.com\/blog\/#\/schema\/person\/image\/","url":"https:\/\/secure.gravatar.com\/avatar\/deaa9c46b9b57fbb117ac9a9e51ff5835f9320bd26661dd55bb9a162fc24d905?s=96&d=https%3A%2F%2Fcdnblog.webkul.com%2Fblog%2Fwp-content%2Fuploads%2F2019%2F10%2Fmike.png&r=g","contentUrl":"https:\/\/secure.gravatar.com\/avatar\/deaa9c46b9b57fbb117ac9a9e51ff5835f9320bd26661dd55bb9a162fc24d905?s=96&d=https%3A%2F%2Fcdnblog.webkul.com%2Fblog%2Fwp-content%2Fuploads%2F2019%2F10%2Fmike.png&r=g","caption":"Dinesh Yadav"},"description":"Dinesh Yadav, a seasoned Technical Project Manager in the WordPress department, excels in Marketplace Development Services. With deep expertise in WooCommerce modules. He crafts tailored solutions, optimizing performance and ensuring seamless user experiences for complex, scalable online marketplaces.","url":"https:\/\/webkul.com\/blog\/author\/dineshyadav-wp\/"}]}},"amp_enabled":true,"_links":{"self":[{"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/posts\/378251","targetHints":{"allow":["GET"]}}],"collection":[{"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/posts"}],"about":[{"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/types\/post"}],"author":[{"embeddable":true,"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/users\/498"}],"replies":[{"embeddable":true,"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/comments?post=378251"}],"version-history":[{"count":37,"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/posts\/378251\/revisions"}],"predecessor-version":[{"id":405775,"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/posts\/378251\/revisions\/405775"}],"wp:attachment":[{"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/media?parent=378251"}],"wp:term":[{"taxonomy":"category","embeddable":true,"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/categories?post=378251"},{"taxonomy":"post_tag","embeddable":true,"href":"https:\/\/webkul.com\/blog\/wp-json\/wp\/v2\/tags?post=378251"}],"curies":[{"name":"wp","href":"https:\/\/api.w.org\/{rel}","templated":true}]}}