(* copyright 2004 Serge LEBLANC *) (* this software is under GNU GPL *) type Xml_version = [ '0'--'9'+ ('.' '0'--'9'+)* ] ;; type Xml_int = [ '0'--'9'+ ] ;; type Xml_id = Xml_int ;; type Xml_kind = "individual" | "delegate" ;; type Xml_login = Latin1 ;; type Xml_password = Latin1 ;; type Xml_group = Latin1 ;; type Xml_participant = [ Xml_login Xml_password Xml_group+ ] ;; type Xml_participant_base = [ Xml_participant* ] ;; type Xml_tag = Latin1 ;; type Xml_classification_base = [ Xml_tag* ] ;; type Xml_description = Latin1 ;; type Xml_author = Latin1 ;; type Xml_limit_date = Latin1 ;; type Xml_link = Latin1 ;; type Xml_vote = [ []* ] ;; type Xml_elected = Xml_int ;; type Xml_response = [ Xml_description Xml_author Xml_link* ] ;; type Xml_question = [ Xml_description Xml_author Xml_limit_date Xml_response* Xml_vote* Xml_elected* ] ;; type Xml_question_base = [ Xml_question* ] ;; type Xml_demexp_base = [ Xml_participant_base Xml_classification_base Xml_question_base ] ;; type Ocaml_int = -1073741824 -- 1073741823 ;; type Ocaml_string = Latin1 ;; type Ocaml_kind = `Individual | `Delegate ;; type Ocaml_participant = {| kind=Ocaml_kind; login=Ocaml_string; password=Ocaml_string; groups=[ Ocaml_string* ] |} ;; (* type Ocaml_option_string = `None | (`Some,Ocaml_string) ;; *) type Ocaml_response = {| r_id=Ocaml_int; r_desc=Ocaml_string; r_author=Ocaml_string; r_links=[ Ocaml_string* ] |} ;; type Ocaml_vote = {| voter=Ocaml_int; choices=[ Ocaml_int* ] |} ;; type Ocaml_elected = Ocaml_int ;; type Ocaml_tag = Ocaml_string ;; type Ocaml_question = {| q_desc=Ocaml_string; q_author=Ocaml_string; limit_date=Ocaml_string; responses=[ Ocaml_response* ]; votes=[ Ocaml_vote* ]; elected=[ Ocaml_elected* ] |} ;; type Ocaml_xml_content={| version=Ocaml_string; participants=[ (Ocaml_int,Ocaml_participant)* ]; tags=[ (Ocaml_int,Ocaml_tag)* ]; questions=[ (Ocaml_int,Ocaml_question)* ] |} ;; (* xml->ocaml transformation functions *) let trans_xml_participants (p : [ Xml_participant* ]) : [ (Ocaml_int,Ocaml_participant)* ] = let trans_kind (Xml_kind -> Ocaml_kind) | "individual" -> `Individual | "delegate" -> `Delegate in map p with [ l p; g ] -> match (int_of i) with | x&Ocaml_int -> (x, { kind=(trans_kind k); login=l; password=p; groups=(map g with s -> s) }) | _ -> raise "Invalid p_id value" ;; let trans_xml_tags (t : [ Xml_tag* ]) : [ (Ocaml_int,Ocaml_string)* ] = map t with s -> match (int_of i) with | x&Ocaml_int -> (x,s) | _ -> raise "Invalid t_id value" ;; let trans_xml_questions (q : [ Xml_question* ]) : [ (Ocaml_int, Ocaml_question)* ] = let trans_response (r : [ Xml_response* ]) : [ Ocaml_response* ] = map r with [ d a l::Xml_link* ] -> match (int_of i) with | x&Ocaml_int -> { r_id=x; r_desc=d; r_author=a; r_links=(map l with s -> s) } | _ -> raise "Invalid r_id value" in let trans_vote (v : [ Xml_vote* ]) : [ Ocaml_vote* ] = map v with s -> match (int_of i) with | x&Ocaml_int -> { voter=x; choices=(map s with [] -> match (int_of i) with | x&Ocaml_int -> x | _ -> raise "Invalid choice value" ) } | _ -> raise "Invalid voter element" in let trans_elected (e : [ Xml_elected* ]) : [ Ocaml_elected* ] = map e with i -> match (int_of i) with | x&Ocaml_int -> x | _ -> raise "Invalid elected value" in map q with [ d a l r::Xml_response* v::Xml_vote* e::Xml_elected* ] -> match (int_of i) with | x&Ocaml_int -> (x, { q_desc=d; q_author=a; limit_date=l; responses=(trans_response r); votes=(trans_vote v); elected=(trans_elected e) }) | _ -> raise "Invalid q_id value" ;; (* load functions *) let load_xml_demexp_participants (f : Latin1) : [ (Ocaml_int,Ocaml_participant)* ] = let d : Xml_demexp_base = match load_xml f with | x&Xml_demexp_base -> x | _ -> raise "Not a Demexp document" in trans_xml_participants ([d]/Xml_participant_base/Xml_participant) ;; let load_xml_demexp_tags (f : Latin1) : [ (Ocaml_int,Ocaml_string)* ] = let d : Xml_demexp_base = match load_xml f with | x&Xml_demexp_base -> x | _ -> raise "Not a Demexp document" in trans_xml_tags ([d]/Xml_classification_base/Xml_tag) ;; let load_xml_demexp_questions (f : Latin1) : [ (Ocaml_int,Ocaml_question)* ] = let d : Xml_demexp_base = match load_xml f with | x&Xml_demexp_base -> x | _ -> raise "Not a Demexp document" in trans_xml_questions ([d]/Xml_question_base/Xml_question) ;; let load_xml_demexp (f : Latin1) : Ocaml_xml_content = let d : Xml_demexp_base = match load_xml f with | x&Xml_demexp_base -> x | _ -> raise "Not a Demexp document" in { version=(match d with _ -> v); participants=(trans_xml_participants ([d]/Xml_participant_base/Xml_participant)); tags=(trans_xml_tags ([d]/Xml_classification_base/Xml_tag)); questions=(trans_xml_questions ([d]/Xml_question_base/Xml_question)) } ;; (* ocaml->xml transformation functions *) let trans_ocaml_int (i : Ocaml_int) : Xml_int = let s = string_of i in match s with x&Xml_int -> x | _ -> raise ("unvalid id : " @ s) let trans_ocaml_participants (a : [(Ocaml_int,Ocaml_participant)*]) : [Xml_participant*] = let trans_groups ([ Ocaml_string* ] -> [ Xml_group+ ]) g&[Ocaml_string+] -> (map g with s&Latin1 -> s) | [] -> raise "inadmissible empty participant groups" in let trans_kind (Ocaml_kind -> Xml_kind) | `Individual -> "individual" | `Delegate -> "delegate" in map a with (i,{| kind=q; login=l; password=p; groups=g |}) -> [ l p !(trans_groups g) ] ;; let trans_ocaml_tags (a : [(Ocaml_int,Ocaml_string)*]) : [Xml_tag*] = map a with (i,s) -> s ;; let trans_ocaml_questions (a : [(Ocaml_int,Ocaml_question)*]) : [Xml_question*] = let trans_responses (r : [Ocaml_response*]) : [Xml_response*] = let trans_links (l : [Ocaml_string*]) : [Xml_link*] = map l with s&Latin1 -> s in map r with {| r_id=i; r_desc=d; r_author=a; r_links=l |} -> [ d a !(trans_links l) ] (* | {| r_id=i; r_desc=d; r_author=a |} -> [ d a ] *) in let trans_votes (v : [Ocaml_vote*]) : [Xml_vote*] = map v with {| voter=i; choices=c |} -> (map c with i&Int -> []) in let trans_elected (e : [Ocaml_elected*]) : [Xml_elected*] = map e with i&Int -> (trans_ocaml_int i) in map a with (i,{| q_desc=d; q_author=a; limit_date=l; responses=r; votes=v; elected=e |}) -> [ d a l !(trans_responses r) !(trans_votes v) !(trans_elected e) ] ;; let save_xml_demexp_participants (f : Latin1)(a : [ (Ocaml_int,Ocaml_participant)* ]) : [] = dump_to_file_utf8 f (print_xml_utf8 (trans_ocaml_participants a)) ;; let save_xml_demexp_tags (f : Latin1)(a : [ (Ocaml_int,Ocaml_string)* ]) : [] = dump_to_file_utf8 f (print_xml_utf8 (trans_ocaml_tags a)) ;; let save_xml_demexp_questions (f : Latin1)(a : [ (Ocaml_int,Ocaml_question)* ]) : [] = dump_to_file_utf8 f (print_xml_utf8 (trans_ocaml_questions a)) ;; let save_xml_demexp (f : Latin1)(c : Ocaml_xml_content) : [] = let content = match c with { version=v; participants=p; tags=t; questions=q } -> [ (trans_ocaml_participants p) (trans_ocaml_tags t) (trans_ocaml_questions q) ] in dump_to_file_utf8 f ("" @ (print_xml_utf8 content)) ;;