Como usar o cache de análise do ANTLR no Babelfish
A partir das versões 5.7.0 e 6.2.0 do Babelfish, é possível usar um cache persistente dos resultados da análise do ANTLR para rotinas armazenadas em T-SQL (procedimentos e funções) a fim de reduzir a latência da primeira execução.
Com o cache de análise de procedimentos:
-
Rotinas T-SQL grandes (com centenas a milhares de linhas) deixam de incorrer na sobrecarga da análise completa de T-SQL na primeira execução de cada nova sessão.
-
O resultado analisado é serializado uma única vez no momento de
CREATE/ALTERdo procedimento ou da função, armazenado no catálogo e reutilizado entre sessões, emulando o comportamento de cache global do sistema do SQL Server. -
O recurso é controlado pelo GUC
babelfishpg_tsql.enable_antlr_parse_cacheno nível da sessão, com substituições opcionais por rotina por meio desys.enable_antlr_parse_cache(). -
Por padrão, o recurso fica DESATIVADO.
Desempenho: para rotinas grandes, a análise do ANTLR pode levar vários segundos. Com o cache de análise do ANTLR, o tempo de análise na primeira execução é reduzido a alguns milissegundos. As execuções subsequentes na mesma sessão são atendidas pelo cache da sessão (menos de um milissegundo) e não são afetadas.
Noções básicas sobre o cache de análise do ANTLR
O Babelfish precisa validar a sintaxe T-SQL analisando o corpo de uma rotina na primeira vez que ela é executada em uma sessão. Normalmente, esse resultado da análise fica em cache apenas durante a sessão, portanto, cada nova conexão realiza a análise novamente desde o início. O cache de análise persiste o resultado no catálogo para que novas sessões possam reutilizá-lo.
Como funciona:
-
Em
CREATE/ALTER: quando o cache está ativado, o Babelfish analisa a rotina e armazena o resultado serializado da análise no cache persistente. -
Primeira execução sem uma entrada persistente: se não houver uma entrada em cache (por exemplo, se a rotina tiver sido criada antes da ativação do cache), o Babelfish executará a análise normal do ANTLR e preencherá o cache persistente.
-
Primeira execução em uma sessão posterior: o Babelfish carrega e desserializa o resultado da análise armazenado em cache em vez de analisá-lo novamente. É nesse ponto que ocorre a economia de tempo.
-
Execuções subsequentes na mesma sessão: são atendidas pelo cache da sessão (comportamento inalterado).
-
Se um resultado em cache estiver ausente ou tiver sido criado por uma versão diferente do Babelfish, o Babelfish executará a análise normal do ANTLR e preencherá novamente o cache persistente quando o cache estiver ativado.
-
Se o Babelfish encontrar um erro ao serializar ou desserializar um resultado em cache, a instrução falhará e retornará um erro. Desative o cache para a rotina afetada e tente executar a instrução novamente, ou tente executá-la em uma nova sessão com o GUC de cache desativado. Se o erro persistir, entre em contato com o suporte da AWS.
Observação da melhoria no tempo de análise
É possível medir o efeito usando SET BABELFISH_STATISTICS PROFILE ON, que informa o Babelfish T-SQL Batch Parsing Time de cada lote. Primeiro, crie um procedimento grande com o cache ativado para preencher o cache persistente. Em seguida, compare a primeira execução do procedimento em duas sessões novas separadas: uma com o cache desativado, que ignora a entrada persistente, e outra com o cache ativado, que reutiliza essa entrada. Como alternativa, se o cache não estava ativado quando o procedimento foi criado, execute-o em duas sessões novas separadas, ambas com o cache ativado: a primeira execução preenche o cache persistente, e a segunda o reutiliza.
No exemplo a seguir, primeiro crie o procedimento com o cache ATIVADO para preencher o cache persistente:
-- New session 0: caching ON (at CREATE PROCEDURE time) SELECT set_config('babelfishpg_tsql.enable_antlr_parse_cache', 'on', false); GO CREATE PROCEDURE dbo.updateInformation @region VARCHAR(50) AS BEGIN ... END; GO
Em seguida, em uma nova sessão com o cache DESATIVADO (o padrão), execute o procedimento:
-- New session 1: caching OFF (default) SET BABELFISH_STATISTICS PROFILE ON; GO EXEC dbo.updateInformation @region = 'EMEA'; -- first call in this session GO
O perfil de estatísticas informa um tempo de análise elevado:
Babelfish T-SQL Batch Parsing Time: 20359.465 ms
Por fim, em outra nova sessão com o cache ATIVADO, execute o procedimento:
-- New session 2: caching ON SELECT set_config('babelfishpg_tsql.enable_antlr_parse_cache', 'on', false); GO SET BABELFISH_STATISTICS PROFILE ON; GO EXEC dbo.updateInformation @region = 'EMEA'; -- first call in this session GO
O perfil de estatísticas informa um tempo de análise significativamente menor:
Babelfish T-SQL Batch Parsing Time: 150.927 ms
A primeira execução em uma nova sessão reduz o tempo de análise de aproximadamente 20 s para 0,15 s quando a árvore de análise armazenada em cache é reutilizada. A segunda execução e as posteriores na mesma sessão são atendidas pelo cache da sessão em ambos os casos (menos de um milissegundo) e não são afetadas pelo GUC.
Ativação do cache para uma sessão
O recurso é controlado por um GUC no nível da sessão (DESATIVADO por padrão):
-- Enable parse caching for the current session SELECT set_config('babelfishpg_tsql.enable_antlr_parse_cache', 'on', false); GO -- Disable for the current session SELECT set_config('babelfishpg_tsql.enable_antlr_parse_cache', 'off', false); GO
nota
-
O GUC se aplica à sessão e é redefinido para o valor padrão (DESATIVADO) quando a sessão termina.
-
Atualmente, não é possível configurar esse GUC em todo o cluster por meio de
sp_babelfish_configure.
Controle do cache por rotina
É possível substituir o GUC da sessão para uma rotina individual usando sys.enable_antlr_parse_cache, que aceita o ID do objeto da rotina:
-- Force caching ON for a specific routine (even if the session GUC is OFF) SELECT sys.enable_antlr_parse_cache(sys.object_id('dbo.my_proc'), true); GO -- Force caching OFF for a specific routine — "kill switch" -- (clears any cached data and blocks caching even if the session GUC is ON) SELECT sys.enable_antlr_parse_cache(sys.object_id('dbo.my_proc'), false); GO -- Reset to default; the routine follows the session GUC SELECT sys.enable_antlr_parse_cache(sys.object_id('dbo.my_proc'), NULL); GO
nota
-
É necessário ser o proprietário da rotina ou membro do perfil sysadmin para alterar a configuração de cache da rotina.
-
A configuração por rotina persiste entre sessões (ela é armazenada no catálogo) e é preservada entre
ALTER; ela é removida quando a rotina é excluída.
Verificação das estatísticas do cache
sys.antlr_parse_cache_stats() retorna a atividade do cache de análise para a sessão atual:
SELECT * FROM sys.antlr_parse_cache_stats(); GO
A tabela a seguir descreve cada coluna da saída.
| Coluna | Descrição |
|---|---|
cache_hits |
Quantidade de execuções de rotinas nas quais um resultado de análise armazenado em cache foi reutilizado. |
cache_misses |
Quantidade de execuções de rotinas nas quais o cache estava ativado, mas não foi encontrada nenhuma entrada de cache utilizável. |
cache_writes |
Quantidade de gravações bem-sucedidas no cache persistente. |
cache_evictions |
Quantidade de entradas em cache que foram invalidadas ou removidas (por exemplo, devido ao mecanismo de desativação de emergência ou à alternância do GUC). |
cache_errors |
Quantidade de falhas de serialização ou desserialização. |
Os contadores são específicos de cada sessão e são redefinidos ao estabelecer uma nova conexão.
Exemplo de cenário
-- Enable caching for this session SELECT set_config('babelfishpg_tsql.enable_antlr_parse_cache', 'on', false); GO CREATE PROCEDURE dbo.report_proc @region VARCHAR(50) AS BEGIN -- large multi-statement T-SQL body ... SELECT @region; END; GO -- First execution in a brand-new session: served from the persistent cache (fast) EXEC dbo.report_proc @region = 'APAC'; GO -- Inspect cache activity for this session SELECT * FROM sys.antlr_parse_cache_stats(); GO -- Opt this routine out of caching regardless of the session setting SELECT sys.enable_antlr_parse_cache(sys.object_id('dbo.report_proc'), false); GO
Considerações sobre atualização
-
O cache de análise do ANTLR está vinculado a uma versão específica do Babelfish. Quando a versão do Babelfish muda, os resultados de análise armazenados em cache deixam de ser reutilizados. As novas execuções analisam novamente a rotina e preenchem o cache automaticamente quando ele está ativado.
-
As rotinas existentes criadas antes das versões 5.7.0 e 6.2.0 são armazenadas em cache na próxima operação de
CREATEouALTERou durante uma execução em uma sessão sem cache previamente preenchido, assim que o cache é ativado.
Limitações importantes
-
Padrão DESATIVADO: o recurso precisa ser ativado explicitamente por sessão (ou forçado por rotina).
-
Tipo de conexão: o cache fica ativo somente em conexões TDS (protocolo do SQL Server), não em conexões psql/libpq.
-
Não armazenados em cache: gatilhos, gatilhos de evento e funções de valor de tabela em linha (ITVFs) não são armazenados em cache nesta versão.
-
Configuração em todo o cluster: atualmente, não é possível definir o GUC da sessão por meio de
sp_babelfish_configure.