Excel это не сложно
Добро пожаловать, Гость. Пожалуйста, войдите или зарегистрируйтесь.
28.03.2024, 14:36:30

Войти
Интересные и полезные статьи по работе с Excel и VBA можно найти в разделе ХИТРОСТИ
33 233 Сообщений в 5 454 Тем от 6 750 Пользователей
Последний пользователь: Alex1210
*
Перейти на сайт Хитрости Надстройка MulTEx Обучающие тренинги Наша группа ВКонтакте
Правила форума Начало Помощь Поиск Календарь Войти Регистрация Выйти
+  Excel это не сложно
|-+  Основные форумы
| |-+  Вопросы по Excel и VBA
| | |-+  выборка данных из кучи xml файлов в таблицу excel
Страниц: 1 2 3 4 [Все]   Вниз
Печать
Автор Тема: выборка данных из кучи xml файлов в таблицу excel  (Прочитано 16553 раз)
0 Пользователей и 1 Гость смотрят эту тему.
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« : 21.07.2021, 08:22:06 »

Всем привет. Стоит задача выбрать из кучи xml файлов нужную информацию и добавить ее в таблицу excel. Изучая форумы, литературу и иные источники написал код vba, который должен это делать, но он прокручивается в пустую, не пойму в чем дело. Ошибок ни каких не выдает и данных тоже не выбирает. Знающие люди направьте на путь истинный.
пример xml файла прилагаю
мой код
Код: (vb)

Private Sub CommandButtonImport_Click()

Dim fd As Office.FileDialog
    Set fd = Application.FileDialog(msoFileDialogFilePicker)
    With fd
            .Filters.Clear
            .Title = "Select Multiple XML Files"
            .Filters.Add "XML File", "*.xml", 1
            .AllowMultiSelect = True
                       
        If .Show = True Then
            Dim xdoc As Object
            Set xdoc = CreateObject("MSXML2.DOMdocument")
            xdoc.async = False: xdoc.validateOnParse = False
            row_number = 1
            For i = 1 To .SelectedItems.Count
                xmlFileName = fd.SelectedItems(i)
                xdoc.Load (xmlFileName)
                xdoc.SetProperty "SelectionNamespaces", "xmlns:ns='urn:customs.ru:Information:ExchangeDocuments:ED_Container:5.13.1'"
                Set xdocE = xdoc.DocumentElement
                For Each xdocE In xdoc.SelectNodes("ns:ED_Container/ns:ContainerDoc/ns:DocBody/ns:ESADout_CU")
                Aplication.Range("DTRange").Cells(row_number, 1).Value = xdocE.SelectSingleNode("/comment()").Text
                Aplication.Range("DTRange").Cells(row_number, 2).Value = xdocE.SelectSingleNode("ns:CustomsProcedure").Text
                Aplication.Range("DTRange").Cells(row_number, 3).Value = xdocE.SelectSingleNode("ns:CustomsModeCode").Text
                Aplication.Range("DTRange").Cells(row_number, 4).Value = xdocE.SelectSingleNode("ns:catESAD_cu:GoodsNumeric").Text
                Aplication.Range("DTRange").Cells(row_number, 5).Value = xdocE.SelectSingleNode("ns:catESAD_cu:GoodsTNVEDCode").Text
                row_number = row_number + 1
                Next xdocE
     
              Next i
        End If
                         
    End With

End Sub



вытягиваю данные вот в такую таблицу
INFORMATION            
            
DT   napr   proc   goods   TN_VED
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #1 : 21.07.2021, 08:24:39 »

на всякий случай это файл с таблицей
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #2 : 21.07.2021, 10:31:43 »

направьте на путь истинный
начать я бы рекомендовал с пошаговой отладки и просмотра чего так откуда получаете: Отлов ошибок и отладка кода VBA
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #3 : 21.07.2021, 15:24:09 »

Так ошибок не выдаёт и ничего не выбирает. В том то и дело  Плачущий. Сижу ломаю голову, может вообще код кривой. Я так то не очень силён в vba, тем более по отношению к xml
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #4 : 21.07.2021, 20:35:28 »

ошибок не выдаёт и ничего не выбирает
так почитайте статью и примените пошаговую отладку, чтобы посмотреть что на каком шаге у Вас происходит и какие значения получаете.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #5 : 22.07.2021, 04:00:59 »

Спасибо за совет, по всей видимости код не отрабатывает эти строки

Код: (vb)
Aplication.Range("DTRange").Cells(row_number, 1).Value = xdocE.SelectSingleNode("comment()").Text
                Aplication.Range("DTRange").Cells(row_number, 2).Value = xdocE.SelectSingleNode("dout:CustomsProcedure").Text
                Aplication.Range("DTRange").Cells(row_number, 3).Value = xdocE.SelectSingleNode("dout:CustomsModeCode").Text
                Aplication.Range("DTRange").Cells(row_number, 4).Value = xdocE.SelectSingleNode("atc:catESAD_cu:GoodsNumeric").Text
                Aplication.Range("DTRange").Cells(row_number, 5).Value = xdocE.SelectSingleNode("atc:catESAD_cu:GoodsTNVEDCode").Text
                row_number = row_number + 1
                Next xdocE


с for each сразу перескакивает на next i, что не так не пойму.
Он их не запускает при пошаговой отработке.
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #6 : 22.07.2021, 09:14:55 »

for each сразу перескакивает на next i
это значит, что нет доступных элементов для перебора в узле "ns:ED_Container/ns:ContainerDoc/ns:DocBody/ns:ESADout_CU".
Запишите так:
Код: (vb)
For Each xdocE In xdoc.SelectNodes("ED_Container/ContainerDoc/DocBody/ESADout_CU")

да и вообще везде уберите ns:
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #7 : 22.07.2021, 09:33:41 »

это значит, что нет доступных элементов для перебора в узле "ns:ED_Container/ns:ContainerDoc/ns:DocBody/ns:ESADout_CU".
Запишите так:
Код: (vb)
For Each xdocE In xdoc.SelectNodes("ED_Container/ContainerDoc/DocBody/ESADout_CU")

да и вообще везде уберите ns:


В xml  файле несколько пространств имен, сейчас немного по другому выглядит данная часть кода. Если убрать указание на конкретное пространство имен наверное тогда комп вообще ничего не поймет откуда что брать.

Код: (vb)
xdoc.Load (xmlFileName)
                xdoc.SetProperty "SelectionNamespaces", "xmlns:cont='urn:customs.ru:Information:ExchangeDocuments:ED_Container:5.13.1'"
                xdoc.SetProperty "SelectionNamespaces", "xmlns:dout='urn:customs.ru:Information:CustomsDocuments:ESADout_CU:5.17.0'"
                xdoc.SetProperty "SelectionNamespaces", "xmlns:atc='urn:customs.ru:CUESADCommonAggregateTypesCust:5.17.0'"
                Set xdocE = xdoc.DocumentElement
                For Each xdocE In xdoc.SelectNodes("cont:ED_Container/cont:ContainerDoc/cont:DocBody/dout:ESADout_CU")
                Application.Range("DTRange").Cells(row_number, 1).Value = xdocE.SelectSingleNode("comment()").Text
                Application.Range("DTRange").Cells(row_number, 2).Value = xdocE.SelectSingleNode("dout:CustomsProcedure").Text
                Application.Range("DTRange").Cells(row_number, 3).Value = xdocE.SelectSingleNode("dout:CustomsModeCode").Text
                Application.Range("DTRange").Cells(row_number, 4).Value = xdocE.SelectSingleNode("atc:catESAD_cu:GoodsNumeric").Text
                Application.Range("DTRange").Cells(row_number, 5).Value = xdocE.SelectSingleNode("atc:catESAD_cu:GoodsTNVEDCode").Text
                row_number = row_number + 1
                Next xdocE
   
   
              Next i
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #8 : 22.07.2021, 10:14:05 »

наверное тогда
Может сначала надо попробовать? Я вот попробовал, прежде чем посоветовать. А Вы, прежде чем написать? Уберите отсылки на пространства имен - в схеме у Вас в приложенном файле узлы ими не отмечены.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #9 : 23.07.2021, 02:33:50 »

Может сначала надо попробовать?

Я тысячекратно извиняюсь. Конечно нужно пробовать, т.к. не попробуешь не узнаешь.

Код: (vb)
xdoc.SetProperty "SelectionNamespaces", "xmlns:cont='urn:customs.ru:Information:ExchangeDocuments:ED_Container:5.13.1'"
                xdoc.SetProperty "SelectionNamespaces", "xmlns:dout='urn:customs.ru:Information:CustomsDocuments:ESADout_CU:5.17.0'"
                xdoc.SetProperty "SelectionNamespaces", "xmlns:atc='urn:customs.ru:CUESADCommonAggregateTypesCust:5.17.0'"
                Set xdocE = xdoc.DocumentElement
                For Each xdocE In xdoc.SelectNodes("ED_Container/ContainerDoc/DocBody/ESADout_CU")
                Application.Range("DTRange").Cells(row_number, 1).Value = xdocE.SelectSingleNode("/comment()").Text
                Application.Range("DTRange").Cells(row_number, 2).Value = xdocE.SelectSingleNode("CustomsProcedure").Text
                Application.Range("DTRange").Cells(row_number, 3).Value = xdocE.SelectSingleNode("CustomsModeCode").Text
                Application.Range("DTRange").Cells(row_number, 4).Value = xdocE.SelectSingleNode("GoodsNumeric").Text
                Application.Range("DTRange").Cells(row_number, 5).Value = xdocE.SelectSingleNode("GoodsTNVEDCode").Text
                row_number = row_number + 1


Выбирает но не все

Код: (vb)
Application.Range("DTRange").Cells(row_number, 4).Value = xdocE.SelectSingleNode("GoodsNumeric").Text
                Application.Range("DTRange").Cells(row_number, 5).Value = xdocE.SelectSingleNode("GoodsTNVEDCode").Text


по этим 2 строчкам дает ошибку Run time error 91.
Я так понимаю несоответствие типа данных. Им не подходит значение Text?
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #10 : 23.07.2021, 04:08:17 »

Вот такое сообщение выдает. Не задана объектная переменная - не пойму что он хочет.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #11 : 23.07.2021, 04:40:41 »

как я понял проблема в этой строке
Код: (vb)
 For Each xdocE In xdoc.SelectNodes("ED_Container/ContainerDoc/DocBody/ESADout_CU")  

пробовал написать так
Код: (vb)
For Each xdocE In xdoc.SelectNodes("ED_Container/ContainerDoc/DocBody/ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods")

не помогло. Заполняется только первый столбец.
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #12 : 23.07.2021, 09:38:36 »

по этим 2 строчкам дает ошибку
Сложно что-то говорить наверняка, когда Вы работаете с одним файлом, а на форум приложили другой Улыбка Но. Ошибка явно не в этой строке
For Each xdocE In xdoc.SelectNodes("ED_Container/ContainerDoc/DocBody/ESADout_CU")
т.к. другие-то свойства из узла определяются и записываются. Проблема именно в тех узлах, на которых ошибку дает. Возможно, Вы просто неправильно к ним обращаетесь. Может быть там надо использовать не .Text, а NodeValue. А возможно они вообще не являются узлами и к ним надо обращаться через Nodes/ChildNodes
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #13 : 23.07.2021, 10:01:14 »

наверняка, когда Вы работаете с одним файлом, а на форум приложили другой

Структура файла полностью идентична, только содержимое подчищено. Эти 2 поля не должен был трогать, т.к. в них нет конфиденциальной информации.
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #14 : 23.07.2021, 10:18:48 »

Так и просмотрите структуру-то. У Вас эти поля вложены в подчиненные узлы, а Вы хотите их напрямую из узла ESADout_CU получить. Вот так работает без проблем:
Код: (vb)
Application.Range("DTRange").Cells(row_number, 4).Value = xdocE.SelectSingleNode("ESADout_CUGoodsShipment/ESADout_CUGoods/catESAD_cu:GoodsNumeric").Text
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #15 : 23.07.2021, 12:07:36 »

Вот так работает без проблем:
Точно. Я пробовал так только без ESADout_ прописывал. Попозже проверю.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #16 : 23.07.2021, 13:32:45 »

Если в ESADout_CUGoodsShipment есть 2 или более вложений ESADout_CUGoods в которых catESAD_cu:GoodsNumeric и catESAD_cu:GoodsTNVEDCode разные, хотя последнее может быть и одинаковым. Из таких файлов xml тянет только первую запись остальные пропускает. Как сделать чтоб брало все. Пример xml могу закинуть позже.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #17 : 23.07.2021, 14:31:13 »

вот пример кода с двумя областями содержащими выше указанные подобласти. Как прокрутить все подобласти?
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #18 : 26.07.2021, 04:53:16 »

вот корректный xml файл
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #19 : 26.07.2021, 06:02:42 »

ESADout содержит item7 (ESADout_CUGoodsShipment), который в свою очередь содержит item15 и item16 (ESADout_CUGoods), которые включают item1 (catESAD_cu:GoodsNumeric) и item7 (catESAD_cu:GoodsTNVEDCode). ESADout_CUGoods может быть хоть 100 штук и они содержат разные catESAD_cu:GoodsNumeric и catESAD_cu:GoodsTNVEDCode. Как дописать код чтобы значения из всех catESAD_cu:GoodsNumeric и catESAD_cu:GoodsTNVEDCode построчно добавились.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #20 : 26.07.2021, 11:52:14 »

Как я понимаю нужно перед записью в 4 столбец добавить условие если таких записей больше 1 (есть отдельный нод в котором записывается сколько таких вложений) то надо пройтись по всем вложениям, а потом уже перейти к обработке следующего файла, а если равен 1 то заполнить столбцы и идти к следующему файлу. Возник вопрос как правильно прописать условие такой то нод > 1.  И можно ли в уже открытой функции если писать ещё одну если. И можно ли обращаться к item
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #21 : 26.07.2021, 15:27:22 »

Разбор таможенных деклараций не самая интересная задача. Но муторная. И текущий вопрос явно не будет последним. Я с такими файлами уже работал и могу сказать одно: для начала надо всю задачу для себя сформулировать и разложить на алгоритмы.
В общем и целом, Вам надо делать что-то вроде цикла сразу по всем ESADout_CUGoods в схеме, а потом дергать оттуда информацию
Код: (vb)
Set nESADout_CUGoods = xmlDoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods")
For Each nCUGoods In nESADout_CUGoods
sGoodsNumeric = nCUGoods.SelectSingleNode("catESAD_cu:GoodsNumeric").nodetypedvalue
sGoodsTNVEDCode = nCUGoods.SelectSingleNode("catESAD_cu:GoodsTNVEDCode").nodetypedvalue
Next
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #22 : 27.07.2021, 00:42:19 »

Разбор таможенных деклараций не самая интересная задача. Но муторная. И текущий вопрос явно не будет последним. Я с такими файлами уже работал и могу сказать одно: для начала надо всю задачу для себя сформулировать и разложить на алгоритмы.
В общем и целом, Вам надо делать что-то вроде цикла сразу по всем ESADout_CUGoods в схеме, а потом дергать оттуда информацию
На сегодняшний день задача простая выбрать информацию о номерах ДТ, направлении перемещения, процедуру, номера товаров, код ТНВЭД. Просто до этого с xml не работал. С dbf файлами работал, но там все просто через access вытягивал все что угодно. Вот и хочу понять принципы работы с xml, мне главное в excel стянуть все правильно, а дальше я уже другими методами обработаю. Примеров в сети по работе с  xml ДТ нет и это плохо, так бы может и вопросов было меньше. Спасибо Вам, что направляете на путь истинный
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #23 : 27.07.2021, 09:05:51 »

в общем доработал код и получилось следующее
Код: (vb)
Private Sub CommandButtonImport_Click()

Dim fd As Office.FileDialog
    Set fd = Application.FileDialog(msoFileDialogFilePicker)
    With fd
            .Filters.clear
            .Title = "Select Multiple XML Files"
            .Filters.Add "XML File", "*.xml", 1
            .AllowMultiSelect = True
                       
        If .Show = True Then
            Dim xdoc As Object
            Set xdoc = CreateObject("MSXML2.DOMdocument")
            xdoc.async = False: xdoc.validateOnParse = False
            row_number = 1
            For i = 1 To .SelectedItems.Count
                xmlFileName = fd.SelectedItems(i)
                xdoc.Load (xmlFileName)
                Set xdocE = xdoc.DocumentElement
                For Each xdocE In xdoc.SelectNodes("ED_Container/ContainerDoc/DocBody/ESADout_CU")
               
                Application.Range("DTRange").Cells(row_number, 1).Value = Right(xdocE.SelectSingleNode("/comment()").Text, 23)
                Application.Range("DTRange").Cells(row_number, 2).Value = xdocE.SelectSingleNode("CustomsProcedure").Text
                Application.Range("DTRange").Cells(row_number, 3).Value = xdocE.SelectSingleNode("CustomsModeCode").Text
               
                Set nESADout_CUGoodsShipment = xdoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment")
                For Each nCUGoodsShipment In nESADout_CUGoodsShipment
                sTotalGoodsNumber = nCUGoodsShipment.SelectSingleNode("catESAD_cu:TotalGoodsNumber").nodeTypedValue
                Next
               
                Set nESADout_CUGoods = xdoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods")
                For Each nCUGoods In nESADout_CUGoods
                sGoodsNumeric = nCUGoods.SelectSingleNode("catESAD_cu:GoodsNumeric").nodeTypedValue
                sGoodsTNVEDCode = nCUGoods.SelectSingleNode("catESAD_cu:GoodsTNVEDCode").nodeTypedValue
                sGoodsMarking = nCUGoods.SelectSingleNode("catESAD_cu:GoodsGroupDescription/catESAD_cu:GoodsGroupInformation/catESAD_cu:GoodsMarking").nodeTypedValue
               
                Application.Range("DTRange").Cells(row_number, 4).Value = sGoodsNumeric
                Application.Range("DTRange").Cells(row_number, 5).Value = sGoodsTNVEDCode
                Application.Range("DTRange").Cells(row_number, 6).Value = sGoodsMarking
                row_number = row_number + 1
               
                If sTotalGoodsNumber > 1 Then GoTo a1 Else GoTo a2
                   
               
a1:             If Application.Range("DTRange").Cells(row_number, 1).Value = "" Then Application.Range("DTRange").Cells(row_number, 1).Value = Application.Range("DTRange").Cells(row_number - 1, 1).Value
                If Application.Range("DTRange").Cells(row_number, 2).Value = "" Then Application.Range("DTRange").Cells(row_number, 2).Value = Application.Range("DTRange").Cells(row_number - 1, 2).Value
                If Application.Range("DTRange").Cells(row_number, 3).Value = "" Then Application.Range("DTRange").Cells(row_number, 3).Value = Application.Range("DTRange").Cells(row_number - 1, 3).Value
                Next nCUGoods
               
a2:             Next xdocE
   
               
              Next i
                If Application.Range("DTRange").Cells(row_number, 5).Value = "" Then Application.Range("DTRange").Cells(row_number, 1).Value = ""
                If Application.Range("DTRange").Cells(row_number, 5).Value = "" Then Application.Range("DTRange").Cells(row_number, 2).Value = ""
                If Application.Range("DTRange").Cells(row_number, 5).Value = "" Then Application.Range("DTRange").Cells(row_number, 3).Value = ""
        End If
                         
    End With

End Sub

как вы и сказали вопросы остались Улыбка
Но они появились после того как захотелось еще одно поле увидеть
 sGoodsMarking = nCUGoods.SelectSingleNode("catESAD_cu:GoodsGroupDescription/catESAD_cu:GoodsGroupInformation/catESAD_cu:GoodsMarking").nodeTypedValue
И как оказалось оно есть не во всех ДТ. Когда код доходит до этих ДТ спотыкается и выдает ошибку. Подскажите как можно обойти эту ошибку. Пробовал On Error GoTo, но или не там прописывал или не правильно понял как им пользоваться.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #24 : 27.07.2021, 09:35:44 »

пробовал еще On Error Resume Next вначало кода впихнуть, тогда в те ДТ где этого поля нет прописывается значение из предыдущей ДТ. Мне надо чтобы поле осталось пустым.
« Последнее редактирование: 27.07.2021, 10:02:46 от dr_peper » Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #25 : 27.07.2021, 10:39:37 »

Ну здесь надо просто включить логику и смекалку Улыбка
Код: (vb)
On Error Resume Next
sGoodsMarking="" 'обнуляем переменную, чтобы при возникновении ошибки она оставалась пустой
'пробуем запомнить в переменную значение. Если ошибка - переменная останется пустой
sGoodsMarking = nCUGoods.SelectSingleNode("catESAD_cu:GoodsGroupDescription/catESAD_cu:GoodsGroupInformation/catESAD_cu:GoodsMarking").nodeTypedValue

Примеров в сети по работе с  xml ДТ нет
Потому что они не отличаются от работы с любым другим XML. А примеров работы с узлами и схемами XML полно. Надо просто начинать вникать с саму работу с XML и все.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #26 : 27.07.2021, 14:25:15 »

примеров работы с узлами и схемами XML полно. Надо просто начинать вникать с саму работу с XML и все.
В тех примерах почему то всегда слишком простые до безобразия xml схемы и выборки делаются гораздо проще. С файлами ДТ они не работают. Вообще кроме Вас дельного никто больше не подсказал. Буду пробовать дальше разбираться. Из тех подсказок, что вы дали уже появилась какая то ясность в голове. Мне главное вытянуть все необходимое в excel дальше по старинке обработаю его в access.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #27 : 13.09.2021, 04:19:32 »

Возник вопрос: можно ли сразу тянуть из xml данные с конкретным значением.
Например: если тег <catESAD_cu:PresentedDocumentModeCode> = 0422 то берем значения из тегов <cat_ru:PrDocumentNumber> и <cat_ru:PrDocumentDate>.
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #28 : 13.09.2021, 11:15:28 »

можно ли сразу тянуть из xml данные с конкретным значением
попробую угадать: таких примеров Вы тоже не нашли? Улыбка
если тег <catESAD_cu:PresentedDocumentModeCode> = 0422
лучше приведите полностью текст узла и скажите где искать 0422. Потому что есть подозрение, что Ваше понимания тега отличается от моего...Вполне возможно, что это не тег, а атрибут.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #29 : 14.09.2021, 01:02:20 »

попробую угадать: таких примеров Вы тоже не нашли? Улыбка лучше приведите полностью текст узла и скажите где искать 0422. Потому что есть подозрение, что Ваше понимания тега отличается от моего...Вполне возможно, что это не тег, а атрибут.


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

В этой области находятся нужные данные //ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument

в таком теге должно быть 0422 (таких тегов с разным внутренним значением много) <catESAD_cu:PresentedDocumentModeCode>01999</catESAD_cu:PresentedDocumentModeCode>
эти 2 тего на выгрузку в таблицу <cat_ru:PrDocumentDate>2021-05-11</cat_ru:PrDocumentDate> и <cat_ru:PrDocumentNumber>2021</cat_ru:PrDocumentNumber>
« Последнее редактирование: 14.09.2021, 01:12:27 от dr_peper » Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #30 : 14.09.2021, 08:24:09 »

я как то неправильно формулирую свои запросы гуглу
почти уверен в этом. Я вот набираю xpath xml и нахожу кучу примеров под различные нужды.
Например, под Вашу задачу должно быть что-то вроде этого:
Код: (vb)
For each oEl in xmlDoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument[catESAD_cu:PresentedDocumentModeCode=0422]/cat_ru:PrDocumentNumber")
' обработка
Next
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #31 : 15.09.2021, 09:02:08 »


Например, под Вашу задачу должно быть что-то вроде этого:


Вы уж меня простите, но не пойму как дописать Вашу часть кода чтоб заработало.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #32 : 04.10.2021, 09:14:21 »

Например, под Вашу задачу должно быть что-то вроде этого:
Код: (vb)
For each oEl in xmlDoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument[catESAD_cu:PresentedDocumentModeCode=0422]/cat_ru:PrDocumentNumber")
' обработка
Next


Не получается у меня с Вашим примером разобраться. Написал вот так, но он перебирает все значения и пишет только последнее. А как взять 0422 не пойму.
Код: (vb)
Set nESADout_CUPresentedDocument = xdoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument")
                For Each nPresentedDocument In nESADout_CUPresentedDocument
                sGoodsPresentedDocumentModeCode = nPresentedDocument.SelectSingleNode("catESAD_cu:PresentedDocumentModeCode").Text
                Next
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #33 : 04.10.2021, 10:11:59 »

перебирает все значения и пишет только последнее
изучайте циклы. For Each перебирает все значения, но в переменную sGoodsPresentedDocumentModeCode Вы запомнить можете только одно. Вот оно одно и запоминается - то, которое было на последнем проходе цикла, ибо все предыдущие затираются, что логично.
А как взять 0422 не пойму
внимательнее смотреть, что предлагают. Посмотрите на мой код и на свой - найдите отличия. Хотя бы по значению 0422.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #34 : 04.10.2021, 10:44:39 »

Посмотрите на мой код и на свой - найдите отличия. Хотя бы по значению 0422.


Код: (vb)
Set nESADout_CUPresentedDocument = xdoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument")
                For Each nPresentedDocument In nESADout_CUPresentedDocument.SelectSingleNode("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument[catESAD_cu:PresentedDocumentModeCode=0422]/cat_ru:PrDocumentNumber").Text


Ну вот так переписал, выдает ошибку
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #35 : 04.10.2021, 14:47:57 »

Ну вот так переписал, выдает ошибку
Ну и да. Вы упорно не хотите понимать и учить принципы xpath и даже переписать мой код не можете правильно. Мне на протяжении трех страниц темы немного уже поднадоело про азы программирования рассказывать и давать готовые решения под Ваши задачи.
Вот Вы приложили код. Вы сами понимаете, что он должен сделать? Где должен быть просмотрен заданный Вами в цикле путь к узлу? Уверен, что нет. И опять Вы даже не попытались сравнить мой код со своим.
У меня обращение к узлу в цикле идет напрямую из xmlDoc.DocumentElement.SelectNodes. А у Вас что за выдумки? Сначала указываете в переменной nESADout_CUPresentedDocument путь к "//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument", а потом еще из этого узла хотите получить опять тот же путь "//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument....". Конечно, будет ошибка, потому что код делает то, что ему говорят, а не то, что Вы хотите увидеть в итоге.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #36 : 04.10.2021, 22:12:50 »

Мне на протяжении трех страниц темы немного уже поднадоело про азы программирования рассказывать и давать готовые решения под Ваши задачи.
Всегда думал, что такого рода форумы создаются для помощи людям которые не особо шарят в чем то, но хотят разобраться.
А такие профи как Вы им помогают в этом.
Я уже много читал про xml и xpath, но пока четкой картинки нет.
Спасибо за помощь.
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #37 : 05.10.2021, 03:40:34 »

Код: (vb)
Set nESADout_CUPresentedDocument = xdoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument")
                For Each nPresentedDocument In nESADout_CUPresentedDocument
                sGoodsPresentedDocumentModeCode = nPresentedDocument.SelectSingleNode("catESAD_cu:PresentedDocumentModeCode").Text
                sPrDocumentNumber = nPresentedDocument.SelectSingleNode("cat_ru:PrDocumentNumber").Text
                
                If sGoodsPresentedDocumentModeCode Like "0422" Then Application.Range("DTRange").Cells(row_number, 8).Value = sGoodsPresentedDocumentModeCode: Application.Range("DTRange").Cells(row_number, 9).Value = sPrDocumentNumber
                
                Next

Не получается как у Вас сделать. Смог только так, при этом виснет жестко, т.к. перебирает каждый узел.

Заменил if на case, обработалось гораздо быстрее.

Код: (vb)
Select Case sGoodsPresentedDocumentModeCode
                Case "0422"
                Application.Range("DTRange").Cells(row_number, 8).Value = sGoodsPresentedDocumentModeCode
                Application.Range("DTRange").Cells(row_number, 9).Value = sPrDocumentNumber
                Case Else
                GoTo a3
                End Select


Может всетаки поделитесь своим решением, чтобы лишние узлы не обрабатывать?
« Последнее редактирование: 05.10.2021, 03:56:55 от dr_peper » Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #38 : 05.10.2021, 05:43:51 »

C case вышел самообман Смеющийся
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #39 : 05.10.2021, 10:03:28 »

Код: (vb)
 Set nESADout_CUPresentedDocument = xdoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/*[catESAD_cu:PresentedDocumentModeCode=04022]")
                For Each nPresentedDocument In nESADout_CUPresentedDocument
                sGoodsPresentedDocumentModeCode = nPresentedDocument.SelectSingleNode("catESAD_cu:PresentedDocumentModeCode").Text
                sPrDocumentNumber = nPresentedDocument.SelectSingleNode("cat_ru:PrDocumentNumber").Text
                Next

Так или нет?
Прокомментируйте пожалуйста.
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #40 : 06.10.2021, 09:53:37 »

Так или нет?
Вот без обид, но. Вы предлагаете мне скачать файл XML из начала темы, убедиться, что там есть все эти узлы, затем написать с нуля код, в который где-то поместить приведенный Вами кусок кода выше и проверить - оно работает или нет? В то время как Вы можете просто запустить свой готовый код у себя на корректных данных и посмотреть даже в пошаговом режиме что отбирается и что получается. Очень странный вопрос ко мне, на мой взгляд...
Могу сказать только это: виду обращение к узлам выглядит верно(в общем-то, я это и предлагал, ну да ладно). Но Вы почему-то так и не ознакомились с азами работы в циклах. У Вас опять будет в переменных значение последнего отобранного узла. Мы это уже обсуждали выше.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #41 : 07.10.2021, 02:25:05 »

Вы предлагаете мне скачать файл XML из начала темы, убедиться, что там есть все эти узлы, затем написать с нуля код, в который где-то поместить приведенный Вами кусок кода выше и проверить - оно работает или нет? У Вас опять будет в переменных значение последнего отобранного узла. Мы это уже обсуждали выше.

Да я просто хотел чтобы Вы посмотрели на правильность написания кода, без проверки .
Я в пошаговом цикле прогнал, заметил что сохраняется последнее значение и добавил строки для обнуления значений.

Код: (vb)
Set nESADout_CUPresentedDocument = xdoc.DocumentElement.SelectNodes("//ESADout_CU/ESADout_CUGoodsShipment/ESADout_CUGoods/ESADout_CUPresentedDocument[catESAD_cu:PresentedDocumentModeCode=04022]")
                sGoodsPresentedDocumentModeCode = ""
                sPrDocumentNumber = ""
                For Each nPresentedDocument In nESADout_CUPresentedDocument
                sGoodsPresentedDocumentModeCode = nPresentedDocument.SelectSingleNode("catESAD_cu:PresentedDocumentModeCode").Text
                sPrDocumentNumber = nPresentedDocument.SelectSingleNode("cat_ru:PrDocumentNumber").Text
                Next
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #42 : 07.10.2021, 11:00:36 »

Вот скажите, для чего Вам цикл? Зачем обнулять? Вам же надо эти значения куда-то записывать? Так и записывайте внутри цикла в ячейки, изменяя счетчик по ходу цикла. Или я вообще не понимаю, что Вы хотите и что я должен проверить на правильность...
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #43 : 07.10.2021, 13:01:48 »

Вот скажите, для чего Вам цикл? Зачем обнулять? Вам же надо эти значения куда-то записывать?
Я их записываю только это ниже в моем коде. Цикл нужен т. К. Эти значения идут потоварно  в дт, по каким то товарам есть, а по каким то нет.
Записан
Дмитрий Щербаков(The_Prist)
Администратор
Ветеран
*****

Репутация: +485/-0
Офлайн Офлайн

Сообщений: 5 828



Просмотр профиля WWW
« Ответ #44 : 07.10.2021, 13:28:45 »

Вы, видимо, до сих пор не понимаете назначение цикла и принцип работы.
Осваивайте пошаговую отладку - я в теме уже давал ссылку.
Вот найдет код у Вас 10 значений для PresentedDocumentModeCode=04022. И что попадет у Вас при записи
только это ниже в моем коде
?
Очевидно, что только последнее значение, а не все 10. Все же настоятельно рекомендую хотя бы книжку какую-то начать по VBA читать и постигать азы от простого к сложному. Или я до сих пор не понимаю, что Вы там ниже записываете и зачем цикл.
Записан

Даже самый простой вопрос можно превратить в огромную проблему. Достаточно не уметь формулировать вопросы...
Пункты приёма Спасибов:    -41001332272872  -R298726502453
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #45 : 23.11.2022, 07:09:48 »

Всем привет.
Столкнулся с проблемой обработки полей с описанием товаров. Видимо есть ограничение на 250 символов поэтому описание бьется на 2 тега

<catESAD_cu:GoodsDescription>ЭЛЕКТРИЧЕСКАЯ НАГРЕВАТЕЛЬНАЯ СИСТЕМА (ЖАКЕТЫ) ДЛЯ ОБОГРЕВА СИСТЕМ УПРАВЛЕНИЯ КЛАПАНОВ, НА НАПРЯЖЕНИЕ 120 В, В РАЗАБРАННОМ ВИДЕ, СОСТОИТ ИЗ НЕСКОЛЬКИ ЧАСТЕЙ, С СОЕДИНИТЕЛНЫМИ ФИТИНГАМИ, ПЕРЕХОДНИКАМИ, ПРЕДНАЗНАЧЕНА ДЛЯ ПРИМЕНЕНИЯ НА ОБЪЕКТАХ</catESAD_cu:GoodsDescription>
<catESAD_cu:GoodsDescription>НЕФТЕГАЗОВОЙ ОТРАСЛИ, ВСЕГО 2 КОМПЛЕКТА</catESAD_cu:GoodsDescription>

пробовал и selectnodes и selectchildnodes берет только значение первого тега.
Подскажите, плиз как выбрать оба тега можно в разные столбцы
 
Записан
dr_peper
Новичок
*

Репутация: +0/-0
Офлайн Офлайн

Сообщений: 43


Просмотр профиля
« Ответ #46 : 24.11.2022, 03:22:37 »

нашел такое решение, может кому пригодиться

Код: (vb)
Set nodeXML = nCUGoods.getElementsByTagName("catESAD_cu:GoodsDescription")
                For k = 0 To nodeXML.Length - 1
                If k = 0 Then sGoodsDescription1 = nodeXML(k).Text
                If k = 1 Then sGoodsDescription2 = nodeXML(k).Text
                Next
Записан
Страниц: 1 2 3 4 [Все]   Вверх
Печать
Перейти в:  

Powered by MySQL Powered by PHP Powered by SMF 1.1.21 | SMF © 2006-2011, Simple Machines Valid XHTML 1.0! Valid CSS!
Яндекс.Метрика Рейтинг@Mail.ru