packages feed

mmark 0.0.7.6 → 0.0.8.0

raw patch · 18 files changed

+434/−377 lines, 18 filesdep ~containersdep ~microlenssetup-changedPVP ok

version bump matches the API change (PVP)

Dependency ranges changed: containers, microlens

API changes (from Hackage documentation)

+ Text.MMark.Internal.Type: Blockquote :: [Block a] -> Block a
+ Text.MMark.Internal.Type: CellAlignCenter :: CellAlign
+ Text.MMark.Internal.Type: CellAlignDefault :: CellAlign
+ Text.MMark.Internal.Type: CellAlignLeft :: CellAlign
+ Text.MMark.Internal.Type: CellAlignRight :: CellAlign
+ Text.MMark.Internal.Type: CodeBlock :: Maybe Text -> Text -> Block a
+ Text.MMark.Internal.Type: CodeSpan :: Text -> Inline
+ Text.MMark.Internal.Type: Emphasis :: NonEmpty Inline -> Inline
+ Text.MMark.Internal.Type: Extension :: Endo Bni -> Render (Block (Ois, Html ())) -> Endo Inline -> Render Inline -> Extension
+ Text.MMark.Internal.Type: Heading1 :: a -> Block a
+ Text.MMark.Internal.Type: Heading2 :: a -> Block a
+ Text.MMark.Internal.Type: Heading3 :: a -> Block a
+ Text.MMark.Internal.Type: Heading4 :: a -> Block a
+ Text.MMark.Internal.Type: Heading5 :: a -> Block a
+ Text.MMark.Internal.Type: Heading6 :: a -> Block a
+ Text.MMark.Internal.Type: Image :: NonEmpty Inline -> URI -> Maybe Text -> Inline
+ Text.MMark.Internal.Type: LineBreak :: Inline
+ Text.MMark.Internal.Type: Link :: NonEmpty Inline -> URI -> Maybe Text -> Inline
+ Text.MMark.Internal.Type: MMark :: Maybe Value -> [Bni] -> Extension -> MMark
+ Text.MMark.Internal.Type: Naked :: a -> Block a
+ Text.MMark.Internal.Type: OrderedList :: Word -> NonEmpty [Block a] -> Block a
+ Text.MMark.Internal.Type: Paragraph :: a -> Block a
+ Text.MMark.Internal.Type: Plain :: Text -> Inline
+ Text.MMark.Internal.Type: Render :: ((a -> Html ()) -> a -> Html ()) -> Render a
+ Text.MMark.Internal.Type: Strikeout :: NonEmpty Inline -> Inline
+ Text.MMark.Internal.Type: Strong :: NonEmpty Inline -> Inline
+ Text.MMark.Internal.Type: Subscript :: NonEmpty Inline -> Inline
+ Text.MMark.Internal.Type: Superscript :: NonEmpty Inline -> Inline
+ Text.MMark.Internal.Type: Table :: NonEmpty CellAlign -> NonEmpty (NonEmpty a) -> Block a
+ Text.MMark.Internal.Type: ThematicBreak :: Block a
+ Text.MMark.Internal.Type: UnorderedList :: NonEmpty [Block a] -> Block a
+ Text.MMark.Internal.Type: [extBlockRender] :: Extension -> Render (Block (Ois, Html ()))
+ Text.MMark.Internal.Type: [extBlockTrans] :: Extension -> Endo Bni
+ Text.MMark.Internal.Type: [extInlineRender] :: Extension -> Render Inline
+ Text.MMark.Internal.Type: [extInlineTrans] :: Extension -> Endo Inline
+ Text.MMark.Internal.Type: [mmarkBlocks] :: MMark -> [Bni]
+ Text.MMark.Internal.Type: [mmarkExtension] :: MMark -> Extension
+ Text.MMark.Internal.Type: [mmarkYaml] :: MMark -> Maybe Value
+ Text.MMark.Internal.Type: [runRender] :: Render a -> (a -> Html ()) -> a -> Html ()
+ Text.MMark.Internal.Type: data Block a
+ Text.MMark.Internal.Type: data CellAlign
+ Text.MMark.Internal.Type: data Extension
+ Text.MMark.Internal.Type: data Inline
+ Text.MMark.Internal.Type: data MMark
+ Text.MMark.Internal.Type: data Ois
+ Text.MMark.Internal.Type: getOis :: Ois -> NonEmpty Inline
+ Text.MMark.Internal.Type: instance Control.DeepSeq.NFData Text.MMark.Internal.Type.CellAlign
+ Text.MMark.Internal.Type: instance Control.DeepSeq.NFData Text.MMark.Internal.Type.Inline
+ Text.MMark.Internal.Type: instance Control.DeepSeq.NFData Text.MMark.Internal.Type.MMark
+ Text.MMark.Internal.Type: instance Control.DeepSeq.NFData a => Control.DeepSeq.NFData (Text.MMark.Internal.Type.Block a)
+ Text.MMark.Internal.Type: instance Data.Data.Data Text.MMark.Internal.Type.CellAlign
+ Text.MMark.Internal.Type: instance Data.Data.Data Text.MMark.Internal.Type.Inline
+ Text.MMark.Internal.Type: instance Data.Data.Data a => Data.Data.Data (Text.MMark.Internal.Type.Block a)
+ Text.MMark.Internal.Type: instance Data.Foldable.Foldable Text.MMark.Internal.Type.Block
+ Text.MMark.Internal.Type: instance GHC.Base.Functor Text.MMark.Internal.Type.Block
+ Text.MMark.Internal.Type: instance GHC.Base.Monoid (Text.MMark.Internal.Type.Render a)
+ Text.MMark.Internal.Type: instance GHC.Base.Monoid Text.MMark.Internal.Type.Extension
+ Text.MMark.Internal.Type: instance GHC.Base.Semigroup (Text.MMark.Internal.Type.Render a)
+ Text.MMark.Internal.Type: instance GHC.Base.Semigroup Text.MMark.Internal.Type.Extension
+ Text.MMark.Internal.Type: instance GHC.Classes.Eq Text.MMark.Internal.Type.CellAlign
+ Text.MMark.Internal.Type: instance GHC.Classes.Eq Text.MMark.Internal.Type.Inline
+ Text.MMark.Internal.Type: instance GHC.Classes.Eq a => GHC.Classes.Eq (Text.MMark.Internal.Type.Block a)
+ Text.MMark.Internal.Type: instance GHC.Classes.Ord Text.MMark.Internal.Type.CellAlign
+ Text.MMark.Internal.Type: instance GHC.Classes.Ord Text.MMark.Internal.Type.Inline
+ Text.MMark.Internal.Type: instance GHC.Classes.Ord a => GHC.Classes.Ord (Text.MMark.Internal.Type.Block a)
+ Text.MMark.Internal.Type: instance GHC.Generics.Generic (Text.MMark.Internal.Type.Block a)
+ Text.MMark.Internal.Type: instance GHC.Generics.Generic Text.MMark.Internal.Type.CellAlign
+ Text.MMark.Internal.Type: instance GHC.Generics.Generic Text.MMark.Internal.Type.Inline
+ Text.MMark.Internal.Type: instance GHC.Show.Show Text.MMark.Internal.Type.CellAlign
+ Text.MMark.Internal.Type: instance GHC.Show.Show Text.MMark.Internal.Type.Inline
+ Text.MMark.Internal.Type: instance GHC.Show.Show Text.MMark.Internal.Type.MMark
+ Text.MMark.Internal.Type: instance GHC.Show.Show a => GHC.Show.Show (Text.MMark.Internal.Type.Block a)
+ Text.MMark.Internal.Type: mkOisInternal :: NonEmpty Inline -> Ois
+ Text.MMark.Internal.Type: newtype Render a
+ Text.MMark.Internal.Type: type Bni = Block (NonEmpty Inline)
+ Text.MMark.Render: applyBlockRender :: Render (Block (Ois, Html ())) -> Block (Ois, Html ()) -> Html ()
+ Text.MMark.Render: applyInlineRender :: Render Inline -> Inline -> Html ()
+ Text.MMark.Render: defaultBlockRender :: (Block (Ois, Html ()) -> Html ()) -> Block (Ois, Html ()) -> Html ()
+ Text.MMark.Render: defaultInlineRender :: (Inline -> Html ()) -> Inline -> Html ()
+ Text.MMark.Render: newline :: Html ()
+ Text.MMark.Render: render :: MMark -> Html ()
+ Text.MMark.Trans: applyBlockTrans :: Endo Bni -> Bni -> Bni
+ Text.MMark.Trans: applyInlineTrans :: Endo Inline -> Inline -> Inline
+ Text.MMark.Util: asPlainText :: NonEmpty Inline -> Text
+ Text.MMark.Util: headerFragment :: Text -> URI
+ Text.MMark.Util: headerId :: NonEmpty Inline -> Text

Files

CHANGELOG.md view
@@ -1,3 +1,8 @@+## MMark 0.0.8.0++* Exposed the following modules: `Text.MMark.Internal.Type`,+  `Text.MMark.Render`, `Text.MMark.Trans`, `Text.MMark.Util`.+ ## MMark 0.0.7.6  * The test suite now passes with `modern-uri-0.3.4.4`.
− Setup.hs
@@ -1,6 +0,0 @@-module Main (main) where--import Distribution.Simple--main :: IO ()-main = defaultMain
Text/MMark.hs view
@@ -133,11 +133,11 @@   ) where -import qualified Control.Foldl as L+import Control.Foldl qualified as L import Data.Aeson+import Text.MMark.Internal.Type import Text.MMark.Parser (MMarkErr (..), parse) import Text.MMark.Render (render)-import Text.MMark.Type  ---------------------------------------------------------------------------- -- Extensions@@ -186,7 +186,7 @@ -- -- @since 0.0.2.0 runScannerM ::-  Monad m =>+  (Monad m) =>   -- | Document to scan   MMark ->   -- | 'L.FoldM' to use
Text/MMark/Extension.hs view
@@ -102,10 +102,10 @@   ) where -import qualified Control.Foldl as L+import Control.Foldl qualified as L import Data.Monoid hiding ((<>)) import Lucid-import Text.MMark.Type+import Text.MMark.Internal.Type import Text.MMark.Util  -- | Create an extension that performs a transformation on 'Block's of@@ -164,7 +164,7 @@ -- -- @since 0.0.2.0 scannerM ::-  Monad m =>+  (Monad m) =>   -- | Initial state   m a ->   -- | Folding function
+ Text/MMark/Internal/Type.hs view
@@ -0,0 +1,241 @@+{-# LANGUAGE DeriveDataTypeable #-}+{-# LANGUAGE DeriveFoldable #-}+{-# LANGUAGE DeriveFunctor #-}+{-# LANGUAGE DeriveGeneric #-}+{-# LANGUAGE RecordWildCards #-}++-- |+-- Module      :  Text.MMark.Internal.Type+-- Copyright   :  © 2017–present Mark Karpov+-- License     :  BSD 3 clause+--+-- Maintainer  :  Mark Karpov <markkarpov92@gmail.com>+-- Stability   :  experimental+-- Portability :  portable+--+-- Internal type definitions. The public subset of these is re-exported from+-- "Text.MMark.Extension".+--+-- @since 0.0.8.0+module Text.MMark.Internal.Type+  ( MMark (..),+    Extension (..),+    Render (..),+    Bni,+    Block (..),+    CellAlign (..),+    Inline (..),+    Ois,+    mkOisInternal,+    getOis,+  )+where++import Control.DeepSeq+import Data.Aeson+import Data.Data (Data)+import Data.Function (on)+import Data.List.NonEmpty (NonEmpty (..))+import Data.Monoid hiding ((<>))+import Data.Text (Text)+import Data.Typeable (Typeable)+import GHC.Generics+import Lucid+import Text.URI (URI (..))++-- | Representation of complete markdown document. You can't look inside of+-- 'MMark' on purpose. The only way to influence an 'MMark' document you+-- obtain as a result of parsing is via the extension mechanism.+data MMark = MMark+  { -- | Parsed YAML document at the beginning (optional)+    mmarkYaml :: Maybe Value,+    -- | Actual contents of the document+    mmarkBlocks :: [Bni],+    -- | Extension specifying how to process and render the blocks+    mmarkExtension :: Extension+  }++instance NFData MMark where+  rnf MMark {..} = rnf mmarkYaml `seq` rnf mmarkBlocks++-- | Dummy instance.+--+-- @since 0.0.5.0+instance Show MMark where+  show = const "MMark {..}"++-- | An extension. You can apply extensions with 'Text.MMark.useExtension'+-- and 'Text.MMark.useExtensions' functions. The "Text.MMark.Extension"+-- module provides tools for writing your own extensions.+--+-- Note that 'Extension' is an instance of 'Semigroup' and 'Monoid', i.e.+-- you can combine several extensions into one. Since the @('<>')@ operator+-- is right-associative and 'mconcat' is a right fold under the hood, the+-- expression+--+-- > l <> r+--+-- means that the extension @r@ will be applied before the extension @l@,+-- similar to how 'Endo' works. This may seem counter-intuitive, but only+-- with this logic we get consistency of ordering with more complex+-- expressions:+--+-- > e2 <> e1 <> e0 == e2 <> (e1 <> e0)+--+-- Here, @e0@ will be applied first, then @e1@, then @e2@. The same applies+-- to expressions involving 'mconcat'—extensions closer to beginning of the+-- list passed to 'mconcat' will be applied later.+data Extension = Extension+  { -- | Block transformation+    extBlockTrans :: Endo Bni,+    -- | Block render+    extBlockRender :: Render (Block (Ois, Html ())),+    -- | Inline transformation+    extInlineTrans :: Endo Inline,+    -- | Inline render+    extInlineRender :: Render Inline+  }++instance Semigroup Extension where+  x <> y =+    Extension+      { extBlockTrans = on (<>) extBlockTrans x y,+        extBlockRender = on (<>) extBlockRender x y,+        extInlineTrans = on (<>) extInlineTrans x y,+        extInlineRender = on (<>) extInlineRender x y+      }++instance Monoid Extension where+  mempty =+    Extension+      { extBlockTrans = mempty,+        extBlockRender = mempty,+        extInlineTrans = mempty,+        extInlineRender = mempty+      }+  mappend = (<>)++-- | An internal type that captures the extensible rendering process we use.+-- 'Render' has a function inside which transforms a rendering function of+-- the type @a -> Html ()@.+--+-- @since 0.0.8.0+newtype Render a = Render+  {runRender :: (a -> Html ()) -> a -> Html ()}++instance Semigroup (Render a) where+  Render f <> Render g = Render (f . g)++instance Monoid (Render a) where+  mempty = Render id+  mappend = (<>)++-- | A shortcut for the frequently used type @'Block' ('NonEmpty'+-- 'Inline')@.+type Bni = Block (NonEmpty Inline)++-- | We can think of a markdown document as a collection of+-- blocks—structural elements like paragraphs, block quotations, lists,+-- headings, thematic breaks, and code blocks. Some blocks (like block+-- quotes and list items) contain other blocks; others (like headings and+-- paragraphs) contain inline content, see 'Inline'.+--+-- We can divide blocks into two types: container blocks, which can contain+-- other blocks, and leaf blocks, which cannot.+data Block a+  = -- | Thematic break, leaf block+    ThematicBreak+  | -- | Heading (level 1), leaf block+    Heading1 a+  | -- | Heading (level 2), leaf block+    Heading2 a+  | -- | Heading (level 3), leaf block+    Heading3 a+  | -- | Heading (level 4), leaf block+    Heading4 a+  | -- | Heading (level 5), leaf block+    Heading5 a+  | -- | Heading (level 6), leaf block+    Heading6 a+  | -- | Code block, leaf block with info string and contents+    CodeBlock (Maybe Text) Text+  | -- | Naked content, without an enclosing tag+    Naked a+  | -- | Paragraph, leaf block+    Paragraph a+  | -- | Blockquote container block+    Blockquote [Block a]+  | -- | Ordered list ('Word' is the start index), container block+    OrderedList Word (NonEmpty [Block a])+  | -- | Unordered list, container block+    UnorderedList (NonEmpty [Block a])+  | -- | Table, first argument is the alignment options, then we have a+    -- 'NonEmpty' list of rows, where every row is a 'NonEmpty' list of+    -- cells, where every cell is an @a@ thing.+    --+    -- The first row is always the header row, because pipe-tables that we+    -- support cannot lack a header row.+    --+    -- @since 0.0.4.0+    Table (NonEmpty CellAlign) (NonEmpty (NonEmpty a))+  deriving (Show, Eq, Ord, Data, Typeable, Generic, Functor, Foldable)++instance (NFData a) => NFData (Block a)++-- | Options for cell alignment in tables.+--+-- @since 0.0.4.0+data CellAlign+  = -- | No specific alignment specified+    CellAlignDefault+  | -- | Left-alignment+    CellAlignLeft+  | -- | Right-alignment+    CellAlignRight+  | -- | Center-alignment+    CellAlignCenter+  deriving (Show, Eq, Ord, Data, Typeable, Generic)++instance NFData CellAlign++-- | Inline markdown content.+data Inline+  = -- | Plain text+    Plain Text+  | -- | Line break (hard)+    LineBreak+  | -- | Emphasis+    Emphasis (NonEmpty Inline)+  | -- | Strong emphasis+    Strong (NonEmpty Inline)+  | -- | Strikeout+    Strikeout (NonEmpty Inline)+  | -- | Subscript+    Subscript (NonEmpty Inline)+  | -- | Superscript+    Superscript (NonEmpty Inline)+  | -- | Code span+    CodeSpan Text+  | -- | Link with text, destination, and optionally title+    Link (NonEmpty Inline) URI (Maybe Text)+  | -- | Image with description, URL, and optionally title+    Image (NonEmpty Inline) URI (Maybe Text)+  deriving (Show, Eq, Ord, Data, Typeable, Generic)++instance NFData Inline++-- | A wrapper for “original inlines”. Source inlines are wrapped in this+-- during rendering of inline components and then it's available to block+-- render, but only for inspection. Altering of 'Ois' is not possible+-- because the user cannot construct a value of the 'Ois' type, he\/she can+-- only inspect it with 'getOis'.+newtype Ois = Ois (NonEmpty Inline)++-- | Make an 'Ois' value. This is an internal constructor that should not be+-- exposed!+mkOisInternal :: NonEmpty Inline -> Ois+mkOisInternal = Ois++-- | Project @'NonEmpty' 'Inline'@ from 'Ois'.+getOis :: Ois -> NonEmpty Inline+getOis (Ois inlines) = inlines
Text/MMark/Parser.hs view
@@ -24,35 +24,35 @@   ) where -import Control.Applicative (Alternative, liftA2)+import Control.Applicative hiding (many, some) import Control.Monad-import qualified Control.Monad.Combinators.NonEmpty as NE-import qualified Data.Aeson as Aeson+import Control.Monad.Combinators.NonEmpty qualified as NE+import Data.Aeson qualified as Aeson import Data.Bifunctor (Bifunctor (..)) import Data.Bool (bool)-import qualified Data.Char as Char-import qualified Data.DList as DList+import Data.Char qualified as Char+import Data.DList qualified as DList import Data.HTML.Entities (htmlEntityMap)-import qualified Data.HashMap.Strict as HM+import Data.HashMap.Strict qualified as HM import Data.List.NonEmpty (NonEmpty (..), (<|))-import qualified Data.List.NonEmpty as NE+import Data.List.NonEmpty qualified as NE import Data.Maybe (catMaybes, fromJust, isJust, isNothing) import Data.Monoid (Any (..)) import Data.Ratio ((%))-import qualified Data.Set as E+import Data.Set qualified as E import Data.Text (Text)-import qualified Data.Text as T-import qualified Data.Text.Encoding as TE+import Data.Text qualified as T+import Data.Text.Encoding qualified as TE import Lens.Micro ((^.))-import qualified Text.Email.Validate as Email+import Text.Email.Validate qualified as Email+import Text.MMark.Internal.Type import Text.MMark.Parser.Internal-import Text.MMark.Type import Text.MMark.Util import Text.Megaparsec hiding (State (..), parse) import Text.Megaparsec.Char hiding (eol)-import qualified Text.Megaparsec.Char.Lexer as L+import Text.Megaparsec.Char.Lexer qualified as L import Text.URI (URI)-import qualified Text.URI as URI+import Text.URI qualified as URI import Text.URI.Lens (uriPath)  #if !defined(ghcjs_HOST_OS)@@ -518,7 +518,7 @@         <$ manyTill           (optional nonEmptyLine)           (endOfTable >>= guard)-          <* sc+        <* sc  -- | Parse a paragraph or naked text (in some cases). pParagraph :: BParser (Block Isp)@@ -816,7 +816,7 @@     mkLabel = T.unwords . T.words . asPlainText  -- | Parse a URI.-pUri :: (Ord e, Show e, MonadParsec e Text m) => m URI+pUri :: (MonadParsec e Text m) => m URI pUri = between (char '<') (char '>') URI.parser <|> naked   where     naked = do@@ -831,7 +831,7 @@       return r  -- | Parse a title of a link or an image.-pTitle :: MonadParsec MMarkErr Text m => m Text+pTitle :: (MonadParsec MMarkErr Text m) => m Text pTitle =   choice     [ p '\"' '\"',@@ -845,7 +845,7 @@          in manyEscapedWith f "unescaped character"  -- | Parse label of a reference link.-pRefLabel :: MonadParsec MMarkErr Text m => m (Int, Text)+pRefLabel :: (MonadParsec MMarkErr Text m) => m (Int, Text) pRefLabel = do   try $ do     void (char '[')@@ -927,7 +927,7 @@   where     go !n = liftA2 (:) (m n) (go (n + 1)) <|> pure [] -foldMany :: MonadPlus m => m (a -> a) -> m (a -> a)+foldMany :: (MonadPlus m) => m (a -> a) -> m (a -> a) foldMany f = go id   where     go g =@@ -935,7 +935,7 @@         Nothing -> pure g         Just h -> go (h . g) -foldMany' :: MonadPlus m => m ([a] -> [a]) -> m [a]+foldMany' :: (MonadPlus m) => m ([a] -> [a]) -> m [a] foldMany' f = ($ []) <$> go id   where     go g =@@ -943,13 +943,13 @@         Nothing -> pure g         Just h -> go (g . h) -foldSome :: MonadPlus m => m (a -> a) -> m (a -> a)+foldSome :: (MonadPlus m) => m (a -> a) -> m (a -> a) foldSome f = liftA2 (flip (.)) f (foldMany f) -foldSome' :: MonadPlus m => m ([a] -> [a]) -> m [a]+foldSome' :: (MonadPlus m) => m ([a] -> [a]) -> m [a] foldSome' f = liftA2 ($) f (foldMany' f) -sepByCount :: MonadPlus m => Int -> m a -> m sep -> m [a]+sepByCount :: (MonadPlus m) => Int -> m a -> m sep -> m [a] sepByCount 0 _ _ = pure [] sepByCount n p sep = liftA2 (:) p (count (n - 1) (sep *> p)) @@ -957,7 +957,7 @@ nonEmptyLine = takeWhile1P Nothing notNewline  manyEscapedWith ::-  MonadParsec MMarkErr Text m =>+  (MonadParsec MMarkErr Text m) =>   (Char -> Bool) ->   String ->   m Text@@ -970,7 +970,7 @@     ]  someEscapedWith ::-  MonadParsec MMarkErr Text m =>+  (MonadParsec MMarkErr Text m) =>   (Char -> Bool) ->   m Text someEscapedWith f =@@ -981,13 +981,13 @@       (:) <$> satisfy f     ] -escapedChar :: MonadParsec e Text m => m Char+escapedChar :: (MonadParsec e Text m) => m Char escapedChar =   label "escaped character" $     try (char '\\' *> satisfy isAsciiPunctuation)  -- | Parse an HTML5 entity reference.-entityRef :: MonadParsec MMarkErr Text m => m String+entityRef :: (MonadParsec MMarkErr Text m) => m String entityRef = do   o <- getOffset   let f (TrivialError _ us es) = TrivialError o us es@@ -1004,7 +1004,7 @@     Just txt -> return (T.unpack txt)  -- | Parse a numeric character using the given numeric parser.-numRef :: MonadParsec MMarkErr Text m => m Char+numRef :: (MonadParsec MMarkErr Text m) => m Char numRef = do   o <- getOffset   let f = between (string "&#") (char ';')@@ -1013,19 +1013,19 @@     then customFailure' o (InvalidNumericCharacter n)     else return (Char.chr n) -sc :: MonadParsec e Text m => m ()+sc :: (MonadParsec e Text m) => m () sc = void $ takeWhileP (Just "white space") isSpaceN -sc1 :: MonadParsec e Text m => m ()+sc1 :: (MonadParsec e Text m) => m () sc1 = void $ takeWhile1P (Just "white space") isSpaceN -sc' :: MonadParsec e Text m => m ()+sc' :: (MonadParsec e Text m) => m () sc' = void $ takeWhileP (Just "white space") isSpace -sc1' :: MonadParsec e Text m => m ()+sc1' :: (MonadParsec e Text m) => m () sc1' = void $ takeWhile1P (Just "white space") isSpace -eol :: MonadParsec e Text m => m ()+eol :: (MonadParsec e Text m) => m () eol =   void . label "newline" $     choice@@ -1034,7 +1034,7 @@         string "\r"       ] -eol' :: MonadParsec e Text m => m Bool+eol' :: (MonadParsec e Text m) => m Bool eol' = option False (True <$ eol)  ----------------------------------------------------------------------------@@ -1152,7 +1152,7 @@   SubscriptFrame -> "~"   SuperscriptFrame -> "^" -replaceEof :: forall e. Show e => String -> ParseError Text e -> ParseError Text e+replaceEof :: String -> ParseError Text e -> ParseError Text e replaceEof altLabel = \case   TrivialError pos us es -> TrivialError pos (f <$> us) (E.map f es)   FancyError pos xs -> FancyError pos xs@@ -1245,7 +1245,7 @@     toNaked (Paragraph inner) = Naked inner     toNaked other = other -succeeds :: Alternative m => m () -> m Bool+succeeds :: (Alternative m) => m () -> m Bool succeeds m = True <$ m <|> pure False  prependErr :: Int -> MMarkErr -> [Block Isp] -> [Block Isp]@@ -1259,7 +1259,7 @@ toNesTokens :: Text -> NonEmpty Char toNesTokens = NE.fromList . T.unpack -unexpEic :: MonadParsec e Text m => ErrorItem Char -> m a+unexpEic :: (MonadParsec e Text m) => ErrorItem Char -> m a unexpEic x =   failure     (Just x)@@ -1278,7 +1278,7 @@  -- | Report custom failure at specified location. customFailure' ::-  MonadParsec MMarkErr Text m =>+  (MonadParsec MMarkErr Text m) =>   Int ->   MMarkErr ->   m a
Text/MMark/Parser/Internal.hs view
@@ -47,8 +47,8 @@ import Data.Bifunctor import Data.Function ((&)) import Data.HashMap.Strict (HashMap)-import qualified Data.HashMap.Strict as HM-import qualified Data.List.NonEmpty as NE+import Data.HashMap.Strict qualified as HM+import Data.List.NonEmpty qualified as NE import Data.Ratio ((%)) import Data.Text (Text) import Data.Text.Metrics (damerauLevenshteinNorm)@@ -56,7 +56,7 @@ import Lens.Micro.Extras (view) import Text.MMark.Parser.Internal.Type import Text.Megaparsec hiding (State)-import qualified Text.Megaparsec as M+import Text.Megaparsec qualified as M import Text.URI (URI)  ----------------------------------------------------------------------------@@ -252,7 +252,7 @@     }  -- | Locally change state in a state monad and then restore it back.-locally :: MonadState s m => Lens' s a -> a -> m b -> m b+locally :: (MonadState s m) => Lens' s a -> a -> m b -> m b locally l x m = do   y <- gets (^. l)   modify' (set l x)
Text/MMark/Parser/Internal/Type.hs view
@@ -47,17 +47,17 @@  import Control.DeepSeq import Data.CaseInsensitive (CI)-import qualified Data.CaseInsensitive as CI+import Data.CaseInsensitive qualified as CI import Data.Data (Data) import Data.HashMap.Strict (HashMap)-import qualified Data.HashMap.Strict as HM+import Data.HashMap.Strict qualified as HM import Data.Hashable (Hashable) import Data.List (intercalate) import Data.List.NonEmpty (NonEmpty (..))-import qualified Data.List.NonEmpty as NE+import Data.List.NonEmpty qualified as NE import Data.Proxy import Data.Text (Text)-import qualified Data.Text as T+import Data.Text qualified as T import Data.Typeable (Typeable) import GHC.Generics import Lens.Micro.TH@@ -208,10 +208,13 @@       showTokens (Proxy :: Proxy Text) dels         ++ " should be in left- or right- flanking position"     ListStartIndexTooBig n ->-      "ordered list start numbers must be nine digits or less, " ++ show n+      "ordered list start numbers must be nine digits or less, "+        ++ show n         ++ " is too big"     ListIndexOutOfOrder actual expected ->-      "list index is out of order: " ++ show actual ++ ", expected "+      "list index is out of order: "+        ++ show actual+        ++ ", expected "         ++ show expected     DuplicateReferenceDefinition name ->       "duplicate reference definitions are not allowed: \""
Text/MMark/Render.hs view
@@ -12,8 +12,15 @@ -- Portability :  portable -- -- MMark rendering machinery.+--+-- @since 0.0.8.0 module Text.MMark.Render   ( render,+    applyBlockRender,+    defaultBlockRender,+    applyInlineRender,+    defaultInlineRender,+    newline,   ) where @@ -22,13 +29,13 @@ import Data.Char (isSpace) import Data.Function (fix) import Data.List.NonEmpty (NonEmpty (..))-import qualified Data.List.NonEmpty as NE-import qualified Data.Text as T+import Data.List.NonEmpty qualified as NE+import Data.Text qualified as T import Lucid+import Text.MMark.Internal.Type import Text.MMark.Trans-import Text.MMark.Type import Text.MMark.Util-import qualified Text.URI as URI+import Text.URI qualified as URI  -- | Render a 'MMark' markdown document. You can then render @'Html' ()@ to -- various things:@@ -50,6 +57,8 @@         . fmap (applyInlineTrans extInlineTrans)  -- | Apply a 'Render' to a given @'Block' 'Html' ()@.+--+-- @since 0.0.8.0 applyBlockRender ::   Render (Block (Ois, Html ())) ->   Block (Ois, Html ()) ->@@ -57,6 +66,8 @@ applyBlockRender r = fix (runRender r . defaultBlockRender)  -- | The default 'Block' render.+--+-- @since 0.0.8.0 defaultBlockRender ::   -- | Rendering function to use to render sub-blocks   (Block (Ois, Html ()) -> Html ()) ->@@ -131,10 +142,14 @@       CellAlignCenter -> [style_ "text-align:center"]  -- | Apply a render to a given 'Inline'.+--+-- @since 0.0.8.0 applyInlineRender :: Render Inline -> Inline -> Html () applyInlineRender r = fix (runRender r . defaultInlineRender)  -- | The default render for 'Inline' elements.+--+-- @since 0.0.8.0 defaultInlineRender ::   -- | Rendering function to use to render sub-inlines   (Inline -> Html ()) ->@@ -165,5 +180,7 @@      in img_ (alt_ (asPlainText desc) : src_ (URI.render src) : title)  -- | HTML containing a newline.+--+-- @since 0.0.8.0 newline :: Html () newline = "\n"
Text/MMark/Trans.hs view
@@ -10,6 +10,8 @@ -- Portability :  portable -- -- MMark block\/inline transformation helpers.+--+-- @since 0.0.8.0 module Text.MMark.Trans   ( applyBlockTrans,     applyInlineTrans,@@ -17,9 +19,11 @@ where  import Data.Monoid hiding ((<>))-import Text.MMark.Type+import Text.MMark.Internal.Type  -- | Apply block transformation in the @'Endo' 'Bni'@ form to a block 'Bni'.+--+-- @since 0.0.8.0 applyBlockTrans :: Endo Bni -> Bni -> Bni applyBlockTrans trans@(Endo f) = \case   Blockquote xs -> f (Blockquote (s xs))@@ -31,6 +35,8 @@  -- | Apply inline transformation in the @'Endo' 'Inline'@ form to an -- 'Inline'.+--+-- @since 0.0.8.0 applyInlineTrans :: Endo Inline -> Inline -> Inline applyInlineTrans trans@(Endo f) = \case   Emphasis xs -> f (Emphasis (s xs))
− Text/MMark/Type.hs
@@ -1,237 +0,0 @@-{-# LANGUAGE DeriveDataTypeable #-}-{-# LANGUAGE DeriveFoldable #-}-{-# LANGUAGE DeriveFunctor #-}-{-# LANGUAGE DeriveGeneric #-}-{-# LANGUAGE RecordWildCards #-}---- |--- Module      :  Text.MMark.Type--- Copyright   :  © 2017–present Mark Karpov--- License     :  BSD 3 clause------ Maintainer  :  Mark Karpov <markkarpov92@gmail.com>--- Stability   :  experimental--- Portability :  portable------ Internal type definitions. Some of these are re-exported in the public--- modules.-module Text.MMark.Type-  ( MMark (..),-    Extension (..),-    Render (..),-    Bni,-    Block (..),-    CellAlign (..),-    Inline (..),-    Ois,-    mkOisInternal,-    getOis,-  )-where--import Control.DeepSeq-import Data.Aeson-import Data.Data (Data)-import Data.Function (on)-import Data.List.NonEmpty (NonEmpty (..))-import Data.Monoid hiding ((<>))-import Data.Text (Text)-import Data.Typeable (Typeable)-import GHC.Generics-import Lucid-import Text.URI (URI (..))---- | Representation of complete markdown document. You can't look inside of--- 'MMark' on purpose. The only way to influence an 'MMark' document you--- obtain as a result of parsing is via the extension mechanism.-data MMark = MMark-  { -- | Parsed YAML document at the beginning (optional)-    mmarkYaml :: Maybe Value,-    -- | Actual contents of the document-    mmarkBlocks :: [Bni],-    -- | Extension specifying how to process and render the blocks-    mmarkExtension :: Extension-  }--instance NFData MMark where-  rnf MMark {..} = rnf mmarkYaml `seq` rnf mmarkBlocks---- | Dummy instance.------ @since 0.0.5.0-instance Show MMark where-  show = const "MMark {..}"---- | An extension. You can apply extensions with 'Text.MMark.useExtension'--- and 'Text.MMark.useExtensions' functions. The "Text.MMark.Extension"--- module provides tools for writing your own extensions.------ Note that 'Extension' is an instance of 'Semigroup' and 'Monoid', i.e.--- you can combine several extensions into one. Since the @('<>')@ operator--- is right-associative and 'mconcat' is a right fold under the hood, the--- expression------ > l <> r------ means that the extension @r@ will be applied before the extension @l@,--- similar to how 'Endo' works. This may seem counter-intuitive, but only--- with this logic we get consistency of ordering with more complex--- expressions:------ > e2 <> e1 <> e0 == e2 <> (e1 <> e0)------ Here, @e0@ will be applied first, then @e1@, then @e2@. The same applies--- to expressions involving 'mconcat'—extensions closer to beginning of the--- list passed to 'mconcat' will be applied later.-data Extension = Extension-  { -- | Block transformation-    extBlockTrans :: Endo Bni,-    -- | Block render-    extBlockRender :: Render (Block (Ois, Html ())),-    -- | Inline transformation-    extInlineTrans :: Endo Inline,-    -- | Inline render-    extInlineRender :: Render Inline-  }--instance Semigroup Extension where-  x <> y =-    Extension-      { extBlockTrans = on (<>) extBlockTrans x y,-        extBlockRender = on (<>) extBlockRender x y,-        extInlineTrans = on (<>) extInlineTrans x y,-        extInlineRender = on (<>) extInlineRender x y-      }--instance Monoid Extension where-  mempty =-    Extension-      { extBlockTrans = mempty,-        extBlockRender = mempty,-        extInlineTrans = mempty,-        extInlineRender = mempty-      }-  mappend = (<>)---- | An internal type that captures the extensible rendering process we use.--- 'Render' has a function inside which transforms a rendering function of--- the type @a -> Html ()@.-newtype Render a = Render-  {runRender :: (a -> Html ()) -> a -> Html ()}--instance Semigroup (Render a) where-  Render f <> Render g = Render (f . g)--instance Monoid (Render a) where-  mempty = Render id-  mappend = (<>)---- | A shortcut for the frequently used type @'Block' ('NonEmpty'--- 'Inline')@.-type Bni = Block (NonEmpty Inline)---- | We can think of a markdown document as a collection of--- blocks—structural elements like paragraphs, block quotations, lists,--- headings, thematic breaks, and code blocks. Some blocks (like block--- quotes and list items) contain other blocks; others (like headings and--- paragraphs) contain inline content, see 'Inline'.------ We can divide blocks into two types: container blocks, which can contain--- other blocks, and leaf blocks, which cannot.-data Block a-  = -- | Thematic break, leaf block-    ThematicBreak-  | -- | Heading (level 1), leaf block-    Heading1 a-  | -- | Heading (level 2), leaf block-    Heading2 a-  | -- | Heading (level 3), leaf block-    Heading3 a-  | -- | Heading (level 4), leaf block-    Heading4 a-  | -- | Heading (level 5), leaf block-    Heading5 a-  | -- | Heading (level 6), leaf block-    Heading6 a-  | -- | Code block, leaf block with info string and contents-    CodeBlock (Maybe Text) Text-  | -- | Naked content, without an enclosing tag-    Naked a-  | -- | Paragraph, leaf block-    Paragraph a-  | -- | Blockquote container block-    Blockquote [Block a]-  | -- | Ordered list ('Word' is the start index), container block-    OrderedList Word (NonEmpty [Block a])-  | -- | Unordered list, container block-    UnorderedList (NonEmpty [Block a])-  | -- | Table, first argument is the alignment options, then we have a-    -- 'NonEmpty' list of rows, where every row is a 'NonEmpty' list of-    -- cells, where every cell is an @a@ thing.-    ---    -- The first row is always the header row, because pipe-tables that we-    -- support cannot lack a header row.-    ---    -- @since 0.0.4.0-    Table (NonEmpty CellAlign) (NonEmpty (NonEmpty a))-  deriving (Show, Eq, Ord, Data, Typeable, Generic, Functor, Foldable)--instance NFData a => NFData (Block a)---- | Options for cell alignment in tables.------ @since 0.0.4.0-data CellAlign-  = -- | No specific alignment specified-    CellAlignDefault-  | -- | Left-alignment-    CellAlignLeft-  | -- | Right-alignment-    CellAlignRight-  | -- | Center-alignment-    CellAlignCenter-  deriving (Show, Eq, Ord, Data, Typeable, Generic)--instance NFData CellAlign---- | Inline markdown content.-data Inline-  = -- | Plain text-    Plain Text-  | -- | Line break (hard)-    LineBreak-  | -- | Emphasis-    Emphasis (NonEmpty Inline)-  | -- | Strong emphasis-    Strong (NonEmpty Inline)-  | -- | Strikeout-    Strikeout (NonEmpty Inline)-  | -- | Subscript-    Subscript (NonEmpty Inline)-  | -- | Superscript-    Superscript (NonEmpty Inline)-  | -- | Code span-    CodeSpan Text-  | -- | Link with text, destination, and optionally title-    Link (NonEmpty Inline) URI (Maybe Text)-  | -- | Image with description, URL, and optionally title-    Image (NonEmpty Inline) URI (Maybe Text)-  deriving (Show, Eq, Ord, Data, Typeable, Generic)--instance NFData Inline---- | A wrapper for “original inlines”. Source inlines are wrapped in this--- during rendering of inline components and then it's available to block--- render, but only for inspection. Altering of 'Ois' is not possible--- because the user cannot construct a value of the 'Ois' type, he\/she can--- only inspect it with 'getOis'.-newtype Ois = Ois (NonEmpty Inline)---- | Make an 'Ois' value. This is an internal constructor that should not be--- exposed!-mkOisInternal :: NonEmpty Inline -> Ois-mkOisInternal = Ois---- | Project @'NonEmpty' 'Inline'@ from 'Ois'.-getOis :: Ois -> NonEmpty Inline-getOis (Ois inlines) = inlines
Text/MMark/Util.hs view
@@ -10,7 +10,9 @@ -- Stability   :  experimental -- Portability :  portable ----- Internal utilities.+-- Misc utilities.+--+-- @since 0.0.8.0 module Text.MMark.Util   ( asPlainText,     headerId,@@ -21,13 +23,15 @@ import Data.Char (isAlphaNum, isSpace) import Data.List.NonEmpty (NonEmpty (..)) import Data.Text (Text)-import qualified Data.Text as T-import Text.MMark.Type+import Data.Text qualified as T+import Text.MMark.Internal.Type import Text.URI (URI (..))-import qualified Text.URI as URI+import Text.URI qualified as URI  -- | Convert a non-empty collection of 'Inline's into their plain text -- representation. This is used e.g. to render image descriptions.+--+-- @since 0.0.8.0 asPlainText :: NonEmpty Inline -> Text asPlainText = foldMap $ \case   Plain txt -> txt@@ -46,6 +50,8 @@ -- extensions. -- -- See also: 'headerFragment'.+--+-- @since 0.0.8.0 headerId :: NonEmpty Inline -> Text headerId =   T.intercalate "-"@@ -56,6 +62,8 @@  -- | Generate a 'URI' containing only a fragment from its textual -- representation. Useful for getting URL from id of a header.+--+-- @since 0.0.8.0 headerFragment :: Text -> URI headerFragment fragment =   URI
bench/memory/Main.hs view
@@ -1,7 +1,7 @@ module Main (main) where -import qualified Data.Text.IO as T-import qualified Text.MMark as MMark+import Data.Text.IO qualified as T+import Text.MMark qualified as MMark import Weigh  main :: IO ()
bench/speed/Main.hs view
@@ -1,8 +1,8 @@ module Main (main) where  import Criterion.Main-import qualified Data.Text.IO as T-import qualified Text.MMark as MMark+import Data.Text.IO qualified as T+import Text.MMark qualified as MMark  main :: IO () main =
mmark.cabal view
@@ -1,11 +1,11 @@ cabal-version:   2.4 name:            mmark-version:         0.0.7.6+version:         0.0.8.0 license:         BSD-3-Clause license-file:    LICENSE.md maintainer:      Mark Karpov <markkarpov92@gmail.com> author:          Mark Karpov <markkarpov92@gmail.com>-tested-with:     ghc ==8.10.7 ghc ==9.0.2 ghc ==9.2.1+tested-with:     ghc ==9.4.7 ghc ==9.6.3 ghc ==9.8.1 homepage:        https://github.com/mmark-md/mmark bug-reports:     https://github.com/mmark-md/mmark/issues synopsis:        Strict markdown processor for writers@@ -33,36 +33,36 @@     exposed-modules:         Text.MMark         Text.MMark.Extension+        Text.MMark.Internal.Type+        Text.MMark.Render+        Text.MMark.Trans+        Text.MMark.Util      other-modules:         Text.MMark.Parser         Text.MMark.Parser.Internal         Text.MMark.Parser.Internal.Type-        Text.MMark.Render-        Text.MMark.Trans-        Text.MMark.Type-        Text.MMark.Util -    default-language: Haskell2010+    default-language: GHC2021     build-depends:         aeson >=0.11 && <3,-        base >=4.13 && <5.0,+        base >=4.15 && <5,         case-insensitive >=1.2 && <1.3,         containers >=0.5 && <0.7,-        deepseq >=1.3 && <1.5,-        dlist >=0.8 && <2.0,+        deepseq >=1.3 && <1.6,+        dlist >=0.8 && <2,         email-validate >=2.2 && <2.4,         foldl >=1.2 && <1.5,-        hashable >=1 && <1.5,+        hashable >=1 && <1.6,         html-entity-map >=0.1 && <0.2,-        lucid >=2.9.13 && <3.0,-        megaparsec >=8.0 && <10.0,+        lucid >=2.9.13 && <3,+        megaparsec >=8 && <10,         microlens >=0.4 && <0.5,         microlens-th >=0.4 && <0.5,         modern-uri >=0.3.4.4 && <0.4,-        mtl >=2.0 && <3.0,-        parser-combinators >=0.4 && <2.0,-        text >=0.2 && <2.1,+        mtl >=2 && <3,+        parser-combinators >=0.4 && <2,+        text >=0.2 && <2.2,         text-metrics >=0.3 && <0.4,         unordered-containers >=0.2.5 && <0.3 @@ -70,16 +70,13 @@         build-depends: yaml >=0.11.5 && <0.12      if flag(dev)-        ghc-options: -O0 -Wall -Werror+        ghc-options:+            -Wall -Werror -Wredundant-constraints -Wpartial-fields+            -Wunused-packages      else         ghc-options: -O2 -Wall -    if flag(dev)-        ghc-options:-            -Wcompat -Wincomplete-record-updates -Wincomplete-uni-patterns-            -Wnoncanonical-monad-instances-     if impl(ghcjs >=0)         ghcjs-options: +RTS -K1G -RTS -Wall @@ -92,22 +89,24 @@         Text.MMark.ExtensionSpec         Text.MMark.TestUtils -    default-language: Haskell2010+    default-language: GHC2021     build-depends:-        QuickCheck >=2.4 && <3.0,+        QuickCheck >=2.4 && <3,         aeson >=0.11 && <3,-        base >=4.13 && <5.0,+        base >=4.15 && <5,         foldl >=1.2 && <1.5,-        hspec >=2.0 && <3.0,-        hspec-megaparsec >=2.0 && <3.0,-        lucid >=2.9.13 && <3.0,-        megaparsec >=8.0 && <10.0,+        hspec >=2 && <3,+        hspec-megaparsec >=2 && <3,+        lucid >=2.9.13 && <3,+        megaparsec >=8 && <10,         mmark,         modern-uri >=0.3.4.4 && <0.4,-        text >=0.2 && <2.1+        text >=0.2 && <2.2      if flag(dev)-        ghc-options: -O0 -Wall -Werror+        ghc-options:+            -Wall -Werror -Wredundant-constraints -Wpartial-fields+            -Wunused-packages      else         ghc-options: -O2 -Wall@@ -119,15 +118,17 @@     type:             exitcode-stdio-1.0     main-is:          Main.hs     hs-source-dirs:   bench/speed-    default-language: Haskell2010+    default-language: GHC2021     build-depends:-        base >=4.13 && <5.0,-        criterion >=0.6.2.1 && <1.6,+        base >=4.15 && <5,+        criterion >=0.6.2.1 && <1.7,         mmark,-        text >=0.2 && <2.1+        text >=0.2 && <2.2      if flag(dev)-        ghc-options: -O2 -Wall -Werror+        ghc-options:+            -Wall -Werror -Wredundant-constraints -Wpartial-fields+            -Wunused-packages      else         ghc-options: -O2 -Wall@@ -139,15 +140,17 @@     type:             exitcode-stdio-1.0     main-is:          Main.hs     hs-source-dirs:   bench/memory-    default-language: Haskell2010+    default-language: GHC2021     build-depends:-        base >=4.13 && <5.0,+        base >=4.15 && <5,         mmark,-        text >=0.2 && <2.1,+        text >=0.2 && <2.2,         weigh >=0.0.4      if flag(dev)-        ghc-options: -O2 -Wall -Werror+        ghc-options:+            -Wall -Werror -Wredundant-constraints -Wpartial-fields+            -Wunused-packages      else         ghc-options: -O2 -Wall
tests/Text/MMark/ExtensionSpec.hs view
@@ -6,15 +6,15 @@  import Data.List.NonEmpty (NonEmpty (..)) import Data.Text (Text)-import qualified Data.Text as T-import qualified Lucid as L+import Data.Text qualified as T+import Lucid qualified as L import Test.Hspec import Test.QuickCheck-import qualified Text.MMark as MMark+import Text.MMark qualified as MMark import Text.MMark.Extension (Block (..), Inline (..))-import qualified Text.MMark.Extension as Ext+import Text.MMark.Extension qualified as Ext import Text.MMark.TestUtils-import qualified Text.URI as URI+import Text.URI qualified as URI  spec :: Spec spec = parallel $ do
tests/Text/MMark/TestUtils.hs view
@@ -15,13 +15,13 @@ where  import Control.Monad-import qualified Data.List.NonEmpty as NE+import Data.List.NonEmpty qualified as NE import Data.Text (Text)-import qualified Data.Text.Lazy as TL-import qualified Lucid as L+import Data.Text.Lazy qualified as TL+import Lucid qualified as L import Test.Hspec import Text.MMark (MMark, MMarkErr)-import qualified Text.MMark as MMark+import Text.MMark qualified as MMark import Text.Megaparsec  ----------------------------------------------------------------------------
tests/Text/MMarkSpec.hs view
@@ -3,24 +3,24 @@  module Text.MMarkSpec (spec) where -import qualified Control.Foldl as L+import Control.Foldl qualified as L import Data.Aeson import Data.Char import Data.List.NonEmpty (NonEmpty (..))-import qualified Data.List.NonEmpty as NE+import Data.List.NonEmpty qualified as NE import Data.Monoid import Data.Text (Text)-import qualified Data.Text as T-import qualified Data.Text.IO as TIO+import Data.Text qualified as T+import Data.Text.IO qualified as TIO import Lucid import Test.Hspec import Test.Hspec.Megaparsec import Text.MMark (MMarkErr (..))-import qualified Text.MMark as MMark+import Text.MMark qualified as MMark import Text.MMark.Extension (Inline (..))-import qualified Text.MMark.Extension as Ext+import Text.MMark.Extension qualified as Ext import Text.MMark.TestUtils-import Text.Megaparsec (ErrorFancy (..), Stream)+import Text.Megaparsec (ErrorFancy (..))  -- NOTE This test suite is mostly based on (sometimes altered) examples from -- the Common Mark specification. We use the version 0.28 (2017-08-01),@@ -1346,7 +1346,11 @@          in s               ~-> err                 7-                ( utok '\\' <> etoks "//" <> etok '#' <> etok '/' <> etok '<'+                ( utok '\\'+                    <> etoks "//"+                    <> etok '#'+                    <> etok '/'+                    <> etok '<'                     <> etok '?'                     <> elabel "ASCII alpha character"                     <> euri@@ -1379,7 +1383,11 @@          in s               ~-> err                 7-                ( utok '"' <> etoks "//" <> etok '#' <> etok '/' <> etok '<'+                ( utok '"'+                    <> etoks "//"+                    <> etok '#'+                    <> etok '/'+                    <> etok '<'                     <> etok '?'                     <> elabel "ASCII alpha character"                     <> euri@@ -1521,7 +1529,10 @@          in s               ~~-> [ err                        9-                       ( utok '[' <> etoks "&#" <> etok '&' <> etok ']'+                       ( utok '['+                           <> etoks "&#"+                           <> etok '&'+                           <> etok ']'                            <> elabel "escaped character"                        ),                      err 17 (utok '[' <> etok ']' <> eic)@@ -1531,7 +1542,10 @@          in s               ~~-> [ err                        9-                       ( utok '[' <> etoks "&#" <> etok '&' <> etok ']'+                       ( utok '['+                           <> etoks "&#"+                           <> etok '&'+                           <> etok ']'                            <> elabel "escaped character"                        ),                      err 21 (utok '[' <> etok ']' <> eic)@@ -1864,7 +1878,10 @@          in s               ~-> err                 23-                ( utoks "so" <> etok '\'' <> etok '\"' <> etok '('+                ( utoks "so"+                    <> etok '\''+                    <> etok '\"'+                    <> etok '('                     <> elabel "white space"                     <> elabel "newline"                 )@@ -2111,27 +2128,27 @@ -- Helpers  -- | Unexpected end of inline block.-ueib :: Stream s => ET s+ueib :: ET s ueib = ulabel "end of inline block"  -- | Expecting end of inline block.-eeib :: Stream s => ET s+eeib :: ET s eeib = elabel "end of inline block"  -- | Expecting end of URI.-euri :: Stream s => ET s+euri :: ET s euri = elabel "end of URI"  -- | Expecting inline content.-eic :: Stream s => ET s+eic :: ET s eic = elabel "inline content"  -- | Expecting white space.-ews :: Stream s => ET s+ews :: ET s ews = elabel "white space"  -- | Expecting code span content.-ecsc :: Stream s => ET s+ecsc :: ET s ecsc = elabel "code span content"  -- | Expecting common URI components.