First of all what I know :
Index management is useful for increasing store performance.
EAV
has one disadvantage.it will store data in different tables. So that retrieving data is time-consuming.
So that we will store data into a single table.
when data is changed we will update this single table (nothing but indexing update)
mysql trigger
:
perform some query actions based on some table insert/update/delete.
So Magento using a trigger for example when the price is updating it will store entity_id
into the changelog table.
there is a statement in devdocs for implementing triggers magento2 using Magento/Framework/Mview
.
can you anyone explain the flow of this functionality.
I mean what is view
, action
, processor
etc?
Best Answer
In official documentation: https://devdocs.magento.com/guides/v2.3/extension-dev-guide/indexing.html there is the stement:
MView stands for Materialized View which is a snapshot of the database at a point in time. https://en.wikipedia.org/wiki/Materialized_view Why would we need to duplicate tables. Indexers are costly to run, especially when there is traffic on category pages, customers place orders and admins save products. On product save the cache gets invalidated (off topic). In case of stock indexer, before it ends the execution, it sends the entity ids affected as cache tags to be cleaned (full page cache type). In Magento 2.0 categories ids of purchased products are sent. In Magento 2.1 the product ids are sent.
There are 2 MySQL tables that keep indexer codes and statuses:
indexer_state
mview_state
mview_state
works withUpdate by Schedule
in Admin > System > Indexer ManagementUpdate by Schedule
makes the indexers to be run in cron.There are 3 entries in
Magento_Indexer/etc/contab.xml
:indexer_reindex_all_invalid
is run onindexer_state
. There are is still the need to run 'normal' indexers in cronindexer_update_all_views
is run onmview_state
indexer_clean_all_changelogs
- clears changelogs used bymview_state
Note that cron indexer group tasks run in a separate php process, as declared in
etc/contab_groups.xml
:<use_separate_process>1</use_separate_process>
.Changelog tables are:
[indexer name]_cl
(suffixed with_cl
). e.g.cataloginventory_stock_cl
. If you have indexers set toUpdate by Schedule
and save a product in admin you'll see theentity_id
of that product in this table. It's a big circle, I'm thinking place order or create shipment will add here an entry too.Someone provided an example in official devdoc on how to create new materialized views and what are the interface methods required (disregard the above statement about orders in the snippet bellow):
This will make sense:
//public function execute($ids); Used by mview, allows you to process multiple **entities** in the "Update on schedule" mode }
Where$ids
parameter has the entities ids from*_cl
tables.What is the link between cache invalidation and indexers. Categories pages are now full page cached (built-in full page cache or through Varnish).
There is
\Magento\Indexer\Model\Processor\InvalidateCache::afterUpdateMview
:Back to
Magento\Indexer\Cron\UpdateMview::execute()
:Magento\Indexer\Model\Processor::updateMview()
:In
app/etc/di.xml
there is:Magento\Framework\Mview\ViewInterface
app/etc/di.xml
In
Magento\Framework\Mview\View::update()
there is:If you search in
vendor/
directory forMagento\Framework\Mview\ActionInterface
you'll find for example this:In
\Magento\CatalogInventory\Model\Indexer
:In this class there is:
And it looks like it goes back to 'normal' class of indexers' execute` method which is used by MView.
About cache cleaning after Stock Indexer. When an order is placed on checkout, the quantities are subtracted using this observer:
\Magento\CatalogInventory\Observer\SubtractQuoteInventoryObserver
Further, another observer triggers indexer (but not directly on Mview/Indexer by Schedule):
\Magento\CatalogInventory\Observer\ReindexQuoteInventoryObserver
In Mview case, when the new quantities are subtracted in
SubtractQuoteInventoryObserver
, the MySQL trigger (created for Mview) will insert a row incataloginventory_stock_cl
, marking that a reindex (stock & fulltext) needs to be done to those purchased product ids. There are many MySQL triggers created for Mview. See them all withSHOW TRIGGERS;
.When a product gets out of stock after checkout you'll see 2 rows inserted in that table (Magento saves 2 times stock item in these 2 observers).
When cron runs stock indexer in Mview mode the affected product ids (in M2.1) or categories ids (in M2.0) are sent to cache clean as cache tags. By cache I mean full page cache type. Example:
catalog_product_99
or other cache tag format depending on the Magento version. The same when Mview is not enabled.\Magento\CatalogInventory\Model\Indexer\Stock\AbstractAction::_reindexRows
And Magento_PageCache has observer
\Magento\PageCache\Observer\FlushCacheByTags
that will clean full page cache type by tags. It does it for buil-in full page cache. Varnish related code is in\Magento\CacheInvalidate\Observer\InvalidateVarnishObserver
.There is a free extension that will deny cache clean on still in stock products after customer checkout:
https://github.com/daniel-ifrim/innovo-cache-improve
Cache cleaning only on out of stock products after checkout was introduced in default Magento 2.2.x. See
\Magento\CatalogInventory\Model\Indexer\Stock\CacheCleaner
.I'm thinking the cron execution for indexer in
Admin > Stores > Configuration > Advanced > System > Cron configuration options for group: index
should be set to much more than 1 minute.