1

This is the information that the XML string has.

<?xml version="1.0" encoding="UTF-8"?>
<string xmlns="http://tempuri.org/">
<statusInfo><vendorClaimID>BRADY12478018AETNA</vendorClaimID>
<statusID>0</statusID><statusDescription>Unvalidated</statusDescription>
</statusInfo></string>

But this is how it comes in.. You will have to scroll to the right to see all of it.

'<?xml version="1.0" encoding="utf-8"?>'#$D#$A'<string xmlns="http://tempuri.org/">&lt;statusInfo&gt;&lt;vendorClaimID&gt;BRADY12478018AETNA&lt;/vendorClaimID&gt;&lt;statusID&gt;0&lt;/statusID&gt;&lt;statusDescription&gt;Unvalidated&lt;/statusDescription&gt;&lt;/statusInfo&gt;</string>'

I have loaded the string into a XMLDoc, but don't know how to access the values easily from here..

var
doc: IXMLDocument;


doc := LoadXMLData(xmlString);

Thanks!

Trevor
  • 16,080
  • 9
  • 52
  • 83
  • Does this make any sense or is this string even something that can be parsed? – Trevor May 22 '12 at 21:13
  • Made an edit the xml string hopefully its easier to understand now. – Trevor May 22 '12 at 22:17
  • Thanks for you help.. Well I'm getting this string in response to a web service call. Maybe this little bit of info from the web service documentation will help.. "Receiving the Response In most cases, the response for each web service call is returned as XML or formatted text. For example, the above URL would return: <Payer><Name>1199 National Benefit Fund</Name><ApexPayerID>13162</ApexPayerID></Payer>< ... "" – Trevor May 22 '12 at 23:01
  • The above format is what is what my original string looked like but after writing it to an xml file and grabbing the text it looks more like what you see in my current revision. – Trevor May 22 '12 at 23:03

2 Answers2

7

You can use XPath to extract the values of the nodes

Check this sample

{$APPTYPE CONSOLE}

{$R *.res}

uses
  MSXML,
  SysUtils,
  ActiveX,
  ComObj;


Const

XMLStr=
'<?xml version="1.0" encoding="UTF-8"?> '+
'<string xmlns="http://tempuri.org/">'+
' <statusInfo>'+
'  <vendorClaimID>BRADY12478018AETNA</vendorClaimID> '+
'  <statusID>0</statusID><statusDescription>Unvalidated</statusDescription> '+
' </statusInfo>'+
'</string> ';

procedure Test;
Var
  XMLDOMDocument  : IXMLDOMDocument;
  XMLDOMNode      : IXMLDOMNode;
begin
  XMLDOMDocument:=CoDOMDocument.Create;
  XMLDOMDocument.loadXML(XmlStr);
  XMLDOMNode := XMLDOMDocument.selectSingleNode('//string/statusInfo/vendorClaimID');
  if XMLDOMNode<>nil then
    Writeln(Format('vendorClaimID %s',[String(XMLDOMNode.Text)]));

  XMLDOMNode := XMLDOMDocument.selectSingleNode('//string/statusInfo/statusID');
  if XMLDOMNode<>nil then
    Writeln(Format('statusID %s',[String(XMLDOMNode.Text)]));

  XMLDOMNode := XMLDOMDocument.selectSingleNode('//string/statusInfo/statusDescription');
  if XMLDOMNode<>nil then
    Writeln(Format('statusDescription %s',[String(XMLDOMNode.Text)]));
end;


begin
 try
    CoInitialize(nil);
    try
      Test;
    finally
      CoUninitialize;
    end;
 except
    on E:EOleException do
        Writeln(Format('EOleException %s %x', [E.Message,E.ErrorCode]));
    on E:Exception do
        Writeln(E.Classname, ':', E.Message);
 end;
 Writeln('Press Enter to exit');
 Readln;
end.
RRUZ
  • 134,889
  • 20
  • 356
  • 483
  • You can use XPath with IXMLDocument if its internal vendor engine is set to MSXML. – Remy Lebeau May 22 '12 at 23:22
  • Great this is working with the string you have supplied. Do you have any idea of what I can do when the string (response) I get looks like this? ''#$D#$A'<statusInfo><vendorClaimID>BRADY12478018AETNA</vendorClaimID><statusID>0</statusID><statusDescription>Unvalidated</statusDescription></statusInfo>' that '#$D#$A' seems to be throwing it off and i'm having trouble getting rid of it. – Trevor May 23 '12 at 14:53
  • The whole string is not showing after the ... but hopefully you get whats happening. I also added it to my main question. Thanks – Trevor May 23 '12 at 14:56
  • Ok, then you must decode first you XML, try using the `HTTPDecode` function of the HTTPApp unit and then parse the result string with the above method or using the Remy answer. – RRUZ May 23 '12 at 15:19
  • I tried the HTTPDecode function but It still didn't read the string correctly once I load it it can't find any of the nodes. :( – Trevor May 23 '12 at 16:30
  • Ahh, yes HTMLDecode that makes sense, that was my problem the whole time, I just didn't realize it when I asked the question. ThankYou! – Trevor May 23 '12 at 16:44
4

Each node in the XML will be represented as an IXMLNode in the IXMLDocument, in the same hierarchy that they appear in the XML. It would help if you first look at the XML with the nodes indented so you can see the hierarchy more clearly:

<?xml version="1.0" encoding="UTF-8"?> 
<string xmlns="http://tempuri.org/"> 
  <statusInfo>
    <vendorClaimID>BRADY12478018AETNA</vendorClaimID> 
    <statusID>0</statusID>
    <statusDescription>Unvalidated</statusDescription> 
  </statusInfo>
</string> 

One you understand the hierarchy, you can write code for it:

var 
  doc: IXMLDocument;
  statusInfo: IXMLNode;
  vendorClaimID: String;
  statusID: Integer;
  statusDescription: String;
begin 
  doc := LoadXMLData(xmlString);
  statusInfo := doc.DocumentElement.ChildNodes['statusInfo'];
  vendorClaimID := statusInfo.ChildNodes['vendorClaimID'].Text;
  statusID := StrToInt(statusInfo.ChildNodes['statusID'].Text);
  statusDescription := statusInfo.ChildNodes['statusDescription'].Text; 
end;

Alternatively:

var 
  doc: IXMLDocument;
  statusInfo: IXMLNode;
  vendorClaimID: String;
  statusID: Integer;
  statusDescription: String;
begin 
  doc := LoadXMLData(xmlString);
  statusInfo := doc.DocumentElement.ChildNodes['statusInfo'];
  vendorClaimID := VarToStr(statusInfo.ChildValues['vendorClaimID']);
  statusID := StrToInt(VarToStr(statusInfo.ChildValues['statusID']));
  statusDescription := VarToStr(statusInfo.ChildValues['statusDescription']); 
end;

If you use Delphi's XML Data Binding wizard, it will generate interfaces that will parse the XML for you:

var 
  doc: IXMLDocument;
  statusInfo: IXMLstatusInfoType;
  vendorClaimID: String;
  statusID: Integer;
  statusDescription: String;
begin 
  doc := LoadXMLData(xmlString);
  statusInfo := Getstring(doc).statusInfo;
  vendorClaimID := statusInfo.vendorClaimID;
  statusID := statusInfo.statusID;
  statusDescription := statusInfo.statusDescription; 
end;
RRUZ
  • 134,889
  • 20
  • 356
  • 483
Remy Lebeau
  • 555,201
  • 31
  • 458
  • 770