/Prelude-v14.0.0/JSON/renderYAML

Copy path to clipboard

Examples

  renderYAML
( JSON.array
[ JSON.bool True
, JSON.string "Hello"
, JSON.object
[ { mapKey = "foo", mapValue = JSON.null }
, { mapKey = "bar", mapValue = JSON.double 1.0 }
]
]
)
≡ ''
- true
- "Hello"
- ! "foo": null
! "bar": 1.0
''

Source

{- Render a `JSON` value as `Text` in YAML format.

The generated YAML text will only contain escaped object keys and
string values and might therefore not be very human readable.

However, it is useful for debugging `JSON` values or for tests.
For anything more sophisticated you should use `dhall-to-json` or
`dhall-to-yaml`.
-}

let JSON =
./core.dhall sha256:5dc1135d5481cfd6fde625aaed9fcbdb7aa7c14f2e76726aa5fdef028a5c10f5
? ./core.dhall

let Text/concatSep =
../Text/concatSep sha256:e4401d69918c61b92a4c0288f7d60a6560ca99726138ed8ebc58dca2cd205e58
? ../Text/concatSep

let List/drop =
../List/drop sha256:af983ba3ead494dd72beed05c0f3a17c36a4244adedf7ced502c6512196ed0cf
? ../List/drop

let List/null =
../List/null sha256:2338e39637e9a50d66ae1482c0ed559bbcc11e9442bfca8f8c176bbcd9c4fc80
? ../List/null

let List/map =
../List/map sha256:dd845ffb4568d40327f2a817eb42d1c6138b929ca758d50bc33112ef3c885680
? ../List/map

let List/concatMap =
../List/concatMap sha256:3b2167061d11fda1e4f6de0522cbe83e0d5ac4ef5ddf6bb0b2064470c5d3fb64
? ../List/concatMap

let Optional/map =
../Optional/map sha256:501534192d988218d43261c299cc1d1e0b13d25df388937add784778ab0054fa
? ../Optional/map

let NonEmpty
: Type → Type
= λ(a : Type) → { head : a, tail : List a }

let uncons
: ∀(a : Type) → List a → Optional (NonEmpty a)
= λ(a : Type)
→ λ(ls : List a)
Optional/map
a
(NonEmpty a)
(λ(head : a) → { head = head, tail = List/drop 1 a ls })
(List/head a ls)

let nonEmptyToList
: ∀(a : Type) → NonEmpty a → List a
= λ(a : Type) → λ(nonEmpty : NonEmpty a) → [ nonEmpty.head ] # nonEmpty.tail

let concatNonEmpty
: ∀(a : Type) → NonEmpty (NonEmpty a) → NonEmpty a
= λ(a : Type)
→ λ(lss : NonEmpty (NonEmpty a))
→ { head = lss.head.head
, tail =
lss.head.tail
# List/concatMap (NonEmpty a) a (nonEmptyToList a) lss.tail
}

let Block
: Type
= NonEmpty Text

let indentBlockWith
: Text → Text → BlockBlock
= λ(headIndent : Text)
→ λ(tailIndent : Text)
→ λ(block : Block)
→ { head = headIndent ++ block.head
, tail = List/map Text Text (λ(t : Text) → tailIndent ++ t) block.tail
}

let manyBlocks
: Block → List BlockBlock
= λ(ifEmpty : Block)
→ λ(blocks : List Block)
→ merge
{ Some = concatNonEmpty Text, None = ifEmpty }
(uncons Block blocks)

let singleLine
: Text → Block
= λ(text : Text) → { head = text, tail = [] : List Text }

let indentKeyedBlock
: Text → Text → Text → BlockBlock
= λ(key : Text)
→ λ(spacer : Text)
→ λ(indentation : Text)
→ λ(block : Block)
→ if List/null Text block.tail

then singleLine (key ++ spacer ++ block.head)

else indentBlockWith
key
indentation
{ head = "", tail = nonEmptyToList Text block }

let blockToText
: Block → Text
= λ(block : Block) → Text/concatSep "\n" (nonEmptyToList Text block) ++ "\n"

let renderYAML
: JSON.Type → Text
= λ(json : JSON.Type)
→ let ObjectField = { mapKey : Text, mapValue : Block }

in blockToText
( json
Block
{ string = λ(x : Text) → singleLine (Text/show x)
, double = λ(x : Double) → singleLine (Double/show x)
, integer = λ(x : Integer) → singleLine (JSON.renderInteger x)
, object =
λ(fields : List ObjectField)
manyBlocks
(singleLine "{}")
( List/map
ObjectField
Block
( λ(e : ObjectField)
indentKeyedBlock
"! ${Text/show e.mapKey}:"
" "
" "
e.mapValue
)
fields
)
, array =
λ(elements : List Block)
manyBlocks
(singleLine "[]")
( List/map
Block
Block
(indentBlockWith "- " " ")
elements
)
, bool =
λ(x : Bool) → singleLine (if x then "true" else "false")
, null = singleLine "null"
}
)

let example0 =
assert
: renderYAML
( JSON.array
[ JSON.bool True
, JSON.string "Hello"
, JSON.object
[ { mapKey = "foo", mapValue = JSON.null }
, { mapKey = "bar", mapValue = JSON.double 1.0 }
]
]
)
≡ ''
- true
- "Hello"
- ! "foo": null
! "bar": 1.0
''

in renderYAML