Android Question How to parse "strange" xml

vecino

Well-Known Member
Licensed User
Longtime User
Hi, a webservice soap returns a strange xml and I can't extract the information.
What can I use to get it?
Thank you very much.

XML:
<?xml version="1.0"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/">
  <SOAP-ENV:Body SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:NS1="urn:wsNewGES2000Intf-IwsNewGES2000">
    <NS1:PDA_DatosArticuloResponse xmlns:NS2="urn:wsNewGES2000Intf">
      <NS2:PDADatosArticulo id="1" xsi:type="NS2:PDADatosArticulo">
        <Codigo xsi:type="xsd:string">B1001</Codigo>
        <Nombre xsi:type="xsd:string">PAT. LISA FAMILIAR 260 GRS X 12 B.</Nombre>
        <Existencias xsi:type="xsd:double">0</Existencias>
        <Costo xsi:type="xsd:double">1.2</Costo>
        <Margen0 xsi:type="xsd:double">3</Margen0>
        <PVP0 xsi:type="xsd:double">1.212</PVP0>
        <Margen1 xsi:type="xsd:double">2</Margen1>
        <PVP1 xsi:type="xsd:double">1.224</PVP1>
        <Margen2 xsi:type="xsd:double">0</Margen2>
        <PVP2 xsi:type="xsd:double">1.236</PVP2>
        <Margen3 xsi:type="xsd:double">4</Margen3>
        <PVP3 xsi:type="xsd:double">1.248</PVP3>
      </NS2:PDADatosArticulo>
      <return href="#1"/>
    </NS1:PDA_DatosArticuloResponse>
  </SOAP-ENV:Body>
</SOAP-ENV:Envelope>
 

emexes

Expert
Licensed User
All the solutions I've seen are good,

All the solutions were XML parsing pared down to be as simple and understandable as possible that worked for your sample data.

but what would happen if the XML contains more than one element with the same name?.

The looping solutions in posts #10 and #11 would return all the elements, including elements with same name.

The access-element-by-name solutions would return the first element of that name.
 
Upvote 0

vecino

Well-Known Member
Licensed User
Longtime User
🤔🤔🤔🤔
All the solutions I've seen are good, but what would happen if the XML contains more than one element with the same name?
g.

XML:
<NS2:pDADatosArticulo id="1" xsi:type="NS2:pDADatosArticulo">
......
</NS2:pDADatosArticulo>

<NS2:pDADatosArticulo id="2" xsi:type="NS2:pDADatosArticulo">
......
</NS2:pDADatosArticulo>

Then we would have a problem, Houston :)
Actually in this case there is no problem because it is a matter of reading a barcode and asking for the information only for that item.
 
Upvote 0

emexes

Expert
Licensed User
RIghto... this modified (but no extra lines) XML field extraction Subroutine:

B4X:
Sub GetXMLField(XML As String, RecordID As String, FieldName As String) As String
    Dim Pattern As String = "<NS2.*?id=""" & RecordID & """.*?<" & FieldName & " .*?>(.*?)</" & FieldName & ">"
    Dim XMLMatcher As Matcher = Regex.Matcher(Pattern, XML.Replace(Chr(10), ""))
    If XMLMatcher.Find Then
        Return XMLMatcher.Group(1)
    End If
    Return "XML record " & RecordID & " field " & FieldName & " not found"    'or whatever you prefer to signify not found
End Sub

and this sample multi-record XML:

B4X:
Dim SampleXML As String = $"<?xml version="1.0"?>
<SOAP-ENV:Envelope xmlns:SOAP-ENV="http://schemas.xmlsoap.org/soap/envelope/" xmlns:xsd="http://www.w3.org/2001/XMLSchema" xmlns:xsi="http://www.w3.org/2001/XMLSchema-instance" xmlns:SOAP-ENC="http://schemas.xmlsoap.org/soap/encoding/">
  <SOAP-ENV:Body SOAP-ENV:encodingStyle="http://schemas.xmlsoap.org/soap/encoding/" xmlns:NS1="urn:wsNewGES2000Intf-IwsNewGES2000">
    <NS1:PDA_DatosArticuloResponse xmlns:NS2="urn:wsNewGES2000Intf">
      <NS2:PDADatosArticulo id="1" xsi:type="NS2:PDADatosArticulo">
        <Codigo xsi:type="xsd:string">B1001</Codigo>
        <Nombre xsi:type="xsd:string">PRIMO PAT. LISA FAMILIAR 260 GRS X 12 B.</Nombre>
        <Existencias xsi:type="xsd:double">0</Existencias>
        <Costo xsi:type="xsd:double"><B>1.1</B></Costo>
        <Margen0 xsi:type="xsd:double">3</Margen0>
        <PVP0 xsi:type="xsd:double">1.212</PVP0>
        <Margen1 xsi:type="xsd:double">2</Margen1>
        <PVP1 xsi:type="xsd:double">1.224</PVP1>
        <Margen2 xsi:type="xsd:double">0</Margen2>
        <PVP2 xsi:type="xsd:double">1.236</PVP2>
        <Margen3 xsi:type="xsd:double">4</Margen3>
        <PVP3 xsi:type="xsd:double">1.248</PVP3>
      </NS2:PDADatosArticulo>
      <NS2:PDADatosArticulo id="2" xsi:type="NS2:PDADatosArticulo">
        <Codigo xsi:type="xsd:string">B2002</Codigo>
        <Nombre xsi:type="xsd:string">SECONDO PAT. LISA FAMILIAR 260 GRS X 12 B.</Nombre>
        <Existencias xsi:type="xsd:double">0</Existencias>
        <Costo xsi:type="xsd:double"><B>1.2</B></Costo>
        <Margen0 xsi:type="xsd:double">3</Margen0>
        <PVP0 xsi:type="xsd:double">1.212</PVP0>
        <Margen1 xsi:type="xsd:double">2</Margen1>
        <PVP1 xsi:type="xsd:double">1.224</PVP1>
        <Margen2 xsi:type="xsd:double">0</Margen2>
        <PVP2 xsi:type="xsd:double">1.236</PVP2>
        <Margen3 xsi:type="xsd:double">4</Margen3>
        <PVP3 xsi:type="xsd:double">1.248</PVP3>
      </NS2:PDADatosArticulo>
      <NS2:PDADatosArticulo id="3" xsi:type="NS2:PDADatosArticulo">
        <Codigo xsi:type="xsd:string">B3003</Codigo>
        <Nombre xsi:type="xsd:string">TERZO PAT. LISA FAMILIAR 260 GRS X 12 B.</Nombre>
        <Existencias xsi:type="xsd:double">0</Existencias>
        <Costo xsi:type="xsd:double"><B>1.3</B></Costo>
        <Margen0 xsi:type="xsd:double">3</Margen0>
        <PVP0 xsi:type="xsd:double">1.212</PVP0>
        <Margen1 xsi:type="xsd:double">2</Margen1>
        <PVP1 xsi:type="xsd:double">1.224</PVP1>
        <Margen2 xsi:type="xsd:double">0</Margen2>
        <PVP2 xsi:type="xsd:double">1.236</PVP2>
        <Margen3 xsi:type="xsd:double">4</Margen3>
        <PVP3 xsi:type="xsd:double">1.248</PVP3>
      </NS2:PDADatosArticulo>
      <NS2:PDADatosArticulo id="4" xsi:type="NS2:PDADatosArticulo">
        <Codigo xsi:type="xsd:string">B4004</Codigo>
        <Nombre xsi:type="xsd:string">QUARTO PAT. LISA FAMILIAR 260 GRS X 12 B.</Nombre>
        <Existencias xsi:type="xsd:double">0</Existencias>
        <Costo xsi:type="xsd:double"><B>1.4</B></Costo>
        <Margen0 xsi:type="xsd:double">3</Margen0>
        <PVP0 xsi:type="xsd:double">1.212</PVP0>
        <Margen1 xsi:type="xsd:double">2</Margen1>
        <PVP1 xsi:type="xsd:double">1.224</PVP1>
        <Margen2 xsi:type="xsd:double">0</Margen2>
        <PVP2 xsi:type="xsd:double">1.236</PVP2>
        <Margen3 xsi:type="xsd:double">4</Margen3>
        <PVP3 xsi:type="xsd:double">1.248</PVP3>
      </NS2:PDADatosArticulo>
      <return href="#1"/>
    </NS1:PDA_DatosArticuloResponse>
  </SOAP-ENV:Body>
</SOAP-ENV:Envelope>
"$

tested using this:

B4X:
For RecordID = 1 To 5    'SampleXML only has records 1..4 ie no record 5
    Log(RecordID & TAB & GetXMLField(SampleXML, RecordID, "Nombre"))
Next

results in:

Log ouput:
Waiting for debugger to connect...
Program started.
1    PRIMO PAT. LISA FAMILIAR 260 GRS X 12 B.
2    SECONDO PAT. LISA FAMILIAR 260 GRS X 12 B.
3    TERZO PAT. LISA FAMILIAR 260 GRS X 12 B.
4    QUARTO PAT. LISA FAMILIAR 260 GRS X 12 B.
5    XML record 5 field Nombre not found

Runtime efficiency is dismal 😥 but good enough for proof-of-concept mockup 🏆
 
Last edited:
Upvote 0
Top