OCaml HTML5 parser/serialiser based on Python's JustHTML
1(** Simple test for nesting_checker functionality *) 2 3let () = 4 (* Create a message collector *) 5 let collector = Html5_checker.Message_collector.create () in 6 7 (* Get the nesting checker *) 8 let module C = (val Html5_checker__Nesting_checker.checker : Html5_checker__Checker.S) in 9 let state = C.create () in 10 11 (* Test 1: <a> cannot contain another <a> *) 12 Printf.printf "Test 1: Checking <a href> inside <a href>\n"; 13 C.start_element state ~name:"a" ~namespace:None ~attrs:[("href", "#")] collector; 14 C.start_element state ~name:"a" ~namespace:None ~attrs:[("href", "#")] collector; 15 16 let errors1 = Html5_checker.Message_collector.errors collector in 17 Printf.printf " Found %d error(s)\n" (List.length errors1); 18 List.iter (fun msg -> 19 Printf.printf " - %s\n" msg.Html5_checker.Message.message 20 ) errors1; 21 22 C.end_element state ~name:"a" ~namespace:None collector; 23 C.end_element state ~name:"a" ~namespace:None collector; 24 Html5_checker.Message_collector.clear collector; 25 26 (* Test 2: <button> inside <a> *) 27 Printf.printf "\nTest 2: Checking <button> inside <a href>\n"; 28 C.start_element state ~name:"a" ~namespace:None ~attrs:[("href", "#")] collector; 29 C.start_element state ~name:"button" ~namespace:None ~attrs:[] collector; 30 31 let errors2 = Html5_checker.Message_collector.errors collector in 32 Printf.printf " Found %d error(s)\n" (List.length errors2); 33 List.iter (fun msg -> 34 Printf.printf " - %s\n" msg.Html5_checker.Message.message 35 ) errors2; 36 37 C.end_element state ~name:"button" ~namespace:None collector; 38 C.end_element state ~name:"a" ~namespace:None collector; 39 Html5_checker.Message_collector.clear collector; 40 41 (* Test 3: form inside form *) 42 Printf.printf "\nTest 3: Checking <form> inside <form>\n"; 43 C.start_element state ~name:"form" ~namespace:None ~attrs:[] collector; 44 C.start_element state ~name:"form" ~namespace:None ~attrs:[] collector; 45 46 let errors3 = Html5_checker.Message_collector.errors collector in 47 Printf.printf " Found %d error(s)\n" (List.length errors3); 48 List.iter (fun msg -> 49 Printf.printf " - %s\n" msg.Html5_checker.Message.message 50 ) errors3; 51 52 C.end_element state ~name:"form" ~namespace:None collector; 53 C.end_element state ~name:"form" ~namespace:None collector; 54 Html5_checker.Message_collector.clear collector; 55 56 (* Test 4: header inside footer *) 57 Printf.printf "\nTest 4: Checking <header> inside <footer>\n"; 58 C.start_element state ~name:"footer" ~namespace:None ~attrs:[] collector; 59 C.start_element state ~name:"header" ~namespace:None ~attrs:[] collector; 60 61 let errors4 = Html5_checker.Message_collector.errors collector in 62 Printf.printf " Found %d error(s)\n" (List.length errors4); 63 List.iter (fun msg -> 64 Printf.printf " - %s\n" msg.Html5_checker.Message.message 65 ) errors4; 66 67 C.end_element state ~name:"header" ~namespace:None collector; 68 C.end_element state ~name:"footer" ~namespace:None collector; 69 Html5_checker.Message_collector.clear collector; 70 71 (* Test 5: input (not hidden) inside button *) 72 Printf.printf "\nTest 5: Checking <input type=text> inside <button>\n"; 73 C.start_element state ~name:"button" ~namespace:None ~attrs:[] collector; 74 C.start_element state ~name:"input" ~namespace:None ~attrs:[("type", "text")] collector; 75 76 let errors5 = Html5_checker.Message_collector.errors collector in 77 Printf.printf " Found %d error(s)\n" (List.length errors5); 78 List.iter (fun msg -> 79 Printf.printf " - %s\n" msg.Html5_checker.Message.message 80 ) errors5; 81 82 C.end_element state ~name:"input" ~namespace:None collector; 83 C.end_element state ~name:"button" ~namespace:None collector; 84 Html5_checker.Message_collector.clear collector; 85 86 (* Test 6: valid nesting - should not error *) 87 Printf.printf "\nTest 6: Checking valid nesting: <div> inside <div>\n"; 88 C.start_element state ~name:"div" ~namespace:None ~attrs:[] collector; 89 C.start_element state ~name:"div" ~namespace:None ~attrs:[] collector; 90 91 let errors6 = Html5_checker.Message_collector.errors collector in 92 Printf.printf " Found %d error(s)\n" (List.length errors6); 93 if List.length errors6 = 0 then 94 Printf.printf " OK: No errors as expected\n"; 95 96 C.end_element state ~name:"div" ~namespace:None collector; 97 C.end_element state ~name:"div" ~namespace:None collector; 98 Html5_checker.Message_collector.clear collector; 99 100 (* Test 7: area without map ancestor *) 101 Printf.printf "\nTest 7: Checking <area> without <map> ancestor\n"; 102 C.start_element state ~name:"area" ~namespace:None ~attrs:[] collector; 103 104 let errors7 = Html5_checker.Message_collector.errors collector in 105 Printf.printf " Found %d error(s)\n" (List.length errors7); 106 List.iter (fun msg -> 107 Printf.printf " - %s\n" msg.Html5_checker.Message.message 108 ) errors7; 109 110 C.end_element state ~name:"area" ~namespace:None collector; 111 Html5_checker.Message_collector.clear collector; 112 113 (* Test 8: area with map ancestor (valid) *) 114 Printf.printf "\nTest 8: Checking <area> with <map> ancestor (valid)\n"; 115 C.start_element state ~name:"map" ~namespace:None ~attrs:[] collector; 116 C.start_element state ~name:"area" ~namespace:None ~attrs:[] collector; 117 118 let errors8 = Html5_checker.Message_collector.errors collector in 119 Printf.printf " Found %d error(s)\n" (List.length errors8); 120 if List.length errors8 = 0 then 121 Printf.printf " OK: No errors as expected\n"; 122 123 C.end_element state ~name:"area" ~namespace:None collector; 124 C.end_element state ~name:"map" ~namespace:None collector; 125 126 Printf.printf "\nAll tests completed!\n"