Что не так с использованием XPath в C#?

Я пытаюсь немного очистить приложение C#.

Я пытаюсь получить доступ к 4 частям информации на следующей странице: https://smstestbed.nist.gov/vds/current

  • CreationTime
  • Доступность
  • Линейные координаты X и Y

В следующей функции я запрашиваю поток данных в реальном времени с удаленного обрабатывающего инструмента. Моя проблема заключается в том, что, хотя я смог напечатать CreationTime на терминале, мое использование XPath ужасно неуклюже, и, поскольку Эта ссылка, кажется, предполагает, что я должен иметь возможность делать то, что я делаю, в двух строках после моего комментарий

«// Это должен быть гораздо лучший способ доступа к данным, но по какой-то причине вторая строка не работает»

К сожалению, я получаю Доступность Узел was Null.

public static void PollNIST()
    {
        string NISTSourceURL = "https://smstestbed.nist.gov/vds/current";  // Gives us a human friendly reference to the HTM
        //-------------------------------- Current (mostly) Working Version---------------------------------------------------------------------------------
        // Retrieve raw HTML
        var NISTTargetURL = NISTSourceURL;
        var NISTHttpClient = new HttpClient();
        var NISTXMLRaw = NISTHttpClient.GetStringAsync(NISTTargetURL);  // We now have all of the HTML / XML Data as a raw string
                                                                        //Console.WriteLine(MazXMLRaw.Result);                   // Prints the resulting HTML to a terminal as a debug tool    (Works)   
        XmlDocument CurNISTXML = new XmlDocument();               // Generate Blank XML Doc
        CurNISTXML.LoadXml(NISTXMLRaw.Result);                     // This (".result") passes the actual string?, should then be loaded into new XML file

        var elementHeader = CurNISTXML.GetElementsByTagName("Header");
        var curNISTHeader = elementHeader.Item(0);
        var creationTime = curNISTHeader.Attributes[0];  // We actually have the creationTime            
        string CurNISTTime = creationTime.InnerText; ; //      //*[@id = "mtconnect content"]/ul/li[1]

        //This should be a far better way of accessing the data but for some reason the second line fails
        XmlNode AvailabilityNode = CurNISTXML.SelectSingleNode("/table[1]/tbody/tr[1]");  //*[@id = "mtconnect content"]/table[1]/tbody/tr[1]/td[7] // Xpath Availability
        var CurNISTStatus = AvailabilityNode.InnerText; //      //*[@id = "mtconnect content"]/ul/li[1]


        string CurNistX = ""; //      //*[@id = "mtconnect content"]/table[5]/tbody/tr/td[7]
        string CurNistY = ""; //      //*[@id = "mtconnect content"]/table[6]/tbody/tr/td[7]

        Console.WriteLine("-------BEGIN NIST DATA PACKET-------");
        Console.WriteLine("NIST Time  : " + creationTime.InnerText);
        Console.WriteLine("NIST Status: " + CurNISTStatus);    
        Console.WriteLine("NIST X Pos.: " + CurNistX);
        Console.WriteLine("NIST Y Pos.: " + CurNistY);
        Console.WriteLine("--------END NIST DATA PACKET--------");

        //var currentNIST = new NISTDataSet()// Create new instance ofNISTdata object
    }

Любые идеи?

Вы пытаетесь разобрать html-страницу с помощью xml. Вы используете неправильный URL. Данные доступны в формате XML, но вам нужно использовать другой URL. См .: nist.gov/programs-projects/materials-data-curation-system

jdweng 06.11.2018 11:51

Вы уверены? Если я распечатаю XML-документ для консоли, все будет готово, и время создания будет работать нормально.

GigaJoules 06.11.2018 11:56

Я впервые пишу на C#, поэтому я зацикливаюсь на вещах, которые, вероятно, довольно просты.

GigaJoules 06.11.2018 12:07

Какую xml-ссылку вы используете? То, что вы разместили, - это только html.

jdweng 06.11.2018 12:25

Метка времени получается только при использовании ссылки, указанной в первой строке метода.

GigaJoules 06.11.2018 12:27

Когда я просматриваю исходный код, кажется, что ссылка, заканчивающаяся «/ vds / current», - это путь к XML?

GigaJoules 06.11.2018 12:31

У smstestbed есть расположение схемы в верхней части файла xml. Получите схему из местоположения. Затем используйте инструмент msdn xsd.exe для преобразования XML в классы (параметр / cl / l: cs). Затем используйте сериализацию xml для анализа данных.

jdweng 06.11.2018 12:31

Перейдите по URL-адресу в браузере. XML-файл начинается с: <? Xml version = "1.0" encoding = "UTF-8"?>

jdweng 06.11.2018 13:34

Есть идеи, как я могу напрямую обращаться к XML?

GigaJoules 13.11.2018 11:40

Думаю, я перепутал «источник просмотра» и «проверить». Когда я нажимаю "Просмотр источника", я вижу только XML.

GigaJoules 13.11.2018 11:44

Когда я делаю Console.WriteLine (CurNistXML.InnerXML); я получаю то, что начинается с <? XML version = 1.0 .... "

GigaJoules 13.11.2018 11:48

Содержит ли xml тег «Заголовок» [CurNISTXML.GetElementsByTagName («Заголовок»);]. Я думаю, что xml встроен в Html. Тег заголовка является частью HTML и не существует в Xml.

jdweng 13.11.2018 12:53
Стоит ли изучать PHP в 2026-2027 годах?
Стоит ли изучать PHP в 2026-2027 годах?
Привет всем, сегодня я хочу высказать свои соображения по поводу вопроса, который я уже много раз получал в своем сообществе: "Стоит ли изучать PHP в...
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
Поведение ключевого слова "this" в стрелочной функции в сравнении с нормальной функцией
В JavaScript одним из самых запутанных понятий является поведение ключевого слова "this" в стрелочной и обычной функциях.
Приемы CSS-макетирования - floats и Flexbox
Приемы CSS-макетирования - floats и Flexbox
Здравствуйте, друзья-студенты! Готовы совершенствовать свои навыки веб-дизайна? Сегодня в нашем путешествии мы рассмотрим приемы CSS-верстки - в...
Тестирование функциональных ngrx-эффектов в Angular 16 с помощью Jest
В системе управления состояниями ngrx, совместимой с Angular 16, появились функциональные эффекты. Это здорово и делает код определенно легче для...
Концепция локализации и ее применение в приложениях React ⚡️
Концепция локализации и ее применение в приложениях React ⚡️
Локализация - это процесс адаптации приложения к различным языкам и культурным требованиям. Это позволяет пользователям получить опыт, соответствующий...
Пользовательский скаляр GraphQL
Пользовательский скаляр GraphQL
Листовые узлы системы типов GraphQL называются скалярами. Достигнув скалярного типа, невозможно спуститься дальше по иерархии типов. Скалярный тип...
1
12
141
2
Перейти к ответу Данный вопрос помечен как решенный

Ответы 2

Выражение XPath

/table[1]/tbody/tr[1]

будет успешным только в том случае, если самый внешний элемент документа - это элемент table, что кажется маловероятным. Я не пытался понять логику страницы или вашего кода, но это определенно выглядит неправильно. «/» в начале выражения пути выбирает из корня дерева.

Да, я так и думал, я пробовал несколько разных вещей, поэтому думаю, что там есть одна косая черта.

GigaJoules 06.11.2018 13:39

@GigaJoules Выбирает ли '// table [1] / tbody / tr [1]' то, что вы хотели? Мне непонятно, какой элемент вы пытаетесь выбрать.

Mate Mrše 06.11.2018 15:11

@GigaJoules Мы видим много вопросов, в которых люди разбросали случайные знаки препинания вокруг своих выражений XPath в надежде, что они будут действовать как волшебная волшебная пыль. Это редко бывает эффективной стратегией. Сэкономьте время, прочтите инструкцию.

Michael Kay 06.11.2018 16:57

Я хочу вытащить слово «доступный» из верхней правой ячейки первой таблицы и «значение» количества таблиц «линейный x» и «линейный y»

GigaJoules 07.11.2018 12:33

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

GigaJoules 14.02.2019 11:20
Ответ принят как подходящий

Итак, оказалось, что нет ничего плохого в том, как я извлекал XML, только с моими путями.

public static void PollNIST()
        {
            string NISTSourceURL = "https://smstestbed.nist.gov/vds/current";  // Gives us a human friendly reference to the HTMl
            // string NistXmlUrl = // Someone on stackexchange is claiming that there is another url for the XML but viewsource says otherwise 
            //-------------------------------- Current (mostly) Working Version---------------------------------------------------------------------------------
            var NISTHttpClient = new HttpClient();
            var NISTXMLRaw = NISTHttpClient.GetStringAsync(NISTSourceURL);  // We now have all of the HTML / XML Data as a raw string
                                                                            //Console.WriteLine(MazXMLRaw.Result);                   // Prints the resulting HTML to a terminal as a debug tool    (Works)   
            XmlDocument CurNISTXML = new XmlDocument();               // Generate Blank XML Doc
            CurNISTXML.LoadXml(NISTXMLRaw.Result);                     // This (".result") passes the actual string?, should then be loaded into new XML file

            // Get CreationTime (WORKING!)
            XmlNodeList elementHeader = CurNISTXML.GetElementsByTagName("Header");
            XmlNode curNISTHeader = elementHeader.Item(0);
            XmlAttribute creationTime = curNISTHeader.Attributes[0];  // We now have the creationTime element          
            string CurNISTTime = creationTime.InnerText;  //      //*[@id = "mtconnect content"]/ul/li[1]

            // Get availability (WORKING!)
            XmlNodeList nodeAvailability = CurNISTXML.GetElementsByTagName("Availability");
            XmlNode availability = nodeAvailability.Item(0); // I think this is maybe a bit of a hackish / improper way to do this?
            string curNISTStatus = availability.InnerText;

            //Get linear tool X Coord.
            XmlNodeList deviceStream = CurNISTXML.GetElementsByTagName("ComponentStream");
            XmlNode linearCompXStream = deviceStream.Item(4);
            string curNISTX = linearCompXStream.InnerText; //  We do not need to break down the nodes any further as the value is the only text within

            //Get Linear tool y Coord.            
            XmlNode linearCompYStream = deviceStream.Item(5);
            string curNISTY = linearCompYStream.InnerText; //  We do not need to break down the nodes any further as the value is the only text within


            Console.WriteLine("-------BEGIN NIST DATA PACKET-------");
            Console.WriteLine("NIST Time  : " + creationTime.InnerText);
            Console.WriteLine("NIST Status: " + curNISTStatus);    
            Console.WriteLine("NIST X Pos.: " + curNISTX);
            Console.WriteLine("NIST Y Pos.: " + curNISTY);
            Console.WriteLine("--------END NIST DATA PACKET--------");

            //var currentNIST = new NISTDataSet()// Create new instance ofNISTdata object
        }

работает хорошо.

Другие вопросы по теме