← PostgreSQL: operação e recuperação
07 / 12 · 70 MIN

Diagnosticar sessões e bloqueios

Reconstrói a relação entre titular e sessão bloqueada antes de escolher cancelamento, espera ou terminação.

Criar uma espera que se possa explicar

O conjunto local tem duas linhas de saldo pedagógico, ambas com 100 unidades. A sessão A abre uma transação e altera a primeira para 90 sem confirmar. B abre outra transação e tenta subtrair cinco unidades da mesma linha. Um terceiro cliente observa o servidor enquanto B espera. A ordem é controlada e os dados pertencem apenas ao exercício. Não há transações bancárias reais. Esta preparação permite atribuir o bloqueio a uma relação conhecida, em vez de concluir que uma query lenta precisa imediatamente de outro índice ou de mais CPU. A hipótese é validada antes de escolher uma intervenção.

Juntar estado, espera e bloqueador

No ponto observado, A está idle in transaction e tem xact_start definido. B está active, mas wait_event_type é Lock. A função pg_blocking_pids aplicada ao PID de B inclui o PID de A. Estes elementos são compatíveis: active identifica uma query em execução, mesmo que esteja à espera de um recurso. O titular não precisa de estar a executar SQL naquele instante para conservar locks de uma transação aberta. Num relatório de incidente, regista o instante, a base, a aplicação cliente, a idade da transação e a relação de bloqueio. Evita atribuir todo o tempo decorrido a consumo de CPU.

Uma leitura normal pode continuar

O observador faz SELECT sem FOR UPDATE e recebe 100, o valor confirmado. Não recebe os 90 ainda privados da transação A e não precisa de obter o mesmo lock de linha exigido pelo escritor B. Portanto, conseguir consultar dados não prova que as escritas estejam livres de bloqueio. Esta diferença ajuda a explicar incidentes em que dashboards funcionam enquanto um batch de atualização fica parado. O ensaio trata um conflito de linha específico; outros locks, incluindo locks de tabela usados por certas operações DDL, podem bloquear leituras. Confirma sempre a operação, o modo de lock e o objeto envolvidos.

Cancelar a query que está à espera

O coordenador envia pg_cancel_backend ao PID de B, criado pelo próprio guião. A função devolve true, e o cliente recebe SQLSTATE 57014 com diagnóstico de pedido do utilizador. A ligação permanece aberta, mas a transação explícita fica em erro; o SELECT seguinte devolve 25P02 até ocorrer ROLLBACK. A função de sinalização e o resultado da transação são evidências diferentes. Numa aplicação com pool, uma ligação que responde a nível de transporte pode ainda precisar de limpeza transacional antes de regressar ao pool. O laboratório demonstra a recuperação desta ligação, sem implementar ou validar um pool real.

Cancelar uma sessão ociosa não fecha a transação

Numa nova espera, o guião envia cancelamento ao titular A enquanto este está idle in transaction. O sinal é enviado, mas A continua nessa situação e B continua bloqueada. Não há uma query ativa de A para cancelar nesse ponto. Depois, apenas no cluster descartável, pg_terminate_backend com timeout positivo termina A; o observador confirma que o PID desapareceu. A alteração não confirmada para 90 é revertida, B continua a partir de 100 e devolve 95. Em produção, terminar uma sessão exige compreender proprietário, trabalho perdido e impacto, segundo o processo autorizado. Não é uma receita automática para qualquer espera.

Preservar contexto e limites da observação

O guião usa uma role administrativa local para observar e sinalizar exclusivamente sessões próprias. Um utilizador de aplicação pode não ver os mesmos detalhes nem ter as mesmas permissões. A informação de atividade também precisa de contexto temporal: uma transação de monitorização longa pode conservar uma fotografia, e query_start de uma sessão não ativa refere-se à última query. Antes de agir num PID, confirma novamente a identidade e a ocorrência atual. O exercício fecha ligações e termina o cluster. Não valida autorização entre equipas, recuperação após crash, réplica, carga representativa ou aceitação funcional de uma aplicação real.

-- Read-only diagnosis: correlate state, transaction and blockers.
SELECT pid, application_name, state, xact_start, query_start,
       wait_event_type, wait_event, pg_blocking_pids(pid) AS blockers
FROM pg_stat_activity
WHERE datname = current_database()
  AND pid <> pg_backend_pid();
-- Run cancellation/termination only through the owned lab or an authorized runbook.
NA PRÁTICA

Uma sessão idle in transaction mantém uma atualização não confirmada; outra aparece active com wait_event_type=Lock.

Armadilhas comuns

Interpretar active como CPU ocupada; confundir idle com idle in transaction; cancelar a sessão errada; tomar true como prova de recuperação.

Tópicos relacionados: Transações e concorrência · Diagnóstico e passagem para suporte

Leva esta ideia contigo

O diagnóstico deve explicar quem espera, porquê e que trabalho pertence ao titular. A intervenção precisa de confirmar o resultado.

Criar conta

Referência: Activity state and observation snapshots · PostgreSQL 18 reference semantics;18.6 current stable at review

PostgreSQL® é uma marca registada de PostgreSQL Community Association. A dr.pt é uma plataforma de preparação independente e não está afiliada, associada, patrocinada, autorizada nem aprovada por PostgreSQL Community Association. Os conteúdos e as perguntas são originais, não são perguntas oficiais de exame, e concluir os nossos testes não atribui nem garante qualquer certificação. Os nomes são usados apenas para identificar o tema. Todas as outras marcas pertencem aos respetivos titulares.