2012-06-23 1 views
0

Я пытаюсь выбрать узлы из XML-ответа на веб-службу безрезультатно. По какой-то причине я могу выбрать корневой узел («xmldata»), однако, когда я пытаюсь глубже сверлить («xmldata/customers»), все возвращается пустым! Ниже приведен образец XML, который возвращается веб-сервисом.VBScript не может выбирать узлы XML

<xmldata> 
    <customers> 
    <customerid>22506</customerid> 
    <firstname>Jim</firstname> 
    <issuperadmin>N</issuperadmin> 
    <lastname>Jones</lastname> 
    </customers> 
</xmldata> 

и вот код, который я пытаюсь выбрать customerid, firstname и lastname;

' Send the Xml 
oXMLHttp.send Xml_to_Send 

' Validate the Xml 
dim xmlDoc 
set xmlDoc = Server.CreateObject("Msxml2.DOMDocument") 
xmlDoc.load (oXMLHttp.ResponseXML.text) 
if(len(xmlDoc.text) = 0) then 
    Xml_Returned = "<B>ERROR in Response xml:<BR>ERROR DETAILS:</B><BR><HR><BR>" 
end if 

dim nodeList 
Set nodeList = xmlDoc.SelectNodes("xmldata/customers") 

For Each itemAttrib In nodeList 
    dim custID, custLname, custFname  
    custID =itemAttrib.selectSingleNode("customerid").text 
    custLname =itemAttrib.selectSingleNode("lastname").text 
    custFname =itemAttrib.selectSingleNode("firstname").text 
    response.write("News Subject: " & custID) 
    response.write("<br />News Subject: " & custLname) 
    response.write("<br />News Date: " & custFname) 
Next 

Результат приведенный выше код - zilch! на страницу ничего не написано. Одна странная вещь, если я выбираю корневой элемент и получаю его длину следующим образом;

Set nodeList = xmlDoc.SelectNodes("xmldata") 
Response.Write(nodeList.length) '1 is written to page 

Он правильно определяет длину 1. Однако, когда я пробую то же самое со следующим узлом вниз следующим образом;

Set nodeList2 = xmlDoc.SelectNodes("xmldata/customers") 
Response.Write(nodeList.length) '0 is written to page 

Он возвращает длину 0. ПОЧЕМУ!

Обратите внимание, что это не единственный способ получить доступ к значениям этих узлов. Я просто не могу понять, что я делаю неправильно. Может кто-то, пожалуйста, помогите мне. Приветствия.

ответ

0

Хорошо, поэтому я, наконец, решил, что я делаю неправильно. Поскольку xml, который я извлекал, был из веб-службы, и у меня была ограниченная информация об этом, я использовал следующее для написания xml на странице, чтобы я мог видеть, как он был структурирован.

Response.Write oXMLHttp.ResponseXml.xml 

По какой-то причине (возможно, кто-то может заполнить эту часть) он написал все теги XML в нижнем регистре. Оказывается, после некоторого расследования и после того, как я сделал следующее, я узнал, что это не правда!

dim nodeList 
Set nodeList = xmlDoc.SelectNodes("//xmldata/") 

for each item In nodeList 
    response.write(item.text & " -> Tag Name: " & item.nodeName & "<br />") 
Next 

'this wrote the following to the page 
'22506 -> Tag Name: CustomerID 
'Jim -> Tag Name: FirstName 
'N -> Tag Name: IsSuperAdmin 
'Jones 2 -> Tag Name: LastName 

Как вы видите, выход свойства nodeName показывает теги для верблюжьей кейс. Так что ResponseXML был довольно вводящим в заблуждение и видя, что XPath чувствителен к регистру, мешает мне выбирать узлы, о которых идет речь.

2

Короткий ответ

oXMLHttp.ResponseXML.text может возвращать текст, но не «Строка, содержащая URL, который определяет местоположение файла XML», как требуется для параметра .load. Так заменить

xmlDoc.load (oXMLHttp.ResponseXML.text) 

с

xmlDoc.loadXml oXMLHttp.ResponseXML.xml 

Если это не работает ", так сказать; Затем я попытаюсь предоставить более длинный ответ.

(PS на короткий ответ: AnthonyWJones' совет не преобразовать XML в два раза звук, я предложил это „минимальное влияние на существующий код“ подход в надежде получить OT за первое препятствие, а не как общеприменимая стратегия.)

Longer ответить

Если у вас есть проблемы XML на ASP-странице, вы должны попытаться изолировать и протестировать конкретные проблемы XML в сценарии консоли. Для вашей проблемы я заполнял каркас (.xml файл загрузки, проверьте наличие ошибок) с кодом доступа к узлам с помощью XPath и DOM дерева:

Dim oFS : Set oFS = CreateObject("Scripting.FileSystemObject") 
    Dim sFSpec : sFSpec = oFS.GetAbsolutePathName("..\data\00.xml") 
    Dim oXml : Set oXml = CreateObject("Msxml2.DOMDocument") 

    oXml.setProperty "SelectionLanguage", "XPath" 
    oXml.async = False 
    oXml.load sFSpec 

    If 0 = oXml.parseError.errorCode Then 
    WScript.Echo "loaded:", sFSpec 
    WScript.Echo "root:", oXml.documentElement.tagName 

    Dim sXPath, ndlFnd, ndChild, ndFnd 

    sXPath = "/xmldata/customers" 
    Set ndlFnd = oXml.selectNodes(sXPath) 
    If 0 = ndlFnd.length Then 
     WScript.Echo "no '" & sXPath & "' found" 
    Else 
     WScript.Echo "found", ndlFnd.length, "node(s) for '" & sXPath & "'" 
     sXPath = "firstname" 
     For Each ndChild In ndlFnd 
      WScript.Echo "child:", ndChild.tagName 
      Set ndFnd = ndChild.selectSingleNode(sXPath) 
      If ndFnd Is Nothing Then 
       WScript.Echo "no '" & sXPath & "' found" 
      Else 
       WScript.Echo ndFnd.text, "==", ndChild.childNodes(1).text 
      End If 
     Next 
    End If 
    Else 
    WScript.Echo "errorCode:", oXml.parseError.errorCode 
    WScript.Echo oXml.parseError.reason 
    End If 

выход:

loaded: E:\trials\SoTrials\answers\11166940\data\00.xml 
root: xmldata 
found 1 node(s) for '/xmldata/customers' 
child: customers 
Jim == Jim 

Как вы можете видеть

  1. Я использую стандартные/утвержденные методы для проверки результата отдельных шагов (например, parseError (вместо длины вуд тест), чтобы увидеть, если я хорошо сформированный/действительный/полезный документ)
  2. Когда я сомневаюсь, я поставил WScript.Echo, чтобы убедиться, что мои предположения о том, что VBScript должен доставить воду для удержания.
+0

Привет, Эккерхард, спасибо за ответ. Я попробовал то, что вы предложили, и у меня все еще есть такая же проблема, пытаясь выбрать что-нибудь глубже, чем узел xmldata. – urbanMethod

+0

Приветствия за расширенный ответ. Я решил, что моя проблема связана с чувствительностью к регистру (я опубликовал данные). У меня наверняка будет трещина на скрипте консоли, который вы опубликовали в следующий раз, когда я столкнусь с проблемами XML. – urbanMethod

2

Прежде остановка делает это:

Dim doc : Set xmlDoc = CreateObject("MSXML2.DOMDocument") 
xmlDoc.LoadXML (oXmlHttp.responseXML.xml) 

XML в ответ разбирается в DOM, который затем попросить быть преобразованы обратно в строку (.xml), который затем синтаксический анализ (опять же) в другой DOM (.LoadXML).

ли просто:

Dim xmlDoc : Set xmlDoc = oXmlHttp.responseXML 

Во-вторых, вы правы в своем ответе XPath чувствителен к регистру поэтому ваши XPaths (помимо .text лох, который Ekkehard уже указывал) не будет работать, потому что xml, который вы получаете, не соответствует тому, что, как вы думали, вы получаете.

И, наконец, определение «корпус верблюда» действительно меняется, но в целом этот «почтовый адрес» является верблюжьим корпусом, и этот «PostalAddress» называется «корпусом Паскаля».

+0

спасибо за указание на недостаток в моем коротком ответе. –

+0

Спасибо Энтони за ваш ответ. Тем не менее, у меня все еще нет ответа на реальную проблему, которая вызвала у меня основную проблему: почему все теги, где делаются строчные буквы. Я говорю это, потому что все ошибки кода, которые были указаны, действительно из-за меня экспериментируют, и это не вызвало проблемы. пс. Можно было бы сказать, что дело верховного верблюда успокоило вас? :) – urbanMethod

+0

Я не уверен, как вы обнаружили, что что-то «сделал все теги в нижнем регистре»? MSXML этого не делает. Возможно, если бы вы подробно описали _exactly_, как вам удалось наблюдать это явление. – AnthonyWJones