My agentic slop goes here. Not intended for anyone else!
1(** JMAP JSON Parser Utilities 2 3 This module provides helper functions for parsing JMAP objects using jsonm/ezjsonm. 4 5 All parsing functions should reference specific test files for expected JSON format. 6*) 7 8(** Helper functions for working with ezjsonm values *) 9module Helpers = struct 10 (** Expect a JSON object and return field list *) 11 let expect_object = function 12 | `O fields -> fields 13 | _ -> raise (Jmap_error.Parse_error "Expected JSON object") 14 15 (** Expect a JSON array and return element list *) 16 let expect_array = function 17 | `A items -> items 18 | _ -> raise (Jmap_error.Parse_error "Expected JSON array") 19 20 (** Expect a JSON string *) 21 let expect_string = function 22 | `String s -> s 23 | _ -> raise (Jmap_error.Parse_error "Expected JSON string") 24 25 (** Expect a JSON integer *) 26 let expect_int = function 27 | `Float f -> int_of_float f 28 | _ -> raise (Jmap_error.Parse_error "Expected JSON number") 29 30 (** Expect a JSON boolean *) 31 let expect_bool = function 32 | `Bool b -> b 33 | _ -> raise (Jmap_error.Parse_error "Expected JSON boolean") 34 35 (** Find optional field in object *) 36 let find_field name fields = 37 List.assoc_opt name fields 38 39 (** Require field to be present *) 40 let require_field name fields = 41 match find_field name fields with 42 | Some v -> v 43 | None -> raise (Jmap_error.Parse_error (Printf.sprintf "Missing required field: %s" name)) 44 45 (** Get optional string field *) 46 let get_string_opt name fields = 47 match find_field name fields with 48 | Some (`String s) -> Some s 49 | Some _ -> raise (Jmap_error.Parse_error (Printf.sprintf "Field %s must be a string" name)) 50 | None -> None 51 52 (** Get required string field *) 53 let get_string name fields = 54 match require_field name fields with 55 | `String s -> s 56 | _ -> raise (Jmap_error.Parse_error (Printf.sprintf "Field %s must be a string" name)) 57 58 (** Get optional boolean field with default *) 59 let get_bool_opt name fields default = 60 match find_field name fields with 61 | Some (`Bool b) -> b 62 | Some _ -> raise (Jmap_error.Parse_error (Printf.sprintf "Field %s must be a boolean" name)) 63 | None -> default 64 65 (** Get required boolean field *) 66 let get_bool name fields = 67 match require_field name fields with 68 | `Bool b -> b 69 | _ -> raise (Jmap_error.Parse_error (Printf.sprintf "Field %s must be a boolean" name)) 70 71 (** Get optional int field *) 72 let get_int_opt name fields = 73 match find_field name fields with 74 | Some (`Float f) -> Some (int_of_float f) 75 | Some _ -> raise (Jmap_error.Parse_error (Printf.sprintf "Field %s must be a number" name)) 76 | None -> None 77 78 (** Get required int field *) 79 let get_int name fields = 80 match require_field name fields with 81 | `Float f -> int_of_float f 82 | _ -> raise (Jmap_error.Parse_error (Printf.sprintf "Field %s must be a number" name)) 83 84 (** Parse a map with string keys *) 85 let parse_map parse_value = function 86 | `O fields -> 87 List.map (fun (k, v) -> (k, parse_value v)) fields 88 | _ -> raise (Jmap_error.Parse_error "Expected JSON object for map") 89 90 (** Parse an array *) 91 let parse_array parse_elem = function 92 | `A items -> List.map parse_elem items 93 | `Null -> [] 94 | _ -> raise (Jmap_error.Parse_error "Expected JSON array") 95 96 (** Parse optional array (null or array) *) 97 let parse_array_opt parse_elem = function 98 | `Null -> None 99 | `A items -> Some (List.map parse_elem items) 100 | _ -> raise (Jmap_error.Parse_error "Expected JSON array or null") 101end 102 103(** TODO: Implement specific parsers for each JMAP type. 104 Each parser should reference its corresponding test file. *) 105 106(** Parse JMAP Request 107 Test files: test/data/core/request_*.json *) 108let parse_request json = 109 Jmap_request.Parser.of_json json 110 111(** Parse JMAP Response 112 Test files: test/data/core/response_*.json *) 113let parse_response json = 114 Jmap_response.Parser.of_json json 115 116(** Parse JMAP Session 117 Test files: test/data/core/session.json *) 118let parse_session json = 119 Jmap_session.Parser.of_json json