I have a query (with the purpose of making a view) which is using a few joins to get each column. Performance degrades quickly (exponentially?) for each set of joins added.
What would be a good approach to make this query faster? Please see comments within the query.
If it helps, this is using the WordPress DB schema.
Here is a screenshot of EXPLAIN
PRODUCTS TABLE
+--+----+ |id|name| +--+----+ |1 |test| +--+----+
METADATA TABLE
+----------+--------+-----+ |product_id|meta_key|value| +----------+--------+-----+ |1 |price |9.99 | +----------+--------+-----+ |1 |sku |ABC | +----------+--------+-----+
TERM_RELATIONSHIPS TABLE
+---------+----------------+ |object_id|term_taxonomy_id| +---------+----------------+ |1 |1 | +---------+----------------+ |1 |2 | +---------+----------------+
TERM_TAXONOMY TABLE
+----------------+-------+--------+ |term_taxonomy_id|term_id|taxonomy| +----------------+-------+--------+ |1 |1 |size | +----------------+-------+--------+ |2 |2 |stock | +----------------+-------+--------+
TERMS TABLE
+-------+-----+ |term_id|name | +-------+-----+ |1 |500mg| +-------+-----+ |2 |10 | +-------+-----+
QUERY
SELECT products.id, products.name, price.value AS price, sku.value AS sku, size.name AS size FROM products /* These joins are performing quickly */ INNER JOIN `metadata` AS price ON products.id = price.product_id AND price.meta_key = 'price' INNER JOIN `metadata` AS sku ON products.id = sku.product_id AND sku.meta_key = 'sku' /* Here's the part that is really slowing it down - I run this chunk about 5 times with different strings to match */ INNER JOIN `term_relationships` AS tr ON products.id = tr.object_id INNER JOIN `term_taxonomy` AS tt ON tr.term_taxonomy_id = tt.term_taxonomy_id AND tt.taxonomy = 'size' INNER JOIN `terms` AS size ON tt.term_id = size.term_id
Using the Entity Framework Profiler, I've received the suggestion to reduce the number of joins and, instead, perform several separate queries: link. Each join requires the database to perform additional work, and the complexity and cost of the query grows rapidly with each additional join.
Joins: If your query joins two tables in a way that substantially increases the row count of the result set, your query is likely to be slow. There's an example of this in the subqueries lesson. Aggregations: Combining multiple rows to produce a result requires more computation than simply retrieving those rows.
Multiple joins can be described as a query containing joins of the same or different types used more than once, thus giving them the ability to combine multiple tables. For this article we will first create a database geeks and then create three tables in it and then run our queries on those tables.
Your performance issue is most likely caused by the join with the 'term_taxonomy' table.
All other joins seems to use the primary key (where you probobly have working indexes on).
So my suggestion is to add a compound index on term_taxonomy_id and term_id (or if you must: taxonomy). Like this:
CREATE UNIQUE INDEX idx_term_taxonomy_id_taxonomy ON term_taxonomy( term_taxonomy_id, taxonomy);
Hope this will help you.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With