add(logs): Include a HINT when the LISTEN channel breaks due to a Postgres bug
The HINT shows a SQL command that solves the issue.
This commit is contained in:
committed by
Steve Chavez
parent
aae929a718
commit
250747aadc
@@ -4,6 +4,10 @@ All notable changes to this project will be documented in this file. From versio
|
|||||||
|
|
||||||
## Unreleased
|
## Unreleased
|
||||||
|
|
||||||
|
### Added
|
||||||
|
|
||||||
|
- Log a `HINT` when the LISTEN channel stops working due to a PostgreSQL bug by @laurenceisla in #4581
|
||||||
|
|
||||||
## [14.7] - 2026-03-20
|
## [14.7] - 2026-03-20
|
||||||
|
|
||||||
### Fixed
|
### Fixed
|
||||||
|
|||||||
@@ -10,7 +10,8 @@ import qualified Hasql.Connection as SQL
|
|||||||
import qualified Hasql.Notifications as SQL
|
import qualified Hasql.Notifications as SQL
|
||||||
import PostgREST.AppState (AppState, getConfig)
|
import PostgREST.AppState (AppState, getConfig)
|
||||||
import PostgREST.Config (AppConfig (..))
|
import PostgREST.Config (AppConfig (..))
|
||||||
import PostgREST.Observation (Observation (..))
|
import PostgREST.Observation (Observation (..),
|
||||||
|
isDbListenerBug)
|
||||||
import PostgREST.Version (prettyVersion)
|
import PostgREST.Version (prettyVersion)
|
||||||
|
|
||||||
import qualified PostgREST.AppState as AppState
|
import qualified PostgREST.AppState as AppState
|
||||||
@@ -36,6 +37,8 @@ retryingListen appState = do
|
|||||||
onError err = do
|
onError err = do
|
||||||
AppState.putIsListenerOn appState False
|
AppState.putIsListenerOn appState False
|
||||||
observer $ DBListenFail dbChannel (Right err)
|
observer $ DBListenFail dbChannel (Right err)
|
||||||
|
when (isDbListenerBug err) $
|
||||||
|
observer DBListenBugHint
|
||||||
unless configDbPoolAutomaticRecovery $
|
unless configDbPoolAutomaticRecovery $
|
||||||
killThread mainThreadId
|
killThread mainThreadId
|
||||||
|
|
||||||
|
|||||||
@@ -13,6 +13,7 @@ module PostgREST.Observation
|
|||||||
, observationMessage
|
, observationMessage
|
||||||
, ObservationHandler
|
, ObservationHandler
|
||||||
, showOnSingleLine
|
, showOnSingleLine
|
||||||
|
, isDbListenerBug
|
||||||
) where
|
) where
|
||||||
|
|
||||||
import qualified Data.ByteString.Lazy as LBS
|
import qualified Data.ByteString.Lazy as LBS
|
||||||
@@ -47,6 +48,7 @@ data Observation
|
|||||||
| DBListenStart Text
|
| DBListenStart Text
|
||||||
| DBListenFail Text (Either SQL.ConnectionError SomeException)
|
| DBListenFail Text (Either SQL.ConnectionError SomeException)
|
||||||
| DBListenRetry Int
|
| DBListenRetry Int
|
||||||
|
| DBListenBugHint -- https://github.com/PostgREST/postgrest/issues/3147
|
||||||
| DBListenerGotSCacheMsg ByteString
|
| DBListenerGotSCacheMsg ByteString
|
||||||
| DBListenerGotConfigMsg ByteString
|
| DBListenerGotConfigMsg ByteString
|
||||||
| DBListenerConnectionCleanupFail SomeException
|
| DBListenerConnectionCleanupFail SomeException
|
||||||
@@ -119,6 +121,8 @@ observationMessage = \case
|
|||||||
either showListenerConnError showListenerException listenErr
|
either showListenerConnError showListenerException listenErr
|
||||||
DBListenRetry delay ->
|
DBListenRetry delay ->
|
||||||
"Retrying listening for database notifications in " <> (show delay::Text) <> " seconds..."
|
"Retrying listening for database notifications in " <> (show delay::Text) <> " seconds..."
|
||||||
|
DBListenBugHint ->
|
||||||
|
"HINT: This is likely a bug in the notification queue, try executing the following to solve it: select pg_notification_queue_usage();"
|
||||||
DBListenerGotSCacheMsg channel ->
|
DBListenerGotSCacheMsg channel ->
|
||||||
"Received a schema cache reload message on the " <> show channel <> " channel"
|
"Received a schema cache reload message on the " <> show channel <> " channel"
|
||||||
DBListenerGotConfigMsg channel ->
|
DBListenerGotConfigMsg channel ->
|
||||||
@@ -181,3 +185,6 @@ observationMessage = \case
|
|||||||
|
|
||||||
showOnSingleLine :: Char -> Text -> Text
|
showOnSingleLine :: Char -> Text -> Text
|
||||||
showOnSingleLine split txt = T.intercalate " " $ T.filter (/= split) <$> T.lines txt -- the errors from hasql-notifications come intercalated with "\t\n"
|
showOnSingleLine split txt = T.intercalate " " $ T.filter (/= split) <$> T.lines txt -- the errors from hasql-notifications come intercalated with "\t\n"
|
||||||
|
|
||||||
|
isDbListenerBug :: SomeException -> Bool
|
||||||
|
isDbListenerBug e = "could not access status of transaction" `T.isInfixOf` show e
|
||||||
|
|||||||
Reference in New Issue
Block a user