package decoders-yojson

  1. Overview
  2. Docs

Source file raw.ml

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
(** {2 Yojson implementation} *)

open Decoders

module Json_decodeable : Decode.Decodeable with type value = Yojson.Raw.json =
struct
  type value = Yojson.Raw.json

  let pp fmt json =
    Format.fprintf fmt "@[%s@]" (Yojson.Raw.pretty_to_string json)


  let of_string : string -> (value, string) result =
   fun string ->
    try Ok (Yojson.Raw.from_string string) with
    | Yojson.Json_error msg ->
        Error msg


  let of_file file =
    try Ok (Yojson.Raw.from_file file) with e -> Error (Printexc.to_string e)


  let get_string = function
    | `Stringlit s ->
        (* Stringlits are wrapped in double-quotes. *)
        Some (String.sub s 1 (String.length s - 2))
    | _ ->
        None


  let get_int = function
    | `Intlit value ->
        Some (int_of_string value)
    | _ ->
        None


  let get_float = function
    | `Floatlit value ->
        Some (float_of_string value)
    | `Intlit value ->
        Some (float_of_string value)
    | _ ->
        None


  let get_bool = function `Bool value -> Some value | _ -> None

  let get_null = function `Null -> Some () | _ -> None

  let get_list : value -> value list option = function
    | `List l ->
        Some l
    | _ ->
        None


  let get_key_value_pairs : value -> (value * value) list option = function
    | `Assoc assoc ->
        Some
          (List.map
             (fun (key, value) -> (`Stringlit (Printf.sprintf "%S" key), value))
             assoc)
    | _ ->
        None


  let to_list values = `List values
end

module Decode = struct
  include Decode.Make (Json_decodeable)

  (* Yojson.Raw specific decoders *)

  let stringlit : string decoder =
    { run =
        (function
        | `Stringlit value ->
            Ok value
        | json ->
            (fail "Expected a string").run json)
    }


  let intlit : string decoder =
    { run =
        (function
        | `Intlit value -> Ok value | json -> (fail "Expected an int").run json)
    }


  let floatlit : string decoder =
    { run =
        (function
        | `Floatlit value ->
            Ok value
        | `Intlit value ->
            Ok value
        | json ->
            (fail "Expected a float").run json)
    }
end

module Json_encodeable = struct
  type value = Yojson.Raw.json

  let to_string json = Yojson.Raw.to_string json

  let of_string x = `Stringlit (Printf.sprintf "%S" x)

  let of_int x = `Intlit (string_of_int x)

  let of_float x = `Floatlit (string_of_float x)

  let of_bool x = `Bool x

  let null = `Null

  let of_list xs = `List xs

  let of_key_value_pairs xs =
    `Assoc
      ( xs
      |> Decoders_util.My_list.filter_map (fun (k, v) ->
             Json_decodeable.get_string k
             |> Decoders_util.My_opt.map (fun k -> (k, v))) )
end

module Encode = struct
  include Encode.Make (Json_encodeable)

  let stringlit x = `Stringlit x

  let intlit x = `Intlit x

  let floatlit x = `Floatlit x
end
OCaml

Innovation. Community. Security.