2010-11-01 2 views
0

Я хочу разобрать следующий XMLспециальные символы в XML

XmlElement costCenterElement2 = doc.CreateElement("CostCenter"); 
costCenterElement2.InnerXml = 
    "<CostCenterNumber>2</CostCenterNumber> <CostCenter>" + 
    "G&A: Fin & Acctng" + 
    "</CostCenter>"; 

, но я нашел XML Exception

Произошла ошибка при разборе EntityName.

+0

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

ответ

2
 private string SanitizeXml(string source) 
     { 
      if (string.IsNullOrEmpty(source)) 
      { 
       return source; 
      } 
      if (source.IndexOf('&') < 0) 
      { 
       return source; 
      } 
      StringBuilder result = new StringBuilder(source); 
      result = result.Replace("&lt;", "<>lt;") 
          .Replace("&gt;", "<>gt;") 
          .Replace("&amp;", "<>amp;") 
          .Replace("&apos;", "<>apos;") 
          .Replace("&quot;", "<>quot;"); 
      result = result.Replace("&", "&amp;"); 
      result = result.Replace("<>lt;", "&lt;") 
          .Replace("<>gt;", "&gt;") 
          .Replace("<>amp;", "&amp;") 
          .Replace("<>apos;", "&apos;") 
          .Replace("<>quot;", "&quot;"); 

      return result.ToString(); 
     } 
+0

@AZ хорошая идея, хотя это не обрабатывает такие случаи, как'   'или несимвольные объекты, которые были определены в документе. – LarsH

+0

true. Это просто ха ск. но я не думаю, что есть правильное решение этого. однако он может решить конкретную проблему OP. –

+0

спасибо AZ: ваш метод решает большинство специальных символов –

7

Да уж - & не действует в XML и нужно экранировать в &amp;.

другие персонажи недопустимые символы и их ускользает:

  • < - &lt;
  • > - &gt;
  • "- &quote;
  • '- &apos;

Следующая должно работать :

XmlElement costCenterElement2 = doc.CreateElement("CostCenter"); 
costCenterElement2.InnerXml = 
    "<CostCenterNumber>2</CostCenterNumber> <CostCenter>" + 
    "G&amp;A: Fin &amp; Acctng" + 
    "</CostCenter>"; 

Однако, вы действительно должны создавать CostCenterNumber и CostCenter в качестве элементов, а не как InnerXml.

+0

Вы также можете посмотреть здесь: http://msdn.microsoft.com/en-us/library/aa468560.aspx для получения дополнительной информации. –

+0

спасибо за ваш ответ, но на самом деле эта строка анализируется в параметрах метода, и я не знаю, что строка содержит & или любые специальные символы, которые мне нужны, чтобы избежать всех специальных символов. –

+1

фактически '>' (больше, чем) * is * разрешено в XML и не должно быть экранировано. Но многие люди избегают этого, для симметрии. Кроме того, '' '(' " 'не' "e; ') и' '' прекрасно в текстовых данных, как в заданном вопросе. Они просто не разрешены в значениях атрибутов. – LarsH

1

Обновлено:

@thabet, если строка "<CostCenterNumber>...G&A: Fin & Acctng</CostCenter>" приходит в качестве параметра, и он должен представлять XML, который будет обработан, то он должен быть хорошо сформированный XML, чтобы начать с. В примере, который вы дали, это не так. & сигнализирует начало ссылки на сущность, за ней следует имя объекта и заканчивается ;, который никогда не появляется в строке выше.

Если вам дана целая строка в качестве параметра, некоторые из которых являются разметкой, которая должна быть проанализирована (т. Е. Теги начала и конца), а некоторые из них могут содержать разметку, которая не должна анализироваться (то есть &) , нет чистого и надежного способа «избежать» последнего, а не избежать первого. Вы можете заменить все & персонажами &amp;, но при этом вы можете случайно повернуть &#160; в &amp;#160;, и ваш результат будет неправильным. Если это ваша ситуация, вы получаете входной «XML», где разметка смешана с непассивным текстом, наилучшим обращением является , расскажите человеку, у которого вы получаете XML, что он не является корректным, и им необходимо исправить свои вывод. Есть способы сделать это, что не сложно с помощью стандартных инструментов XML.

Если с другой стороны, у вас есть

<CostCenterNumber>2</CostCenterNumber> 
<CostCenter>...</CostCenter> 

отдельно от переданной строки, и вам нужно подключить в переданной строке в качестве текстового содержания ребенка <CostCenter>, и вы знаете, что это не будет разобран (не содержит элементов), то вы можете сделать это:

  • создать <CostCenterNumber> и <CostCenter> как элементы
  • делают их дети родителя <CostCenter>
  • набор текст содержание CostCenterNumber, используя InnerXml при условии, что нет никакого риска разметки там: eltCCN.InnerXml = "2";
  • создать для элемента ребенка CostCenter текстового узла ребенок, значение которого передается строка: textCC = doc.CreateText(argStr);
  • назначить этот текстовый узел в качестве дочернего элемента ребенка CostCenter: eltCC.AppendChild(textCC);