Что не так с этим файлом или кодом?

Что происходит \ в чем разница? Я пытаюсь вернуть определенный узел из файла XML.

XML-файл:

  <?xml version="1.0" encoding="utf-8"?>
    <JMF SenderID="InkZone-Controller" Version="1.2">
      <Command ID="cmd.00695" Type="Resource">
        <ResourceCMDParams ResourceName="InkZoneProfile" JobID="K_41">
          <InkZoneProfile ID="r0013" Class="Parameter" Locked="false" Status="Available" PartIDKeys="SignatureName SheetName Side Separation" DescriptiveName="Schieberwerte von DI" ZoneWidth="32">
            <InkZoneProfile SignatureName="SIG1">
              <InkZoneProfile Locked="False" SheetName="S1">
                <InkZoneProfile Side="Front" />
              </InkZoneProfile>
            </InkZoneProfile>
          </InkZoneProfile>
        </ResourceCMDParams>
      </Command>
<InkZoneProfile Separation="Cyan" ZoneSettingsX="0 0,005 " />
    </JMF>

Код:

           XmlDocument xmlDoc = new XmlDocument();
            xmlDoc.Load("C:\\test\\test.xml");
            XmlNode root = xmlDoc.DocumentElement;
            var parent = root.SelectSingleNode("/JMF/Command/ResourceCmdParams/InkZoneProfile/InkZoneProfile/InkZoneProfile/InkZoneProfile");

            XmlElement IZP = xmlDoc.CreateElement("InkZoneProfile");
            IZP.SetAttribute("Separation", x.colorname);
            IZP.SetAttribute("ZoneSettingsX", x.colorvalues);
            xmlDoc.DocumentElement.AppendChild(IZP);
            xmlDoc.Save("C:\\test\\test.xml");

Var parent возвращает мне значение NULL. Я отладил, и root и xmlDoc имеют на своем внутреннем тексте XML Content. Но тест, выполненный здесь (выполненный пользователем @har07 по предыдущему вопросу: SelectSingleNode возвращает ноль, даже если управление пространством имен работает без проблем. https://dotnetfiddle.net/vJ8h9S

В чем разница между этими двумя? Они в основном следуют одному и тому же коду, но один работает, а другой нет.
При отладке я обнаружил, что root.InnerXml имеет загруженное содержимое само по себе (так же, как XmlDoc.InnerXml). Но InnerXml не реализует метод для SelectSingleNode. Я считаю, что если я сохраню это в строку, я, вероятно, потеряю отступ и т. Д.

Может кто-нибудь сказать мне, в чем разница или что не так? Спасибо! Пример XML: https://drive.google.com/file/d/0BwU9_GrFRYrTUFhMYWk5blhhZWM/view?usp=sharing

1 ответ

Решение

SetAttribute не автоматически экранировать строку для вас. Поэтому он делает ваш XML-файл недействительным.

Из MSDN о XmlElement.SetAttribute

Любая разметка, такая как синтаксис, который должен быть распознан как ссылка на сущность, обрабатывается как буквальный текст и должна быть надлежащим образом экранирована реализацией, когда она записана.

Найдите в своем коде всю строку, содержащую SetAttribute и использовать SecurityElement.Escape чтобы избежать значения.

Например: измените эти строки:

IZP.SetAttribute("Separation", x.colorname);
IZP.SetAttribute("ZoneSettingsX", x.colorvalues);

Для того, чтобы:

using System.Security;

IZP.SetAttribute("Separation", SecurityElement.Escape(x.colorname));
IZP.SetAttribute("ZoneSettingsX", SecurityElement.Escape(x.colorvalues));

Если имя атрибута содержит какой-либо из <>"'& Вы также должны избежать этого, как значение.

Замечания:

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

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