module Bookhound.Format.Parsers.Yaml (yaml, nil, integer, float, bool, string,
                     list, mapping) where


import Bookhound.Parser              (Parser, andThen, check, exactly,
                                      withError)
import Bookhound.ParserCombinators   (IsMatch (..), maybeWithin, (<#>), (<|>),
                                      (->>-), (|*), (|+), (|++), (|?))
import Bookhound.Parsers.Char        (char, colon, dash, dot, doubleQuote,
                                      hashTag, newLine, question, quote, space,
                                      whiteSpace)
import Bookhound.Parsers.Collections (listOf, mapOf)
import Bookhound.Parsers.Number      (double, hexInt, int, octInt)
import Bookhound.Parsers.String      (blankLine, blankLines, spaces,
                                      spacesOrTabs, tabs, withinDoubleQuotes,
                                      withinQuotes)

import Bookhound.Format.SyntaxTrees.Yaml    (CollectionType (..), YamlExpression (..))

import qualified Bookhound.Parsers.DateTime as Dt

import           Data.List (nub)
import qualified Data.Map  as Map



yaml :: Parser YamlExpression
yaml :: Parser YamlExpression
yaml =  Parser [Char]
normalize forall a. Parser [Char] -> Parser a -> Parser a
`andThen` Int -> Parser YamlExpression
yamlWithIndent (-Int
1)




-- TODO: Add support for anchors and aliases

nil :: Parser YamlExpression
nil :: Parser YamlExpression
nil = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Null"
  forall a b. (a -> b) -> a -> b
$ YamlExpression
YamlNull forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ forall a. IsMatch a => [a] -> Parser a
oneOf [[Char]
"null", [Char]
"Null", [Char]
"NULL"]

integer :: Parser YamlExpression
integer :: Parser YamlExpression
integer = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Integer"
  forall a b. (a -> b) -> a -> b
$ Integer -> YamlExpression
YamlInteger forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser Integer
hexInt forall a. Parser a -> Parser a -> Parser a
<|> Parser Integer
octInt forall a. Parser a -> Parser a -> Parser a
<|> Parser Integer
int)

float :: Parser YamlExpression
float :: Parser YamlExpression
float = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Float"
  forall a b. (a -> b) -> a -> b
$ Double -> YamlExpression
YamlFloat forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser Double
double

bool :: Parser YamlExpression
bool :: Parser YamlExpression
bool = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Bool"
  forall a b. (a -> b) -> a -> b
$ Bool -> YamlExpression
YamlBool forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Bool
True  forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ forall a. IsMatch a => [a] -> Parser a
oneOf [[Char]
"true", [Char]
"True", [Char]
"TRUE"]    forall a. Parser a -> Parser a -> Parser a
<|>
                  Bool
False forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ forall a. IsMatch a => [a] -> Parser a
oneOf [[Char]
"false", [Char]
"False", [Char]
"FALSE"])


dateTime :: Parser YamlExpression
dateTime :: Parser YamlExpression
dateTime = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml DateTime"
  forall a b. (a -> b) -> a -> b
$ ZonedTime -> YamlExpression
YamlDateTime forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser ZonedTime
Dt.dateTime

date :: Parser YamlExpression
date :: Parser YamlExpression
date = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Date"
  forall a b. (a -> b) -> a -> b
$ Day -> YamlExpression
YamlDate forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser Day
Dt.date

time :: Parser YamlExpression
time :: Parser YamlExpression
time = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Time"
  forall a b. (a -> b) -> a -> b
$ TimeOfDay -> YamlExpression
YamlTime forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser TimeOfDay
Dt.time


string :: Int -> Parser YamlExpression
string :: Int -> Parser YamlExpression
string Int
indent = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml String"
  forall a b. (a -> b) -> a -> b
$ [Char] -> YamlExpression
YamlString forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Int -> Parser [Char]
text Int
indent


sequential :: Parser a -> Int -> Parser [YamlExpression]
sequential :: forall a. Parser a -> Int -> Parser [YamlExpression]
sequential Parser a
sep Int
indent = Parser [YamlExpression]
listParser
  where

  listParser :: Parser [YamlExpression]
listParser = forall a. Parser (Int, a) -> Int -> Parser [a]
indentationCheck Parser (Int, YamlExpression)
elemParser Int
indent

  elemParser :: Parser (Int, YamlExpression)
elemParser = do Int
n <- forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser Char
space |*)
                  Parser a
sep forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> Parser Char
whiteSpace
                  YamlExpression
elm <- Int -> Parser YamlExpression
yamlWithIndent Int
n
                  pure (Int
n, YamlExpression
elm)


list :: Int -> Parser YamlExpression
list :: Int -> Parser YamlExpression
list Int
indent = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Json List"
  forall a b. (a -> b) -> a -> b
$   (CollectionType -> [YamlExpression] -> YamlExpression
YamlList CollectionType
Inline   forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser [YamlExpression]
jsonList)
  forall a. Parser a -> Parser a -> Parser a
<|> (CollectionType -> [YamlExpression] -> YamlExpression
YamlList CollectionType
Standard forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser [YamlExpression]
yamlList)
  where
    yamlList :: Parser [YamlExpression]
yamlList = forall a. Parser a -> Int -> Parser [YamlExpression]
sequential Parser Char
dash Int
indent
    jsonList :: Parser [YamlExpression]
jsonList = forall a b. Parser a -> Parser b -> Parser b
maybeWithin Parser [Char]
spacesOrTabs forall a b. (a -> b) -> a -> b
$ forall a. Parser a -> Parser [a]
listOf forall a b. (a -> b) -> a -> b
$ Int -> Parser YamlExpression
yamlWithIndent (-Int
1)


set :: Int -> Parser YamlExpression
set :: Int -> Parser YamlExpression
set Int
indent = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Set"
  forall a b. (a -> b) -> a -> b
$ CollectionType -> [YamlExpression] -> YamlExpression
YamlList CollectionType
Standard forall b c a. (b -> c) -> (a -> b) -> a -> c
. forall a. Eq a => [a] -> [a]
nub forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. Parser a -> Int -> Parser [YamlExpression]
sequential Parser Char
question Int
indent


mapping :: Int -> Parser YamlExpression
mapping :: Int -> Parser YamlExpression
mapping Int
indent = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Yaml Mapping"
  forall a b. (a -> b) -> a -> b
$   (CollectionType -> Map [Char] YamlExpression -> YamlExpression
YamlMap CollectionType
Inline   forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser (Map [Char] YamlExpression)
jsonMap)
  forall a. Parser a -> Parser a -> Parser a
<|> (CollectionType -> Map [Char] YamlExpression -> YamlExpression
YamlMap CollectionType
Standard forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser (Map [Char] YamlExpression)
yamlMap)
  where
    yamlMap :: Parser (Map [Char] YamlExpression)
yamlMap = forall k a. Ord k => [(k, a)] -> Map k a
Map.fromList forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser [([Char], YamlExpression)]
mapParser
    jsonMap :: Parser (Map [Char] YamlExpression)
jsonMap = forall a b. Parser a -> Parser b -> Parser b
maybeWithin Parser [Char]
spacesOrTabs forall a b. (a -> b) -> a -> b
$ forall b a c.
Ord b =>
Parser a -> Parser b -> Parser c -> Parser (Map b c)
mapOf Parser Char
colon (Int -> Parser [Char]
text Int
100) forall a b. (a -> b) -> a -> b
$ Int -> Parser YamlExpression
yamlWithIndent (-Int
1)

    mapParser :: Parser [([Char], YamlExpression)]
mapParser = forall a. Parser (Int, a) -> Int -> Parser [a]
indentationCheck Parser (Int, ([Char], YamlExpression))
keyValueParser Int
indent

    keyValueParser :: Parser (Int, ([Char], YamlExpression))
keyValueParser = do Int
n <- forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser Char
space |*)
                        [Char]
key <- forall a. Show a => a -> [Char]
show forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Int -> Parser YamlExpression
element Int
indent
                        (Parser [Char]
spacesOrTabs |?)
                        Parser Char
colon forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> Parser Char
whiteSpace
                        YamlExpression
value <- Int -> Parser YamlExpression
yamlWithIndent Int
n
                        pure (Int
n, ([Char]
key, YamlExpression
value))



element :: Int -> Parser YamlExpression
element :: Int -> Parser YamlExpression
element Int
indent = forall a. Parser a -> Parser a
exactly (Parser YamlExpression
dateTime forall a. Parser a -> Parser a -> Parser a
<|> Parser YamlExpression
date forall a. Parser a -> Parser a -> Parser a
<|> Parser YamlExpression
time forall a. Parser a -> Parser a -> Parser a
<|> Parser YamlExpression
float forall a. Parser a -> Parser a -> Parser a
<|>
                          Parser YamlExpression
integer forall a. Parser a -> Parser a -> Parser a
<|> Parser YamlExpression
bool forall a. Parser a -> Parser a -> Parser a
<|> Parser YamlExpression
nil) forall a. Parser a -> Parser a -> Parser a
<|>
                    Int -> Parser YamlExpression
string Int
indent

container :: Int -> Parser YamlExpression
container :: Int -> Parser YamlExpression
container Int
indent = Int -> Parser YamlExpression
list Int
indent forall a. Parser a -> Parser a -> Parser a
<|> Int -> Parser YamlExpression
mapping Int
indent forall a. Parser a -> Parser a -> Parser a
<|> Int -> Parser YamlExpression
set Int
indent



yamlWithIndent :: Int -> Parser YamlExpression
yamlWithIndent :: Int -> Parser YamlExpression
yamlWithIndent Int
indent = forall a b. Parser a -> Parser b -> Parser b
maybeWithin ((Parser [Char]
blankLine forall a. Parser a -> Parser a -> Parser a
<|> Parser [Char]
comment forall a. Parser a -> Parser a -> Parser a
<|> Parser [Char]
directive forall a. Parser a -> Parser a -> Parser a
<|>
                                      Parser [Char]
docStart forall a. Parser a -> Parser a -> Parser a
<|> Parser [Char]
docEnd) |+)
                        Parser YamlExpression
yamlValue
  where
    yamlValue :: Parser YamlExpression
yamlValue = Int -> Parser YamlExpression
container Int
indent forall a. Parser a -> Parser a -> Parser a
<|> forall a b. Parser a -> Parser b -> Parser b
maybeWithin Parser [Char]
spacesOrTabs (Int -> Parser YamlExpression
element Int
indent)
    comment :: Parser [Char]
comment = Parser Char
hashTag forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> (forall a. IsMatch a => Parser a -> Parser a
inverse Parser Char
newLine |+) forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* Parser Char
newLine
    directive :: Parser [Char]
directive = forall a. IsMatch a => a -> Parser a
is [Char]
"%" forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> (forall a. IsMatch a => Parser a -> Parser a
inverse Parser Char
space forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> (forall a. IsMatch a => Parser a -> Parser a
inverse Parser Char
newLine |+)) forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* Parser Char
newLine
    docStart :: Parser [Char]
docStart = Parser Char
dash forall a. Parser a -> Integer -> Parser [a]
<#> Integer
3
    docEnd :: Parser [Char]
docEnd = Parser Char
dot forall a. Parser a -> Integer -> Parser [a]
<#> Integer
3



text :: Int -> Parser String
text :: Int -> Parser [Char]
text Int
indent = forall a. Parser a -> Parser a
withinDoubleQuotes (Parser [Char] -> Parser [Char]
quotedParser (forall a. IsMatch a => Parser a -> Parser a
inverse Parser Char
doubleQuote |*))                      forall a. Parser a -> Parser a -> Parser a
<|>
              forall a. Parser a -> Parser a
withinQuotes       (Parser [Char] -> Parser [Char]
quotedParser (forall a. IsMatch a => Parser a -> Parser a
inverse Parser Char
quote       |*))                      forall a. Parser a -> Parser a -> Parser a
<|>
              (forall a. IsMatch a => a -> Parser a
is [Char]
"|" forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> Parser [Char]
blankLine forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> (Parser [Char] -> Parser (Int, [Char])) -> Parser [Char]
plainTextParser Parser [Char] -> Parser (Int, [Char])
literalLineParser)                      forall a. Parser a -> Parser a -> Parser a
<|>
              (forall a. IsMatch a => a -> Parser a
is [Char]
">" forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> Parser [Char]
blankLine forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> (Parser [Char]
spacesOrTabs |?) forall (f :: * -> *) a b. Applicative f => f a -> f b -> f b
*> (Parser [Char] -> Parser (Int, [Char])) -> Parser [Char]
plainTextParser Parser [Char] -> Parser (Int, [Char])
foldingLineParser) forall a. Parser a -> Parser a -> Parser a
<|>
              (Parser [Char] -> Parser (Int, [Char])) -> Parser [Char]
plainTextParser Parser [Char] -> Parser (Int, [Char])
foldingLineParser
  where

    quotedParser :: Parser [Char] -> Parser [Char]
quotedParser Parser [Char]
parser = forall a. Monoid a => [a] -> a
mconcat forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ((forall a b. (a, b) -> b
snd forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser [Char] -> Parser (Int, [Char])
foldingLineParser Parser [Char]
parser) |*)

    plainTextParser :: (Parser [Char] -> Parser (Int, [Char])) -> Parser [Char]
plainTextParser Parser [Char] -> Parser (Int, [Char])
styleParser = Parser Char
allowedStart forall a b.
(ToString a, ToString b) =>
Parser a -> Parser b -> Parser [Char]
->>- Parser [Char]
allowedString forall a b.
(ToString a, ToString b) =>
Parser a -> Parser b -> Parser [Char]
->>-
                                  (forall a. Parser (Int, a) -> Int -> Parser [a]
indentationCheck (Parser [Char] -> Parser (Int, [Char])
styleParser Parser [Char]
allowedString) Int
indent |*)

    foldingLineParser :: Parser [Char] -> Parser (Int, [Char])
foldingLineParser Parser [Char]
parser = do [Char]
sep <- ([Char]
"\n" forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ Parser Char
newLine forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* Parser [Char]
blankLines) forall a. Parser a -> Parser a -> Parser a
<|> ([Char]
" " forall (f :: * -> *) a b. Functor f => a -> f b -> f a
<$ Parser Char
newLine)
                                  Int
n   <- forall a b. Parser a -> Parser b -> Parser b
maybeWithin Parser [Char]
tabs forall a b. (a -> b) -> a -> b
$ forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser Char
space |*)
                                  [Char]
str <- Parser [Char]
parser
                                  pure (Int
n, [Char]
sep forall a. Semigroup a => a -> a -> a
<> [Char]
str)

    literalLineParser :: Parser [Char] -> Parser (Int, [Char])
literalLineParser Parser [Char]
parser = do [Char]
sep <- forall (f :: * -> *) a. Applicative f => a -> f a
pure forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser Char
newLine
                                  Int
n   <- forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser Char
space |*)
                                  [Char]
str <- Parser [Char]
parser
                                  pure (Int
n, [Char]
sep forall a. Semigroup a => a -> a -> a
<> forall a. Int -> a -> [a]
replicate (Int
n forall a. Num a => a -> a -> a
- Int
indent) Char
' ' forall a. Semigroup a => a -> a -> a
<> [Char]
str)

    allowedStart :: Parser Char
allowedStart = forall a. IsMatch a => [a] -> Parser a
noneOf forall a b. (a -> b) -> a -> b
$ [Char]
forbiddenChar forall a. Semigroup a => a -> a -> a
<> [Char
'>', Char
'|', Char
':', Char
'!']

    allowedString :: Parser [Char]
allowedString = (forall a. IsMatch a => [a] -> Parser a
noneOf [Char]
forbiddenChar |*)

    forbiddenChar :: [Char]
forbiddenChar = [Char
'\n', Char
'#', Char
'&', Char
'*', Char
',', Char
'?', Char
'-', Char
':', Char
'[', Char
']', Char
'{', Char
'}']



indentationCheck :: Parser (Int, a) -> Int -> Parser [a]
indentationCheck :: forall a. Parser (Int, a) -> Int -> Parser [a]
indentationCheck Parser (Int, a)
parser Int
indent = ((forall a b. (a, b) -> b
snd forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> forall a. [Char] -> (a -> Bool) -> Parser a -> Parser a
check [Char]
"indentation"
                                  (\(Int
n, a
_) -> Int
n forall a. Ord a => a -> a -> Bool
> Int
indent) Parser (Int, a)
parser) |+)


normalize :: Parser String
normalize :: Parser [Char]
normalize = forall a. [Char] -> Parser a -> Parser a
withError [Char]
"Normalize Yaml"
  forall a b. (a -> b) -> a -> b
$ (Parser [Char]
parserActions forall a b.
(ToString a, ToString b) =>
Parser a -> Parser b -> Parser [Char]
->>- Parser [Char]
normalize) forall a. Parser a -> Parser a -> Parser a
<|> (Parser Char
char |*)
  where

    parserActions :: Parser [Char]
parserActions = Parser [Char]
spreadDashes     forall a. Parser a -> Parser a -> Parser a
<|>
                    Parser [Char]
spreadDashKey    forall a. Parser a -> Parser a -> Parser a
<|>
                    Parser [Char]
spreadKeyDash    forall a. Parser a -> Parser a -> Parser a
<|>
                    Parser [Char]
next

    next :: Parser [Char]
next = forall (f :: * -> *) a. Applicative f => a -> f a
pure forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser Char
char

    spreadDashes :: Parser [Char]
spreadDashes = (forall a. Semigroup a => a -> a -> a
(<>) [Char]
"- ") forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Int, Int) -> [Char]
genDashes forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser (Int, Int)
dashesParser

    genDashes :: (Int, Int) -> [Char]
genDashes (Int
offset, Int
n) = forall (t :: * -> *) a b. Foldable t => (a -> [b]) -> t a -> [b]
concatMap (\Int
x -> [Char]
"- " forall a. Semigroup a => a -> a -> a
<> forall a. Int -> a -> [a]
replicate (Int
offset forall a. Num a => a -> a -> a
+ Int
2 forall a. Num a => a -> a -> a
* Int
x) Char
' ')
                                      [Int
1 .. Int
n forall a. Num a => a -> a -> a
- Int
1]

    dashesParser :: Parser (Int, Int)
dashesParser = do Int
offset <- forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser [Char]
spaces |?)
                      Int
n <- forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> ((Parser Char
dash forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* Parser [Char]
spacesOrTabs) |++)
                      pure (Int
offset, Int
n)


    spreadDashKey :: Parser [Char]
spreadDashKey = (\(Int
offset, [Char]
key) -> forall a. Int -> a -> [a]
replicate Int
offset Char
' ' forall a. Semigroup a => a -> a -> a
<> [Char]
"- " forall a. Semigroup a => a -> a -> a
<>
                                      forall a. Int -> a -> [a]
replicate (Int
offset forall a. Num a => a -> a -> a
+ Int
2) Char
' ' forall a. Semigroup a => a -> a -> a
<> [Char]
key forall a. Semigroup a => a -> a -> a
<> [Char]
": ")
                    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser (Int, [Char])
dashKeyParser

    dashKeyParser :: Parser (Int, [Char])
dashKeyParser = do Int
offset <- forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser [Char]
spaces |?)
                       Parser Char
dash forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* Parser [Char]
spacesOrTabs
                       [Char]
key <- Int -> Parser [Char]
text Int
100 forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* forall a b. Parser a -> Parser b -> Parser b
maybeWithin Parser [Char]
spacesOrTabs Parser Char
colon
                       pure (Int
offset, [Char]
key)


    spreadKeyDash :: Parser [Char]
spreadKeyDash = (\(Int
offset, [Char]
key) -> forall a. Int -> a -> [a]
replicate Int
offset Char
' ' forall a. Semigroup a => a -> a -> a
<> [Char]
key forall a. Semigroup a => a -> a -> a
<> [Char]
": " forall a. Semigroup a => a -> a -> a
<>
                                      forall a. Int -> a -> [a]
replicate (Int
offset forall a. Num a => a -> a -> a
+ Int
2) Char
' ' forall a. Semigroup a => a -> a -> a
<> [Char]
"- ")
                    forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> Parser (Int, [Char])
keyDashParser

    keyDashParser :: Parser (Int, [Char])
keyDashParser = do Int
offset <- forall (t :: * -> *) a. Foldable t => t a -> Int
length forall (f :: * -> *) a b. Functor f => (a -> b) -> f a -> f b
<$> (Parser [Char]
spaces |?)
                       [Char]
key <- Int -> Parser [Char]
text Int
100 forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* forall a b. Parser a -> Parser b -> Parser b
maybeWithin Parser [Char]
spacesOrTabs Parser Char
colon
                       Parser Char
dash forall (f :: * -> *) a b. Applicative f => f a -> f b -> f a
<* Parser [Char]
spacesOrTabs
                       pure (Int
offset, [Char]
key)