121 lines
5.5 KiB
C#
121 lines
5.5 KiB
C#
using Lskj.Util;
|
|
using Newtonsoft.Json;
|
|
using System;
|
|
using System.Data;
|
|
|
|
namespace Lskj.Util.Tests
|
|
{
|
|
internal static class Program
|
|
{
|
|
private static int Main()
|
|
{
|
|
try
|
|
{
|
|
PreservesStylesObjectAsCompactJson();
|
|
PreservesArrayAsCompactJson();
|
|
NormalizesEveryValueInAMixedComplexColumn();
|
|
LeavesScalarColumnsEquivalentToExistingConverter();
|
|
AcceptsSingleObject();
|
|
RejectsInvalidTopLevelValues();
|
|
Console.WriteLine("PASS: JsonUtil complex-value conversion tests");
|
|
return 0;
|
|
}
|
|
catch (Exception ex)
|
|
{
|
|
Console.Error.WriteLine(ex);
|
|
return 1;
|
|
}
|
|
}
|
|
|
|
private static void PreservesStylesObjectAsCompactJson()
|
|
{
|
|
const string json = "[{\"id\":1,\"$styles\":{\"rowstyle\":\"{color:'#FFFF00','background-color':'#FF0000'}\"}}]";
|
|
DataTable table = JsonUtil.ToDataTablePreservingComplexValues(json);
|
|
AssertEqual(1, table.Rows.Count, "styles row count");
|
|
AssertEqual("{\"rowstyle\":\"{color:'#FFFF00','background-color':'#FF0000'}\"}",
|
|
table.Rows[0]["$styles"].ToString(), "styles JSON");
|
|
}
|
|
|
|
private static void PreservesArrayAsCompactJson()
|
|
{
|
|
const string json = "[{\"id\":1,\"items\":[{\"code\":\"A\"},{\"code\":\"B\"}]}]";
|
|
DataTable table = JsonUtil.ToDataTablePreservingComplexValues(json);
|
|
AssertEqual("[{\"code\":\"A\"},{\"code\":\"B\"}]",
|
|
table.Rows[0]["items"].ToString(), "array JSON");
|
|
}
|
|
|
|
private static void NormalizesEveryValueInAMixedComplexColumn()
|
|
{
|
|
const string json = "["
|
|
+ "{\"id\":1,\"payload\":5},"
|
|
+ "{\"id\":2,\"payload\":{\"code\":\"A\"}},"
|
|
+ "{\"id\":3,\"payload\":[1,2]},"
|
|
+ "{\"id\":4,\"payload\":null},"
|
|
+ "{\"id\":5,\"payload\":\"ready\"}]";
|
|
DataTable table = JsonUtil.ToDataTablePreservingComplexValues(json);
|
|
AssertEqual(typeof(string), table.Columns["payload"].DataType, "mixed column type");
|
|
AssertEqual("5", table.Rows[0]["payload"].ToString(), "numeric scalar text");
|
|
AssertEqual("{\"code\":\"A\"}", table.Rows[1]["payload"].ToString(), "object text");
|
|
AssertEqual("[1,2]", table.Rows[2]["payload"].ToString(), "array text");
|
|
AssertTrue(table.Rows[3].IsNull("payload"), "null remains null");
|
|
AssertEqual("ready", table.Rows[4]["payload"].ToString(), "string remains string");
|
|
}
|
|
|
|
private static void LeavesScalarColumnsEquivalentToExistingConverter()
|
|
{
|
|
const string json = "[{\"id\":1,\"title\":\"A\",\"active\":true},{\"id\":2,\"title\":\"B\",\"active\":false}]";
|
|
DataTable expected = JsonConvert.DeserializeObject<DataTable>(json);
|
|
DataTable actual = JsonUtil.ToDataTablePreservingComplexValues(json);
|
|
AssertEqual(expected.Columns.Count, actual.Columns.Count, "scalar column count");
|
|
AssertEqual(expected.Rows.Count, actual.Rows.Count, "scalar row count");
|
|
foreach (DataColumn column in expected.Columns)
|
|
{
|
|
AssertEqual(column.DataType, actual.Columns[column.ColumnName].DataType,
|
|
"scalar column type " + column.ColumnName);
|
|
for (int rowIndex = 0; rowIndex < expected.Rows.Count; rowIndex++)
|
|
{
|
|
AssertEqual(expected.Rows[rowIndex][column.ColumnName],
|
|
actual.Rows[rowIndex][column.ColumnName],
|
|
"scalar value " + column.ColumnName + " row " + rowIndex);
|
|
}
|
|
}
|
|
}
|
|
|
|
private static void AcceptsSingleObject()
|
|
{
|
|
const string json = "{\"ProductId\":\"P001\",\"meta\":{\"source\":\"web\"}}";
|
|
DataTable table = JsonUtil.ToDataTablePreservingComplexValues(json);
|
|
AssertEqual(1, table.Rows.Count, "single object row count");
|
|
AssertEqual("P001", table.Rows[0]["ProductId"].ToString(), "single object scalar");
|
|
AssertEqual("{\"source\":\"web\"}", table.Rows[0]["meta"].ToString(), "single object nested JSON");
|
|
}
|
|
|
|
private static void RejectsInvalidTopLevelValues()
|
|
{
|
|
AssertThrows<ArgumentException>(delegate { JsonUtil.ToDataTablePreservingComplexValues(" "); }, "empty input");
|
|
AssertThrows<JsonReaderException>(delegate { JsonUtil.ToDataTablePreservingComplexValues("{"); }, "invalid JSON");
|
|
AssertThrows<JsonSerializationException>(delegate { JsonUtil.ToDataTablePreservingComplexValues("[1]"); }, "non-object row");
|
|
}
|
|
|
|
private static void AssertThrows<TException>(Action action, string name) where TException : Exception
|
|
{
|
|
try { action(); }
|
|
catch (TException) { return; }
|
|
throw new InvalidOperationException("Expected " + typeof(TException).Name + ": " + name);
|
|
}
|
|
|
|
private static void AssertTrue(bool value, string name)
|
|
{
|
|
if (!value) throw new InvalidOperationException("Assertion failed: " + name);
|
|
}
|
|
|
|
private static void AssertEqual<T>(T expected, T actual, string name)
|
|
{
|
|
if (!object.Equals(expected, actual))
|
|
{
|
|
throw new InvalidOperationException(name + ": expected <" + expected + ">, actual <" + actual + ">");
|
|
}
|
|
}
|
|
}
|
|
}
|