I am currently working on an architecture where I'd like to maintain separate caches (block cache, collection cache, FPC) for each zipcode. I am making the user select a zipcode at the beginning of the journey, and I wrote plugins/observers for modifying various parts of Magento altogether (like fetching product price, which is different for each zipcode).

Everything seems to be working fine when I have cache disabled. But as I enable the cache, the data is cached for the first user and his/her zipcode, and it shows the same data to all users.

Now what I want is to maintain separate cache copies for each zipcode. I know that Magento keeps a separate cache copy for each store view. I did a lot of digging but couldn't find how Magento manages to do it. If someone could guide me to the classes/function which are responsible for the "store-view-based caching", then I could probably write plugins for those functions to maintain a zipcode based caching system.


I finally solved it by writing a plugin for the Magento\Framework\App\PageCache\Identifier class


<?xml version="1.0"?>
<config xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xsi:noNamespaceSchemaLocation="urn:magento:framework:ObjectManager/etc/config.xsd">
    <type name="Magento\Framework\App\PageCache\Identifier">
        <plugin name="append_zipcode_to_page_cache_identifier" type="Vendor\Module\Plugin\App\PageCache\Identifier"/>

And the plugin class, app/code/Vendor/Module/Plugin/App/PageCache/Indentifier.php


namespace Vendor\Module\Plugin\App\PageCache;

use Magento\Framework\App\Http\Context;
use Magento\Framework\App\PageCache\Identifier as Subject;
use Magento\Framework\App\Request\Http;
use Magento\Framework\Exception\NoSuchEntityException;
use Magento\Framework\Serialize\Serializer\Json;

class Identifier

     * @var Http
    private $request;

     * @var Context
    private $context;

     * @var Json
    private $serializer;

     * Identifier constructor.
     * @param Http $request
     * @param Context $context
     * @param Json $serializer
    public function __construct(
        Http $request,
        Context $context,
        Json $serializer
        $this->request = $request;
        $this->context = $context;
        $this->serializer = $serializer;

     * @param Subject $subject
     * @param string $identifier
     * @return string
    public function aroundGetValue(Subject $subject, $identifier) {
        $data = [
            ?: $this->context->getVaryString(),
            $this->getZipcode() // append zipcode to cache identifier
        return sha1($this->serializer->serialize($data));


    protected function getZipcode() {
        return "123456"; // send the actual zipcode here

For modifying the Block Cache and Model Cache, we can write an after plugin for the Magento\Framework\DataObject\IdentityInterface::getIdentities() method

Like So,


<type name="Magento\Framework\DataObject\IdentityInterface">
    <plugin name="block_and_model_cache_modification" type="Vendor\Module\Plugin\Identity" />



namespace Vendor\Module\Plugin;

use Magento\Framework\DataObject\IdentityInterface as Subject;

class Identity
     * @param Subject $subject
     * @param array $identities
     * @return array
    public function afterGetIdentities(Subject $subject, $identities) 
        $identities[] = "My custom identity"; // append whatever identity you want your cache based on
        return $identities;

Hope that helps.

  • Please would you be able to share how you did your plugin for block cache as mine is not working and I have a similar requirement as yours I need the block cache to be unique per customer
    – Goose84
    Aug 5 '18 at 7:49
  • @Goose84 Edited the answer. Check now
    – Jay Ghosh
    Aug 5 '18 at 10:12

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.