2015-04-20 21 views
5

Utknąłem przy usuwaniu nieprawidłowych znaków z pliku XML. Znalazłem REGEX wzór, który należy odizolować wszystko, co znajduje się niedostępny:Usuwanie niedozwolonych znaków z ciągu XML C#

public static string CleanInvalidXmlChars(string text) 
{ 
    // From xml spec valid chars: 
    // #x9 | #xA | #xD | [#x20-#xD7FF] | [#xE000-#xFFFD] | [#x10000-#x10FFFF]  
    // any Unicode character, excluding the surrogate blocks, FFFE, and FFFF. 
    string re = @"[^\x09\x0A\x0D\x20-\xD7FF\xE000-\xFFFD\x10000-x10FFFF]"; 
    return Regex.Replace(text, re, ""); 
} 

i tu jest mój kod, który odczytuje dane z SQL Server (dobrze, to fragment)

using (var cmd = new SqlCommand(Context.Command, connection)) 
{ 
    cmd.CommandTimeout = Context.CommandTimeout; 

    using (var reader = cmd.ExecuteReader()) 
    { 

     StringBuilder xmlResults = new StringBuilder(string.Empty); 

     while (reader.Read()) 
     { 
      xmlResults.Append(reader.GetString(0)); 
     } 

     if (!string.IsNullOrWhiteSpace(xmlResults.ToString())) 
     { 
      var doc = new XmlDocument(); 
      XmlReader xmlReader = XmlReader.Create(new StringReader(xmlResults.ToString())); 

      doc.Load(xmlReader); 

      var nav = doc.CreateNavigator(); 
      var objs = nav.Select("/index/type"); 

      foreach (XPathNavigator obj in objs) 
      { 
       o.OnNext(obj); 
      } 
     } 

    } 
} 

Próbowałem owijania CleanInvalindXmlChars w różnych miejscach:

while (reader.Read()) 
{ 
    xmlResults.Append(CleanInvalindXmlChars(reader.GetString(0))); 
} 

albo w

XmlReader xmlReader = XmlReader.Create(new StringReader(CleanInvalindXmlChars(xmlResults.ToString()))); 

W jednej komórce czytam symbol X0B (mogę to zastąpić w SQL Serverze, ale chcę być na to bezpieczny).

Jednak ja zawsze kończy się błędem

System.Xml.XmlException: '', wartość szesnastkowa 0x0B, jest nieważny charakter. Linia 115, pozycja 33407.

Czy ktoś mógłby mi pomóc rozwiązać ten problem?

+1

Brakuje lewego ukośnika przed 'x10FFFF'. Wątpię jednak, że rozwiąże to problem. –

+0

Czy próbowałeś usunąć ten symbol 'VT' z' input = Regex.Replace (input, @ "[\ x0B]", string.Empty); '? Sądzę, że potrzebujesz tego nieprawidłowego wyrażenia XML charge - '[\ u0000- \ u000C \ u000C \ u000E- \ u0019] +' - aby dopasować i usunąć wszystkie niepoprawne znaki XML z ciągu. –

Odpowiedz

1

Jest to metoda oparta na innych niż Regex czyszczeniu danych ciągów. Dodałem 0x0B który nie jest usuwany przez regex masz Wysłany:

public static string stripNonValidXMLCharacters(string textIn) 
{ 
    if (String.IsNullOrEmpty(textIn)) 
     return textIn; 

    StringBuilder textOut = new StringBuilder(textIn.Length); 

    foreach (Char current in textIn) 
     if ((current == 0x9 || current == 0xA || current == 0xB || current == 0xD) || 
      ((current >= 0x20) && (current <= 0xD7FF)) || 
      ((current >= 0xE000) && (current <= 0xFFFD)) || 
      ((current >= 0x10000) && (current <= 0x10FFFF))) 
      textOut.Append(current); 

    return textOut.ToString(); 
} 
+0

Próbowałem twojej metody, ale wciąż mam problem. Może umieszczam 'stripNonValidXMLCharacters' w niewłaściwym miejscu? robię to na 'XmlReader XmlReader = XmlReader.Create (nowy StringReader (stripNonValidXMLCharacters (xmlResults.ToString())));' Niestety niepokoić o to, ale jestem zupełnie nowy na C# –

+0

Zmieniłem go do statycznej metody, która prawdopodobnie powinna rozwiązać twój problem – Jaco

+0

Dzięki, To rozwiązało to. –

2

Here to samo pytanie z przyjętym answer i alternatywnej answer że wolę (kod skopiowane poniżej).

public static string XmlCharacterWhitelist(string in_string) { 
    if(in_string == null) return null; 

    StringBuilder sbOutput = new StringBuilder(); 
    char ch; 

    for(int i = 0; i < in_string.Length; i++) { 
     ch = in_string[i]; 
     if((ch >= 0x0020 && ch <= 0xD7FF) || 
      (ch >= 0xE000 && ch <= 0xFFFD) || 
      ch == 0x0009 || 
      ch == 0x000A || 
      ch == 0x000D) { 
      sbOutput.Append(ch); 
     } 
    } 
    return sbOutput.ToString(); 
}