Прошу подсказать... Что делаю: 1. Есть веб-сервис 1С. На него посылаю запрос и получаю ответ через SOAP запрос. 2. Текст ответа падает в переменную "Ответ". 3. Делаю парсинг "подручными" методами.
Внутри ответа веб-сервиса идут блоки: <m:НеподписанныйДокумент> информация </m:НеподписанныйДокумент> *1234 - это какая то информация номера документов и т.д.
Проблема в том, что таких блоков (<m:НеподписанныйДокумент> информация </m:НеподписанныйДокумент>) может быть 50 шт. и более. Мне же нужна информация из этих блоков (сумма, номера, УИД и т.д).
Сейчас забираю данные кустарным способом. Высчитываю шапку и тд. - работает честно говоря не стабильно.
Sub qwert()
Dim s
s = "<soap:Envelope xmlns:soap=""""http://www.w3.org/2003/05/soap-envelope"""">"
s = s & vbCrLf & "<soap:Body>"
s = s & vbCrLf & "<m:getUPDListResponse xmlns:m=""""itPersona"""">"
s = s & vbCrLf & "<m:return xmlns:xs=""""http://www.w3.org/2001/XMLSchema"""" xmlns:xsi=""""http://www.w3.org/2001/XMLSchema-instance"""">"
s = s & vbCrLf & "<m:НеподписанныйДокумент>"
s = s & vbCrLf & "<m:Номер>1234 </m:Номер>"
s = s & vbCrLf & "<m:Дата>2020-09-05</m:Дата>"
s = s & vbCrLf & "<m:Сумма>50.7</m:Сумма>"
s = s & vbCrLf & "<m:УИД>1234</m:УИД>"
s = s & vbCrLf & "<m:ИдентификторЭДО>1234</m:ИдентификторЭДО>"
s = s & vbCrLf & "<m:ОбменЭДО>false</m:ОбменЭДО>"
s = s & vbCrLf & "<m:Статус>Отправлен по почте</m:Статус>"
s = s & vbCrLf & "<m:ДатаСтатуса>2020-09-30T10:48:14</m:ДатаСтатуса>"
s = s & vbCrLf & "</m:НеподписанныйДокумент>"
s = s & vbCrLf & "</m:return>"
s = s & vbCrLf & "</m:getUPDListResponse>"
s = s & vbCrLf & "</soap:Body>"
s = s & vbCrLf & "</soap:Envelope>"
' Debug.Print s
Debug.Print "Номер", get_dan(s, "Номер")
Debug.Print "Сумма", get_dan(s, "Сумма")
Debug.Print "УИД", get_dan(s, "УИД")
End Sub
Function get_dan(s, kl)
If InStr(1, s, kl) > 0 Then
get_dan = Split(Split(s, kl & ">")(1), "<")(0)
End If
End Function
большая часть кода формирование списка в дебаггере Номер 1234 Сумма 50.7 УИД 1234
или в цикле
Код
a = Split("Номер,Сумма,УИД", ",")
For i = 0 To UBound(a)
Debug.Print a(i), get_dan(s, a(i))
Next i
'Reference: Microsoft XML, v3.0
Dim xml As New MSXML2.DOMDocument, elem As MSXML2.IXMLDOMElement
xml.async = False 'отключаем асинхонный запрос, иначе данные не успевают загрузиться
xml.LoadXML (Ответ) 'загружаем ответ xml
For Each elem In xml.DocumentElement.SelectNodes("//soap:Body/m:getUPDListResponse/m:return/m:НеподписанныйДокумент")
Debug.Print elem.SelectSingleNode("m:Номер").Text
Next elem
если блоков <m:НеподписанныйДокумент много, то сначала разбить текст Split по "<m:НеподписанныйДокумент" и потом в цикле обработать все элементы начиная с первого
webley, Очень интересно. Однако при тесте возник конфликт с Microsoft XML, v3.0. Так как уже используется в запросе Microsoft XML, v6.0. И то и то выбрать не даёт.
Попробовал прописать MSXML2.DOMDocument60 - не ругается, но похоже чего то не хватает, так как выдаёт на строке: For Each elem In xml.DocumentElement.SelectNodes("//soap:Body/m:getUPDListResponse/m:return/m:НеподписанныйДокумент")
Код
Sub h()
Dim xml As New MSXML2.DOMDocument60, elem As MSXML2.IXMLDOMElement
xml.async = False 'отключаем асинхонный запрос, иначе данные не успевают загрузиться
xml.LoadXML (ответ) 'загружаем ответ xml
For Each elem In xml.DocumentElement.SelectNodes("//soap:Body/m:getUPDListResponse/m:return/m:НеподписанныйДокумент")
Debug.Print elem.SelectSingleNode("m:Номер").Text
Next elem
End Sub
То есть структура сейчас такая (затёр некоторые данные входа ибо закрытый ресурс)
Ещё думаю что должно быть с soap:Envelope:
Код
For Each elem In xml.DocumentElement.SelectNodes("//soap:Envelope/soap:Body/m:getUPDListResponse/m:return/m:НеподписанныйДокумент")
Но пока не помогло.
Полный код:
Код
Public ответ As Variant
Sub ntcn()
инн = Sheets("упд").Range("b1")
'Set and instantiate our working objects
Dim Req As Object
Dim sEnv As String
Dim Resp As New MSXML2.DOMDocument60
Set Req = CreateObject("MSXML2.XMLHTTP")
Set Resp = CreateObject("MSXML2.DOMDocument.6.0")
Req.Open "Post", "ссылка на веб сервис 1С", False
' we create our SOAP envelope for submission to the Web Service
sEnv = sEnv & " <soapenv:Envelope "
sEnv = sEnv & " xmlns:soapenv=""http://schemas.xmlsoap.org/soap/envelope/"""
sEnv = sEnv & " xmlns:itp=""rrrr"">"
sEnv = sEnv & " <soapenv:Header/>"
sEnv = sEnv & " <soapenv:Body>"
sEnv = sEnv & " <itp:getUPDList>"
sEnv = sEnv & " <itp:INN>" & инн & "</itp:INN>"
sEnv = sEnv & " </itp:getметод>"
sEnv = sEnv & " </soapenv:Body>"
sEnv = sEnv & " </soapenv:Envelope>"
' Send SOAP Request
Req.send (sEnv)
ответ = Req.responseText
Call h
End Sub
Sub h()
Dim xml As New MSXML2.DOMDocument60, elem As MSXML2.IXMLDOMElement
xml.async = False
xml.LoadXML (ответ)
For Each elem In xml.DocumentElement.SelectNodes("//soap:Body/m:getUPDListResponse/m:return/m:НеподписанныйДокумент")
Debug.Print elem.SelectSingleNode("m:Номер").Text
Next elem
End Sub
просто размножил блок <m:НеподписанныйДокумент>"..... "</m:НеподписанныйДокумент>"
Код
a = Split("Номер,Сумма,УИД", ",") ' "список нужніх параметров через запятую без пробела
u = Split(s, "<m:НеподписанныйДокумент>")
For k = 0 To UBound(u)
Debug.Print
Debug.Print "Документ № " & k
For i = 0 To UBound(a)
Debug.Print a(i), get_dan(u(k), a(i))
Next i
Next k
поэтому данные одинаковые. лениво менять Документ № 1 Номер 1234 Сумма 50.7 УИД 1234