Execute EXPLAIN em uma consulta SQL para verificar se o PolarDB utiliza índices colunares em memória (IMCIs) para acelerá-la. Consultas aceleradas por IMCI geram um formato de plano de execução distinto, facilmente identificável.
Pré-requisitos
Antes de começar, verifique se você tem:
Um nó de armazenamento colunar somente leitura adicionado ao cluster PolarDB for MySQL
IMCIs criados nas tabelas referenciadas nas consultas
Um endpoint de cluster com Transactional/Analytical Processing Splitting ativado
Como ler planos de execução IMCI
Quando uma consulta é executada no nó de armazenamento colunar usando IMCIs, a saída do EXPLAIN muda do formato de tabela padrão do MySQL para um formato de árvore horizontal.
Sinal principal: Procure IMCI Execution Plan na coluna Extra Info da primeira linha. A presença dessa string indica que a consulta está sendo acelerada por IMCIs. Se a saída utilizar o formato de tabela padrão sem esse cabeçalho, a consulta estará sendo executada em índices de armazenamento de linhas.
Consulta SQL utilizada nos exemplos abaixo:
EXPLAIN SELECT l_orderkey, SUM(l_extendedprice * (1 - l_discount)) AS revenue, o_orderdate, o_shippriority
FROM customer, orders, lineitem
WHERE c_mktsegment = 'BUILDING'
AND c_custkey = o_custkey
AND l_orderkey = o_orderkey
AND o_orderdate < date '1995-03-24'
AND l_shipdate > date '1995-03-24'
GROUP BY l_orderkey, o_orderdate, o_shippriority
ORDER BY revenue DESC, o_orderdate;
Plano de execução de armazenamento de linhas — formato de tabela padrão do MySQL, sem aceleração IMCI:
+----+-------------+----------+------------+------+--------------------+------------+---------+-----------------------------+--------+----------+----------------------------------------------+
| id | select_type | table | partitions | type | possible_keys | key | key_len | ref | rows | filtered | Extra |
+----+-------------+----------+------------+------+--------------------+------------+---------+-----------------------------+--------+----------+----------------------------------------------+
| 1 | SIMPLE | customer | NULL | ALL | PRIMARY | NULL | NULL | NULL | 147630 | 10.00 | Using where; Using temporary; Using filesort |
| 1 | SIMPLE | orders | NULL | ref | PRIMARY,ORDERS_FK1 | ORDERS_FK1 | 4 | tpch100g.customer.C_CUSTKEY | 14 | 33.33 | Using where |
| 1 | SIMPLE | lineitem | NULL | ref | PRIMARY | PRIMARY | 4 | tpch100g.orders.O_ORDERKEY | 4 | 33.33 | Using where |
+----+-------------+----------+------------+------+--------------------+------------+---------+-----------------------------+--------+----------+----------------------------------------------+
3 rows in set, 1 warning (0.00 sec)
Plano de execução de armazenamento colunar — formato de árvore horizontal, aceleração IMCI confirmada:
+----+----------------------------+----------+--------+--------+-----------------------------------------------------------------------------+
| ID | Operator | Name | E-Rows | E-Cost | Extra Info |
+----+----------------------------+----------+--------+--------+-----------------------------------------------------------------------------+
| 1 | Select Statement | | | | IMCI Execution Plan (max_dop = 4, max_query_mem = 858993459) |
| 2 | └─Sort | | | | Sort Key: revenue DESC,o_orderdate ASC |
| 3 | └─Hash Groupby | | | | Group Key: (lineitem.L_ORDERKEY, orders.O_ORDERDATE, orders.O_SHIPPRIORITY) |
| 4 | └─Hash Join | | | | Join Cond: orders.O_ORDERKEY = lineitem.L_ORDERKEY |
| 5 | ├─Hash Join | | | | Join Cond: customer.C_CUSTKEY = orders.O_CUSTKEY |
| 6 | │ ├─Table Scan | customer | | | Cond: (C_MKTSEGMENT = "BUILDING") |
| 7 | │ └─Table Scan | orders | | | Cond: (O_ORDERDATE < 03/24/1995) |
| 8 | └─Table Scan | lineitem | | | Cond: (L_SHIPDATE > 03/24/1995) |
+----+----------------------------+----------+--------+--------+-----------------------------------------------------------------------------+
8 rows in set (0.01 sec)
Verifique a cobertura do IMCI antes de executar consultas
Um IMCI acelera uma consulta apenas quando cobre todas as colunas referenciadas nela. Se alguma tabela ou coluna não estiver coberta, o IMCI não terá efeito.
Para verificar se os IMCIs do cluster cobrem todas as colunas de uma instrução SQL, chame dbms_imci.check_columnar_index():
CALL dbms_imci.check_columnar_index('SELECT COUNT(*) FROM t1 WHERE t1.a > 1');
Se todas as colunas estiverem cobertas, o procedimento armazenado retornará um conjunto de resultados vazio.
Caso alguma coluna não esteja coberta, o procedimento armazenado retornará as tabelas e colunas descobertas. Crie IMCIs para essas colunas antes de executar a consulta.
Para obter a instrução DDL necessária para criar um IMCI que cubra todas as colunas de uma consulta, chame dbms_imci.columnar_advise():
dbms_imci.columnar_advise('<query_string>');
Para mais informações, consulte Verificar se um IMCI foi criado para uma tabela em uma instrução SQL e Obter a instrução DDL usada para criar um IMCI.
Perguntas frequentes
Por que minha consulta não usa IMCIs?
Uma consulta utiliza aceleração IMCI somente quando as quatro condições a seguir são atendidas:
Existe um nó de armazenamento colunar somente leitura no cluster
Existem IMCIs em todas as tabelas referenciadas na consulta
O custo estimado de execução da consulta excede o limiar configurado
A consulta é roteada para o nó de armazenamento colunar somente leitura
Siga as etapas abaixo para identificar qual condição não está sendo atendida.
Etapa 1: Verifique se a consulta chega ao nó de armazenamento colunar
Confira se o nó de armazenamento colunar somente leitura está listado nos selected nodes do endpoint de cluster. Utilize o SQL Explorer para confirmar se a consulta foi realmente roteada para esse nó.
O PolarProxy roteia uma consulta para o nó de armazenamento colunar apenas quando:
A conexão da consulta ocorre pelo cluster endpoint
O Transactional/Analytical Processing Splitting está ativado para o endpoint de cluster
O custo estimado da consulta excede o limiar definido por
loose_imci_ap_threshold(ouloose_cost_threshold_for_imciem versões anteriores do mecanismo)
Para forçar o roteamento de uma consulta ao nó de armazenamento colunar durante testes, adicione a dica /*FORCE_IMCI_NODES*/ antes da palavra-chave SELECT:
/*FORCE_IMCI_NODES*/EXPLAIN SELECT COUNT(*) FROM t1 WHERE t1.a > 1;
Alternativamente, crie um endpoint personalizado associado ao nó de armazenamento colunar para garantir o roteamento. Para mais informações, consulte Distribuição de solicitações baseada em HTAP entre nós de armazenamento de linhas e colunar.
O parâmetroloose_imci_ap_thresholdsubstitui oloose_cost_threshold_for_imcinas versões menores do mecanismo 8.0.1.1.39 ou posterior, ou 8.0.2.2.23 ou posterior.
Etapa 2: Verifique se o custo da consulta atende ao limiar
No nó de armazenamento colunar, o otimizador estima o custo de execução da consulta. Se a estimativa exceder o limiar definido por loose_imci_ap_threshold ou cost_threshold_for_imci, o otimizador utilizará IMCIs. Caso contrário, ele recorrerá aos índices de armazenamento de linhas.
Se o EXPLAIN mostrar um plano de armazenamento de linhas mesmo após a consulta chegar ao nó de armazenamento colunar, compare o custo estimado com o limiar:
-- View the execution plan
EXPLAIN SELECT * FROM t1;
-- Get the estimated cost of the previous query
SHOW STATUS LIKE 'Last_query_cost';
Se a conexão for feita pelo endpoint de cluster, adicione/*ROUTE_TO_LAST_USED*/para ler o custo do nó correto:/*ROUTE_TO_LAST_USED*/SHOW STATUS LIKE 'Last_query_cost';
Se o custo estimado estiver abaixo do limiar, ajuste o parâmetro loose_imci_ap_threshold ou loose_cost_threshold_for_imci, ou substitua o limiar para uma única consulta usando uma dica:
/*FORCE_IMCI_NODES*/EXPLAIN SELECT /*+ SET_VAR(cost_threshold_for_imci=0) */ COUNT(*) FROM t1 WHERE t1.a > 1;
Para mais informações, consulte Especificar os limiares para distribuição automática de solicitações.
Etapa 3: Verifique a cobertura de colunas do IMCI
Chame dbms_imci.check_columnar_index() para confirmar se os IMCIs cobrem todas as tabelas e colunas da consulta:
CALL dbms_imci.check_columnar_index('SELECT COUNT(*) FROM t1 WHERE t1.a > 1');
Se o procedimento armazenado retornar tabelas ou colunas descobertas, crie IMCIs para elas. Um conjunto de resultados vazio indica que todas as colunas estão cobertas.
Etapa 4: Verifique os limites de uso do IMCI
Os IMCIs não suportam alguns padrões de consulta. Revise os Limites de uso do IMCI para confirmar se a consulta é elegível.
Se a consulta ainda não utilizar IMCIs após a conclusão de todas as quatro etapas, consulte as Melhores práticas do IMCI ou entre em contato com o suporte.
Como criar o IMCI adequado para uma consulta?
Uma consulta utiliza um IMCI apenas quando este cobre todas as colunas referenciadas. Use dbms_imci.columnar_advise() para gerar a instrução DDL necessária para criar um IMCI que cubra todas as colunas de uma determinada consulta:
dbms_imci.columnar_advise('<query_string>');
Para gerar instruções DDL para um lote de consultas, utilize dbms_imci.columnar_advise_begin(), dbms_imci.columnar_advise() e dbms_imci.columnar_advise_end() em conjunto. Para mais informações, consulte Obter em lote as instruções DDL usadas para criar IMCIs.
Se as colunas de uma consulta não estiverem totalmente cobertas, use ALTER TABLE para adicionar as colunas ausentes a um IMCI existente ou execute a instrução DDL obtida via columnar_advise() para criar um novo.