WiXインストーラー内のXMLを解析しようとしています。 XMLは、Webサーバーから返されるすべてのエラーのオブジェクトになります。私はこのコードで質問のタイトルにエラーが出ています:
XmlDocument xml = new XmlDocument();
try
{
xml.LoadXml(myString);
}
catch (Exception ex)
{
System.IO.File.WriteAllText(@"C:\text.txt", myString + "\r\n\r\n" + ex.Message);
throw ex;
}
myString
はこれです(text.txt
の出力に見られるように)
<?xml version="1.0" encoding="utf-8"?>
<Errors></Errors>
text.txt
は次のようになります。
<?xml version="1.0" encoding="utf-8"?>
<Errors></Errors>
Data at the root level is invalid. Line 1, position 1.
このXMLを解析する必要があるので、エラーがあるかどうかを確認できます。
編集
この質問は、マークされたとおりの重複ではありません。その質問では、質問をしている人はLoadXml
を使用してXMLファイルを解析していました。 LoadXml
の正しい使用法である文字列を解析しています
隠されたキャラクターはおそらくBOMです。問題と解決策の説明は here にあります。JamesBrankinの回答に基づくJames Schubertの功績です here 。
前の答えは隠し文字を削除しますが、最初の行全体も削除します。より正確なバージョンは次のとおりです。
string _byteOrderMarkUtf8 = Encoding.UTF8.GetString(Encoding.UTF8.GetPreamble());
if (xml.StartsWith(_byteOrderMarkUtf8))
{
xml = xml.Remove(0, _byteOrderMarkUtf8.Length);
}
Azure BLOBからXSLTファイルを取得し、それをXslCompiledTransformオブジェクトに読み込むときに、この問題が発生しました。私のマシンでは、ファイルは問題なく見えましたが、BLOBとしてアップロードして取得した後、BOM文字が追加されました。
代わりにLoad()
メソッドを使用すると、問題が解決します。 もっと見る
ここでの問題は、myString
にそのヘッダー行があることでした。最初の行の先頭に隠し文字があったか、行自体がエラーの原因でした。最初の行を次のように切り取りました。
xml.LoadXml(myString.Substring(myString.IndexOf(Environment.NewLine)));
これで問題が解決しました。
問題はエンコードに関するものだと思います。そのため、最初の行(エンコードバイト付き)を削除すると問題が解決する場合があります。
ルートレベルのDataのソリューションは無効です。 1行目、XDocument.Parse(xmlString)
の1.はXDocument.Load( new MemoryStream( xmlContentInBytes ) );
に置き換えられました
私のxml文字列が問題なく見えることに気づきました:
<?xml version="1.0" encoding="utf-8"?>
しかし、別のテキストエディタエンコーディングでは、次のようになりました。
?<?xml version="1.0" encoding="utf-8"?>
最後に、xml文字列ではなく、xml byte []が必要でした。文字列を使用する必要がある場合は、文字列内の「見えない」バイトを探し、エンコーディングを操作して、解析または読み込みのためにxmlコンテンツを調整する必要があります。
それが役立つことを願っています
バイト配列を直接編集することでこの問題を解決しました。 UTF8プリアンブルを収集し、ヘッダーを直接削除します。その後、GetStringメソッドを使用してbyte []を文字列に変換できます。以下を参照してください。念のため、\ rと\ tも削除しました。
XmlDocument configurationXML = new XmlDocument();
List<byte> byteArray = new List<byte>(webRequest.downloadHandler.data);
foreach(byte singleByte in Encoding.UTF8.GetPreamble())
{
byteArray.RemoveAt(byteArray.IndexOf(singleByte));
}
string xml = System.Text.Encoding.UTF8.GetString(byteArray.ToArray());
xml = xml.Replace("\\r", "");
xml = xml.Replace("\\t", "");
Xmlが文字列にある場合、次を使用してバイトオーダーマークを削除します。
xml = new Regex("\\<\\?xml.*\\?>").Replace(xml, "");
異なるエンコーディングでファイルを保存します:
[ファイル]> [名前を付けてファイルを保存...]> [署名なしでUTF-8として保存]。
VS 2017では、[保存]ボタンの横にドロップダウンとしてエンコードがあります。
私は解決策の1つを見つけました。コードの場合、次のようになります-
XmlDocument xml = new XmlDocument();
try
{
// assuming the location of the file is in the current directory
// assuming the file name be loadData.xml
string myString = "./loadData.xml";
xml.Load(myString);
}
catch (Exception ex)
{
System.IO.File.WriteAllText(@"C:\text.txt", myString + "\r\n\r\n" + ex.Message);
throw ex;
}