Imagine this scenario:
I have three tables in my database: Products, Users and Likes, the latter representing a relation between a Product and a User. Now I have a query, which joins Products with the Likes table, counting how many Likes a Product got.
In fact, I need the information about the count much more often than the actual users and I want to use the query above as part of a greater query in a view. Is it possible to optimize the query or the view so that MySQL somehow caches the result of the count query above?
I don’t know of a way to do that with mysql (but I mainly use postgres, so it might be possible and I just don’t know). I would suggest two options:
likes_countcolumn to yourProductstable, createAFTER INSERTandAFTER DELETEtriggers on theLikestable (assuming you never UPDATE that table) that increases the like count of a product when a new row is inserted to theLikestable and decreases it when a row is deleted. Than, add a cronjob that executesUPDATE Products SET likes_count=(SELECT COUNT(1) FROM Likes WHERE product_id = Products.id)once in a while to make sure the values are really up-to-date – maintaining the counts with triggers is never 100% accurate.CREATE VIEW Products_Likes_View AS SELECT product_id, COUNT(*) AS likes_count FROM Likes GROUP BY product_id;, and create a cache table, something likeCREATE TABLE Products_Likes_Cache (product_id INTEGER PRIMARY KEY, likes_count INTEGER NOT NULL);. Than, add a cronjob that executesBEGIN; TRUNCATE Products_Likes_Cache; INSERT INTO Products_Likes_Cache SELECT * FROM Products_Likes_View; COMMIT;which’ll sync the cache table with the up-to-date information from the view. Than, if you need accurate results, you can get the data directly from the view. Otherwise, use the cache table.If you go with the first option, the triggers should look something like this (my MySQL skills are a bit rusty, I might be off with the exact syntax):