co-log-core 0.2.1.1 → 0.3.2.7
raw patch · 8 files changed
Files
- CHANGELOG.md +115/−22
- README.md +33/−92
- co-log-core.cabal +32/−14
- src/Colog/Core.hs +7/−3
- src/Colog/Core/Action.hs +20/−17
- src/Colog/Core/Class.hs +7/−4
- src/Colog/Core/IO.hs +38/−8
- src/Colog/Core/Severity.hs +47/−3
CHANGELOG.md view
@@ -3,73 +3,166 @@ `co-log-core` uses [PVP Versioning][1]. The change log is available [on GitHub][2]. +## 0.3.2.7 — May 27, 2026++## What's Changed++* Allow newer `doctest`s.++**Full Changelog**: https://github.com/co-log/co-log-core/compare/v0.3.2.6...v0.3.2.7++## 0.3.2.6 — January 5, 2026++## What's Changed++* Support ghc-9.14.++**Full Changelog**: https://github.com/co-log/co-log-core/compare/v0.3.2.5...v0.3.2.6++## 0.3.2.5 — March 2, 2025++## What's Changed++* Allow `doctest-0.24`.++**Full Changelog**: https://github.com/co-log/co-log-core/compare/v0.3.2.4...v0.3.2.5++## 0.3.2.4 — January 5, 2025++## What's Changed++* Support ghc-9.12.++**Full Changelog**: https://github.com/co-log/co-log-core/compare/v0.3.2.3...v0.3.2.4++## 0.3.2.3 — December 15, 2024++## What's Changed++* Allow `doctest-0.23`.++**Full Changelog**: https://github.com/co-log/co-log-core/compare/v0.3.2.2...v0.3.2.3++## 0.3.2.2 — May 21, 2024++## What's Changed+* GA(deps): Bump actions/cache from 3 to 4 by @dependabot in https://github.com/co-log/co-log-core/pull/40+* Support ghc-9.10. by @alaendle in https://github.com/co-log/co-log-core/pull/41+++**Full Changelog**: https://github.com/co-log/co-log-core/compare/v0.3.2.1...v0.3.2.2++## 0.3.2.1 — Oct 20, 2023++## What's Changed+* Relax doctest boundaries. by @alaendle in [#32](https://github.com/co-log/co-log-core/pull/32)+* GA(deps): Bump actions/checkout from 3 to 4 by @dependabot in [#35](https://github.com/co-log/co-log-core/pull/35)+* Allow doctest-0.22 by @Vekhir in [#36](https://github.com/co-log/co-log-core/pull/36)+* [#29] Support GHC 9.6 by @vrom911 in [#33](https://github.com/co-log/co-log-core/pull/33)+* Support ghc-9.8 by @alaendle in [#37](https://github.com/co-log/co-log-core/pull/37)+* Publish to hackage directly from GitHub by @alaendle in [#38](https://github.com/co-log/co-log-core/pull/38)++## New Contributors+* @Vekhir made their first contribution in https://github.com/co-log/co-log-core/pull/36++**Full Changelog**: https://github.com/co-log/co-log-core/compare/v0.3.2.0...v0.3.2.1++## 0.3.2.0 — Nov 2, 2022++- [#25](https://github.com/co-log/co-log-core/issues/25):+ Support GHC-9.4.++## 0.3.1.0 — Feb 15, 2022++- [#7](https://github.com/co-log/co-log-core/issues/7):+ Support GHC-9.2.+- [#13](https://github.com/co-log/co-log-core/issues/13):+ Add `WithSeverity` and `mapSeverity` to `Colog.Severity`.++## 🎃 0.3.0.0 — Oct 29, 2021++- [#223](https://github.com/co-log/co-log/pull/223):+ Support GHC-9.0.1.+- [#176](https://github.com/co-log/co-log/issues/176):+ Add `logFlush` action to flush the given `Handle`.++ **Breaking change:** All `withLog*File` functions how flush handle+ after logging each message. Now you'll see logs in the file+ immediately.++ **Migration guide:** If you rely on the previous behaviour, then+ copy-paste corresponding functions and remove flushing.++- Update maintainers information to the new+ [Co-Log](https://github.com/co-log) organization.+ ## 0.2.1.1 — Apr 18, 2020 -* [#186](https://github.com/kowainik/co-log/issues/186):+- [#186](https://github.com/co-log/co-log/issues/186): Support GHC-8.10.1. ## 0.2.1.0 — Jan 19, 2020 -* [#139](https://github.com/kowainik/co-log/issues/139):+- [#139](https://github.com/co-log/co-log/issues/139): Add (unrepresentable) `Functor` instance for `LogAction` with the custom type-error. (by [@vrom911](https://github.com/vrom911))-* [#148](https://github.com/kowainik/co-log/issues/148):+- [#148](https://github.com/co-log/co-log/issues/148): Support GHC-8.8.2. (by [@chshersh](https://github.com/chshersh))-* [#122](https://github.com/kowainik/co-log/issues/122):+- [#122](https://github.com/co-log/co-log/issues/122): Add the `separate` combinator. (by [@vrom911](https://github.com/vrom911))-* [#125](https://github.com/kowainik/co-log/issues/125):+- [#125](https://github.com/co-log/co-log/issues/125): Add monadic versions of contravariant functions. (by [@piq9117](https://github.com/piq9117))-* [#138](https://github.com/kowainik/co-log/issues/138):+- [#138](https://github.com/co-log/co-log/issues/138): Add `hoistLogAction` — higher-order transformation function. (by [@jiribenes](https://github.com/jiribenes))-* [#123](https://github.com/kowainik/co-log/issues/123):+- [#123](https://github.com/co-log/co-log/issues/123): Write default implementation to `getLogAction` via `logActionL`. (by [@SanchayanMaity](https://github.com/SanchayanMaity)) ## 0.2.0.0 — May 5, 2019 -* [#85](https://github.com/kowainik/co-log/issues/85):+- [#85](https://github.com/co-log/co-log/issues/85): Move `overLogAction` to `HasLog` typeclass-* [#101](https://github.com/kowainik/co-log/issues/101):+- [#101](https://github.com/co-log/co-log/issues/101): Add `logActionL` lens with default implementation to `HasLog` type class.-* [#99](https://github.com/kowainik/co-log/issues/99):+- [#99](https://github.com/co-log/co-log/issues/99): Add comonadic combinators: `duplicate` and `multiplicate`.-* [#78](https://github.com/kowainik/co-log/issues/78):+- [#78](https://github.com/co-log/co-log/issues/78): Improve documentation significantly. ## 0.1.1 — Nov 15, 2018 -* [#63](https://github.com/kowainik/co-log/issues/63):+- [#63](https://github.com/co-log/co-log/issues/63): Add `logPrint`, `logPrintStderr`, `logPrintHandle` and `withLogPrintFile` to `Colog.Core.IO`.-* [#46](https://github.com/kowainik/co-log/issues/46):+- [#46](https://github.com/co-log/co-log/issues/46): Moves `logStringStdout`, `logStringStderr`, `logStringHandle`, `withLogStringFile` from `Colog.Actions` to `Colog.Core.IO`.-* [#48](https://github.com/kowainik/co-log/issues/48):+- [#48](https://github.com/co-log/co-log/issues/48): Adds `liftLogIO` function.-* [#49](https://github.com/kowainik/co-log/issues/49):+- [#49](https://github.com/co-log/co-log/issues/49): Add `<&` and `&>`operators for `unLogAction`.-* [#47](https://github.com/kowainik/co-log/issues/47):+- [#47](https://github.com/co-log/co-log/issues/47): Add `doctest` tests.-* [#13](https://github.com/kowainik/co-log/issues/13):+- [#13](https://github.com/co-log/co-log/issues/13): Add `.cabal` file description and improve documentation.-* [#39](https://github.com/kowainik/co-log/issues/39):+- [#39](https://github.com/co-log/co-log/issues/39): Support GHC-8.2.2 and GHC-8.6.2. ## 0.1.0 -* [#38](https://github.com/kowainik/co-log/issues/38):+- [#38](https://github.com/co-log/co-log/issues/38): Rename `cbind` to `cmapM`. -* [#37](https://github.com/kowainik/co-log/issues/37):+- [#37](https://github.com/co-log/co-log/issues/37): Add `base` bounds. ## 0.0.0 -* Initially created.+- Initially created. [1]: https://pvp.haskell.org-[2]: https://github.com/kowainik/co-log/releases+[2]: https://github.com/co-log/co-log-core/releases
README.md view
@@ -1,109 +1,50 @@-# co-log+# co-log-core -[](https://github.com/kowainik/co-log/actions)-[](https://travis-ci.org/kowainik/co-log)-[](https://ci.appveyor.com/project/kowainik/co-log)-[](https://github.com/kowainik/co-log/blob/master/LICENSE)+ +[](https://github.com/co-log/co-log-core/actions)+[![Hackage][hk-img-core]][hk-core]+[](https://github.com/co-log/co-log/blob/main/LICENSE) -| | | | |-| :------------ | :--------------------------------- | :---------------------------------------- | :---------------------------------------------------- |-| `co-log-core` | [![Hackage][hk-img-core]][hk-core] | [![Stackage LTS][lts-img-core]][lts-core] | [![Stackage Nightly][nightly-img-core]][nightly-core] |-| `co-log` | [![Hackage][hk-img]][hk] | [![Stackage LTS][lts-img]][lts] | [![Stackage Nightly][nightly-img]][nightly] |-| `co-log-polysemy` | [![Hackage][hk-img-ps]][hk-ps] | [![Stackage LTS][lts-img-ps]][lts-ps] | [![Stackage Nightly][nightly-img-ps]][nightly-ps] |+`co-log-core` is a lightweight package that provides core types and functions to +work with the @LogAction@ data type which is both simple and powerful. -`co-log` is a composable and configurable logging framework. It-combines all the benefits of Haskell idioms to provide a reasonable-and convenient interface. Though it uses some advanced concepts in its-core, we are striving to provide beginner-friendly API. The library-also contains complete documentation with a lot of beginner-friendly-examples, explanations and tutorials to guide users. The combination-of a pragmatic approach to logging and fundamental Haskell abstractions-allows us to create a highly composable and configurable logging-framework.+## How to use -If you're interested in how different Haskell typeclasses are used to-implement core functions of `co-log`, you can read the following blog-post which goes into detail about internal implementation specifics:+`co-log-core` is compatible with the following GHC+versions - [supported versions](https://matrix.hackage.haskell.org/#/package/co-log-core) -* [co-log: Composable Contravariant Combinatorial Comonadic Configurable Convenient Logging](https://kowainik.github.io/posts/2018-09-25-co-log)+In order to start using `co-log-core` in your project, you+will need to set it up with these steps: -`co-log` is also modular on the level of packages. We care a lot about a-low dependency footprint so you can build your logging only on top of-the minimal required interface for your use-case. This repository contains-the following packages:+1. Add the dependency on `co-log-core` in your project's+ `.cabal` file. For this, you should modify the `build-depends`+ section according to the below section: -* [`co-log-core`](co-log-core): lightweight package with basic data types and- general idea which depends only on `base`.-* [`co-log`](co-log): taggless final implementation of logging library based on- `co-log-core`.-* [`co-log-polysemy`](co-log-polysemy): implementation of logging library based- on `co-log-core` and the [`polysemy`](http://hackage.haskell.org/package/polysemy) extensible effects library.-* [`co-log-benchmark`](co-log-benchmark): benchmarks of the `co-log` library.+ ```haskell+ build-depends: base ^>= LATEST_SUPPORTED_BASE+ , co-log-core ^>= LATEST_VERSION+ ``` -To provide a more user-friendly introduction to the library, we've-created the tutorial series which introduces the main concepts behind `co-log`-smoothly:+2. To use this package, refer to the below example. -* [Intro: Using `LogAction`](https://github.com/kowainik/co-log/blob/master/co-log/tutorials/1-intro/Intro.md)-* [Using custom monad that stores `LogAction` inside its environment](https://github.com/kowainik/co-log/blob/master/co-log/tutorials/2-custom/Custom.md)+ ```haskell+ module Main (main) where -`co-log` also cares about concurrent logging. For this purpose we have the `concurrent-playground`-executable where we experiment with different multithreading scenarios to test the library's behavior.-You can find it here:+ import Prelude hiding (log) -* [tutorials/Concurrent.hs](co-log/tutorials/Concurrent.hs)+ import Colog.Core (LogAction, logStringStdout, (<&)) -## Benchmarks -`co-log` is compared with basic functions like `putStrLn`. Since IO overhead is-big enough, every benchmark dumps 10K messages to output. If a benchmark's name-doesn't contain `Message` then this benchmark simply dumps the string `"message"`-to output, otherwise it works with the `Message` data type from the `co-log`-library.--To run benchmarks, use the following command:--```-cabal v2-run co-log-bench-```--| Benchmarks | Time for 10K messages |-| :------------------------------------------------------ | :-------------------- |-| `Prelude.putStrLn` | ` 5.117ms` |-| `Text.putStrLn` | ` 9.220ms` |-| `ByteString.putStrLn` | ` 2.971ms` |-| `mempty` | ` 1.181ms` |-| `logStringStdout` | ` 5.107ms` |-| `logPrint` | ` 5.248ms` |-| `logTextStdout` | ` 5.351ms` |-| `logByteStringStdout` | ` 2.933ms` |-| `logByteStringStderr` | ` 17.482ms` |-| `ByteString > (stdout <> stderr)` | ` 17.715ms` |-| `Message > format > stdout` | ` 9.188ms` |-| `Message > format > ByteString > stdout` | ` 3.524ms` |-| `Message{callstack} > format > stdout` | ` 9.139ms` |-| `Message{callstack:5} > format > stdout` | ` 9.464ms` |-| `Message{callstack:50} > format > stdout` | ` 9.439ms` |-| `Message{Time,ThreadId} > format > stdout` | ` 54.160ms` |-| `Message{Time,ThreadId} > format > ByteString > stdout` | ` 54.137ms` |-+ app :: LogAction IO String -> IO ()+ app log = do+ log <& "Starting app..."+ log <& "Finishing app..." -[hk-img]: https://img.shields.io/hackage/v/co-log.svg?logo=haskell-[hk-img-ps]: https://img.shields.io/hackage/v/co-log-polysemy.svg?logo=haskell+ main :: IO ()+ main = app logStringStdout+ ```+ + [hk-img-core]: https://img.shields.io/hackage/v/co-log-core.svg?logo=haskell-[hk]: https://hackage.haskell.org/package/co-log-[hk-ps]: https://hackage.haskell.org/package/co-log-polysemy [hk-core]: https://hackage.haskell.org/package/co-log-core-[lts-img]: http://stackage.org/package/co-log/badge/lts-[lts-img-ps]: http://stackage.org/package/co-log-polysemy/badge/lts-[lts-img-core]: http://stackage.org/package/co-log-core/badge/lts-[lts]: http://stackage.org/lts/package/co-log-[lts-ps]: http://stackage.org/lts/package/co-log-polysemy-[lts-core]: http://stackage.org/lts/package/co-log-core-[nightly-img]: http://stackage.org/package/co-log/badge/nightly-[nightly-img-ps]: http://stackage.org/package/co-log-polysemy/badge/nightly-[nightly-img-core]: http://stackage.org/package/co-log-core/badge/nightly-[nightly]: http://stackage.org/nightly/package/co-log-[nightly-ps]: http://stackage.org/nightly/package/co-log-polysemy-[nightly-core]: http://stackage.org/nightly/package/co-log-core
co-log-core.cabal view
@@ -1,6 +1,6 @@ cabal-version: 2.4 name: co-log-core-version: 0.2.1.1+version: 0.3.2.7 synopsis: Composable Contravariant Comonadic Logging Library description: This package provides core types and functions to work with the @LogAction@ data type which is both simple and powerful.@@ -21,13 +21,13 @@ * [co-log-polysemy](http://hackage.haskell.org/package/co-log-polysemy): extensible effects implementation based on @polysemy@. -homepage: https://github.com/kowainik/co-log-bug-reports: https://github.com/kowainik/co-log/issues+homepage: https://github.com/co-log/co-log-core+bug-reports: https://github.com/co-log/co-log-core/issues license: MPL-2.0 license-file: LICENSE author: Dmitrii Kovanikov-maintainer: Kowainik <xrom.xkov@gmail.com>-copyright: 2018-2020 Kowainik+maintainer: Co-Log <xrom.xkov@gmail.com>+copyright: 2018-2020 Kowainik, 2021-2026 Co-Log category: Logging, Contravariant, Comonad build-type: Simple stability: stable@@ -36,15 +36,23 @@ tested-with: GHC == 8.2.2 GHC == 8.4.4 GHC == 8.6.5- GHC == 8.8.3- GHC == 8.10.1+ GHC == 8.8.4+ GHC == 8.10.7+ GHC == 9.0.2+ GHC == 9.2.8+ GHC == 9.4.8+ GHC == 9.6.7+ GHC == 9.8.4+ GHC == 9.10.3+ GHC == 9.12.2+ GHC == 9.14.1 source-repository head type: git- location: https://github.com/kowainik/co-log.git+ location: https://github.com/co-log/co-log-core.git common common-options- build-depends: base >= 4.10.1.0 && < 4.15+ build-depends: base >= 4.10.1.0 && < 4.23 ghc-options: -Wall -Wcompat@@ -61,9 +69,19 @@ ghc-options: -Wmissing-deriving-strategies if impl(ghc >= 8.10) ghc-options: -Wunused-packages+ if impl(ghc >= 9.0)+ ghc-options: -Winvalid-haddock+ if impl(ghc >= 9.2)+ ghc-options: -Wredundant-bang-patterns+ -Woperator-whitespace+ if impl(ghc >= 9.4)+ ghc-options: -Wredundant-strictness-flags+ -Wforall-identifier default-language: Haskell2010 default-extensions: ConstraintKinds+ DeriveFunctor+ DeriveTraversable DeriveGeneric DerivingStrategies GeneralizedNewtypeDeriving@@ -81,15 +99,15 @@ import: common-options hs-source-dirs: src exposed-modules: Colog.Core- Colog.Core.Action- Colog.Core.Class- Colog.Core.Severity- Colog.Core.IO+ Colog.Core.Action+ Colog.Core.Class+ Colog.Core.Severity+ Colog.Core.IO test-suite doctest import: common-options type: exitcode-stdio-1.0 hs-source-dirs: test main-is: Doctests.hs- build-depends: doctest ^>= 0.16.0+ build-depends: doctest >= 0.16.0 && < 1.0.0 , Glob ^>= 0.10.0
src/Colog/Core.hs view
@@ -1,7 +1,10 @@ {- |-Copyright: (c) 2018-2020 Kowainik-SPDX-License-Identifier: MPL-2.0-Maintainer: Kowainik <xrom.xkov@gmail.com>+Module : Colog.Core+Copyright : (c) 2018-2020 Kowainik, 2021-2026 Co-Log+SPDX-License-Identifier : MPL-2.0+Maintainer : Co-Log <xrom.xkov@gmail.com>+Stability : Stable+Portability : Portable Exports all core functionality. @co-log-core@ is a lightweight package that defines only core data type and various combinators to work with it.@@ -25,6 +28,7 @@ * __"Colog.Core.IO":__ basic loggers that work with 'Control.Monad.IO.Class.MonadIO' and 'String'. * __"Colog.Core.Severity":__ logger severity. -}+ module Colog.Core ( module Colog.Core.Action , module Colog.Core.Class
src/Colog/Core/Action.hs view
@@ -6,9 +6,12 @@ {-# LANGUAGE UndecidableInstances #-} {- |-Copyright: (c) 2018-2020 Kowainik-SPDX-License-Identifier: MPL-2.0-Maintainer: Kowainik <xrom.xkov@gmail.com>+Module : Colog.Core.Action+Copyright : (c) 2018-2020 Kowainik, 2021-2026 Co-Log+SPDX-License-Identifier : MPL-2.0+Maintainer : Co-Log <xrom.xkov@gmail.com>+Stability : Stable+Portability : Portable Implements core data types and combinators for logging actions. -}@@ -63,15 +66,15 @@ , hoistLogAction ) where -import Control.Monad (when, (<=<), (>=>))-import Data.Coerce (coerce)-import Data.Foldable (fold, for_, traverse_)-import Data.Kind (Constraint)-import Data.List.NonEmpty (NonEmpty (..))-import Data.Monoid (Monoid (..))-import Data.Semigroup (Semigroup (..), stimesMonoid)-import Data.Void (Void, absurd)-import GHC.TypeLits (ErrorMessage (..), TypeError)+import Control.Monad (when, (<=<), (>=>))+import Data.Coerce (coerce)+import Data.Foldable (fold, for_, traverse_)+import Data.Kind (Constraint)+import Data.List.NonEmpty (NonEmpty (..))+import Data.Monoid (Monoid (..))+import Data.Semigroup (Semigroup (..), stimesMonoid)+import Data.Void (Void, absurd)+import GHC.TypeLits (ErrorMessage (..), TypeError) #if MIN_VERSION_base(4,12,0) import qualified Data.Functor.Contravariant as Contravariant@@ -164,12 +167,12 @@ where UnrepresentableClass = TypeError ( 'Text "'LogAction' cannot have a 'Functor' instance by design."- ':$$: 'Text "However, you've attempted to use this instance."+ ' :$$: 'Text "However, you've attempted to use this instance." #if MIN_VERSION_base(4,12,0)- ':$$: 'Text ""- ':$$: 'Text "Probably you meant 'Contravariant' class instance with the following methods:"- ':$$: 'Text " * contramap :: (a -> b) -> LogAction m b -> LogAction m a"- ':$$: 'Text " * (>$) :: b -> LogAction m b -> LogAction m a"+ ' :$$: 'Text ""+ ' :$$: 'Text "Probably you meant 'Contravariant' class instance with the following methods:"+ ' :$$: 'Text " * contramap :: (a -> b) -> LogAction m b -> LogAction m a"+ ' :$$: 'Text " * (>$) :: b -> LogAction m b -> LogAction m a" #endif )
src/Colog/Core/Class.hs view
@@ -3,9 +3,12 @@ {-# LANGUAGE Rank2Types #-} {- |-Copyright: (c) 2018-2020 Kowainik-SPDX-License-Identifier: MPL-2.0-Maintainer: Kowainik <xrom.xkov@gmail.com>+Module : Colog.Core.Class+Copyright : (c) 2018-2020 Kowainik, 2021-2026 Co-Log+SPDX-License-Identifier : MPL-2.0+Maintainer : Co-Log <xrom.xkov@gmail.com>+Stability : Stable+Portability : Portable Provides type class for values that has access to 'LogAction'. -}@@ -18,7 +21,7 @@ , Lens' ) where -import Colog.Core.Action (LogAction)+import Colog.Core.Action (LogAction) import Data.Functor.Const (Const (..))
src/Colog/Core/IO.hs view
@@ -1,9 +1,12 @@ {-# LANGUAGE CPP #-} {- |-Copyright: (c) 2018-2020 Kowainik-SPDX-License-Identifier: MPL-2.0-Maintainer: Kowainik <xrom.xkov@gmail.com>+Module : Colog.Core.IO+Copyright : (c) 2018-2020 Kowainik, 2021-2026 Co-Log+SPDX-License-Identifier : MPL-2.0+Maintainer : Co-Log <xrom.xkov@gmail.com>+Stability : Stable+Portability : Portable Introduces logging actions working in 'MonadIO'. These actions are very basic and inefficient because they use the 'String' data type. If you don't want to@@ -27,11 +30,14 @@ -- * Various combinators , liftLogIO+ , logFlush ) where -import Colog.Core.Action (LogAction (..))+import Colog.Core.Action (LogAction (..)) import Control.Monad.IO.Class (MonadIO, liftIO)-import System.IO (Handle, IOMode (AppendMode), hPrint, hPutStrLn, stderr, withFile)+import Data.Semigroup ((<>))+import System.IO (Handle, IOMode (AppendMode), hFlush, hPrint,+ hPutStrLn, stderr, withFile) {- $setup@@ -43,6 +49,8 @@ ---------------------------------------------------------------------------- {- | Action that prints 'String' to stdout.+This action does not flush the output buffer.+If buffering mode is block buffering, the effect of this action can be delayed. >>> logStringStdout <& "foo" foo@@ -53,6 +61,8 @@ {-# SPECIALIZE logStringStdout :: LogAction IO String #-} {- | Action that prints 'String' to stderr.+This action does not flush the output buffer.+If buffering mode is block buffering, the effect of this action can be delayed. >>> logStringStderr <& "foo" foo@@ -63,6 +73,8 @@ {-# SPECIALIZE logStringStderr :: LogAction IO String #-} {- | Action that prints 'String' to 'Handle'.+This action does not flush the output buffer.+If buffering mode is block buffering, the effect of this action can be delayed. >>> logStringHandle stderr <& "foo" foo@@ -77,7 +89,7 @@ file only once at the start of the application and write to 'Handle' instead of opening file each time we need to write to it. -Opens file in 'AppendMode'.+Opens file in 'AppendMode'. Automatically flushes the output buffer. #ifndef mingw32_HOST_OS @@ -88,7 +100,8 @@ #endif -} withLogStringFile :: MonadIO m => FilePath -> (LogAction m String -> IO r) -> IO r-withLogStringFile path action = withFile path AppendMode $ action . logStringHandle+withLogStringFile path action = withFile path AppendMode $ \handle ->+ action (logStringHandle handle <> logFlush handle) {-# INLINE withLogStringFile #-} {-# SPECIALIZE withLogStringFile :: FilePath -> (LogAction IO String -> IO r) -> IO r #-} @@ -97,6 +110,8 @@ ---------------------------------------------------------------------------- {- | Action that prints to stdout using 'Show'.+This action does not flush the output buffer.+If buffering mode is block buffering, the effect of this action can be delayed. >>> logPrint <& 5 5@@ -107,6 +122,8 @@ {-# SPECIALIZE logPrint :: Show a => LogAction IO a #-} {- | Action that prints to stderr using 'Show'.+This action does not flush the output buffer.+If buffering mode is block buffering, the effect of this action can be delayed. >>> logPrintStderr <& 5 5@@ -117,6 +134,8 @@ {-# SPECIALIZE logPrintStderr :: Show a => LogAction IO a #-} {- | Action that prints to a 'Handle' using 'Show'.+This action does not flush the output buffer.+If buffering mode is block buffering, the effect of this action can be delayed. >>> logPrintHandle stderr <& 5 5@@ -133,7 +152,8 @@ => FilePath -> (LogAction m a -> IO r) -> IO r-withLogPrintFile path action = withFile path AppendMode $ action . logPrintHandle+withLogPrintFile path action = withFile path AppendMode $ \handle ->+ action (logPrintHandle handle <> logFlush handle) {-# INLINE withLogPrintFile #-} {-# SPECIALIZE withLogPrintFile :: Show a => FilePath -> (LogAction IO a -> IO r) -> IO r #-} @@ -150,3 +170,13 @@ liftLogIO :: MonadIO m => LogAction IO msg -> LogAction m msg liftLogIO (LogAction action) = LogAction (liftIO . action) {-# INLINE liftLogIO #-}++{- | This action can be used in combination with other actions to flush+a handle every time you log anything.++@since 0.3.0.0+-}+logFlush :: MonadIO m => Handle -> LogAction m a+logFlush handle = LogAction $ const $ liftIO $ hFlush handle+{-# INLINE logFlush #-}+{-# SPECIALIZE logFlush :: Handle -> LogAction IO a #-}
src/Colog/Core/Severity.hs view
@@ -1,9 +1,12 @@ {-# LANGUAGE PatternSynonyms #-} {- |-Copyright: (c) 2018-2020 Kowainik-SPDX-License-Identifier: MPL-2.0-Maintainer: Kowainik <xrom.xkov@gmail.com>+Module : Colog.Core.Severity+Copyright : (c) 2018-2020 Kowainik, 2021-2026 Co-Log+SPDX-License-Identifier : MPL-2.0+Maintainer : Co-Log <xrom.xkov@gmail.com>+Stability : Stable+Portability : Portable This module introduces 'Severity' data type for expressing how severe the message is. Also, it contains useful functions and patterns for work with 'Severity'.@@ -31,6 +34,8 @@ , pattern W , pattern E , filterBySeverity+ , WithSeverity (..)+ , mapSeverity ) where import Data.Ix (Ix)@@ -99,3 +104,42 @@ -> LogAction m a filterBySeverity s fs = cfilter (\a -> fs a >= s) {-# INLINE filterBySeverity #-}++-- Note: the order of the fields here is to allow the constructor to be used infix.+{-| A message tagged with a 'Severity'.+ +It is common to want to log various types of messages tagged with a severity. +'WithSeverity' provides a standard way to do so while allowing the messages to be processed independently of the severity.++It is easy to 'cmap' over a 'LogAction m (WithSeverity a)', or to filter based on the severity.++@+logSomething :: 'LogAction' m ('WithSeverity' 'String') -> m ()+logSomething logger = logger <& "hello" \`WithSeverity\` 'Info'++cmap' :: (b -> a) -> 'LogAction' m ('WithSeverity' a) -> 'LogAction' m ('WithSeverity' b)+cmap' f action = 'cmap' ('fmap' f) action++filterBySeverity' :: ('Applicative' m) => 'Severity' -> 'LogAction' m ('WithSeverity' a) -> 'LogAction' m ('WithSeverity' a)+filterBySeverity' threshold action = 'filterBySeverity' threshold 'getSeverity' action+@++@since 0.3.1.0+-}+data WithSeverity msg = WithSeverity { getMsg :: msg , getSeverity :: Severity }+ deriving stock (Show, Eq, Ord, Functor, Foldable, Traversable)++{- | Map the given function over the severity of a 'WithSeverity'.+ +This can be useful to operate generically over the severity, for example:++@+suppressErrors :: 'LogAction' m ('WithSeverity' msg) -> 'LogAction' m ('WithSeverity' msg)+suppressErrors = 'cmap' ('mapSeverity' (\s -> if s == 'Error' then 'Warning' else s))+@++@since 0.3.1.0+-}+mapSeverity :: (Severity -> Severity) -> WithSeverity msg -> WithSeverity msg+mapSeverity f (WithSeverity msg sev) = WithSeverity msg (f sev)+{-# INLINE mapSeverity #-}