Рубрики
Без рубрики

Проверка Javax BigDecimal

Краткий и практический обзор проверки BigDecimal с использованием Javax.

Автор оригинала: baeldung.

1. введение

В учебнике Основы валидации Java Bean мы рассмотрели , как применять базовую javax валидацию к различным типам, и в этом учебнике мы сосредоточимся на использовании javax валидации с BigDecimal .

2. Проверка экземпляров BigDecimal

К сожалению, с BigDecimal мы не можем использовать классические @Min или @Max аннотации javax.

К счастью, у нас есть специальный набор аннотаций для работы с ними:

  • @DecimalMin

  • @Цифры

  • @DecimalMax

BigDecimal является первым выбором для финансовых расчетов из-за его высокой точности .

Давайте посмотрим на ваш Счет-фактура класс, который имеет поле типа BigDecimal :

public class Invoice {

    @DecimalMin(value = "0.0", inclusive = false)
    @Digits(integer=3, fraction=2)
    private BigDecimal price;
    private String description;

    public Invoice(BigDecimal price, String description) {
        this.price = price;
        this.description = description;
    }
}

2.1. @DecimalMin

Аннотированный элемент должен быть числом, значение которого больше или равно указанному минимуму. |/@DecimalMin имеет атрибут inclusive , который указывает, является ли указанное минимальное значение включающим или исключающим.

2.2. @DecimalMax

@DecimalMax является аналогом @DecimalMin . Аннотированный элемент должен быть числом, значение которого меньше или равно указанному максимуму. @DecimalMax имеет атрибут inclusive , который указывает, является ли указанное максимальное значение включающим или исключающим.

Кроме того, @Min и @Max принимают только длинные значения. В @DecimalMin и @DecimalMax мы можем указать значение в формате string , которое может быть любого числового типа.

2.3. @Цифры

Во многих случаях нам нужно проверить количество цифр в интеграле части и дроби части десятичного числа.

Аннотация @Digit имеет два атрибута, целое число и дробь , для указания количества разрешенных цифр в интеграле части и дроби части числа .

Согласно официальной документации , integer позволяет нам указать максимальное количество целых цифр, принятых для этого числа . Но это верно только для не десятичных чисел. Для десятичных чисел он проверяет точное количество цифр в целой части числа. Мы увидим это в нашем тестовом примере.

Аналогично, атрибут fraction позволяет нам указать максимальное количество дробных цифр, принятых для этого числа.

2.4. Тестовые случаи

Давайте посмотрим на эти аннотации в действии.

Во-первых, мы добавим тест, который создаст счет-фактуру с недопустимой ценой в соответствии с нашей проверкой и проверит, что проверка завершится неудачей:

public class InvoiceUnitTest {

    private static Validator validator;

    @BeforeClass
    public static void setupValidatorInstance() {
        validator = Validation.buildDefaultValidatorFactory().getValidator();
    }

    @Test
    public void whenPriceIntegerDigitLessThanThreeWithDecimalValue_thenShouldGiveConstraintViolations() {
        Invoice invoice = new Invoice(new BigDecimal(10.21), "Book purchased");
 
        Set> violations = validator.validate(invoice);
 
        assertThat(violations.size()).isEqualTo(1);
        violations.forEach(action -> assertThat(action.getMessage())
                .isEqualTo("numeric value out of bounds (<3 digits>.<2 digits> expected)"));
    }
}

Теперь давайте проверим валидацию с правильной ценой, которая является целочисленным значением:

@Test
public void whenPriceIntegerDigitLessThanThreeWithIntegerValue_thenShouldNotGiveConstraintViolations() {
    Invoice invoice = new Invoice(new BigDecimal(10), "Book purchased");
 
    Set> violations = validator.validate(invoice);
 
    assertThat(violations.size()).isEqualTo(0);
}

Если мы установим цену с более чем 3 цифрами в интегральной части, мы увидим ошибку проверки:

@Test
public void whenPriceIntegerDigitGreaterThanThree_thenShouldGiveConstraintViolations() {
    Invoice invoice = new Invoice(new BigDecimal(1021.21), "Book purchased");
 
    Set> violations = validator.validate(invoice);
 
    assertThat(violations.size()).isEqualTo(1);
    violations.forEach(action -> assertThat(action.getMessage())
      .isEqualTo("numeric value out of bounds (<3 digits>.<2 digits> expected)"));
}

Цена, равная 000.00, также должна подтверждать ограничение:

@Test
public void whenPriceIsZero_thenShouldGiveConstraintViolations() {
    Invoice invoice = new Invoice(new BigDecimal(000.00), "Book purchased");
 
    Set> violations = validator.validate(invoice);
 
    assertThat(violations.size()).isEqualTo(1);
    violations.forEach(action -> assertThat(action.getMessage())
      .isEqualTo("must be greater than 0.0"));
}

Наконец, давайте рассмотрим случай с ценой, которая больше 0:

@Test
public void whenPriceIsGreaterThanZero_thenShouldNotGiveConstraintViolations() {
    Invoice invoice = new Invoice(new BigDecimal(100.50), "Book purchased");
 
    Set> violations = validator.validate(invoice);
 
    assertThat(violations.size()).isEqualTo(0);
}

3. Заключение

В этой статье мы рассмотрели, как использовать javax проверку для BigDecimal.

Все фрагменты кода можно найти на GitHub.