我正在使用XDocument
生成 utf-8 XML 文件。
XDocument xml_document = new XDocument(
new XDeclaration("1.0", "utf-8", null),
new XElement(ROOT_NAME,
new XAttribute("note", note)
)
);
...
xml_document.Save(@file_path);
正确生成文件并使用xsd文件验证并成功。
当我尝试将XML文件上传到在线服务时,该服务说我的文件是wrong at line 1
;我发现问题是由文件的第一个字节上的BOM引起的。
您知道为什么将BOM附加到文件中,如何在没有文件的情况下保存文件?
如Byte order mark维基百科文章中所述:
虽然Unicode标准允许使用BOM UTF-8 它不需要或 推荐它。字节顺序没有 意思是UTF-8所以只有BOM 用于识别文本流或 文件为UTF-8或已转换 来自另一种具有BOM
的格式
是XDocument
问题还是我应该联系在线服务提供商的人员要求解析器升级?
答案 0 :(得分:58)
使用XmlTextWriter
并将其传递给XDocument的Save()方法,这样您就可以更好地控制所使用的编码类型:
var doc = new XDocument(
new XDeclaration("1.0", "utf-8", null),
new XElement("root", new XAttribute("note", "boogers"))
);
using (var writer = new XmlTextWriter(".\\boogers.xml", new UTF8Encoding(false)))
{
doc.Save(writer);
}
UTF8Encoding
类构造函数有一个重载,指定是否使用带有布尔值的BOM(字节顺序标记),在您的情况false
中。
使用Notepad ++验证了此代码的结果,以检查文件的编码。
答案 1 :(得分:26)
首先:服务提供商必须根据XML规范处理它,该规范声明在UTF-8表示的情况下可能存在BOM。
您可以强制保存XML而不使用BOM:
XmlWriterSettings settings = new XmlWriterSettings();
settings.Encoding = new UTF8Encoding(false); // The false means, do not emit the BOM.
using (XmlWriter w = XmlWriter.Create("my.xml", settings))
{
doc.Save(w);
}
(从这里用Google搜索:http://social.msdn.microsoft.com/Forums/en/xmlandnetfx/thread/ccc08c65-01d7-43c6-adf3-1fc70fdb026a)
答案 2 :(得分:1)
使用 XDocument 时摆脱BOM字符的最便捷方法是保存文档,然后直接将文件读取为文件,然后将其写回。 File例程将为您删除字符:
XDocument xTasks = new XDocument();
XElement xRoot = new XElement("tasklist",
new XAttribute("timestamp",lastUpdated),
new XElement("lasttask",lastTask)
);
...
xTasks.Add(xRoot);
xTasks.Save("tasks.xml");
// read it straight in, write it straight back out. Done.
string[] lines = File.ReadAllLines("tasks.xml");
File.WriteAllLines("tasks.xml",lines);
(这很好,但是为了方便起见 - 至少你会有一个格式良好的文件上传到你的在线提供商);)
答案 3 :(得分:0)
通过UTF-8文档
String XMLDec = xDoc.Declaration.ToString();
StringBuilder sb = new StringBuilder(XMLDec);
sb.Append(xDoc.ToString());
Encoding encoding = new UTF8Encoding(false); // false = without BOM
File.WriteAllText(outPath, sb.ToString(), encoding);