/****************************************************************************** * Copyright (c) 2000-2014 Ericsson Telecom AB * All rights reserved. This program and the accompanying materials * are made available under the terms of the Eclipse Public License v1.0 * which accompanies this distribution, and is available at * http://www.eclipse.org/legal/epl-v10.html ******************************************************************************/ module exer_rec { import from ReadXml all; import from rec { type Neg; function check_match } // -- -- -- -- -- -- -- -- -- -- -- EMBED-VALUES type record Emb1 { record of universal charstring emb, charstring name, float price } with { variant "embedValues" } external function encEmb1(in Emb1 e) return octetstring with { extension "prototype(convert) encode(XER:XER_EXTENDED)" } const Emb1 c_emb1_plain := { emb := { "I bring you delicious", " for the price of ", " only" }, name := "pie", price:= 3.141592 } template Nodes t_plain := { // node_type , depth, name, value, namespace { XML_READER_TYPE_ELEMENT , 0, "Emb1" , "", "" }, //0 { XML_READER_TYPE_TEXT , 1, "#text", "I bring you delicious", "" }, //1 { XML_READER_TYPE_ELEMENT , 1, "name" , "", ""}, //2 { XML_READER_TYPE_TEXT , 2, "#text", "pie", "" }, //3 { XML_READER_TYPE_END_ELEMENT, 1, "name" , "", ""}, //4 { XML_READER_TYPE_TEXT , 1, "#text", " for the price of ", "" }, //5 { XML_READER_TYPE_ELEMENT , 1, "price", "", ""}, //6 { XML_READER_TYPE_TEXT , 2, "#text", "3.141592", "" }, //7 { XML_READER_TYPE_END_ELEMENT, 1, "price", "", ""}, //8 { XML_READER_TYPE_TEXT , 1, "#text", " only", "" }, //9 { XML_READER_TYPE_END_ELEMENT, 0, "Emb1" , "", "" } //10 } testcase exer_rec_plain() runs on Neg { var octetstring o; var Nodes nodes; o := encEmb1(c_emb1_plain); nodes := gather(o); check_match(nodes, t_plain); } // -- -- -- -- -- -- -- -- -- -- BEFORE const Emb1 c_emb1_before := c_emb1_plain with { erroneous (price) "before := 'C0FFEE'O " } template Nodes t_before modifies t_plain := { -,-, -,-,-, -, { XML_READER_TYPE_ELEMENT , 1, "OCTET_STRING", "", "" }, { XML_READER_TYPE_TEXT , 2, "#text" , "C0FFEE", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "OCTET_STRING", "", "" }, t_plain[6], t_plain[7], t_plain[8], t_plain[9], t_plain[10] } const Emb1 c_emb1_before2 := c_emb1_plain with { erroneous (emb[2]) "before := 'C0FFEE'O " } template Nodes t_before2 modifies t_plain := { -,-, -,-,-, -, -,-,-, { XML_READER_TYPE_TEXT , 1, "#text" , "C0FFEE only", "" }, t_plain[10] } testcase exer_rec_before() runs on Neg { var octetstring o; var Nodes nodes; o := encEmb1(c_emb1_before); nodes := gather(o); check_match(nodes, t_before); o := encEmb1(c_emb1_before2); nodes := gather(o); check_match(nodes, t_before2); } // -- -- -- -- -- -- -- -- ATTRIBUTE -- -- -- -- -- -- -- -- type record RA { charstring a1, integer a2, charstring content } with { variant (a1,a2) "attribute" } external function encAtr(in RA r) return octetstring with { extension "prototype(convert) encode(XER:XER_EXTENDED)" } const RA c_atr_plain := { a1 := "first", a2 := 42, content := "stuff" } template Nodes t_atr_plain := { // node_type , depth, name, value, ns { XML_READER_TYPE_ELEMENT , 0, "RA" , "" , ""}, //0 { XML_READER_TYPE_ATTRIBUTE , 1, "a1" , "first", ""}, { XML_READER_TYPE_ATTRIBUTE , 1, "a2" , "42" , ""}, //2 { XML_READER_TYPE_ELEMENT , 1, "content", "" , ""}, { XML_READER_TYPE_TEXT , 2, "#text" , "stuff", ""}, //4 { XML_READER_TYPE_END_ELEMENT, 1, "content", "" , ""}, { XML_READER_TYPE_END_ELEMENT, 0, "RA" , "" , ""} //6 } testcase exer_attr() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_plain); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_plain); } // -- -- -- -- -- -- -- -- before type charstring abefore with { variant "attribute" } const RA c_atr_before1 := c_atr_plain with { erroneous (a1) "before := abefore:""b4"" " } // The abefore type supplies the name. The "attribute" variant of abefore ensures // that it doesn't write an element amongst the attributes, like this: // b4 a1='first' a2='42'> ... // The decoder chokes badly on this invalid XML. template Nodes t_atr_before1 /*modifies t_atr_plain*/ := { t_atr_plain[0], { XML_READER_TYPE_ATTRIBUTE , 1, "abefore", "b4", ""}, t_atr_plain[1], t_atr_plain[2], t_atr_plain[3], t_atr_plain[4], t_atr_plain[5], t_atr_plain[6] } testcase exer_attr_before1() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_before1); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_before1); } // . . . . . raw before const RA c_atr_before1raw := c_atr_plain with { erroneous (a1) "before(raw) := "" b4='beef ore'"" " } // need space here---------------^ to produce well-formed XML template Nodes t_atr_before1raw := { t_atr_plain[0], { XML_READER_TYPE_ATTRIBUTE , 1, "b4", "beef ore", ""}, t_atr_plain[1], t_atr_plain[2], t_atr_plain[3], t_atr_plain[4], t_atr_plain[5], t_atr_plain[6] } testcase exer_attr_before1raw() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_before1raw); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_before1raw); } // -- -- -- -- -- -- -- -- replace type charstring replacement with { variant "attribute" } const RA c_atr_replace2 := c_atr_plain with { erroneous (a2) "value := replacement : ""substitute"" " } template Nodes t_atr_replace2 modifies t_atr_plain := { -,-, { XML_READER_TYPE_ATTRIBUTE , 1, "replacement", "substitute", ""}, -,-,-,- } testcase exer_attr_replace2() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_replace2); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_replace2); } // . . . . . raw replace const RA c_atr_replace2raw := c_atr_plain with { erroneous (a2) "value(raw) := "" foo='bar'"" " } // space needed here------------^ for well-formed XML template Nodes t_atr_replace2raw modifies t_atr_plain := { -,-, // start-element, attribute a1 // then the replacement { XML_READER_TYPE_ATTRIBUTE , 1, "foo", "bar", ""}, -,-,-,- } testcase exer_attr_replace2raw() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_replace2raw); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_replace2raw); } // -- -- -- -- -- -- -- -- after const RA c_atr_after2 := c_atr_plain with { erroneous (a2) "after := abefore : ""a-fter"" " } template Nodes t_atr_after2 modifies t_atr_plain := { -,-,-, // start-element, attribute a1, attribute a2 // then the extra attribute after { XML_READER_TYPE_ATTRIBUTE, 1, "abefore", "a-fter", "" }, t_atr_plain[3], t_atr_plain[4], t_atr_plain[5], t_atr_plain[6] } testcase exer_attr_after2() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_after2); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_after2); } // . . . . . raw after const RA c_atr_after2raw := c_atr_plain with { erroneous (a2) "after(raw) := "" after='shave'"" " } // space needed here------------^ for well-formed XML template Nodes t_atr_after2raw modifies t_atr_plain := { -,-,-, // start-element, attribute a1, attribute a2 // then the extra attribute after { XML_READER_TYPE_ATTRIBUTE, 1, "after", "shave", "" }, t_atr_plain[3], t_atr_plain[4], t_atr_plain[5], t_atr_plain[6] } testcase exer_attr_after2raw() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_after2raw); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_after2raw); } // -- -- -- -- -- -- -- -- omit const RA c_atr_omit1 := c_atr_plain with { erroneous (a1) "value := omit" } template Nodes t_atr_omit1 := { t_atr_plain[0], // start-element //t_atr_plain[1], // attribute a1 omitted t_atr_plain[2], // attribute a2 t_atr_plain[3], t_atr_plain[4], t_atr_plain[5], t_atr_plain[6] } const RA c_atr_omit2 := c_atr_plain with { erroneous (a2) "value := omit" } template Nodes t_atr_omit2 modifies t_atr_omit1 := { -, t_atr_plain[1], // instead of a1 being omitted and a2 present, here a1 is present -,-,-,- } testcase exer_attr_omit1() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_omit1); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_omit1); o := encAtr(c_atr_omit2); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_omit2); } // . . . . . . . omit all before const RA c_atr_omit_all_before2 := c_atr_plain with { erroneous (a2) "before := omit all" } template Nodes t_atr_omit_all_before2 := { t_atr_plain[0], // start-element //t_atr_plain[1], // attribute a1 omitted t_atr_plain[2], // attribute a2 t_atr_plain[3], t_atr_plain[4], t_atr_plain[5], t_atr_plain[6] } const RA c_atr_omit_all_before3 := c_atr_plain with { erroneous (content) "before := omit all" } template Nodes t_atr_omit_all_before3 := { t_atr_plain[0], // start-element //t_atr_plain[1], // attribute a1 omitted //t_atr_plain[2], // attribute a2 omitted t_atr_plain[3], t_atr_plain[4], t_atr_plain[5], t_atr_plain[6] } testcase exer_attr_omit_all_before() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_omit_all_before2); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_omit_all_before2); o := encAtr(c_atr_omit_all_before3); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_omit_all_before3); } // . . . . . . . omit all after const RA c_atr_omit_all_after2 := c_atr_plain with { erroneous (a2) "after := omit all" } template Nodes t_atr_omit_all_after2 := { t_atr_plain[0], // start-element t_atr_plain[1], // attribute a1 t_atr_plain[2] // attribute a2 //t_atr_plain[3], \\ //t_atr_plain[4], >> content element omitted //t_atr_plain[5], // //t_atr_plain[6] // RA end tag omitted: empty element } const RA c_atr_omit_all_after1 := c_atr_plain with { erroneous (a1) "after := omit all" } template Nodes t_atr_omit_all_after1 := { t_atr_plain[0], // start-element t_atr_plain[1] // attribute a1 //t_atr_plain[2], // attribute a2 omitted //t_atr_plain[3], \\ //t_atr_plain[4], >> content element omitted //t_atr_plain[5], // //t_atr_plain[6] // RA end tag omitted: empty element } testcase exer_attr_omit_all_after() runs on Neg { var octetstring o; var Nodes nodes; o := encAtr(c_atr_omit_all_after2); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_omit_all_after2); o := encAtr(c_atr_omit_all_after1); nodes := gather(o, ignore_ws); check_match(nodes, t_atr_omit_all_after1); } // -- -- -- -- -- -- -- -- USE-QNAME -- -- -- -- -- -- -- -- type record QN { universal charstring uri optional, universal charstring name } with { variant "XSD:QName" } external function encQN(in QN q) return octetstring with { extension "prototype(convert) encode(XER:XER_EXTENDED)" } const QN c_qn := { "uri", "nm" } const QN c_uqn:= { omit , "nm" } // b0:nm template Nodes t_qn := { { XML_READER_TYPE_ELEMENT , 0, "QN", "", "" }, { XML_READER_TYPE_ATTRIBUTE , 1, "xmlns:b0", "uri", "http://www.w3.org/2000/xmlns/" }, { XML_READER_TYPE_TEXT , 1, "#text", "b0:nm", "" }, { XML_READER_TYPE_END_ELEMENT, 0, "QN", "", "" } } // nm template Nodes t_uqn := { { XML_READER_TYPE_ELEMENT , 0, "QN", "", "" }, // no namespace { XML_READER_TYPE_TEXT , 1, "#text", "nm", "" }, { XML_READER_TYPE_END_ELEMENT, 0, "QN", "", "" } } testcase exer_qname_plain() runs on Neg { var octetstring o; var Nodes nodes; o := encQN(c_qn); nodes := gather(o, ignore_ws); check_match(nodes, t_qn); o := encQN(c_uqn); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn); } // .. .. .. .. before const QN c_qn_before0 := c_qn with { erroneous (uri) "before := abefore : ""mae ni"" " } template Nodes t_qn_before0 modifies t_qn := { -,-, { XML_READER_TYPE_ATTRIBUTE , 1, "abefore", "mae ni", "" }, t_qn[2], t_qn[3] } const QN c_qn_before0raw := c_qn with { erroneous (uri) "before(raw) := "" rawbefore='hi!'"" " } // spece for well-formed XML------^ template Nodes t_qn_before0raw modifies t_qn := { -,-, { XML_READER_TYPE_ATTRIBUTE , 1, "rawbefore", "hi!", "" }, t_qn[2], t_qn[3] } const QN c_uqn_before0 := c_uqn with { erroneous (uri) "before := abefore : ""mae ni"" " } template Nodes t_uqn_before0 modifies t_uqn := { -, { XML_READER_TYPE_ATTRIBUTE , 1, "abefore", "mae ni", "" }, t_uqn[1], t_uqn[2] } const QN c_uqn_before0raw := c_uqn with { erroneous (uri) "before(raw) := "" rawbefore='hi!'"" " } // spece for well-formed XML------^ template Nodes t_uqn_before0raw modifies t_uqn := { -, { XML_READER_TYPE_ATTRIBUTE , 1, "rawbefore", "hi!", "" }, t_uqn[1], t_uqn[2] } //// const QN c_qn_before1 := c_qn with { erroneous (name) "before := ""mae ni"" " } template Nodes t_qn_before1 modifies t_qn := { -,-, { XML_READER_TYPE_ELEMENT , 1, "CHARSTRING", "", "" }, { XML_READER_TYPE_TEXT , 2, "#text" , "mae ni", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "CHARSTRING", "", "" }, { XML_READER_TYPE_TEXT , 1, "#text" , "\nb0:nm", "" }, //almost t_qn[2], t_qn[3] } const QN c_qn_before1raw := c_qn with { erroneous (name) "before(raw) := ""rawb4,"" " } template Nodes t_qn_before1raw modifies t_qn := { -,-, { XML_READER_TYPE_TEXT , 1, "#text" , "rawb4,b0:nm", "" }, //almost t_qn[2] t_qn[3] } const QN c_uqn_before1 := c_uqn with { erroneous (name) "before := ""mae ni"" " } template Nodes t_uqn_before1 modifies t_uqn := { -, { XML_READER_TYPE_ELEMENT , 1, "CHARSTRING", "", "" }, { XML_READER_TYPE_TEXT , 2, "#text" , "mae ni", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "CHARSTRING", "", "" }, { XML_READER_TYPE_TEXT , 1, "#text" , "\nnm", "" }, //almost t_uqn[2], t_uqn[2] } const QN c_uqn_before1raw := c_uqn with { erroneous (name) "before(raw) := ""rawb4,"" " } template Nodes t_uqn_before1raw modifies t_uqn := { -, { -,-,-, "rawb4,nm",- }, t_uqn[2] } testcase exer_qname_before() runs on Neg { var octetstring o; var Nodes nodes; o := encQN(c_qn_before0); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_before0); o := encQN(c_qn_before0raw); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_before0raw); o := encQN(c_uqn_before0); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_before0); o := encQN(c_uqn_before0raw); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_before0raw); o := encQN(c_qn_before1); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_before1); o := encQN(c_qn_before1raw); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_before1raw); o := encQN(c_uqn_before1); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_before1); o := encQN(c_uqn_before1raw); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_before1raw); } // .. .. .. .. replace const QN c_qn_replace0 := c_qn with { erroneous (uri) "value := replacement : ""nagara"" " } template Nodes t_qn_replace0 modifies t_qn := { -, // start element { XML_READER_TYPE_ATTRIBUTE , 1, "replacement", "nagara", "" }, -,- // #text, end element } const QN c_qn_replace0raw := c_qn with { erroneous (uri) "value(raw) := "" nagara='1'"" " } template Nodes t_qn_replace0raw modifies t_qn := { -, // start element { XML_READER_TYPE_ATTRIBUTE , 1, "nagara", "1", "" }, -,- // #text, end element } const QN c_qn_replace1 := c_qn with { erroneous (name) "value := ""nagara"" " } template Nodes t_qn_replace1 modifies t_qn := { -,-, { XML_READER_TYPE_ELEMENT , 1, "CHARSTRING", "", "" }, { XML_READER_TYPE_TEXT , 2, "#text" , "nagara", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "CHARSTRING", "", "" }, t_qn[3] } const QN c_qn_replace1raw := c_qn with { erroneous (name) "value(raw) := ""nagara"" " } template Nodes t_qn_replace1raw modifies t_qn := { -,-, { XML_READER_TYPE_TEXT , 1, "#text", "nagara", "" }, - } const QN c_uqn_replace0 := c_uqn with { erroneous (uri) "value := replacement : ""nagara"" " } template Nodes t_uqn_replace0 modifies t_uqn := { -, // start element { XML_READER_TYPE_ATTRIBUTE , 1, "replacement", "nagara", "" }, t_uqn[1], t_uqn[2] // #text, end element } const QN c_uqn_replace0raw := c_uqn with { erroneous (uri) "value(raw) := "" nagara='1'"" " } template Nodes t_uqn_replace0raw modifies t_uqn := { -, // start element { XML_READER_TYPE_ATTRIBUTE , 1, "nagara", "1", "" }, t_uqn[1], t_uqn[2] // #text, end element } const QN c_uqn_replace1 := c_uqn with { erroneous (name) "value := ""nagara"" " } template Nodes t_uqn_replace1 modifies t_uqn := { -, { XML_READER_TYPE_ELEMENT , 1, "CHARSTRING", "", "" }, { XML_READER_TYPE_TEXT , 2, "#text" , "nagara", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "CHARSTRING", "", "" }, t_uqn[2] } const QN c_uqn_replace1raw := c_uqn with { erroneous (name) "value(raw) := ""nagara"" " } template Nodes t_uqn_replace1raw modifies t_uqn := { -, { XML_READER_TYPE_TEXT , 1, "#text", "nagara", "" }, - } testcase exer_qname_replace() runs on Neg { var octetstring o; var Nodes nodes; o := encQN(c_qn_replace0); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_replace0); o := encQN(c_qn_replace0raw); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_replace0raw); o := encQN(c_qn_replace1); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_replace1); o := encQN(c_qn_replace1raw); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_replace1raw); o := encQN(c_uqn_replace0); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_replace0); o := encQN(c_uqn_replace0raw); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_replace0raw); o := encQN(c_uqn_replace1); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_replace1); o := encQN(c_uqn_replace1raw); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_replace1raw); } // .. .. .. .. after const QN c_qn_after0 := c_qn with { erroneous (uri) "after := abefore : ""ato de"" " } template Nodes t_qn_after0 modifies t_qn := { -,-, { XML_READER_TYPE_ATTRIBUTE , 1, "abefore", "ato de", "" }, t_qn[2], t_qn[3] } const QN c_qn_after0raw := c_qn with { erroneous (uri) "after(raw) := "" rawafter='Rafter'"" " } // space needed here ------------^ for well-formed XML template Nodes t_qn_after0raw modifies t_qn := { -,-, { XML_READER_TYPE_ATTRIBUTE , 1, "rawafter", "Rafter", "" }, t_qn[2], t_qn[3] } const QN c_qn_after1 := c_qn with { erroneous (name) "after := abefore : ""ato de"" " } template Nodes t_qn_after1 modifies t_qn := { -,-, { XML_READER_TYPE_TEXT , 1, "#text", "b0:nm abefore='ato de'", "" }, - } const QN c_qn_after1raw := c_qn with { erroneous (name) "after(raw) := "" is hot!"" " } template Nodes t_qn_after1raw modifies t_qn := { -,-, { XML_READER_TYPE_TEXT , 1, "#text", "b0:nm is hot!", "" }, - } const QN c_uqn_after0 := c_uqn with { erroneous (uri) "after := abefore : ""ato de"" " } template Nodes t_uqn_after0 modifies t_uqn := { -, { XML_READER_TYPE_ATTRIBUTE , 1, "abefore", "ato de", "" }, t_uqn[1], t_uqn[2] } const QN c_uqn_after0raw := c_uqn with { erroneous (uri) "after(raw) := "" rawafter='Rafter'"" " } // space needed here ------------^ for well-formed XML template Nodes t_uqn_after0raw modifies t_uqn := { -, { XML_READER_TYPE_ATTRIBUTE , 1, "rawafter", "Rafter", "" }, t_uqn[1], t_uqn[2] } const QN c_uqn_after1 := c_uqn with { erroneous (name) "after := abefore : ""ato de"" " } template Nodes t_uqn_after1 modifies t_uqn := { -, { XML_READER_TYPE_TEXT , 1, "#text", "nm abefore='ato de'", "" }, - } const QN c_uqn_after1raw := c_uqn with { erroneous (name) "after(raw) := "" is hot!"" " } template Nodes t_uqn_after1raw modifies t_uqn := { -, { XML_READER_TYPE_TEXT , 1, "#text", "nm is hot!", "" }, - } testcase exer_qname_after() runs on Neg { var octetstring o; var Nodes nodes; o := encQN(c_qn_after0); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_after0); o := encQN(c_qn_after0raw); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_after0raw); o := encQN(c_qn_after1); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_after1); o := encQN(c_qn_after1raw); nodes := gather(o, ignore_ws); check_match(nodes, t_qn_after1raw); o := encQN(c_uqn_after0); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_after0); o := encQN(c_uqn_after0raw); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_after0raw); o := encQN(c_uqn_after1); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_after1); o := encQN(c_uqn_after1raw); nodes := gather(o, ignore_ws); check_match(nodes, t_uqn_after1raw); } // -- -- -- -- -- -- -- -- USE-ORDER -- -- -- -- -- -- -- -- // "Plain" USE-ORDER type record UO { record of enumerated { id, name, price, color } order, integer id, charstring name, float price, charstring color } with { variant "element"; variant "useOrder"; variant "namespace as 'http://www.example.com' prefix 'exm'"; } external function encUO(in UO u) return octetstring with { extension "prototype(convert) encode(XER:XER_EXTENDED)" } const UO c_uo_plain := { order := { id, name, color, price }, // color before price id := 1, name := "shoes", price := 9.99, color := "brown" } template Nodes t_uo_plain := { { XML_READER_TYPE_ELEMENT , 0, "exm:UO", "", "http://www.example.com" }, //0 { XML_READER_TYPE_ATTRIBUTE , 1, "xmlns:exm", "http://www.example.com", "http://www.w3.org/2000/xmlns/"}, { XML_READER_TYPE_ELEMENT , 1, "id" , "", "" }, //2 { XML_READER_TYPE_TEXT , 2, "#text", "1", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "id" , "", "" }, { XML_READER_TYPE_ELEMENT , 1, "name" , "", "" }, //5 { XML_READER_TYPE_TEXT , 2, "#text", "shoes", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "name" , "", "" }, { XML_READER_TYPE_ELEMENT , 1, "color", "", "" }, //8 { XML_READER_TYPE_TEXT , 2, "#text", "brown", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "color", "", "" }, { XML_READER_TYPE_ELEMENT , 1, "price", "", "" }, //11 { XML_READER_TYPE_TEXT , 2, "#text", "9.990000", "" }, { XML_READER_TYPE_END_ELEMENT, 1, "price", "", "" }, { XML_READER_TYPE_END_ELEMENT, 0, "exm:UO", "", "http://www.example.com" } //14 } testcase uo_plain() runs on Neg { var octetstring o; var Nodes nodes; o := encUO(c_uo_plain); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_plain); } const UO c_uo_omit_order := c_uo_plain with { erroneous (order) "value := omit" } // Omitting the controller member of USE-ORDER has no effect // (the order field itself is not written to the output). const UO c_uo_omit_name := c_uo_plain with { erroneous (name) "value := omit" } template Nodes t_uo_omit_name modifies t_uo_plain := { -,-, -,-,-, // 0-4 (start element and ) // omit 5-7 (name) t_uo_plain[8], t_uo_plain[9], t_uo_plain[10], // t_uo_plain[11], t_uo_plain[12], t_uo_plain[13], // t_uo_plain[14] // end element } const UO c_uo_omit_price := c_uo_plain with { erroneous (price) "value := omit" } template Nodes t_uo_omit_price modifies t_uo_plain := { -,-, -,-,-, -,-,-, -,-,-, // 0-10 (start element, , , ) // omit 11-13 (price) t_uo_plain[14] } const UO c_uo_omit_color := c_uo_plain with { erroneous (color) "value := omit" } template Nodes t_uo_omit_color modifies t_uo_plain := { -,-, -,-,-, -,-,-, // 0-7 (start element, , ) // omit 8-10 (color) t_uo_plain[11], t_uo_plain[12], t_uo_plain[13], // price t_uo_plain[14] } testcase uo_omit() runs on Neg { var octetstring o; var Nodes nodes; o := encUO(c_uo_omit_order); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_plain); o := encUO(c_uo_omit_name); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_omit_name); o := encUO(c_uo_omit_price); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_omit_price); o := encUO(c_uo_omit_color); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_omit_color); } // fields: id, name, price, color // output: id, name, color, price // 2-4 5-7 8-10 11-13 const UO c_uo_omit_after_order := c_uo_plain with { erroneous (order) "after := omit all" // after order: that's everything! } template Nodes t_uo_omit_after_order modifies t_uo_plain := { -,- // just the (empty) start element with the namespace attribute } const UO c_uo_omit_after_name := c_uo_plain with { erroneous (name) "after := omit all" // after name: price, color } template Nodes t_uo_omit_after_name modifies t_uo_plain := { -,-, -,-,-, -,-,-, // 0-7 (start element, , ) // omit 8-13 (price, color) t_uo_plain[14] } const UO c_uo_omit_after_price := c_uo_plain with { erroneous (price) "after := omit all" // after price: that's just color } template Nodes t_uo_omit_after_price modifies t_uo_plain := { -,-, -,-,-, -,-,-, // 0-7 (start element, , ) // omit 8-10 t_uo_plain[11], t_uo_plain[12], t_uo_plain[13], // t_uo_plain[14] } testcase uo_omit_after() runs on Neg { var octetstring o; var Nodes nodes; o := encUO(c_uo_omit_after_name); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_omit_after_name); o := encUO(c_uo_omit_after_price); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_omit_after_price); o := encUO(c_uo_omit_after_order); nodes := gather(o, ignore_ws); check_match(nodes, t_uo_omit_after_order); } // -- -- -- -- -- -- -- -- -- -- USE-NIL type enumerated ProductColor0 { red(0), green(1), blue(2) } // useNil on the type (record) type record Size { integer sizeval optional } with { variant "useNil" } type record NilProduct { charstring name, ProductColor0 color, Size size } external function encNP(in NilProduct n) return octetstring with { extension "prototype(convert) encode(XER:XER_EXTENDED)" } const NilProduct c_np_present := { name := "shirt", color := red, size := { 10 } } /* "\n" & "\tshirt\n" & "\tred\n" & "\t10\n" & "\n" & */ template Nodes t_np_present := { { XML_READER_TYPE_ELEMENT , 0, "NilProduct", "", ""}, //0 { XML_READER_TYPE_ELEMENT , 1, "name", "", ""}, //1 { XML_READER_TYPE_TEXT , 2, "#text", "shirt", ""}, { XML_READER_TYPE_END_ELEMENT, 1, "name", "", ""}, { XML_READER_TYPE_ELEMENT , 1, "color", "", ""}, //4 { XML_READER_TYPE_TEXT , 2, "#text", "red", ""}, { XML_READER_TYPE_END_ELEMENT, 1, "color", "", ""}, { XML_READER_TYPE_ELEMENT , 1, "size", "", ""}, //7 { XML_READER_TYPE_TEXT , 2, "#text", "10", ""}, { XML_READER_TYPE_END_ELEMENT, 1, "size", "", ""}, { XML_READER_TYPE_END_ELEMENT, 0, "NilProduct", "", ""} //10 } //template integer n_np_present := lengthof(t_np_present); const NilProduct c_np_absent := { name := "no shirt", color := red, size := { omit } } /* "\n" & // 0-1 "\tno shirt\n" & //2-4 "\tred\n" & //5-7 "\t\n" & //8-9 "\n" & //10 */ template Nodes t_np_absent := { // type depth, name, value, ns { XML_READER_TYPE_ELEMENT , 0, "NilProduct", "", ""}, //0 { XML_READER_TYPE_ATTRIBUTE , 1, "xmlns:xsi", "http://www.w3.org/2001/XMLSchema-instance", "http://www.w3.org/2000/xmlns/"}, { XML_READER_TYPE_ELEMENT , 1, "name", "", ""}, //2 { XML_READER_TYPE_TEXT , 2, "#text", "no shirt", ""}, { XML_READER_TYPE_END_ELEMENT, 1, "name", "", ""}, { XML_READER_TYPE_ELEMENT , 1, "color", "", ""}, //5 { XML_READER_TYPE_TEXT , 2, "#text", "red", ""}, { XML_READER_TYPE_END_ELEMENT, 1, "color", "", ""}, { XML_READER_TYPE_ELEMENT , 1, "size", "", ""}, //8 { XML_READER_TYPE_ATTRIBUTE , 2, "xsi:nil", "true", "http://www.w3.org/2001/XMLSchema-instance"}, { XML_READER_TYPE_END_ELEMENT, 0, "NilProduct", "", ""} //10 } testcase unil_plain() runs on Neg { var octetstring o; var Nodes nodes; o := encNP(c_np_present); nodes := gather(o, ignore_ws); check_match(nodes, t_np_present); o := encNP(c_np_absent); nodes := gather(o, ignore_ws); check_match(nodes, t_np_absent); } // -- -- -- -- -- -- -- -- -- -- -- REPLACE const NilProduct c_np_present_omit := c_np_present with { erroneous (size) "value := omit" } /* shirt red */ template Nodes t_np_present_omit modifies t_np_present := { -,-,-,-,-,-,-, // 0-6 // 7-9 omit: #text t_np_present[10] } const NilProduct c_np_present_omit_raw := c_np_present with { erroneous (size) "value(raw) := """" " } template Nodes t_np_present_omit_raw modifies t_np_present := { -, -,-,-, -,-,-, // 0-6, -, // start element // 8-9 omit: no #text or t_np_present[10] } const NilProduct c_np_present_omit_member := c_np_present with { erroneous (size.sizeval) "value := omit" } /* shirt red */ template Nodes t_np_present_omit_member modifies t_np_present := { -, -,-,-, -,-,-, // 0-6, -, // start element { XML_READER_TYPE_ATTRIBUTE , 2, "xmlns:xsi", "http://www.w3.org/2001/XMLSchema-instance", "http://www.w3.org/2000/xmlns/"}, t_np_absent[9], // xsi:nil=true // 8-9 omit: no #text or t_np_present[10] } const NilProduct c_np_present_omit_member_raw := c_np_present with { erroneous (size.sizeval) "value(raw) := ""cool!"" " } template Nodes t_np_present_omit_member_raw modifies t_np_present := { -, -,-,-, -,-,-, // 0-6, -, // start element { XML_READER_TYPE_TEXT , 2, "#text", "\ncool!", ""}, // #text changed -, // - // } // making a "present" disappear testcase unil_present_to_omit() runs on Neg { var octetstring o; var Nodes nodes; o := encNP(c_np_present_omit); nodes := gather(o, ignore_ws); check_match(nodes, t_np_present_omit); o := encNP(c_np_present_omit_raw); nodes := gather(o, ignore_ws); check_match(nodes, t_np_present_omit_raw); o := encNP(c_np_present_omit_member); nodes := gather(o, ignore_ws); check_match(nodes, t_np_present_omit_member); o := encNP(c_np_present_omit_member_raw); nodes := gather(o, ignore_ws); check_match(nodes, t_np_present_omit_member_raw); } const NilProduct c_np_absent_rez := c_np_absent with { erroneous (size) "value := Size : { 42 }" } template Nodes t_np_absent_rez modifies t_np_absent := { -,-, //0-1: start-element, xsi namespace -,-,-, -,-,-, // 2-7: name and color { XML_READER_TYPE_ELEMENT , 1, "Size", "", ""}, // should be same as t_np_absent[8] { XML_READER_TYPE_TEXT , 2, "#text", "42", "" }, // text { XML_READER_TYPE_END_ELEMENT, 1, "Size", "", ""}, t_np_absent[10] // end element } const NilProduct c_np_absent_rez_member := c_np_absent with { erroneous (size.sizeval) "value := 1" } template Nodes t_np_absent_rez_member modifies t_np_absent := { -,-, //0-1: start-element, xsi namespace -,-,-, -,-,-, // 2-7: name and color { XML_READER_TYPE_ELEMENT , 1, "size", "", ""}, // should be same as t_np_absent[8] { XML_READER_TYPE_TEXT , 2, "#text", "1", "" }, // text { XML_READER_TYPE_END_ELEMENT, 1, "size", "", ""}, t_np_absent[10] // end element } // making an "omit" reappear testcase unil_absent_to_present() runs on Neg { var octetstring o; var Nodes nodes; o := encNP(c_np_absent_rez); nodes := gather(o, ignore_ws); check_match(nodes, t_np_absent_rez); o := encNP(c_np_absent_rez_member); nodes := gather(o, ignore_ws); check_match(nodes, t_np_absent_rez_member); } } with { encode "XML"; variant "controlNamespace 'http://www.w3.org/2001/XMLSchema-instance' prefix 'xsi'" }