Перейти к основному содержимому

Проверка Javax BigDecimal

· 3 мин. чтения

1. Введение

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

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

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

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

@DecimalMin

@Цифры

  • @DecimalMax

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

Давайте посмотрим на наш класс Invoice , который имеет поле типа 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 имеет включающий атрибут , который указывает, является ли указанное минимальное значение включающим или исключающим.

2.2. @DecimalMax

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

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

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 whenMoreThanThreeIntegerDigits_thenShouldGiveConstraintViolations() {
Invoice invoice = new Invoice(new BigDecimal("1021.21"), "Book purchased");
Set<ConstraintViolation<Invoice>> violations = validator.validate(invoice);
assertThat(violations).hasSize(1);
assertThat(violations)
.extracting("message")
.containsOnly("numeric value out of bounds (<3 digits>.<2 digits> expected)");
}
}

Теперь давайте проверим валидацию с правильной ценой:

@Test
public void whenLessThanThreeIntegerDigits_thenShouldNotGiveConstraintViolations() {
Invoice invoice = new Invoice(new BigDecimal("10.21"), "Book purchased");
Set<ConstraintViolation<Invoice>> violations = validator.validate(invoice);
assertThat(violations).isEmpty();
}

Аналогичным образом посмотрим, как работает проверка для дробной части:

@Test
public void whenTwoFractionDigits_thenShouldNotGiveConstraintViolations() {
Invoice invoice = new Invoice(new BigDecimal("99.99"), "Book purchased");
Set<ConstraintViolation<Invoice>> violations = validator.validate(invoice);
assertThat(violations).isEmpty();
}

@Test
public void whenMoreThanTwoFractionDigits_thenShouldGiveConstraintViolations() {
Invoice invoice = new Invoice(new BigDecimal("99.999"), "Book purchased");
Set<ConstraintViolation<Invoice>> violations = validator.validate(invoice);
assertThat(violations).hasSize(1);
assertThat(violations)
.extracting("message")
.containsOnly("numeric value out of bounds (<3 digits>.<2 digits> expected)");
}

Цена, равная 0,00, должна нарушать наше ограничение:

@Test
public void whenPriceIsZero_thenShouldGiveConstraintViolations() {
Invoice invoice = new Invoice(new BigDecimal("0.00"), "Book purchased");
Set<ConstraintViolation<Invoice>> violations = validator.validate(invoice);
assertThat(violations).hasSize(1);
assertThat(violations)
.extracting("message")
.containsOnly("must be greater than 0.0");
}

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

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

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

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

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