Hi all,
I've been struggling with this for the better part of today. I find Json
decoders really hard to grasp, for some reason, especially when there's a
weird mapping you need to do. My JSON looks like this, and is an abstract
syntax tree of "select * from submissions where age < 10":
{
"0": {
"0": "select",
"1": [],
"2": {
"type": "SelectList"
},
"3": {
"0": {
"0": "from",
"1": [
{
"0": "submissions",
"1": null,
"2": null,
"3": null,
"4": null,
"5": null,
"type": "TablePrimary_table_or_query_name"
}
],
"type": "FromClause"
},
"1": {
"0": "where",
"1": {
"0": null,
"1": {
"0": [
"age"
],
"1": {
"0": "<",
"1": "10",
"type": "ComparisonPredicatePart2"
},
"type": "ComparisonPredicate"
},
"type": "BooleanFactor"
},
"type": "WhereClause"
},
"2": null,
"3": null,
"type": "TableExpression"
},
"type": "QuerySpecification"
},
"1": null,
"2": null,
"type": "CursorSpecification"
}
I'd like to be able decode it into a node union type and type alias:
type Node =
Empty
| Node NodeRecord
type alias NodeRecord = {
type' : String
, primitiveValue: Maybe String
, children : List Node
}
Now, because each child of the node is listed as a key-value pair in the
node itself, I'm not sure how to write the decoder so that each of the
key-value pairs except "type" are mapped into `children` field of the
NodeRecord. At the end of post, that code was the best I could come up
with, but I get an error:
"TypeError: Cannot read property 'tag' of undefined".
function runHelp(decoder, value)
{
switch (decoder.tag) <-------- this is where it fails.
{
case 'bool':
return (typeof value === 'boolean')
? ok(value)
: badPrimitive('a Bool', value);
case 'int':
if (typeof value !== 'number') {
return badPrimitive('an Int', value);
....
I'm not sure how to debug this, or whether I'm going down the right path.
Below is the decoder code I have. Can anyone give me a hint? Thanks.
nodeDecoder : Decoder Node
nodeDecoder =
oneOf [
null Empty
, string `andThen` primitiveNodeDecoder
, parentNodeDecoder
]
primitiveNodeDecoder : String -> Decoder Node
primitiveNodeDecoder primitive =
object3 fromFields
(succeed "primitive")
(maybe (succeed primitive))
(succeed [])
parentNodeDecoder : Decoder Node
parentNodeDecoder =
object3 fromFields
("type" := string)
(maybe ("primitiveValue" := string))
("children" := childrenDecoder)
childrenDecoder : Decoder (List Node)
childrenDecoder =
customDecoder (dict value) (\nodeDict ->
let
children = nodeDict |> Dict.remove "type" |> Dict.values
b = Debug.log "children" children
combineResults = List.foldr (Result.map2 (::)) (Ok [])
childDecoder = lazy (\_ -> nodeDecoder)
results = combineResults (List.map (decodeValue childDecoder)
children)
c = Debug.log "results" results
in
results
--
You received this message because you are subscribed to the Google Groups "Elm
Discuss" group.
To unsubscribe from this group and stop receiving emails from it, send an email
to [email protected].
For more options, visit https://groups.google.com/d/optout.