2016-09-28 11 views
7

Tôi có một ứng dụng cốt lõi aspnet chạy với cấu hình tiếng Anh không (Tây Ban Nha):ASPNET Lõi Decimal ràng buộc không làm việc trên phi tiếng Anh Culture

public void Configure(IApplicationBuilder app, IHostingEnvironment env, ILoggerFactory loggerFactory) 
    { 
     ...... 
     app.UseRequestLocalization(new RequestLocalizationOptions 
     { 
      DefaultRequestCulture = new RequestCulture(new CultureInfo("es-AR")) 
      ,SupportedCultures = new List<CultureInfo> 
      { 
       new CultureInfo("es-AR") 
      } 
      ,SupportedUICultures = new List<CultureInfo> 
      { 
       new CultureInfo("es") 
      } 
     }); 

     ......... 
    } 

Trong một số thập phân tiếng anh đã phần thập phân của nó phân cách bằng một dấu chấm , nhưng trong Tây Ban Nha một dấu phẩy được sử dụng:

  • 10256,35 tiếng anh
  • 10256,35 Tây Ban Nha

tôi có hành động này trong một bộ điều khiển:

[HttpPost] 
public decimal Test(decimal val) 
{ 
    return val; 
} 

Nếu tôi sử dụng người đưa thư và gửi đến hành động mà một json như thế này {val: 15.30}, sau đó val trong hành động recives 0 (ràng buộc không làm việc vì sự văn hóa). Nếu tôi gửi một json như thế này {val: 15,30} thì trong hành động tôi recive 15.30 Vấn đề tôi có là, tôi cần hành động để chấp nhận số thập phân bằng dấu phẩy, bởi vì đó là định dạng đến từ văn bản loại đầu vào các biểu mẫu của ứng dụng. Nhưng tôi cũng cần phải chấp nhận số thập phân với dấu chấm xuất phát từ yêu cầu ở định dạng json. Không có cách nào để chỉ định một số thập phân/float trong json chấp nhận dấu phẩy (gửi nó dưới dạng chuỗi không phải là một tùy chọn). Tôi có thể làm cái này như thế nào??? Tôi đang lái xe của tôi tự điên với điều này.

Cảm ơn !!

+0

Bạn sẽ cần phải tạo một ModelBinder tùy chỉnh mà đọc 'contentType' và phân tích giá trị tùy thuộc vào loại nội dung –

+0

trong MVC5 Tôi đã sử dụng một mô hình tùy chỉnh chất kết dính và nó giải quyết vấn đề của tôi, cho lõi mvc bạn có thể tìm thấy giải pháp tương tự ở đây [Custom Model Binding trong ASP.Net Core 1.0 (RTM)] (http://intellitect.com/custom-model-binding -in-asp-net-core-1-0 /) – Ziyad

Trả lời

8

Rõ ràng, ràng buộc thập phân trong lõi ASP.NET 1.0.0 không phải là bất biến văn hóa theo mặc định. Mô hình ràng buộc phụ thuộc vào văn hóa máy chủ.

Bạn có thể thay đổi hành vi này bằng cách ràng buộc mô hình tùy chỉnh theo đề xuất của Stephen Muecke. Dưới đây là tôi dựa trên Custom Model Binding in ASP.Net Core 1.0 (RTM)

public class InvariantDecimalModelBinderProvider : IModelBinderProvider 
{ 
    public IModelBinder GetBinder(ModelBinderProviderContext context) 
    { 
     if (context == null) throw new ArgumentNullException(nameof(context)); 

     if (!context.Metadata.IsComplexType && (context.Metadata.ModelType == typeof(decimal) || context.Metadata.ModelType == typeof(decimal?))) 
     { 
      return new InvariantDecimalModelBinder(context.Metadata.ModelType); 
     } 

     return null; 
    } 
} 

public class InvariantDecimalModelBinder : IModelBinder 
{ 
    private readonly SimpleTypeModelBinder _baseBinder; 

    public InvariantDecimalModelBinder(Type modelType) 
    { 
     _baseBinder = new SimpleTypeModelBinder(modelType); 
    } 

    public Task BindModelAsync(ModelBindingContext bindingContext) 
    { 
     if (bindingContext == null) throw new ArgumentNullException(nameof(bindingContext)); 

     var valueProviderResult = bindingContext.ValueProvider.GetValue(bindingContext.ModelName); 

     if (valueProviderResult != ValueProviderResult.None) 
     { 
      bindingContext.ModelState.SetModelValue(bindingContext.ModelName, valueProviderResult); 

      var valueAsString = valueProviderResult.FirstValue; 
      decimal result; 

      // Use invariant culture 
      if (decimal.TryParse(valueAsString, NumberStyles.AllowDecimalPoint | NumberStyles.AllowLeadingSign, CultureInfo.InvariantCulture, out result)) 
      { 
       bindingContext.Result = ModelBindingResult.Success(result); 
       return Task.CompletedTask; 
      } 
     } 

     // If we haven't handled it, then we'll let the base SimpleTypeModelBinder handle it 
     return _baseBinder.BindModelAsync(bindingContext); 
    } 
} 

Và trong Startup.cs:

services.AddMvc(config => 
{ 
    config.ModelBinderProviders.Insert(0, new InvariantDecimalModelBinderProvider()); 
}); 
+1

Chỉ cần nhận xét cho người khác, bản sao/dán này sẽ ngừng các số âm. Để tránh điều đó trong thập phân.TryParse cũng thêm numberStyles.AllowLeadingSign cho kiểu. Thanx rất nhiều – adopilot

+0

Đã chỉnh sửa để thêm NumberStyles.AllowLeadingSign. @ Chuyên ngành kỹ thuật –

Các vấn đề liên quan