use existing debug machinery for explain
explain is a kind of debug message, but not formatted in the same way. So it makes sense to reuse the debug machinery for it, since that is already quite optimised. Sponsored-by: Dartmouth College's DANDI project
This commit is contained in:
parent
fbf19338be
commit
409572c9e4
3 changed files with 49 additions and 16 deletions
|
@ -1,6 +1,6 @@
|
|||
{- git-annex debugging
|
||||
-
|
||||
- Copyright 2021 Joey Hess <id@joeyh.name>
|
||||
- Copyright 2021-2023 Joey Hess <id@joeyh.name>
|
||||
-
|
||||
- Licensed under the GNU AGPL version 3 or higher.
|
||||
-}
|
||||
|
@ -8,8 +8,11 @@
|
|||
module Annex.Debug (
|
||||
DebugSelector(..),
|
||||
DebugSource(..),
|
||||
RawDebugMessage(..),
|
||||
debug,
|
||||
debug',
|
||||
fastDebug,
|
||||
fastDebug',
|
||||
configureDebug,
|
||||
debugSelectorFromGitConfig,
|
||||
parseDebugSelector,
|
||||
|
@ -17,7 +20,7 @@ module Annex.Debug (
|
|||
|
||||
import Common
|
||||
import qualified Annex
|
||||
import Utility.Debug hiding (fastDebug)
|
||||
import Utility.Debug hiding (fastDebug, fastDebug')
|
||||
import qualified Utility.Debug
|
||||
import Annex.Debug.Utility
|
||||
|
||||
|
@ -25,7 +28,11 @@ import Annex.Debug.Utility
|
|||
-- is read from the Annex monad, which avoids any IORef access overhead
|
||||
-- when debugging is not enabled.
|
||||
fastDebug :: DebugSource -> String -> Annex.Annex ()
|
||||
fastDebug src msg = do
|
||||
fastDebug = fastDebug'
|
||||
|
||||
fastDebug' :: DebugMessage msg => DebugSource -> msg -> Annex.Annex ()
|
||||
fastDebug' src msg = do
|
||||
rd <- Annex.getRead id
|
||||
when (Annex.debugenabled rd) $
|
||||
liftIO $ Utility.Debug.fastDebug (Annex.debugselector rd) src msg
|
||||
liftIO $ Utility.Debug.fastDebug' (Annex.debugselector rd) src msg
|
||||
|
||||
|
|
|
@ -50,6 +50,7 @@ module Messages (
|
|||
outputMessage,
|
||||
withMessageState,
|
||||
MessageState,
|
||||
explain,
|
||||
prompt,
|
||||
mkPrompter,
|
||||
sanitizeTopLevelExceptionMessages,
|
||||
|
@ -281,6 +282,11 @@ debugDisplayer = do
|
|||
S.hPutStr stderr (safeOutput s <> "\n")
|
||||
hFlush stderr
|
||||
|
||||
explain :: Maybe String -> String -> Annex ()
|
||||
explain Nothing _ = return ()
|
||||
explain (Just f) msg = fastDebug' "explain" $
|
||||
RawDebugMessage ('[' : f ++ " " ++ msg ++ "]")
|
||||
|
||||
{- Should commands that normally output progress messages have that
|
||||
- output disabled? -}
|
||||
commandProgressDisabled :: Annex Bool
|
||||
|
|
|
@ -1,6 +1,6 @@
|
|||
{- Debug output
|
||||
-
|
||||
- Copyright 2021 Joey Hess <id@joeyh.name>
|
||||
- Copyright 2021-2023 Joey Hess <id@joeyh.name>
|
||||
-
|
||||
- License: BSD-2-clause
|
||||
-}
|
||||
|
@ -12,10 +12,14 @@
|
|||
module Utility.Debug (
|
||||
DebugSource(..),
|
||||
DebugSelector(..),
|
||||
DebugMessage,
|
||||
RawDebugMessage(..),
|
||||
configureDebug,
|
||||
getDebugSelector,
|
||||
debug,
|
||||
fastDebug
|
||||
debug',
|
||||
fastDebug,
|
||||
fastDebug'
|
||||
) where
|
||||
|
||||
import qualified Data.ByteString as S
|
||||
|
@ -50,6 +54,22 @@ instance Sem.Semigroup DebugSelector where
|
|||
instance Monoid DebugSelector where
|
||||
mempty = NoDebugSelector
|
||||
|
||||
class DebugMessage msg where
|
||||
formatDebugMessage :: DebugSource -> msg -> IO S.ByteString
|
||||
|
||||
instance DebugMessage String where
|
||||
formatDebugMessage (DebugSource src) msg = do
|
||||
t <- encodeBS . formatTime defaultTimeLocale "[%F %X%Q]"
|
||||
<$> getZonedTime
|
||||
return (t <> " (" <> src <> ") " <> encodeBS msg)
|
||||
|
||||
-- Debug message to be displayed without the usual time stamp
|
||||
-- and source information.
|
||||
newtype RawDebugMessage = RawDebugMessage String
|
||||
|
||||
instance DebugMessage RawDebugMessage where
|
||||
formatDebugMessage _ (RawDebugMessage msg) = pure (encodeBS msg)
|
||||
|
||||
-- | Configures debugging.
|
||||
configureDebug
|
||||
:: (S.ByteString -> IO ())
|
||||
|
@ -76,7 +96,10 @@ debugConfigGlobal = unsafePerformIO $ newIORef (dontshow, selectnone)
|
|||
-- have to consult a IORef each time, using it in a tight loop may slow
|
||||
-- down the program.
|
||||
debug :: DebugSource -> String -> IO ()
|
||||
debug src msg = readIORef debugConfigGlobal >>= \case
|
||||
debug = debug'
|
||||
|
||||
debug' :: DebugMessage msg => DebugSource -> msg -> IO ()
|
||||
debug' src msg = readIORef debugConfigGlobal >>= \case
|
||||
(displayer, NoDebugSelector) ->
|
||||
displayer =<< formatDebugMessage src msg
|
||||
(displayer, DebugSelector p)
|
||||
|
@ -88,15 +111,12 @@ debug src msg = readIORef debugConfigGlobal >>= \case
|
|||
-- When the DebugSelector does not let the message be displayed, this runs
|
||||
-- very quickly, allowing it to be used inside tight loops.
|
||||
fastDebug :: DebugSelector -> DebugSource -> String -> IO ()
|
||||
fastDebug NoDebugSelector src msg = do
|
||||
fastDebug = fastDebug'
|
||||
|
||||
fastDebug' :: DebugMessage msg => DebugSelector -> DebugSource -> msg -> IO ()
|
||||
fastDebug' NoDebugSelector src msg = do
|
||||
(displayer, _) <- readIORef debugConfigGlobal
|
||||
displayer =<< formatDebugMessage src msg
|
||||
fastDebug (DebugSelector p) src msg
|
||||
| p src = fastDebug NoDebugSelector src msg
|
||||
fastDebug' (DebugSelector p) src msg
|
||||
| p src = fastDebug' NoDebugSelector src msg
|
||||
| otherwise = return ()
|
||||
|
||||
formatDebugMessage :: DebugSource -> String -> IO S.ByteString
|
||||
formatDebugMessage (DebugSource src) msg = do
|
||||
t <- encodeBS . formatTime defaultTimeLocale "[%F %X%Q]"
|
||||
<$> getZonedTime
|
||||
return (t <> " (" <> src <> ") " <> encodeBS msg)
|
||||
|
|
Loading…
Reference in a new issue