module Data.GI.CodeGen.Haddock
( deprecatedPragma
, writeDocumentation
, RelativeDocPosition(..)
, writeHaddock
, writeArgDocumentation
, writeReturnDocumentation
, addSectionDocumentation
) where
#if !MIN_VERSION_base(4,13,0)
import Control.Monad (mapM_, unless)
#else
import Control.Monad (unless)
#endif
import qualified Data.Map as M
#if !MIN_VERSION_base(4,11,0)
import Data.Monoid ((<>))
#endif
import qualified Data.Text as T
import Data.Text (Text)
import Data.GI.GIR.Arg (Arg(..))
import Data.GI.GIR.BasicTypes (Name(Name))
import Data.GI.GIR.Callable (Callable(..))
import Data.GI.GIR.Deprecation (DeprecationInfo(..))
import Data.GI.GIR.Documentation (Documentation(..))
import Data.GI.CodeGen.Code (CodeGen, config, line, HaddockSection,
getC2HMap, addSectionFormattedDocs)
import Data.GI.CodeGen.Config (modName, overrides)
import Data.GI.CodeGen.CtoHaskellMap (Hyperlink(..))
import Data.GI.CodeGen.GtkDoc (GtkDoc(..), Token(..), CRef(..), Language(..),
Link(..), ListItem(..), parseGtkDoc,
DocSymbolName(..), resolveDocSymbol, docName)
import Data.GI.CodeGen.Overrides (onlineDocsMap)
import Data.GI.CodeGen.SymbolNaming (lowerSymbol, signalHaskellName,
haddockSignalAnchor)
data RelativeDocPosition = DocBeforeSymbol
| DocAfterSymbol
formatHaddock :: M.Map CRef Hyperlink -> Text -> Text -> GtkDoc -> Text
formatHaddock :: Map CRef Hyperlink -> Text -> Text -> GtkDoc -> Text
formatHaddock Map CRef Hyperlink
c2h Text
docBase Text
defaultNS (GtkDoc [Token]
tokens) = [Text] -> Text
T.concat ([Text] -> Text) -> [Text] -> Text
forall a b. (a -> b) -> a -> b
$ (Token -> Text) -> [Token] -> [Text]
forall a b. (a -> b) -> [a] -> [b]
map Token -> Text
formatToken [Token]
tokens
where formatToken :: Token -> Text
formatToken :: Token -> Text
formatToken (Literal Text
l) = Text -> Text
escape Text
l
formatToken (Comment Text
_) = Text
""
formatToken (Verbatim Text
v) = Text
"@" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
escape Text
v Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"@"
formatToken (CodeBlock Maybe Language
l Text
c) = Maybe Language -> Text -> Text
formatCodeBlock Maybe Language
l Text
c
formatToken (ExternalLink Link
l) = Link -> Text -> Text
formatLink Link
l Text
docBase
formatToken (Image Link
l) = Link -> Text -> Text
formatImage Link
l Text
docBase
formatToken (SectionHeader Int
l GtkDoc
h) =
Map CRef Hyperlink -> Text -> Text -> Int -> GtkDoc -> Text
formatSectionHeader Map CRef Hyperlink
c2h Text
docBase Text
defaultNS Int
l GtkDoc
h
formatToken (List [ListItem]
l) = Map CRef Hyperlink -> Text -> Text -> [ListItem] -> Text
formatList Map CRef Hyperlink
c2h Text
docBase Text
defaultNS [ListItem]
l
formatToken (SymbolRef CRef
cr) = case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup CRef
cr Map CRef Hyperlink
c2h of
Just Hyperlink
hr -> Hyperlink -> Text
formatHyperlink Hyperlink
hr
Maybe Hyperlink
Nothing -> Map CRef Hyperlink -> Text -> CRef -> Text
formatUnknownCRef Map CRef Hyperlink
c2h Text
defaultNS CRef
cr
formatUnknownCRef :: M.Map CRef Hyperlink -> Text -> CRef -> Text
formatUnknownCRef :: Map CRef Hyperlink -> Text -> CRef -> Text
formatUnknownCRef Map CRef Hyperlink
_ Text
_ (OldFunctionRef Text
f) = Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
f Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"()"
formatUnknownCRef Map CRef Hyperlink
_ Text
defaultNS (FunctionRef DocSymbolName
n) =
Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ DocSymbolName -> Text -> Text
formatDocSymbol DocSymbolName
n Text
defaultNS
formatUnknownCRef Map CRef Hyperlink
_ Text
_ (ParamRef Text
p) = Text
"/@" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
lowerSymbol Text
p Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"@/"
formatUnknownCRef Map CRef Hyperlink
_ Text
_ (LocalSignalRef Text
s) =
let sn :: Text
sn = Text -> Text
signalHaskellName Text
s
in Text
"[" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
sn Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"](#" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
haddockSignalAnchor Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
sn Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
")"
formatUnknownCRef Map CRef Hyperlink
c2h Text
defaultNS (SignalRef DocSymbolName
docSymbol Text
signal) =
let owner :: Name
owner@(Name Text
ns Text
n) = DocSymbolName -> Text -> Name
resolveDocSymbol DocSymbolName
docSymbol Text
defaultNS
in case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (DocSymbolName -> CRef
TypeRef (Name -> DocSymbolName
docName Name
owner)) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
ns Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
n Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"::" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
signal
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"::" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
signal
formatUnknownCRef Map CRef Hyperlink
c2h Text
_ (OldSignalRef Text
owner Text
signal) =
case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (Text -> CRef
CTypeRef Text
owner) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
owner Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"::" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
signal
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"::" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
signal
formatUnknownCRef Map CRef Hyperlink
c2h Text
_ (OldPropertyRef Text
owner Text
prop) =
case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (Text -> CRef
CTypeRef Text
owner) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
owner Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
":" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
prop
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
":" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
prop
formatUnknownCRef Map CRef Hyperlink
c2h Text
defaultNS (PropertyRef DocSymbolName
docSymbol Text
prop) =
let owner :: Name
owner@(Name Text
ns Text
n) = DocSymbolName -> Text -> Name
resolveDocSymbol DocSymbolName
docSymbol Text
defaultNS
in case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (DocSymbolName -> CRef
TypeRef (Name -> DocSymbolName
docName Name
owner)) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
ns Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
n Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
":" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
prop
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
":" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
prop
formatUnknownCRef Map CRef Hyperlink
c2h Text
_ (VMethodRef Text
owner Text
vmethod) =
case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (Text -> CRef
CTypeRef Text
owner) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
owner Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
vmethod Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"()"
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
vmethod Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"()"
formatUnknownCRef Map CRef Hyperlink
c2h Text
defaultNS (VFuncRef DocSymbolName
docSymbol Text
vmethod) =
let owner :: Name
owner@(Name Text
ns Text
n) = DocSymbolName -> Text -> Name
resolveDocSymbol DocSymbolName
docSymbol Text
defaultNS
in case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (DocSymbolName -> CRef
TypeRef (Name -> DocSymbolName
docName Name
owner)) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
ns Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
n Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
vmethod Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"()"
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
vmethod Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"()"
formatUnknownCRef Map CRef Hyperlink
c2h Text
defaultNS(MethodRef DocSymbolName
docSymbol Text
method) =
let owner :: Name
owner@(Name Text
ns Text
n) = DocSymbolName -> Text -> Name
resolveDocSymbol DocSymbolName
docSymbol Text
defaultNS
in case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (DocSymbolName -> CRef
TypeRef (Name -> DocSymbolName
docName Name
owner)) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
ns Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
n Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
method Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"()"
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
method Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"()"
formatUnknownCRef Map CRef Hyperlink
c2h Text
_ (StructFieldRef Text
owner Text
field) =
case CRef -> Map CRef Hyperlink -> Maybe Hyperlink
forall k a. Ord k => k -> Map k a -> Maybe a
M.lookup (Text -> CRef
CTypeRef Text
owner) Map CRef Hyperlink
c2h of
Maybe Hyperlink
Nothing -> Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ Text
owner Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
field
Just Hyperlink
r -> Hyperlink -> Text
formatHyperlink Hyperlink
r Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
formatCRef Text
field
formatUnknownCRef Map CRef Hyperlink
_ Text
_ (CTypeRef Text
t) = Text -> Text
formatCRef Text
t
formatUnknownCRef Map CRef Hyperlink
_ Text
defaultNS (TypeRef DocSymbolName
n) =
Text -> Text
formatCRef (Text -> Text) -> Text -> Text
forall a b. (a -> b) -> a -> b
$ DocSymbolName -> Text -> Text
formatDocSymbol DocSymbolName
n Text
defaultNS
formatUnknownCRef Map CRef Hyperlink
_ Text
_ (ConstantRef Text
t) = Text -> Text
formatCRef Text
t
formatDocSymbol :: DocSymbolName -> Text -> Text
formatDocSymbol :: DocSymbolName -> Text -> Text
formatDocSymbol (RelativeName Text
n) Text
defaultNS = Text
defaultNS Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
n
formatDocSymbol (AbsoluteName Text
ns Text
n) Text
_ = Text
ns Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"." Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
n
formatCRef :: Text -> Text
formatCRef :: Text -> Text
formatCRef Text
t = Text
"@/" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
escape Text
t Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"/@"
formatHyperlink :: Hyperlink -> Text
formatHyperlink :: Hyperlink -> Text
formatHyperlink (TypeIdentifier Text
t) = Text
"t'" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
t Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"'"
formatHyperlink (ValueIdentifier Text
t) = Text
"'" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
t Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"'"
formatHyperlink (ModuleLink Text
m) = Text
"\"" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
m Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"\""
formatHyperlink (ModuleLinkWithAnchor Maybe Text
mLabel Text
m Text
a) =
case Maybe Text
mLabel of
Maybe Text
Nothing -> Text
"\"" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
m Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"#" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
a Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"\""
Just Text
label -> Text
"[" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
label Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"](\"" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
m Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"#" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
a Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"\")"
formatCodeBlock :: Maybe Language -> Text -> Text
formatCodeBlock :: Maybe Language -> Text -> Text
formatCodeBlock Maybe Language
maybeLang Text
code =
let header :: Text
header = case Maybe Language
maybeLang of
Maybe Language
Nothing -> Text
""
Just (Language Text
lang) -> Text
"\n=== /" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
lang Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
" code/\n"
birdTrack :: Text -> Text
birdTrack = [Text] -> Text
T.unlines ([Text] -> Text) -> (Text -> [Text]) -> Text -> Text
forall b c a. (b -> c) -> (a -> b) -> a -> c
. (Text -> Text) -> [Text] -> [Text]
forall a b. (a -> b) -> [a] -> [b]
map (Char -> Text -> Text
T.cons Char
'>') ([Text] -> [Text]) -> (Text -> [Text]) -> Text -> [Text]
forall b c a. (b -> c) -> (a -> b) -> a -> c
. Text -> [Text]
T.lines
in Text
header Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text -> Text
birdTrack Text
code
qualifiedWith :: Text -> Text -> Text
qualifiedWith :: Text -> Text -> Text
qualifiedWith Text
address Text
docBase =
if Text
"http://" Text -> Text -> Bool
`T.isPrefixOf` Text
address Bool -> Bool -> Bool
|| Text
"https://" Text -> Text -> Bool
`T.isPrefixOf` Text
address
then Text
address
else if Text
"/" Text -> Text -> Bool
`T.isSuffixOf` Text
docBase
then Text
docBase Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
address
else Text
docBase Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
"/" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
address
formatLink :: Link -> Text -> Text
formatLink :: Link -> Text -> Text
formatLink (Link {linkName :: Link -> Text
linkName = Text
name, linkAddress :: Link -> Text
linkAddress = Text
address}) Text
docBase =
let address' :: Text
address' = Text
address Text -> Text -> Text
`qualifiedWith` Text
docBase
name' :: Text
name' = HasCallStack => Text -> Text -> Text -> Text
Text -> Text -> Text -> Text
T.replace Text
">" Text
"\\>" Text
name
in Text
"<" Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
address' Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
" " Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
name' Text -> Text -> Text
forall a. Semigroup a => a -> a -> a
<> Text
">"
formatImage :: Link -> Text -> Text
formatImage :: Link -> Text -> Text
formatImage (Link {linkName :: Link -> Text
linkName = Text
name, linkAddress :: Link -> Text
linkAddress = Text
address}) Text
docBase =