{-# LANGUAGE DuplicateRecordFields #-}
{-# LANGUAGE RecordWildCards       #-}

module Logging.Sink (Sink(..)) where

import           Prelude        hiding (filter)

import           Logging.Class
import           Logging.Filter
import           Logging.Level
import           Logging.Logger
import           Logging.Record


-- |'Sink' represents a single logging channel.
--
-- A "logging channel" indicates an area of an application. Exactly how an
-- "area" is defined is up to the application developer. Since an
-- application can have any number of areas, logging channels are identified
-- by a unique string. Application areas can be nested (e.g. an area
-- of "input processing" might include sub-areas "read CSV files", "read
-- XLS files" and "read Gnumeric files"). To cater for this natural nesting,
-- channel names are organized into a namespace hierarchy where levels are
-- separated by periods, much like the  Haskell module namespace. So
-- in the instance given above, channel names might be "Input" for the upper
-- level, and "Input.Csv", "Input.Xls" and "Input.Gnu" for the sub-levels.
-- There is no arbitrary limit to the depth of nesting.
--
-- Note: The namespaces are case sensitive.
--
data Sink = Sink { logger    :: Logger
                 , level     :: Level
                 , filterer  :: Filterer
                 , handlers  :: [SomeHandler]
                 , disabled  :: Bool
                 , propagate :: Bool -- ^ It will pop up until root or the
                                     -- ancestor's propagation is disabled
                 }

instance Filterable Sink where
  filter Sink{..} rcd@LogRecord{level=level'}
    | disabled = False
    | level' < level = False
    | otherwise = filter filterer rcd