Skip to content

Adding globalization for decimal, double and single for conversion. #97

New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Merged
merged 1 commit into from
Jul 18, 2015
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
42 changes: 42 additions & 0 deletions JSONAPI.Tests/ActionFilters/DefaultFilteringTransformerTests.cs
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
using System;
using System.Collections.Generic;
using System.Globalization;
using System.Linq;
using System.Net;
using System.Net.Http;
using System.Threading;
using System.Web.Http;
using FluentAssertions;
using JSONAPI.ActionFilters;
Expand Down Expand Up @@ -689,6 +691,19 @@ public void Filters_by_matching_decimal_property()
returnedArray[0].Id.Should().Be("170");
}

[TestMethod]
public void Filters_by_matching_decimal_property_non_en_US()
{
var currentCulture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = new CultureInfo("se-SE");

var returnedArray = GetArray("http://api.example.com/dummies?filter[decimal-field]=4.03");
returnedArray.Length.Should().Be(1);
returnedArray[0].Id.Should().Be("170");

Thread.CurrentThread.CurrentCulture = currentCulture;
}

[TestMethod]
public void Filters_by_missing_decimal_property()
{
Expand Down Expand Up @@ -1039,6 +1054,20 @@ public void Filters_by_matching_single_property()
returnedArray[0].Id.Should().Be("370");
}

[TestMethod]
public void Filters_by_matching_single_property_non_en_US()
{
var currentCulture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = new CultureInfo("se-SE");

var returnedArray = GetArray("http://api.example.com/dummies?filter[single-field]=21.56901");
returnedArray.Length.Should().Be(1);
returnedArray[0].Id.Should().Be("370");

Thread.CurrentThread.CurrentCulture = currentCulture;
}


[TestMethod]
public void Filters_by_missing_single_property()
{
Expand Down Expand Up @@ -1074,6 +1103,19 @@ public void Filters_by_matching_double_property()
returnedArray[0].Id.Should().Be("390");
}

[TestMethod]
public void Filters_by_matching_double_property_non_en_US()
{
var currentCulture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = new CultureInfo("se-SE");

var returnedArray = GetArray("http://api.example.com/dummies?filter[double-field]=12.3453489012");
returnedArray.Length.Should().Be(1);
returnedArray[0].Id.Should().Be("390");

Thread.CurrentThread.CurrentCulture = currentCulture;
}

[TestMethod]
public void Filters_by_missing_double_property()
{
Expand Down
20 changes: 20 additions & 0 deletions JSONAPI.Tests/Core/ResourceTypeRegistrarTests.cs
Original file line number Diff line number Diff line change
Expand Up @@ -7,7 +7,9 @@
using System.Collections.Generic;
using System.Collections;
using System.Diagnostics;
using System.Globalization;
using System.Linq;
using System.Threading;
using FluentAssertions;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
Expand Down Expand Up @@ -561,6 +563,24 @@ public void BuildRegistration_sets_up_correct_attribute_for_Decimal_field()
AssertAttribute(reg, "decimal-field", null, 0m, "0", g => g.DecimalField);
}

[TestMethod]
public void BuildRegistration_sets_up_correct_attribute_for_Decimal_field_non_en_US()
{
// Set up non US culture
var culture = Thread.CurrentThread.CurrentCulture;
Thread.CurrentThread.CurrentCulture = new CultureInfo("se-SE");

// Arrange
var registrar = new ResourceTypeRegistrar(new DefaultNamingConventions(new PluralizationService()));

// Act
var reg = registrar.BuildRegistration(typeof(AttributeGrabBag));

AssertAttribute(reg, "decimal-field", "20000000000.1234", 20000000000.1234m, "20000000000.1234", g => g.DecimalField);

Thread.CurrentThread.CurrentCulture = culture;
}

[TestMethod]
public void BuildRegistration_sets_up_correct_attribute_for_nullable_Decimal_field()
{
Expand Down
12 changes: 10 additions & 2 deletions JSONAPI/Core/DecimalAttributeValueConverter.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using System;
using System.Globalization;
using System.Reflection;
using Newtonsoft.Json;
using Newtonsoft.Json.Linq;
Expand Down Expand Up @@ -26,7 +27,14 @@ public JToken GetValue(object resource)
{
var value = _property.GetValue(resource);
if (value == null) return null;
return value.ToString();
try
{
return ((Decimal)value).ToString(CultureInfo.InvariantCulture);
}
catch (InvalidCastException e)
{
throw new JsonSerializationException("Could not serialize decimal value.", e);
}
}

public void SetValue(object resource, JToken value)
Expand All @@ -37,7 +45,7 @@ public void SetValue(object resource, JToken value)
{
var stringTokenValue = value.Value<string>();
Decimal d;
if (!Decimal.TryParse(stringTokenValue, out d))
if (!Decimal.TryParse(stringTokenValue, NumberStyles.Any, CultureInfo.InvariantCulture, out d))
throw new JsonSerializationException("Could not parse decimal value.");
_property.SetValue(resource, d);
}
Expand Down
13 changes: 7 additions & 6 deletions JSONAPI/QueryableTransformers/DefaultFilteringTransformer.cs
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
using System;
using System.Globalization;
using System.Linq;
using System.Linq.Expressions;
using System.Net;
Expand Down Expand Up @@ -248,40 +249,40 @@ private Expression GetPredicateBodyForField(ResourceTypeAttribute resourceTypeAt
else if (propertyType == typeof(Single))
{
Single value;
expr = Single.TryParse(queryValue, out value)
expr = Single.TryParse(queryValue, NumberStyles.Any, CultureInfo.InvariantCulture, out value)
? GetPropertyExpression(value, prop, param)
: Expression.Constant(false);
}
else if (propertyType == typeof(Single?))
{
Single tmp;
var value = Single.TryParse(queryValue, out tmp) ? tmp : (Single?)null;
var value = Single.TryParse(queryValue, NumberStyles.Any, CultureInfo.InvariantCulture, out tmp) ? tmp : (Single?)null;
expr = GetPropertyExpression(value, prop, param);
}
else if (propertyType == typeof(Double))
{
Double value;
expr = Double.TryParse(queryValue, out value)
expr = Double.TryParse(queryValue, NumberStyles.Any, CultureInfo.InvariantCulture, out value)
? GetPropertyExpression(value, prop, param)
: Expression.Constant(false);
}
else if (propertyType == typeof(Double?))
{
Double tmp;
var value = Double.TryParse(queryValue, out tmp) ? tmp : (Double?)null;
var value = Double.TryParse(queryValue, NumberStyles.Any, CultureInfo.InvariantCulture, out tmp) ? tmp : (Double?)null;
expr = GetPropertyExpression(value, prop, param);
}
else if (propertyType == typeof(Decimal))
{
Decimal value;
expr = Decimal.TryParse(queryValue, out value)
expr = Decimal.TryParse(queryValue, NumberStyles.Any, CultureInfo.InvariantCulture, out value)
? GetPropertyExpression(value, prop, param)
: Expression.Constant(false);
}
else if (propertyType == typeof(Decimal?))
{
Decimal tmp;
var value = Decimal.TryParse(queryValue, out tmp) ? tmp : (Decimal?)null;
var value = Decimal.TryParse(queryValue, NumberStyles.Any, CultureInfo.InvariantCulture, out tmp) ? tmp : (Decimal?)null;
expr = GetPropertyExpression(value, prop, param);
}
else if (propertyType == typeof(DateTime))
Expand Down