From 670605ce91cc5ef3ebdbdf278e136919810d3809 Mon Sep 17 00:00:00 2001 From: MattMo Date: Wed, 10 Jul 2024 06:37:02 -0700 Subject: [PATCH] Bumped package version to 1.8.5. Added enum route argument converting support. Cleaned up code and added unit test. --- Rest.Net.Tests/RouteArgumentConverterTests.cs | 41 ++++++++++ Rest.Net/Rest.Net.csproj | 2 +- Rest.Net/RouteArgumentConverter.cs | 78 +++++++++++++------ 3 files changed, 98 insertions(+), 23 deletions(-) create mode 100644 Rest.Net.Tests/RouteArgumentConverterTests.cs diff --git a/Rest.Net.Tests/RouteArgumentConverterTests.cs b/Rest.Net.Tests/RouteArgumentConverterTests.cs new file mode 100644 index 0000000..85204b3 --- /dev/null +++ b/Rest.Net.Tests/RouteArgumentConverterTests.cs @@ -0,0 +1,41 @@ +using System; +using System.Collections.Generic; +using System.Linq; +using System.Text; +using System.Threading.Tasks; +using FluentAssertions; +using MontoyaTech.Rest.Net; +using Xunit; + +namespace Rest.Net.Tests +{ + public class RouteArgumentConverterTests + { + public enum TestEnum : long + { + A = 1, + B = 2, + C = 3 + } + + [Fact] + public static void RouteArgumentConverter_Should_Convert_To_Enum() + { + var converted = RouteArgumentConverter.Convert("1"); + + converted.GetType().IsEquivalentTo(typeof(TestEnum)).Should().BeTrue(); + + converted.Should().Be(TestEnum.A); + } + + [Fact] + public static void RouteArgumentConverter_Should_Convert_OutOfRange_To_Enum() + { + var converted = RouteArgumentConverter.Convert("4"); + + converted.GetType().IsEquivalentTo(typeof(TestEnum)).Should().BeTrue(); + + ((int)converted).Should().Be(4); + } + } +} diff --git a/Rest.Net/Rest.Net.csproj b/Rest.Net/Rest.Net.csproj index a3a208e..d4d765f 100644 --- a/Rest.Net/Rest.Net.csproj +++ b/Rest.Net/Rest.Net.csproj @@ -17,7 +17,7 @@ MontoyaTech.Rest.Net MontoyaTech.Rest.Net True - 1.8.4 + 1.8.5 Logo_Symbol_Black_Outline.png diff --git a/Rest.Net/RouteArgumentConverter.cs b/Rest.Net/RouteArgumentConverter.cs index 9bb4f67..137ac67 100644 --- a/Rest.Net/RouteArgumentConverter.cs +++ b/Rest.Net/RouteArgumentConverter.cs @@ -19,96 +19,130 @@ namespace MontoyaTech.Rest.Net /// public static T Convert(string input) { - var typeCode = Type.GetTypeCode(typeof(T)); + var result = Convert(typeof(T), input); - if (typeCode == TypeCode.String) + if (result == null) + return default(T); + + return (T)result; + } + + /// + /// Converts a string to a given type if possible. Otherwise returns null. + /// + /// + /// + /// + public static object Convert(Type type, string input) + { + var typeCode = Type.GetTypeCode(type); + + if (type.IsEnum) { - return (dynamic)input; + return Enum.Parse(type, input, true); + } + else if (typeCode == TypeCode.String) + { + return input; } else if (typeCode == TypeCode.Object) { - var castOperator = typeof(T).GetMethod("op_Explicit", new[] { typeof(string) }); + var castOperator = type.GetMethod("op_Explicit", new[] { typeof(string) }); if (castOperator == null) - return default(T); + return null; - return (T)castOperator.Invoke(null, new[] { input }); + return castOperator.Invoke(null, new[] { input }); } else if (typeCode == TypeCode.Double) { double.TryParse(input, out double result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.Single) { float.TryParse(input, out float result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.Decimal) { decimal.TryParse(input, out decimal result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.Int64) { long.TryParse(input, out long result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.Int32) { int.TryParse(input, out int result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.Int16) { short.TryParse(input, out short result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.SByte) { sbyte.TryParse(input, out sbyte result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.UInt64) { ulong.TryParse(input, out ulong result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.UInt32) { uint.TryParse(input, out uint result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.UInt16) { ushort.TryParse(input, out ushort result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.Byte) { byte.TryParse(input, out byte result); - return (dynamic)result; + + return result; } else if (typeCode == TypeCode.Boolean) { if (input == "f" || input == "0" || input == "F") - return (dynamic)false; + return false; bool.TryParse(input, out bool result); - return ((dynamic)result); + + return result; } else if (typeCode == TypeCode.DateTime) { DateTime.TryParse(input, out DateTime result); - return ((dynamic)result); + + return result; } else if (typeCode == TypeCode.Char) { char.TryParse(input, out char result); - return ((dynamic)result); + + return result; } - return default(T); + return null; } } } \ No newline at end of file