Distribution.Fields.Parser

Cabal-3.2.0.0: A framework for packaging Haskell software

License | BSD3
Maintainer | cabal-devel@haskell.org
Portability | portable
Safe Haskell | None
Language | Haskell2010

Distribution.Fields.Parser

Contents

- Types
- Grammar and parsing

Description

Synopsis

- data Field ann
  - = Field !(Name ann) [FieldLine ann]
  - | Section !(Name ann) [SectionArg ann] [Field ann]
- data Name ann = Name !ann !FieldName
- data FieldLine ann = FieldLine !ann !ByteString
- data SectionArg ann
  - = SecArgName !ann !ByteString
  - | SecArgStr !ann !ByteString
  - | SecArgOther !ann !ByteString
- readFields :: ByteString -> Either ParseError [Field Position]
- readFields' :: ByteString -> Either ParseError ([Field Position], [LexWarning])

# Types

data Field ann Source #

A Cabal-like file consists of a series of fields (`foo: bar`) and sections (`library ...`).

Constructors

Field !(Name ann) [FieldLine ann] |
Section !(Name ann) [SectionArg ann] [Field ann] |

#### Instances

Instances details

Functor Field # |
Instance details Defined in Distribution.Fields.Field Methods fmap :: (a -> b) -> Field a -> Field b Source # (<$) :: a -> Field b -> Field a Source #
Foldable Field # |
Instance details Defined in Distribution.Fields.Field Methods fold :: Monoid m => Field m -> m Source # foldMap :: Monoid m => (a -> m) -> Field a -> m Source # foldMap' :: Monoid m => (a -> m) -> Field a -> m Source # foldr :: (a -> b -> b) -> b -> Field a -> b Source # foldr' :: (a -> b -> b) -> b -> Field a -> b Source # foldl :: (b -> a -> b) -> b -> Field a -> b Source # foldl' :: (b -> a -> b) -> b -> Field a -> b Source # foldr1 :: (a -> a -> a) -> Field a -> a Source # foldl1 :: (a -> a -> a) -> Field a -> a Source # toList :: Field a -> [a] Source # null :: Field a -> Bool Source # length :: Field a -> Int Source # elem :: Eq a => a -> Field a -> Bool Source # maximum :: Ord a => Field a -> a Source # minimum :: Ord a => Field a -> a Source # sum :: Num a => Field a -> a Source # product :: Num a => Field a -> a Source #
Traversable Field # |
Instance details Defined in Distribution.Fields.Field Methods traverse :: Applicative f => (a -> f b) -> Field a -> f (Field b) Source # sequenceA :: Applicative f => Field (f a) -> f (Field a) Source # mapM :: Monad m => (a -> m b) -> Field a -> m (Field b) Source # sequence :: Monad m => Field (m a) -> m (Field a) Source #
Eq ann => Eq (Field ann) # |
Instance details Defined in Distribution.Fields.Field Methods (==) :: Field ann -> Field ann -> Bool # (/=) :: Field ann -> Field ann -> Bool #
Show ann => Show (Field ann) # |
Instance details Defined in Distribution.Fields.Field Methods showsPrec :: Int -> Field ann -> ShowS Source # show :: Field ann -> String Source # showList :: [Field ann] -> ShowS Source #

data Name ann Source #

A field name.

Invariant: `ByteString` is lower-case ASCII.

Constructors

Name !ann !FieldName |

#### Instances

Instances details

Functor Name # |
Instance details Defined in Distribution.Fields.Field Methods fmap :: (a -> b) -> Name a -> Name b Source # (<$) :: a -> Name b -> Name a Source #
Foldable Name # |
Instance details Defined in Distribution.Fields.Field Methods fold :: Monoid m => Name m -> m Source # foldMap :: Monoid m => (a -> m) -> Name a -> m Source # foldMap' :: Monoid m => (a -> m) -> Name a -> m Source # foldr :: (a -> b -> b) -> b -> Name a -> b Source # foldr' :: (a -> b -> b) -> b -> Name a -> b Source # foldl :: (b -> a -> b) -> b -> Name a -> b Source # foldl' :: (b -> a -> b) -> b -> Name a -> b Source # foldr1 :: (a -> a -> a) -> Name a -> a Source # foldl1 :: (a -> a -> a) -> Name a -> a Source # toList :: Name a -> [a] Source # null :: Name a -> Bool Source # length :: Name a -> Int Source # elem :: Eq a => a -> Name a -> Bool Source # maximum :: Ord a => Name a -> a Source # minimum :: Ord a => Name a -> a Source # sum :: Num a => Name a -> a Source # product :: Num a => Name a -> a Source #
Traversable Name # |
Instance details Defined in Distribution.Fields.Field Methods traverse :: Applicative f => (a -> f b) -> Name a -> f (Name b) Source # sequenceA :: Applicative f => Name (f a) -> f (Name a) Source # mapM :: Monad m => (a -> m b) -> Name a -> m (Name b) Source # sequence :: Monad m => Name (m a) -> m (Name a) Source #
Eq ann => Eq (Name ann) # |
Instance details Defined in Distribution.Fields.Field Methods (==) :: Name ann -> Name ann -> Bool # (/=) :: Name ann -> Name ann -> Bool #
Show ann => Show (Name ann) # |
Instance details Defined in Distribution.Fields.Field Methods showsPrec :: Int -> Name ann -> ShowS Source # show :: Name ann -> String Source # showList :: [Name ann] -> ShowS Source #

data FieldLine ann Source #

A line of text representing the value of a field from a Cabal file. A field may contain multiple lines.

Invariant: `ByteString` has no newlines.

Constructors

FieldLine !ann !ByteString |

#### Instances

Instances details

Functor FieldLine # |
Instance details Defined in Distribution.Fields.Field Methods fmap :: (a -> b) -> FieldLine a -> FieldLine b Source # (<$) :: a -> FieldLine b -> FieldLine a Source #
Foldable FieldLine # |
Instance details Defined in Distribution.Fields.Field Methods fold :: Monoid m => FieldLine m -> m Source # foldMap :: Monoid m => (a -> m) -> FieldLine a -> m Source # foldMap' :: Monoid m => (a -> m) -> FieldLine a -> m Source # foldr :: (a -> b -> b) -> b -> FieldLine a -> b Source # foldr' :: (a -> b -> b) -> b -> FieldLine a -> b Source # foldl :: (b -> a -> b) -> b -> FieldLine a -> b Source # foldl' :: (b -> a -> b) -> b -> FieldLine a -> b Source # foldr1 :: (a -> a -> a) -> FieldLine a -> a Source # foldl1 :: (a -> a -> a) -> FieldLine a -> a Source # toList :: FieldLine a -> [a] Source # null :: FieldLine a -> Bool Source # length :: FieldLine a -> Int Source # elem :: Eq a => a -> FieldLine a -> Bool Source # maximum :: Ord a => FieldLine a -> a Source # minimum :: Ord a => FieldLine a -> a Source # sum :: Num a => FieldLine a -> a Source # product :: Num a => FieldLine a -> a Source #
Traversable FieldLine # |
Instance details Defined in Distribution.Fields.Field Methods traverse :: Applicative f => (a -> f b) -> FieldLine a -> f (FieldLine b) Source # sequenceA :: Applicative f => FieldLine (f a) -> f (FieldLine a) Source # mapM :: Monad m => (a -> m b) -> FieldLine a -> m (FieldLine b) Source # sequence :: Monad m => FieldLine (m a) -> m (FieldLine a) Source #
Eq ann => Eq (FieldLine ann) # |
Instance details Defined in Distribution.Fields.Field Methods (==) :: FieldLine ann -> FieldLine ann -> Bool # (/=) :: FieldLine ann -> FieldLine ann -> Bool #
Show ann => Show (FieldLine ann) # |
Instance details Defined in Distribution.Fields.Field Methods showsPrec :: Int -> FieldLine ann -> ShowS Source # show :: FieldLine ann -> String Source # showList :: [FieldLine ann] -> ShowS Source #

data SectionArg ann Source #

Section arguments, e.g. name of the library

Constructors

SecArgName !ann !ByteString | identifier, or something which looks like number. Also many dot numbers, i.e. "7.6.3"
SecArgStr !ann !ByteString | quoted string
SecArgOther !ann !ByteString | everything else, mm. operators (e.g. in if-section conditionals)

#### Instances

Instances details

Functor SectionArg # |
Instance details Defined in Distribution.Fields.Field Methods fmap :: (a -> b) -> SectionArg a -> SectionArg b Source # (<$) :: a -> SectionArg b -> SectionArg a Source #
Foldable SectionArg # |
Instance details Defined in Distribution.Fields.Field Methods fold :: Monoid m => SectionArg m -> m Source # foldMap :: Monoid m => (a -> m) -> SectionArg a -> m Source # foldMap' :: Monoid m => (a -> m) -> SectionArg a -> m Source # foldr :: (a -> b -> b) -> b -> SectionArg a -> b Source # foldr' :: (a -> b -> b) -> b -> SectionArg a -> b Source # foldl :: (b -> a -> b) -> b -> SectionArg a -> b Source # foldl' :: (b -> a -> b) -> b -> SectionArg a -> b Source # foldr1 :: (a -> a -> a) -> SectionArg a -> a Source # foldl1 :: (a -> a -> a) -> SectionArg a -> a Source # toList :: SectionArg a -> [a] Source # null :: SectionArg a -> Bool Source # length :: SectionArg a -> Int Source # elem :: Eq a => a -> SectionArg a -> Bool Source # maximum :: Ord a => SectionArg a -> a Source # minimum :: Ord a => SectionArg a -> a Source # sum :: Num a => SectionArg a -> a Source # product :: Num a => SectionArg a -> a Source #
Traversable SectionArg # |
Instance details Defined in Distribution.Fields.Field Methods traverse :: Applicative f => (a -> f b) -> SectionArg a -> f (SectionArg b) Source # sequenceA :: Applicative f => SectionArg (f a) -> f (SectionArg a) Source # mapM :: Monad m => (a -> m b) -> SectionArg a -> m (SectionArg b) Source # sequence :: Monad m => SectionArg (m a) -> m (SectionArg a) Source #
Eq ann => Eq (SectionArg ann) # |
Instance details Defined in Distribution.Fields.Field Methods (==) :: SectionArg ann -> SectionArg ann -> Bool # (/=) :: SectionArg ann -> SectionArg ann -> Bool #
Show ann => Show (SectionArg ann) # |
Instance details Defined in Distribution.Fields.Field Methods showsPrec :: Int -> SectionArg ann -> ShowS Source # show :: SectionArg ann -> String Source # showList :: [SectionArg ann] -> ShowS Source #

# Grammar and parsing

    CabalStyleFile ::= SecElems

    SecElems       ::= SecElem* '\\n'?
    SecElem        ::= '\\n' SecElemLayout | SecElemBraces
    SecElemLayout  ::= FieldLayout | FieldBraces | SectionLayout | SectionBraces
    SecElemBraces  ::= FieldInline | FieldBraces |                 SectionBraces
    FieldLayout    ::= name : line? ('\\n' line)*
    FieldBraces    ::= name : '\\n'? '{' content '}'
    FieldInline    ::= name : content
    SectionLayout  ::= name arg* SecElems
    SectionBraces  ::= name arg* '\\n'? '{' SecElems '}'

and the same thing but left factored...

    SecElems              ::= SecElem*
    SecElem               ::= '\\n' name SecElemLayout
                            |      name SecElemBraces
    SecElemLayout         ::= :   FieldLayoutOrBraces
                            | arg*  SectionLayoutOrBraces
    FieldLayoutOrBraces   ::= '\\n'? '{' content '}'
                            | line? ('\\n' line)*
    SectionLayoutOrBraces ::= '\\n'? '{' SecElems '\\n'? '}'
                            | SecElems
    SecElemBraces         ::= : FieldInlineOrBraces
                            | arg* '\\n'? '{' SecElems '\\n'? '}'
    FieldInlineOrBraces   ::= '\\n'? '{' content '}'
                            | content

Note how we have several productions with the sequence:

    '\\n'? '{'

That is, an optional newline (and indent) followed by a `{` token. In the `SectionLayoutOrBraces` case you can see that this makes it not fully left factored (because `SecElems` can start with a `\n`). Fully left factoring here would be ugly, and though we could use a lookahead of two tokens to resolve the alternatives, we can't conveniently use Parsec's `try` here to get a lookahead of only two. So instead we deal with this case in the lexer by making a line where the first non-space is `{` lex as just the `{` token, without the usual indent token. Then in the parser we can resolve everything with just one token of lookahead and so without using `try`.

readFields :: ByteString -> Either ParseError [Field Position] Source #

Parse cabal style `ByteString` into list of `Field`s, i.e. the cabal AST.

readFields' :: ByteString -> Either ParseError ([Field Position], [LexWarning]) Source #

Like `readFields` but also return lexer warnings