PageRenderTime 77ms CodeModel.GetById 31ms RepoModel.GetById 1ms app.codeStats 1ms

/desktop_clients/Visual Studio/Crear beneficiarios/Json100r3/Source/Src/Newtonsoft.Json.Tests/Converters/XmlNodeConverterTest.cs

https://bitbucket.org/wfpcoslv/maps-examples
C# | 3123 lines | 2643 code | 422 blank | 58 comment | 27 complexity | 94c7e6c587552f6fc1bac475d5194f38 MD5 | raw file
Possible License(s): GPL-2.0

Large files files are truncated, but you can click here to view the full file

  1. #region License
  2. // Copyright (c) 2007 James Newton-King
  3. //
  4. // Permission is hereby granted, free of charge, to any person
  5. // obtaining a copy of this software and associated documentation
  6. // files (the "Software"), to deal in the Software without
  7. // restriction, including without limitation the rights to use,
  8. // copy, modify, merge, publish, distribute, sublicense, and/or sell
  9. // copies of the Software, and to permit persons to whom the
  10. // Software is furnished to do so, subject to the following
  11. // conditions:
  12. //
  13. // The above copyright notice and this permission notice shall be
  14. // included in all copies or substantial portions of the Software.
  15. //
  16. // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
  17. // EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES
  18. // OF MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
  19. // NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT
  20. // HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY,
  21. // WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING
  22. // FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
  23. // OTHER DEALINGS IN THE SOFTWARE.
  24. #endregion
  25. #if !(DNXCORE50 || PORTABLE40)
  26. using System.Globalization;
  27. #if NET20
  28. using Newtonsoft.Json.Utilities.LinqBridge;
  29. #else
  30. using System.Linq;
  31. #endif
  32. using System.Text;
  33. using System;
  34. using System.Collections.Generic;
  35. using Newtonsoft.Json.Tests.Serialization;
  36. using Newtonsoft.Json.Tests.TestObjects;
  37. #if DNXCORE50
  38. using Xunit;
  39. using Test = Xunit.FactAttribute;
  40. using Assert = Newtonsoft.Json.Tests.XUnitAssert;
  41. #else
  42. using NUnit.Framework;
  43. #endif
  44. using Newtonsoft.Json;
  45. using System.IO;
  46. using System.Xml;
  47. using Newtonsoft.Json.Converters;
  48. using Newtonsoft.Json.Utilities;
  49. using Newtonsoft.Json.Linq;
  50. #if !NET20
  51. using System.Xml.Linq;
  52. #endif
  53. namespace Newtonsoft.Json.Tests.Converters
  54. {
  55. [TestFixture]
  56. public class XmlNodeConverterTest : TestFixtureBase
  57. {
  58. #if !PORTABLE || NETSTANDARD1_3
  59. private string SerializeXmlNode(XmlNode node)
  60. {
  61. string json = JsonConvert.SerializeXmlNode(node, Formatting.Indented);
  62. #if !(NET20)
  63. #if !NETSTANDARD1_3
  64. XmlReader reader = new XmlNodeReader(node);
  65. #else
  66. StringReader sr = new StringReader(node.OuterXml);
  67. XmlReader reader = XmlReader.Create(sr);
  68. #endif
  69. XObject xNode;
  70. if (node is XmlDocument)
  71. {
  72. xNode = XDocument.Load(reader);
  73. }
  74. else if (node is XmlAttribute)
  75. {
  76. XmlAttribute attribute = (XmlAttribute)node;
  77. xNode = new XAttribute(XName.Get(attribute.LocalName, attribute.NamespaceURI), attribute.Value);
  78. }
  79. else
  80. {
  81. reader.MoveToContent();
  82. xNode = XNode.ReadFrom(reader);
  83. }
  84. string linqJson = JsonConvert.SerializeXNode(xNode, Formatting.Indented);
  85. Assert.AreEqual(json, linqJson);
  86. #endif
  87. return json;
  88. }
  89. private XmlNode DeserializeXmlNode(string json)
  90. {
  91. return DeserializeXmlNode(json, null);
  92. }
  93. private XmlNode DeserializeXmlNode(string json, string deserializeRootElementName)
  94. {
  95. JsonTextReader reader;
  96. reader = new JsonTextReader(new StringReader(json));
  97. reader.Read();
  98. XmlNodeConverter converter = new XmlNodeConverter();
  99. if (deserializeRootElementName != null)
  100. {
  101. converter.DeserializeRootElementName = deserializeRootElementName;
  102. }
  103. XmlNode node = (XmlNode)converter.ReadJson(reader, typeof(XmlDocument), null, new JsonSerializer());
  104. #if !NET20
  105. string xmlText = node.OuterXml;
  106. reader = new JsonTextReader(new StringReader(json));
  107. reader.Read();
  108. XDocument d = (XDocument)converter.ReadJson(reader, typeof(XDocument), null, new JsonSerializer());
  109. string linqXmlText = d.ToString(SaveOptions.DisableFormatting);
  110. if (d.Declaration != null)
  111. {
  112. linqXmlText = d.Declaration + linqXmlText;
  113. }
  114. Assert.AreEqual(xmlText, linqXmlText);
  115. #endif
  116. return node;
  117. }
  118. #endif
  119. private string IndentXml(string xml)
  120. {
  121. XmlReader reader = XmlReader.Create(new StringReader(xml));
  122. StringWriter sw = new StringWriter();
  123. XmlWriter writer = XmlWriter.Create(sw, new XmlWriterSettings { Indent = true, OmitXmlDeclaration = true });
  124. while (reader.Read())
  125. {
  126. writer.WriteNode(reader, false);
  127. }
  128. writer.Flush();
  129. return sw.ToString();
  130. }
  131. #if !NET20
  132. [Test]
  133. public void SerializeDollarProperty()
  134. {
  135. string json1 = @"{""$"":""test""}";
  136. var doc = JsonConvert.DeserializeXNode(json1);
  137. Assert.AreEqual(@"<_x0024_>test</_x0024_>", doc.ToString());
  138. var json2 = JsonConvert.SerializeXNode(doc);
  139. Assert.AreEqual(json1, json2);
  140. }
  141. [Test]
  142. public void SerializeNonKnownDollarProperty()
  143. {
  144. string json1 = @"{""$JELLY"":""test""}";
  145. var doc = JsonConvert.DeserializeXNode(json1);
  146. Console.WriteLine(doc.ToString());
  147. Assert.AreEqual(@"<_x0024_JELLY>test</_x0024_JELLY>", doc.ToString());
  148. var json2 = JsonConvert.SerializeXNode(doc);
  149. Assert.AreEqual(json1, json2);
  150. }
  151. public class MyModel
  152. {
  153. public string MyProperty { get; set; }
  154. }
  155. [Test]
  156. public void ConvertNullString()
  157. {
  158. JObject json = new JObject();
  159. json["Prop1"] = (string)null;
  160. json["Prop2"] = new MyModel().MyProperty;
  161. var xmlNodeConverter = new XmlNodeConverter { DeserializeRootElementName = "object" };
  162. var jsonSerializerSettings = new JsonSerializerSettings { Converters = new JsonConverter[] { xmlNodeConverter } };
  163. var jsonSerializer = JsonSerializer.CreateDefault(jsonSerializerSettings);
  164. XDocument d = json.ToObject<XDocument>(jsonSerializer);
  165. StringAssert.Equals(@"<object>
  166. <Prop1 />
  167. <Prop2 />
  168. </object>", d.ToString());
  169. }
  170. public class Foo
  171. {
  172. public XElement Bar { get; set; }
  173. }
  174. [Test]
  175. public void SerializeAndDeserializeXElement()
  176. {
  177. Foo foo = new Foo { Bar = null };
  178. string json = JsonConvert.SerializeObject(foo);
  179. Assert.AreEqual(@"{""Bar"":null}", json);
  180. Foo foo2 = JsonConvert.DeserializeObject<Foo>(json);
  181. Assert.IsNull(foo2.Bar);
  182. }
  183. [Test]
  184. public void MultipleNamespacesXDocument()
  185. {
  186. string xml = @"<result xp_0:end=""2014-08-15 13:12:11.9184"" xp_0:start=""2014-08-15 13:11:49.3140"" xp_0:time_diff=""22604.3836"" xmlns:xp_0=""Test1"" p2:end=""2014-08-15 13:13:49.5522"" p2:start=""2014-08-15 13:13:49.0268"" p2:time_diff=""525.4646"" xmlns:p2=""Test2"" />";
  187. XDocument d = XDocument.Parse(xml);
  188. string json = JsonConvert.SerializeObject(d, Formatting.Indented);
  189. StringAssert.AreEqual(@"{
  190. ""result"": {
  191. ""@xp_0:end"": ""2014-08-15 13:12:11.9184"",
  192. ""@xp_0:start"": ""2014-08-15 13:11:49.3140"",
  193. ""@xp_0:time_diff"": ""22604.3836"",
  194. ""@xmlns:xp_0"": ""Test1"",
  195. ""@p2:end"": ""2014-08-15 13:13:49.5522"",
  196. ""@p2:start"": ""2014-08-15 13:13:49.0268"",
  197. ""@p2:time_diff"": ""525.4646"",
  198. ""@xmlns:p2"": ""Test2""
  199. }
  200. }", json);
  201. XDocument doc = JsonConvert.DeserializeObject<XDocument>(json);
  202. StringAssert.AreEqual(xml, doc.ToString());
  203. }
  204. #endif
  205. #if !PORTABLE || NETSTANDARD1_3
  206. [Test]
  207. public void MultipleNamespacesXmlDocument()
  208. {
  209. string xml = @"<result xp_0:end=""2014-08-15 13:12:11.9184"" xp_0:start=""2014-08-15 13:11:49.3140"" xp_0:time_diff=""22604.3836"" xmlns:xp_0=""Test1"" p2:end=""2014-08-15 13:13:49.5522"" p2:start=""2014-08-15 13:13:49.0268"" p2:time_diff=""525.4646"" xmlns:p2=""Test2"" />";
  210. XmlDocument d = new XmlDocument();
  211. d.LoadXml(xml);
  212. string json = JsonConvert.SerializeObject(d, Formatting.Indented);
  213. StringAssert.AreEqual(@"{
  214. ""result"": {
  215. ""@xp_0:end"": ""2014-08-15 13:12:11.9184"",
  216. ""@xp_0:start"": ""2014-08-15 13:11:49.3140"",
  217. ""@xp_0:time_diff"": ""22604.3836"",
  218. ""@xmlns:xp_0"": ""Test1"",
  219. ""@p2:end"": ""2014-08-15 13:13:49.5522"",
  220. ""@p2:start"": ""2014-08-15 13:13:49.0268"",
  221. ""@p2:time_diff"": ""525.4646"",
  222. ""@xmlns:p2"": ""Test2""
  223. }
  224. }", json);
  225. XmlDocument doc = JsonConvert.DeserializeObject<XmlDocument>(json);
  226. StringAssert.AreEqual(xml, doc.OuterXml);
  227. }
  228. [Test]
  229. public void SerializeXmlElement()
  230. {
  231. string xml = @"<payload>
  232. <Country>6</Country>
  233. <FinancialTransactionApprovalRequestUID>79</FinancialTransactionApprovalRequestUID>
  234. <TransactionStatus>Approved</TransactionStatus>
  235. <StatusChangeComment></StatusChangeComment>
  236. <RequestedBy>Someone</RequestedBy>
  237. </payload>";
  238. var xmlDocument = new XmlDocument();
  239. xmlDocument.LoadXml(xml);
  240. var result = xmlDocument.FirstChild.ChildNodes.Cast<XmlNode>().ToArray();
  241. var json = JsonConvert.SerializeObject(result, Formatting.Indented); // <--- fails here with the cast message
  242. StringAssert.AreEqual(@"[
  243. {
  244. ""Country"": ""6""
  245. },
  246. {
  247. ""FinancialTransactionApprovalRequestUID"": ""79""
  248. },
  249. {
  250. ""TransactionStatus"": ""Approved""
  251. },
  252. {
  253. ""StatusChangeComment"": """"
  254. },
  255. {
  256. ""RequestedBy"": ""Someone""
  257. }
  258. ]", json);
  259. }
  260. #endif
  261. #if !NET20
  262. [Test]
  263. public void SerializeXElement()
  264. {
  265. string xml = @"<payload>
  266. <Country>6</Country>
  267. <FinancialTransactionApprovalRequestUID>79</FinancialTransactionApprovalRequestUID>
  268. <TransactionStatus>Approved</TransactionStatus>
  269. <StatusChangeComment></StatusChangeComment>
  270. <RequestedBy>Someone</RequestedBy>
  271. </payload>";
  272. var xmlDocument = XDocument.Parse(xml);
  273. var result = xmlDocument.Root.Nodes().ToArray();
  274. var json = JsonConvert.SerializeObject(result, Formatting.Indented); // <--- fails here with the cast message
  275. StringAssert.AreEqual(@"[
  276. {
  277. ""Country"": ""6""
  278. },
  279. {
  280. ""FinancialTransactionApprovalRequestUID"": ""79""
  281. },
  282. {
  283. ""TransactionStatus"": ""Approved""
  284. },
  285. {
  286. ""StatusChangeComment"": """"
  287. },
  288. {
  289. ""RequestedBy"": ""Someone""
  290. }
  291. ]", json);
  292. }
  293. public class DecimalContainer
  294. {
  295. public decimal Number { get; set; }
  296. }
  297. [Test]
  298. public void FloatParseHandlingDecimal()
  299. {
  300. decimal d = (decimal)Math.PI + 1000000000m;
  301. var x = new DecimalContainer { Number = d };
  302. var json = JsonConvert.SerializeObject(x, Formatting.Indented);
  303. XDocument doc1 = JsonConvert.DeserializeObject<XDocument>(json, new JsonSerializerSettings
  304. {
  305. Converters = { new XmlNodeConverter() },
  306. FloatParseHandling = FloatParseHandling.Decimal
  307. });
  308. var xml = doc1.ToString();
  309. Assert.AreEqual("<Number>1000000003.14159265358979</Number>", xml);
  310. string json2 = JsonConvert.SerializeObject(doc1, Formatting.Indented);
  311. DecimalContainer x2 = JsonConvert.DeserializeObject<DecimalContainer>(json2);
  312. Assert.AreEqual(x.Number, x2.Number);
  313. }
  314. public class DateTimeOffsetContainer
  315. {
  316. public DateTimeOffset Date { get; set; }
  317. }
  318. [Test]
  319. public void DateTimeParseHandlingOffset()
  320. {
  321. DateTimeOffset d = new DateTimeOffset(2012, 12, 12, 12, 44, 1, TimeSpan.FromHours(12).Add(TimeSpan.FromMinutes(34)));
  322. var x = new DateTimeOffsetContainer { Date = d };
  323. var json = JsonConvert.SerializeObject(x, Formatting.Indented);
  324. XDocument doc1 = JsonConvert.DeserializeObject<XDocument>(json, new JsonSerializerSettings
  325. {
  326. Converters = { new XmlNodeConverter() },
  327. DateParseHandling = DateParseHandling.DateTimeOffset
  328. });
  329. var xml = doc1.ToString();
  330. Assert.AreEqual("<Date>2012-12-12T12:44:01+12:34</Date>", xml);
  331. string json2 = JsonConvert.SerializeObject(doc1, Formatting.Indented);
  332. DateTimeOffsetContainer x2 = JsonConvert.DeserializeObject<DateTimeOffsetContainer>(json2);
  333. Assert.AreEqual(x.Date, x2.Date);
  334. }
  335. [Test]
  336. public void GroupElementsOfTheSameName()
  337. {
  338. string xml = "<root><p>Text1<span>Span1</span> <span>Span2</span> Text2</p></root>";
  339. string json = JsonConvert.SerializeXNode(XElement.Parse(xml));
  340. Assert.AreEqual(@"{""root"":{""p"":{""#text"":[""Text1"","" Text2""],""span"":[""Span1"",""Span2""]}}}", json);
  341. XDocument doc = JsonConvert.DeserializeXNode(json);
  342. StringAssert.AreEqual(@"<root>
  343. <p>Text1 Text2<span>Span1</span><span>Span2</span></p>
  344. </root>", doc.ToString());
  345. }
  346. #if !PORTABLE || NETSTANDARD1_3
  347. [Test]
  348. public void SerializeEmptyDocument()
  349. {
  350. XmlDocument doc = new XmlDocument();
  351. doc.LoadXml("<root />");
  352. string json = JsonConvert.SerializeXmlNode(doc, Formatting.Indented, true);
  353. Assert.AreEqual("null", json);
  354. doc = new XmlDocument();
  355. doc.LoadXml("<root></root>");
  356. json = JsonConvert.SerializeXmlNode(doc, Formatting.Indented, true);
  357. Assert.AreEqual(@"""""", json);
  358. XDocument doc1 = XDocument.Parse("<root />");
  359. json = JsonConvert.SerializeXNode(doc1, Formatting.Indented, true);
  360. Assert.AreEqual("null", json);
  361. doc1 = XDocument.Parse("<root></root>");
  362. json = JsonConvert.SerializeXNode(doc1, Formatting.Indented, true);
  363. Assert.AreEqual(@"""""", json);
  364. }
  365. #endif
  366. [Test]
  367. public void SerializeAndDeserializeXmlWithNamespaceInChildrenAndNoValueInChildren()
  368. {
  369. var xmlString = @"<root>
  370. <b xmlns='http://www.example.com/ns'/>
  371. <c>AAA</c>
  372. <test>adad</test>
  373. </root>";
  374. var xml = XElement.Parse(xmlString);
  375. var json1 = JsonConvert.SerializeXNode(xml);
  376. var xmlBack = JsonConvert.DeserializeObject<XElement>(json1);
  377. var equals = XElement.DeepEquals(xmlBack, xml);
  378. Assert.IsTrue(equals);
  379. }
  380. #if !PORTABLE || NETSTANDARD1_3
  381. [Test]
  382. public void DeserializeUndeclaredNamespacePrefix()
  383. {
  384. XmlDocument doc = JsonConvert.DeserializeXmlNode("{ A: { '@xsi:nil': true } }");
  385. Assert.AreEqual(@"<A nil=""true"" />", doc.OuterXml);
  386. XDocument xdoc = JsonConvert.DeserializeXNode("{ A: { '@xsi:nil': true } }");
  387. Assert.AreEqual(doc.OuterXml, xdoc.ToString());
  388. }
  389. #endif
  390. #endif
  391. #if !PORTABLE || NETSTANDARD1_3
  392. [Test]
  393. public void DeserializeMultipleRootElements()
  394. {
  395. string json = @"{
  396. ""Id"": 1,
  397. ""Email"": ""james@example.com"",
  398. ""Active"": true,
  399. ""CreatedDate"": ""2013-01-20T00:00:00Z"",
  400. ""Roles"": [
  401. ""User"",
  402. ""Admin""
  403. ],
  404. ""Team"": {
  405. ""Id"": 2,
  406. ""Name"": ""Software Developers"",
  407. ""Description"": ""Creators of fine software products and services.""
  408. }
  409. }";
  410. ExceptionAssert.Throws<JsonSerializationException>(
  411. () => { JsonConvert.DeserializeXmlNode(json); },
  412. "JSON root object has multiple properties. The root object must have a single property in order to create a valid XML document. Consider specifying a DeserializeRootElementName. Path 'Email', line 3, position 13.");
  413. }
  414. [Test]
  415. public void DocumentSerializeIndented()
  416. {
  417. string xml = @"<?xml version=""1.0"" standalone=""no""?>
  418. <?xml-stylesheet href=""classic.xsl"" type=""text/xml""?>
  419. <span class=""vevent"">
  420. <a class=""url"" href=""http://www.web2con.com/"">
  421. <span class=""summary"">Web 2.0 Conference<![CDATA[my escaped text]]></span>
  422. <abbr class=""dtstart"" title=""2005-10-05"">October 5</abbr>
  423. <abbr class=""dtend"" title=""2005-10-08"">7</abbr>
  424. <span class=""location"">Argent Hotel, San Francisco, CA</span>
  425. </a>
  426. </span>";
  427. XmlDocument doc = new XmlDocument();
  428. doc.LoadXml(xml);
  429. string jsonText = SerializeXmlNode(doc);
  430. string expected = @"{
  431. ""?xml"": {
  432. ""@version"": ""1.0"",
  433. ""@standalone"": ""no""
  434. },
  435. ""?xml-stylesheet"": ""href=\""classic.xsl\"" type=\""text/xml\"""",
  436. ""span"": {
  437. ""@class"": ""vevent"",
  438. ""a"": {
  439. ""@class"": ""url"",
  440. ""@href"": ""http://www.web2con.com/"",
  441. ""span"": [
  442. {
  443. ""@class"": ""summary"",
  444. ""#text"": ""Web 2.0 Conference"",
  445. ""#cdata-section"": ""my escaped text""
  446. },
  447. {
  448. ""@class"": ""location"",
  449. ""#text"": ""Argent Hotel, San Francisco, CA""
  450. }
  451. ],
  452. ""abbr"": [
  453. {
  454. ""@class"": ""dtstart"",
  455. ""@title"": ""2005-10-05"",
  456. ""#text"": ""October 5""
  457. },
  458. {
  459. ""@class"": ""dtend"",
  460. ""@title"": ""2005-10-08"",
  461. ""#text"": ""7""
  462. }
  463. ]
  464. }
  465. }
  466. }";
  467. StringAssert.AreEqual(expected, jsonText);
  468. }
  469. [Test]
  470. public void SerializeNodeTypes()
  471. {
  472. XmlDocument doc = new XmlDocument();
  473. string jsonText;
  474. string xml = @"<?xml version=""1.0"" encoding=""utf-8"" ?>
  475. <xs:schema xs:id=""SomeID""
  476. xmlns=""""
  477. xmlns:xs=""http://www.w3.org/2001/XMLSchema""
  478. xmlns:msdata=""urn:schemas-microsoft-com:xml-msdata"">
  479. <xs:element name=""MyDataSet"" msdata:IsDataSet=""true"">
  480. </xs:element>
  481. </xs:schema>";
  482. XmlDocument document = new XmlDocument();
  483. document.LoadXml(xml);
  484. // XmlAttribute
  485. XmlAttribute attribute = document.DocumentElement.ChildNodes[0].Attributes["IsDataSet", "urn:schemas-microsoft-com:xml-msdata"];
  486. attribute.Value = "true";
  487. jsonText = JsonConvert.SerializeXmlNode(attribute);
  488. Assert.AreEqual(@"{""@msdata:IsDataSet"":""true""}", jsonText);
  489. #if !NET20
  490. XDocument d = XDocument.Parse(xml);
  491. XAttribute a = d.Root.Element("{http://www.w3.org/2001/XMLSchema}element").Attribute("{urn:schemas-microsoft-com:xml-msdata}IsDataSet");
  492. jsonText = JsonConvert.SerializeXNode(a);
  493. Assert.AreEqual(@"{""@msdata:IsDataSet"":""true""}", jsonText);
  494. #endif
  495. // XmlProcessingInstruction
  496. XmlProcessingInstruction instruction = doc.CreateProcessingInstruction("xml-stylesheet", @"href=""classic.xsl"" type=""text/xml""");
  497. jsonText = JsonConvert.SerializeXmlNode(instruction);
  498. Assert.AreEqual(@"{""?xml-stylesheet"":""href=\""classic.xsl\"" type=\""text/xml\""""}", jsonText);
  499. // XmlProcessingInstruction
  500. XmlCDataSection cDataSection = doc.CreateCDataSection("<Kiwi>true</Kiwi>");
  501. jsonText = JsonConvert.SerializeXmlNode(cDataSection);
  502. Assert.AreEqual(@"{""#cdata-section"":""<Kiwi>true</Kiwi>""}", jsonText);
  503. // XmlElement
  504. XmlElement element = doc.CreateElement("xs", "Choice", "http://www.w3.org/2001/XMLSchema");
  505. element.SetAttributeNode(doc.CreateAttribute("msdata", "IsDataSet", "urn:schemas-microsoft-com:xml-msdata"));
  506. XmlAttribute aa = doc.CreateAttribute(@"xmlns", "xs", "http://www.w3.org/2000/xmlns/");
  507. aa.Value = "http://www.w3.org/2001/XMLSchema";
  508. element.SetAttributeNode(aa);
  509. aa = doc.CreateAttribute(@"xmlns", "msdata", "http://www.w3.org/2000/xmlns/");
  510. aa.Value = "urn:schemas-microsoft-com:xml-msdata";
  511. element.SetAttributeNode(aa);
  512. element.AppendChild(instruction);
  513. element.AppendChild(cDataSection);
  514. doc.AppendChild(element);
  515. jsonText = JsonConvert.SerializeXmlNode(element, Formatting.Indented);
  516. StringAssert.AreEqual(@"{
  517. ""xs:Choice"": {
  518. ""@msdata:IsDataSet"": """",
  519. ""@xmlns:xs"": ""http://www.w3.org/2001/XMLSchema"",
  520. ""@xmlns:msdata"": ""urn:schemas-microsoft-com:xml-msdata"",
  521. ""?xml-stylesheet"": ""href=\""classic.xsl\"" type=\""text/xml\"""",
  522. ""#cdata-section"": ""<Kiwi>true</Kiwi>""
  523. }
  524. }", jsonText);
  525. }
  526. [Test]
  527. public void SerializeNodeTypes_Encoding()
  528. {
  529. XmlNode node = DeserializeXmlNode(@"{
  530. ""xs!:Choice!"": {
  531. ""@msdata:IsDataSet!"": """",
  532. ""@xmlns:xs!"": ""http://www.w3.org/2001/XMLSchema"",
  533. ""@xmlns:msdata"": ""urn:schemas-microsoft-com:xml-msdata"",
  534. ""?xml-stylesheet"": ""href=\""classic.xsl\"" type=\""text/xml\"""",
  535. ""#cdata-section"": ""<Kiwi>true</Kiwi>""
  536. }
  537. }");
  538. Assert.AreEqual(@"<xs_x0021_:Choice_x0021_ msdata:IsDataSet_x0021_="""" xmlns:xs_x0021_=""http://www.w3.org/2001/XMLSchema"" xmlns:msdata=""urn:schemas-microsoft-com:xml-msdata""><?xml-stylesheet href=""classic.xsl"" type=""text/xml""?><![CDATA[<Kiwi>true</Kiwi>]]></xs_x0021_:Choice_x0021_>", node.InnerXml);
  539. string json = SerializeXmlNode(node);
  540. StringAssert.AreEqual(@"{
  541. ""xs!:Choice!"": {
  542. ""@msdata:IsDataSet!"": """",
  543. ""@xmlns:xs!"": ""http://www.w3.org/2001/XMLSchema"",
  544. ""@xmlns:msdata"": ""urn:schemas-microsoft-com:xml-msdata"",
  545. ""?xml-stylesheet"": ""href=\""classic.xsl\"" type=\""text/xml\"""",
  546. ""#cdata-section"": ""<Kiwi>true</Kiwi>""
  547. }
  548. }", json);
  549. }
  550. [Test]
  551. public void DocumentFragmentSerialize()
  552. {
  553. XmlDocument doc = new XmlDocument();
  554. XmlDocumentFragment fragement = doc.CreateDocumentFragment();
  555. fragement.InnerXml = "<Item>widget</Item><Item>widget</Item>";
  556. string jsonText = JsonConvert.SerializeXmlNode(fragement);
  557. string expected = @"{""Item"":[""widget"",""widget""]}";
  558. Assert.AreEqual(expected, jsonText);
  559. }
  560. #if !NETSTANDARD1_3
  561. [Test]
  562. public void XmlDocumentTypeSerialize()
  563. {
  564. string xml = @"<?xml version=""1.0"" encoding=""utf-8""?><!DOCTYPE STOCKQUOTE PUBLIC ""-//W3C//DTD StockQuote 1.5//EN"" ""http://www.idontexistnopenopewhatnope123.org/dtd/stockquote_1.5.dtd""><STOCKQUOTE ROWCOUNT=""2""><RESULT><ROW><ASK>0</ASK><BID>0</BID><CHANGE>-16.310</CHANGE><COMPANYNAME>Dow Jones</COMPANYNAME><DATETIME>2014-04-17 15:50:37</DATETIME><DIVIDEND>0</DIVIDEND><EPS>0</EPS><EXCHANGE></EXCHANGE><HIGH>16460.490</HIGH><LASTDATETIME>2014-04-17 15:50:37</LASTDATETIME><LASTPRICE>16408.540</LASTPRICE><LOW>16368.140</LOW><OPEN>16424.140</OPEN><PCHANGE>-0.099</PCHANGE><PE>0</PE><PREVIOUSCLOSE>16424.850</PREVIOUSCLOSE><SHARES>0</SHARES><TICKER>DJII</TICKER><TRADES>0</TRADES><VOLUME>136188700</VOLUME><YEARHIGH>11309.000</YEARHIGH><YEARLOW>9302.280</YEARLOW><YIELD>0</YIELD></ROW><ROW><ASK>0</ASK><BID>0</BID><CHANGE>9.290</CHANGE><COMPANYNAME>NASDAQ</COMPANYNAME><DATETIME>2014-04-17 15:40:01</DATETIME><DIVIDEND>0</DIVIDEND><EPS>0</EPS><EXCHANGE></EXCHANGE><HIGH>4110.460</HIGH><LASTDATETIME>2014-04-17 15:40:01</LASTDATETIME><LASTPRICE>4095.520</LASTPRICE><LOW>4064.700</LOW><OPEN>4080.300</OPEN><PCHANGE>0.227</PCHANGE><PE>0</PE><PREVIOUSCLOSE>4086.230</PREVIOUSCLOSE><SHARES>0</SHARES><TICKER>COMP</TICKER><TRADES>0</TRADES><VOLUME>1784210100</VOLUME><YEARHIGH>4371.710</YEARHIGH><YEARLOW>3154.960</YEARLOW><YIELD>0</YIELD></ROW></RESULT><STATUS>Couldn't find ticker: SPIC?</STATUS><STATUSCODE>2</STATUSCODE></STOCKQUOTE>";
  565. string expected = @"{
  566. ""?xml"": {
  567. ""@version"": ""1.0"",
  568. ""@encoding"": ""utf-8""
  569. },
  570. ""!DOCTYPE"": {
  571. ""@name"": ""STOCKQUOTE"",
  572. ""@public"": ""-//W3C//DTD StockQuote 1.5//EN"",
  573. ""@system"": ""http://www.idontexistnopenopewhatnope123.org/dtd/stockquote_1.5.dtd""
  574. },
  575. ""STOCKQUOTE"": {
  576. ""@ROWCOUNT"": ""2"",
  577. ""RESULT"": {
  578. ""ROW"": [
  579. {
  580. ""ASK"": ""0"",
  581. ""BID"": ""0"",
  582. ""CHANGE"": ""-16.310"",
  583. ""COMPANYNAME"": ""Dow Jones"",
  584. ""DATETIME"": ""2014-04-17 15:50:37"",
  585. ""DIVIDEND"": ""0"",
  586. ""EPS"": ""0"",
  587. ""EXCHANGE"": """",
  588. ""HIGH"": ""16460.490"",
  589. ""LASTDATETIME"": ""2014-04-17 15:50:37"",
  590. ""LASTPRICE"": ""16408.540"",
  591. ""LOW"": ""16368.140"",
  592. ""OPEN"": ""16424.140"",
  593. ""PCHANGE"": ""-0.099"",
  594. ""PE"": ""0"",
  595. ""PREVIOUSCLOSE"": ""16424.850"",
  596. ""SHARES"": ""0"",
  597. ""TICKER"": ""DJII"",
  598. ""TRADES"": ""0"",
  599. ""VOLUME"": ""136188700"",
  600. ""YEARHIGH"": ""11309.000"",
  601. ""YEARLOW"": ""9302.280"",
  602. ""YIELD"": ""0""
  603. },
  604. {
  605. ""ASK"": ""0"",
  606. ""BID"": ""0"",
  607. ""CHANGE"": ""9.290"",
  608. ""COMPANYNAME"": ""NASDAQ"",
  609. ""DATETIME"": ""2014-04-17 15:40:01"",
  610. ""DIVIDEND"": ""0"",
  611. ""EPS"": ""0"",
  612. ""EXCHANGE"": """",
  613. ""HIGH"": ""4110.460"",
  614. ""LASTDATETIME"": ""2014-04-17 15:40:01"",
  615. ""LASTPRICE"": ""4095.520"",
  616. ""LOW"": ""4064.700"",
  617. ""OPEN"": ""4080.300"",
  618. ""PCHANGE"": ""0.227"",
  619. ""PE"": ""0"",
  620. ""PREVIOUSCLOSE"": ""4086.230"",
  621. ""SHARES"": ""0"",
  622. ""TICKER"": ""COMP"",
  623. ""TRADES"": ""0"",
  624. ""VOLUME"": ""1784210100"",
  625. ""YEARHIGH"": ""4371.710"",
  626. ""YEARLOW"": ""3154.960"",
  627. ""YIELD"": ""0""
  628. }
  629. ]
  630. },
  631. ""STATUS"": ""Couldn't find ticker: SPIC?"",
  632. ""STATUSCODE"": ""2""
  633. }
  634. }";
  635. XmlDocument doc1 = new XmlDocument();
  636. doc1.XmlResolver = null;
  637. doc1.LoadXml(xml);
  638. string json1 = JsonConvert.SerializeXmlNode(doc1, Formatting.Indented);
  639. StringAssert.AreEqual(expected, json1);
  640. XmlDocument doc11 = JsonConvert.DeserializeXmlNode(json1);
  641. StringAssert.AreEqual(xml, ToStringWithDeclaration(doc11));
  642. #if !NET20
  643. XDocument doc2 = XDocument.Parse(xml);
  644. string json2 = JsonConvert.SerializeXNode(doc2, Formatting.Indented);
  645. StringAssert.AreEqual(expected, json2);
  646. XDocument doc22 = JsonConvert.DeserializeXNode(json2);
  647. StringAssert.AreEqual(xml, ToStringWithDeclaration(doc22));
  648. #endif
  649. }
  650. #endif
  651. public class Utf8StringWriter : StringWriter
  652. {
  653. public override Encoding Encoding
  654. {
  655. get { return Encoding.UTF8; }
  656. }
  657. public Utf8StringWriter(StringBuilder sb) : base(sb)
  658. {
  659. }
  660. }
  661. #if !NET20
  662. public static string ToStringWithDeclaration(XDocument doc, bool indent = false)
  663. {
  664. StringBuilder builder = new StringBuilder();
  665. using (var writer = XmlWriter.Create(new Utf8StringWriter(builder), new XmlWriterSettings { Indent = indent }))
  666. {
  667. doc.Save(writer);
  668. }
  669. return builder.ToString();
  670. }
  671. #endif
  672. public static string ToStringWithDeclaration(XmlDocument doc, bool indent = false)
  673. {
  674. StringBuilder builder = new StringBuilder();
  675. using (var writer = XmlWriter.Create(new Utf8StringWriter(builder), new XmlWriterSettings { Indent = indent }))
  676. {
  677. doc.Save(writer);
  678. }
  679. return builder.ToString();
  680. }
  681. [Test]
  682. public void NamespaceSerializeDeserialize()
  683. {
  684. string xml = @"<?xml version=""1.0"" encoding=""utf-8"" ?>
  685. <xs:schema xs:id=""SomeID""
  686. xmlns=""""
  687. xmlns:xs=""http://www.w3.org/2001/XMLSchema""
  688. xmlns:msdata=""urn:schemas-microsoft-com:xml-msdata"">
  689. <xs:element name=""MyDataSet"" msdata:IsDataSet=""true"">
  690. <xs:complexType>
  691. <xs:choice maxOccurs=""unbounded"">
  692. <xs:element name=""customers"" >
  693. <xs:complexType >
  694. <xs:sequence>
  695. <xs:element name=""CustomerID"" type=""xs:integer""
  696. minOccurs=""0"" />
  697. <xs:element name=""CompanyName"" type=""xs:string""
  698. minOccurs=""0"" />
  699. <xs:element name=""Phone"" type=""xs:string"" />
  700. </xs:sequence>
  701. </xs:complexType>
  702. </xs:element>
  703. </xs:choice>
  704. </xs:complexType>
  705. </xs:element>
  706. </xs:schema>";
  707. XmlDocument doc = new XmlDocument();
  708. doc.LoadXml(xml);
  709. string jsonText = SerializeXmlNode(doc);
  710. string expected = @"{
  711. ""?xml"": {
  712. ""@version"": ""1.0"",
  713. ""@encoding"": ""utf-8""
  714. },
  715. ""xs:schema"": {
  716. ""@xs:id"": ""SomeID"",
  717. ""@xmlns"": """",
  718. ""@xmlns:xs"": ""http://www.w3.org/2001/XMLSchema"",
  719. ""@xmlns:msdata"": ""urn:schemas-microsoft-com:xml-msdata"",
  720. ""xs:element"": {
  721. ""@name"": ""MyDataSet"",
  722. ""@msdata:IsDataSet"": ""true"",
  723. ""xs:complexType"": {
  724. ""xs:choice"": {
  725. ""@maxOccurs"": ""unbounded"",
  726. ""xs:element"": {
  727. ""@name"": ""customers"",
  728. ""xs:complexType"": {
  729. ""xs:sequence"": {
  730. ""xs:element"": [
  731. {
  732. ""@name"": ""CustomerID"",
  733. ""@type"": ""xs:integer"",
  734. ""@minOccurs"": ""0""
  735. },
  736. {
  737. ""@name"": ""CompanyName"",
  738. ""@type"": ""xs:string"",
  739. ""@minOccurs"": ""0""
  740. },
  741. {
  742. ""@name"": ""Phone"",
  743. ""@type"": ""xs:string""
  744. }
  745. ]
  746. }
  747. }
  748. }
  749. }
  750. }
  751. }
  752. }
  753. }";
  754. StringAssert.AreEqual(expected, jsonText);
  755. XmlDocument deserializedDoc = (XmlDocument)DeserializeXmlNode(jsonText);
  756. Assert.AreEqual(doc.InnerXml, deserializedDoc.InnerXml);
  757. }
  758. [Test]
  759. public void FailOnIncomplete()
  760. {
  761. string json = @"{'Row' : ";
  762. ExceptionAssert.Throws<JsonSerializationException>(
  763. () => JsonConvert.DeserializeXmlNode(json, "ROOT"),
  764. "Unexpected end when reading JSON. Path 'Row', line 1, position 9.");
  765. }
  766. [Test]
  767. public void DocumentDeserialize()
  768. {
  769. string jsonText = @"{
  770. ""?xml"": {
  771. ""@version"": ""1.0"",
  772. ""@standalone"": ""no""
  773. },
  774. ""span"": {
  775. ""@class"": ""vevent"",
  776. ""a"": {
  777. ""@class"": ""url"",
  778. ""span"": {
  779. ""@class"": ""summary"",
  780. ""#text"": ""Web 2.0 Conference"",
  781. ""#cdata-section"": ""my escaped text""
  782. },
  783. ""@href"": ""http://www.web2con.com/""
  784. }
  785. }
  786. }";
  787. XmlDocument doc = (XmlDocument)DeserializeXmlNode(jsonText);
  788. string expected = @"<?xml version=""1.0"" standalone=""no""?>
  789. <span class=""vevent"">
  790. <a class=""url"" href=""http://www.web2con.com/"">
  791. <span class=""summary"">Web 2.0 Conference<![CDATA[my escaped text]]></span>
  792. </a>
  793. </span>";
  794. string formattedXml = GetIndentedInnerXml(doc);
  795. StringAssert.AreEqual(expected, formattedXml);
  796. }
  797. private string GetIndentedInnerXml(XmlNode node)
  798. {
  799. XmlWriterSettings settings = new XmlWriterSettings();
  800. settings.Indent = true;
  801. StringWriter sw = new StringWriter();
  802. using (XmlWriter writer = XmlWriter.Create(sw, settings))
  803. {
  804. node.WriteTo(writer);
  805. }
  806. return sw.ToString();
  807. }
  808. public class Foo2
  809. {
  810. public XmlElement Bar { get; set; }
  811. }
  812. [Test]
  813. public void SerializeAndDeserializeXmlElement()
  814. {
  815. Foo2 foo = new Foo2 { Bar = null };
  816. string json = JsonConvert.SerializeObject(foo);
  817. Assert.AreEqual(@"{""Bar"":null}", json);
  818. Foo2 foo2 = JsonConvert.DeserializeObject<Foo2>(json);
  819. Assert.IsNull(foo2.Bar);
  820. }
  821. [Test]
  822. public void SingleTextNode()
  823. {
  824. string xml = @"<?xml version=""1.0"" standalone=""no""?>
  825. <root>
  826. <person id=""1"">
  827. <name>Alan</name>
  828. <url>http://www.google.com</url>
  829. </person>
  830. <person id=""2"">
  831. <name>Louis</name>
  832. <url>http://www.yahoo.com</url>
  833. </person>
  834. </root>";
  835. XmlDocument doc = new XmlDocument();
  836. doc.LoadXml(xml);
  837. string jsonText = SerializeXmlNode(doc);
  838. XmlDocument newDoc = (XmlDocument)DeserializeXmlNode(jsonText);
  839. Assert.AreEqual(doc.InnerXml, newDoc.InnerXml);
  840. }
  841. [Test]
  842. public void EmptyNode()
  843. {
  844. string xml = @"<?xml version=""1.0"" standalone=""no""?>
  845. <root>
  846. <person id=""1"">
  847. <name>Alan</name>
  848. <url />
  849. </person>
  850. <person id=""2"">
  851. <name>Louis</name>
  852. <url>http://www.yahoo.com</url>
  853. </person>
  854. </root>";
  855. XmlDocument doc = new XmlDocument();
  856. doc.LoadXml(xml);
  857. string jsonText = SerializeXmlNode(doc);
  858. StringAssert.AreEqual(@"{
  859. ""?xml"": {
  860. ""@version"": ""1.0"",
  861. ""@standalone"": ""no""
  862. },
  863. ""root"": {
  864. ""person"": [
  865. {
  866. ""@id"": ""1"",
  867. ""name"": ""Alan"",
  868. ""url"": null
  869. },
  870. {
  871. ""@id"": ""2"",
  872. ""name"": ""Louis"",
  873. ""url"": ""http://www.yahoo.com""
  874. }
  875. ]
  876. }
  877. }", jsonText);
  878. XmlDocument newDoc = (XmlDocument)DeserializeXmlNode(jsonText);
  879. Assert.AreEqual(doc.InnerXml, newDoc.InnerXml);
  880. }
  881. [Test]
  882. public void OtherElementDataTypes()
  883. {
  884. string jsonText = @"{""?xml"":{""@version"":""1.0"",""@standalone"":""no""},""root"":{""person"":[{""@id"":""1"",""Float"":2.5,""Integer"":99},{""Boolean"":true,""@id"":""2"",""date"":""\/Date(954374400000)\/""}]}}";
  885. XmlDocument newDoc = (XmlDocument)DeserializeXmlNode(jsonText);
  886. string expected = @"<?xml version=""1.0"" standalone=""no""?><root><person id=""1""><Float>2.5</Float><Integer>99</Integer></person><person id=""2""><Boolean>true</Boolean><date>2000-03-30T00:00:00Z</date></person></root>";
  887. Assert.AreEqual(expected, newDoc.InnerXml);
  888. }
  889. [Test]
  890. public void NoRootObject()
  891. {
  892. ExceptionAssert.Throws<JsonSerializationException>(() => { XmlDocument newDoc = (XmlDocument)JsonConvert.DeserializeXmlNode(@"[1]"); }, "XmlNodeConverter can only convert JSON that begins with an object. Path '', line 1, position 1.");
  893. }
  894. [Test]
  895. public void RootObjectMultipleProperties()
  896. {
  897. ExceptionAssert.Throws<JsonSerializationException>(
  898. () => { XmlDocument newDoc = (XmlDocument)JsonConvert.DeserializeXmlNode(@"{Prop1:1,Prop2:2}"); },
  899. "JSON root object has multiple properties. The root object must have a single property in order to create a valid XML document. Consider specifying a DeserializeRootElementName. Path 'Prop2', line 1, position 15.");
  900. }
  901. [Test]
  902. public void JavaScriptConstructor()
  903. {
  904. string jsonText = @"{root:{r:new Date(34343, 55)}}";
  905. XmlDocument newDoc = (XmlDocument)DeserializeXmlNode(jsonText);
  906. string expected = @"<root><r><Date>34343</Date><Date>55</Date></r></root>";
  907. Assert.AreEqual(expected, newDoc.InnerXml);
  908. string json = SerializeXmlNode(newDoc);
  909. expected = @"{
  910. ""root"": {
  911. ""r"": {
  912. ""Date"": [
  913. ""34343"",
  914. ""55""
  915. ]
  916. }
  917. }
  918. }";
  919. StringAssert.AreEqual(expected, json);
  920. }
  921. [Test]
  922. public void ForceJsonArray()
  923. {
  924. string arrayXml = @"<root xmlns:json=""http://james.newtonking.com/projects/json"">
  925. <person id=""1"">
  926. <name>Alan</name>
  927. <url>http://www.google.com</url>
  928. <role json:Array=""true"">Admin</role>
  929. </person>
  930. </root>";
  931. XmlDocument arrayDoc = new XmlDocument();
  932. arrayDoc.LoadXml(arrayXml);
  933. string arrayJsonText = SerializeXmlNode(arrayDoc);
  934. string expected = @"{
  935. ""root"": {
  936. ""person"": {
  937. ""@id"": ""1"",
  938. ""name"": ""Alan"",
  939. ""url"": ""http://www.google.com"",
  940. ""role"": [
  941. ""Admin""
  942. ]
  943. }
  944. }
  945. }";
  946. StringAssert.AreEqual(expected, arrayJsonText);
  947. arrayXml = @"<root xmlns:json=""http://james.newtonking.com/projects/json"">
  948. <person id=""1"">
  949. <name>Alan</name>
  950. <url>http://www.google.com</url>
  951. <role json:Array=""true"">Admin1</role>
  952. <role json:Array=""true"">Admin2</role>
  953. </person>
  954. </root>";
  955. arrayDoc = new XmlDocument();
  956. arrayDoc.LoadXml(arrayXml);
  957. arrayJsonText = SerializeXmlNode(arrayDoc);
  958. expected = @"{
  959. ""root"": {
  960. ""person"": {
  961. ""@id"": ""1"",
  962. ""name"": ""Alan"",
  963. ""url"": ""http://www.google.com"",
  964. ""role"": [
  965. ""Admin1"",
  966. ""Admin2""
  967. ]
  968. }
  969. }
  970. }";
  971. StringAssert.AreEqual(expected, arrayJsonText);
  972. arrayXml = @"<root xmlns:json=""http://james.newtonking.com/projects/json"">
  973. <person id=""1"">
  974. <name>Alan</name>
  975. <url>http://www.google.com</url>
  976. <role json:Array=""false"">Admin1</role>
  977. </person>
  978. </root>";
  979. arrayDoc = new XmlDocument();
  980. arrayDoc.LoadXml(arrayXml);
  981. arrayJsonText = SerializeXmlNode(arrayDoc);
  982. expected = @"{
  983. ""root"": {
  984. ""person"": {
  985. ""@id"": ""1"",
  986. ""name"": ""Alan"",
  987. ""url"": ""http://www.google.com"",
  988. ""role"": ""Admin1""
  989. }
  990. }
  991. }";
  992. StringAssert.AreEqual(expected, arrayJsonText);
  993. arrayXml = @"<root>
  994. <person id=""1"">
  995. <name>Alan</name>
  996. <url>http://www.google.com</url>
  997. <role json:Array=""true"" xmlns:json=""http://james.newtonking.com/projects/json"">Admin</role>
  998. </person>
  999. </root>";
  1000. arrayDoc = new XmlDocument();
  1001. arrayDoc.LoadXml(arrayXml);
  1002. arrayJsonText = SerializeXmlNode(arrayDoc);
  1003. expected = @"{
  1004. ""root"": {
  1005. ""person"": {
  1006. ""@id"": ""1"",
  1007. ""name"": ""Alan"",
  1008. ""url"": ""http://www.google.com"",
  1009. ""role"": [
  1010. ""Admin""
  1011. ]
  1012. }
  1013. }
  1014. }";
  1015. StringAssert.AreEqual(expected, arrayJsonText);
  1016. }
  1017. [Test]
  1018. public void MultipleRootPropertiesXmlDocument()
  1019. {
  1020. string json = @"{""count"": 773840,""photos"": null}";
  1021. ExceptionAssert.Throws<JsonSerializationException>(
  1022. () => { JsonConvert.DeserializeXmlNode(json); },
  1023. "JSON root object has multiple properties. The root object must have a single property in order to create a valid XML document. Consider specifying a DeserializeRootElementName. Path 'photos', line 1, position 26.");
  1024. }
  1025. #endif
  1026. #if !NET20
  1027. [Test]
  1028. public void MultipleRootPropertiesXDocument()
  1029. {
  1030. string json = @"{""count"": 773840,""photos"": null}";
  1031. ExceptionAssert.Throws<JsonSerializationException>(
  1032. () => { JsonConvert.DeserializeXNode(json); },
  1033. "JSON root object has multiple properties. The root object must have a single property in order to create a valid XML document. Consider specifying a DeserializeRootElementName. Path 'photos', line 1, position 26.");
  1034. }
  1035. #endif
  1036. [Test]
  1037. public void MultipleRootPropertiesAddRootElement()
  1038. {
  1039. string json = @"{""count"": 773840,""photos"": 773840}";
  1040. #if !PORTABLE
  1041. XmlDocument newDoc = JsonConvert.DeserializeXmlNode(json, "myRoot");
  1042. Assert.AreEqual(@"<myRoot><count>773840</count><photos>773840</photos></myRoot>", newDoc.InnerXml);
  1043. #endif
  1044. #if !NET20
  1045. XDocument newXDoc = JsonConvert.DeserializeXNode(json, "myRoot");
  1046. Assert.AreEqual(@"<myRoot><count>773840</count><photos>773840</photos></myRoot>", newXDoc.ToString(SaveOptions.DisableFormatting));
  1047. #endif
  1048. }
  1049. [Test]
  1050. public void NestedArrays()
  1051. {
  1052. string json = @"{
  1053. ""available_sizes"": [
  1054. [
  1055. ""assets/images/resized/0001/1070/11070v1-max-150x150.jpg"",
  1056. ""assets/images/resized/0001/1070/11070v1-max-150x150.jpg""
  1057. ],
  1058. [
  1059. ""assets/images/resized/0001/1070/11070v1-max-250x250.jpg"",
  1060. ""assets/images/resized/0001/1070/11070v1-max-250x250.jpg""
  1061. ],
  1062. [
  1063. ""assets/images/resized/0001/1070/11070v1-max-250x250.jpg""
  1064. ]
  1065. ]
  1066. }";
  1067. #if !PORTABLE || NETSTANDARD1_3
  1068. XmlDocument newDoc = JsonConvert.DeserializeXmlNode(json, "myRoot");
  1069. string xml = IndentXml(newDoc.InnerXml);
  1070. StringAssert.AreEqual(@"<myRoot>
  1071. <available_sizes>
  1072. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1073. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1074. </available_sizes>
  1075. <available_sizes>
  1076. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1077. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1078. </available_sizes>
  1079. <available_sizes>
  1080. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1081. </available_sizes>
  1082. </myRoot>", IndentXml(newDoc.InnerXml));
  1083. #endif
  1084. #if !NET20
  1085. XDocument newXDoc = JsonConvert.DeserializeXNode(json, "myRoot");
  1086. StringAssert.AreEqual(@"<myRoot>
  1087. <available_sizes>
  1088. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1089. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1090. </available_sizes>
  1091. <available_sizes>
  1092. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1093. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1094. </available_sizes>
  1095. <available_sizes>
  1096. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1097. </available_sizes>
  1098. </myRoot>", IndentXml(newXDoc.ToString(SaveOptions.DisableFormatting)));
  1099. #endif
  1100. #if !PORTABLE || NETSTANDARD1_3
  1101. string newJson = JsonConvert.SerializeXmlNode(newDoc, Formatting.Indented);
  1102. Console.WriteLine(newJson);
  1103. #endif
  1104. }
  1105. [Test]
  1106. public void RoundTripNestedArrays()
  1107. {
  1108. string json = @"{
  1109. ""available_sizes"": [
  1110. [
  1111. ""assets/images/resized/0001/1070/11070v1-max-150x150.jpg"",
  1112. ""assets/images/resized/0001/1070/11070v1-max-150x150.jpg""
  1113. ],
  1114. [
  1115. ""assets/images/resized/0001/1070/11070v1-max-250x250.jpg"",
  1116. ""assets/images/resized/0001/1070/11070v1-max-250x250.jpg""
  1117. ],
  1118. [
  1119. ""assets/images/resized/0001/1070/11070v1-max-250x250.jpg""
  1120. ]
  1121. ]
  1122. }";
  1123. #if !PORTABLE || NETSTANDARD1_3
  1124. XmlDocument newDoc = JsonConvert.DeserializeXmlNode(json, "myRoot", true);
  1125. StringAssert.AreEqual(@"<myRoot>
  1126. <available_sizes json:Array=""true"" xmlns:json=""http://james.newtonking.com/projects/json"">
  1127. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1128. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1129. </available_sizes>
  1130. <available_sizes json:Array=""true"" xmlns:json=""http://james.newtonking.com/projects/json"">
  1131. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1132. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1133. </available_sizes>
  1134. <available_sizes json:Array=""true"" xmlns:json=""http://james.newtonking.com/projects/json"">
  1135. <available_sizes json:Array=""true"">assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1136. </available_sizes>
  1137. </myRoot>", IndentXml(newDoc.InnerXml));
  1138. #endif
  1139. #if !NET20
  1140. XDocument newXDoc = JsonConvert.DeserializeXNode(json, "myRoot", true);
  1141. StringAssert.AreEqual(@"<myRoot>
  1142. <available_sizes json:Array=""true"" xmlns:json=""http://james.newtonking.com/projects/json"">
  1143. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1144. <available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes>
  1145. </available_sizes>
  1146. <available_sizes json:Array=""true"" xmlns:json=""http://james.newtonking.com/projects/json"">
  1147. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1148. <available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1149. </available_sizes>
  1150. <available_sizes json:Array=""true"" xmlns:json=""http://james.newtonking.com/projects/json"">
  1151. <available_sizes json:Array=""true"">assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes>
  1152. </available_sizes>
  1153. </myRoot>", IndentXml(newXDoc.ToString(SaveOptions.DisableFormatting)));
  1154. #endif
  1155. #if !PORTABLE || NETSTANDARD1_3
  1156. string newJson = JsonConvert.SerializeXmlNode(newDoc, Formatting.Indented, true);
  1157. StringAssert.AreEqual(json, newJson);
  1158. #endif
  1159. }
  1160. [Test]
  1161. public void MultipleNestedArraysToXml()
  1162. {
  1163. string json = @"{
  1164. ""available_sizes"": [
  1165. [
  1166. [113, 150],
  1167. ""assets/images/resized/0001/1070/11070v1-max-150x150.jpg""
  1168. ],
  1169. [
  1170. [189, 250],
  1171. ""assets/images/resized/0001/1070/11070v1-max-250x250.jpg""
  1172. ],
  1173. [
  1174. [341, 450],
  1175. ""assets/images/resized/0001/1070/11070v1-max-450x450.jpg""
  1176. ]
  1177. ]
  1178. }";
  1179. #if !PORTABLE || NETSTANDARD1_3
  1180. XmlDocument newDoc = JsonConvert.DeserializeXmlNode(json, "myRoot");
  1181. Assert.AreEqual(@"<myRoot><available_sizes><available_sizes><available_sizes>113</available_sizes><available_sizes>150</available_sizes></available_sizes><available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes></available_sizes><available_sizes><available_sizes><available_sizes>189</available_sizes><available_sizes>250</available_sizes></available_sizes><available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes></available_sizes><available_sizes><available_sizes><available_sizes>341</available_sizes><available_sizes>450</available_sizes></available_sizes><available_sizes>assets/images/resized/0001/1070/11070v1-max-450x450.jpg</available_sizes></available_sizes></myRoot>", newDoc.InnerXml);
  1182. #endif
  1183. #if !NET20
  1184. XDocument newXDoc = JsonConvert.DeserializeXNode(json, "myRoot");
  1185. Assert.AreEqual(@"<myRoot><available_sizes><available_sizes><available_sizes>113</available_sizes><available_sizes>150</available_sizes></available_sizes><available_sizes>assets/images/resized/0001/1070/11070v1-max-150x150.jpg</available_sizes></available_sizes><available_sizes><available_sizes><available_sizes>189</available_sizes><available_sizes>250</available_sizes></available_sizes><available_sizes>assets/images/resized/0001/1070/11070v1-max-250x250.jpg</available_sizes></available_sizes><available_sizes><available_sizes><available_sizes>341</available_sizes><available_sizes>450</available_sizes></available_sizes><available_sizes>assets/images/resized/0001/1070/11070v1-max-450x450.jpg</available_sizes></available_sizes></myRoot>", newXDoc.ToString(SaveOptions.DisableFormatting));
  1186. #endif
  1187. }
  1188. #if !PORTABLE || NETSTANDARD1_3
  1189. [Test]
  1190. public void Encoding()
  1191. {
  1192. XmlDocument doc = new XmlDocument

Large files files are truncated, but you can click here to view the full file