question-mark
Stuck on an issue?

Lightrun Answers was designed to reduce the constant googling that comes with debugging 3rd party libraries. It collects links to all the places you might be looking at while hunting down a tough bug.

And, if you’re still stuck at the end, we’re happy to hop on a call to see how we can help out.

Add option to ScalePrecisionValidator to check digits to left of decimal point

See original GitHub issue

System Details

  • FluentValidation version: 8.1.2
  • Web Framework version: ASP.NET Core 2.1

Issue Description

When using ScalePrecisionValidator to validate input that is going to be saved into MS SQL Server, the validation can pass, but then fail to save into SQL Server due to a difference in how SQL Server looks at precision and scale and how FluentValidation is using it.

If you look at the Decimal Type documentation for SQL Server. It says:

s (scale) The number of decimal digits that will be stored to the right of the decimal point. This number is subtracted from p to determine the maximum number of digits to the left of the decimal point.

If you look at the code for ScalePrecisionValidator. It is just checking if (scale > Scale || precision > Precision). It doesn’t care about how many digits are to the left of the decimal point.

It would be nice to add an option so the behavior of ScalePrecisionValidator could be set up to match what SQL Server expects. This could be something like how IgnoreTrailingZeros works so you opt-in to using this different behavior. I can put up a PR for this change, but wanted to double check if it would be a good approach to this since I saw in #151 that it was just recommended to use a custom validator for this. I think it would be useful for this to be built into ScalePrecisionValidator since SQL Server is a commonly used database and its not obvious what is going wrong when you first run into this difference between the two.

Here is an example of a validator that passes, but then fails when the input goes down to SQL Server.

using FluentValidation;

public class TestClass
{
    public decimal Value { get; set; }
}

public class TestValidator : AbstractValidator<TestClass>
{
    public TestValidator()
    {
        RuleFor(x => x.Value).SetValidator(new ScalePrecisionValidator(4, 9) {IgnoreTrailingZeros = true});
    }
}

var testClass = new TestClass{Value = 123456};
var validator = new TestValidator();

// This passes
var result = validator.Validate(testClass);

However if the SQL Server Value column is also set to a scale of 4 and a precision of 9, inserting the value 123456 throws System.Data.SqlClient.SqlException (0x80131904): Error converting data type numeric to decimal.

Issue Analytics

  • State:closed
  • Created 5 years ago
  • Reactions:1
  • Comments:17 (13 by maintainers)

github_iconTop GitHub Comments

1reaction
JeremySkinnercommented, Mar 30, 2020

Ok, sounds good. If you’d like to get this updated then that’d be appreciated and I’ll happily give it a review.

1reaction
JeremySkinnercommented, Mar 26, 2019

I didn’t write it - it was a contribution to the project made in 2012. I assume it was based on this stackoverflow answer from 2009, as the code is very similar, but I don’t know for sure 🤷‍♂️

My understanding was the original intent of the validator was just to validate the scale value and the precision value - validating the number of digits clearly wasn’t the original author’s intent.

As I posted above, I am very open to this being changed if it would make it more useful but the implications of a breaking change have to be considered (both in terms of functionality, and also re-translation of error messsages), which is why I think @KevinHicksSW’s idea of a subclass is better for now. This is currently waiting on @KevinHicksSW (or someone else) to provide an updated PR, at which point I can get it reviewed and merged.

I’m also open to making this the default behaviour in future, but as that’s a breaking change it’d need to be for a major release (9.0 is the next, which I haven’t started working on yet).

Read more comments on GitHub >

github_iconTop Results From Across the Web

Number of digits after decimal point in pandas
You can use pd.set_option to set the decimal number display precision to e.g. 5 in this case: pd.set_option("display.precision", 5). or use:
Read more >
Use decimal tabs to line up numbers with decimal points
In the Customize Format dialog box, select the Numbers tab and in the Decimal symbol drop-down, select the separator you want to use....
Read more >
Slider Decimal Place - Adobe Support Community - 5630095
I am using the slider tool to blur a set of numbers up from 0 to 2.9. Initially, I had the issue that...
Read more >
Fluent validation decimal precision. All other binary floati
Fluent validation decimal precision. All other binary floating point numbers really have more decimal digits, although printout formatting may hide them.
Read more >
Fluent validation number. If you chose so, you'll need to mod
50. 3. To add controller, right-click on the Controller folder, select Add and then select Controller. Here, I want to check validation for...
Read more >

github_iconTop Related Medium Post

No results found

github_iconTop Related StackOverflow Question

No results found

github_iconTroubleshoot Live Code

Lightrun enables developers to add logs, metrics and snapshots to live code - no restarts or redeploys required.
Start Free

github_iconTop Related Reddit Thread

No results found

github_iconTop Related Hackernoon Post

No results found

github_iconTop Related Tweet

No results found

github_iconTop Related Dev.to Post

No results found

github_iconTop Related Hashnode Post

No results found