Skip to content

Validate multipleOf with exact decimal arithmetic - #151

Open
jnbdz wants to merge 1 commit into
eclipse-vertx:masterfrom
SiteNetSoft:fix-multipleof-precision
Open

Validate multipleOf with exact decimal arithmetic#151
jnbdz wants to merge 1 commit into
eclipse-vertx:masterfrom
SiteNetSoft:fix-multipleof-precision

Conversation

@jnbdz

@jnbdz jnbdz commented Aug 9, 2026

Copy link
Copy Markdown
Contributor

Fixes #106

Motivation

#106 reported multipleOf: 0.001 rejecting values like 1.001, 1.01, 1.02 in the legacy 4.x MultipleOfValidatorFactory. Those cases already pass in the current validator thanks to its epsilon workaround — but the workaround has the opposite defect: the epsilon is absolute (1.1920929e-7, FLT_EPSILON), so any multipleOf smaller than the epsilon accepts every value. For example 0.00000015 validates against multipleOf: 0.0000001 even though it is 1.5× the divisor — a false accept that matters for schemas describing high-precision quantities (8-decimal currency amounts, coordinates).

Changes

Replace the epsilon comparison with an exact remainder computed via BigDecimal on the decimal representation (BigDecimal.valueOf, which the existing toBigDecimal helper already uses). This makes the check exact for the decimal values users write in schemas and instances:

  • the Incorrect Vert.x Open API 'multipleOf' validation #106 cases (1.001 / 0.001 etc.) remain valid — binary rounding artifacts no longer need an epsilon;
  • non-multiples below the old epsilon are now correctly rejected;
  • non-finite values and a zero divisor keep the previous lenient behavior (no error) instead of throwing.

Numbers.remainder had no other callers and is replaced by Numbers.isMultipleOf. The official test-suite multipleOf cases (small numbers, 1e308 overflow with multipleOf: 0.5, float-division-inf) all pass unchanged; full suite green.

Added regression tests covering the #106 values and the sub-epsilon false-accept cases.

The multipleOf check compared a binary floating point remainder against
an absolute epsilon (FLT_EPSILON). This falsely accepts any value when
multipleOf is smaller than the epsilon itself, e.g. 0.00000015 passed
validation against multipleOf 0.0000001. Compute the remainder with
BigDecimal on the decimal representation instead, which removes the
epsilon workaround and its false accepts while keeping the rounding
artifact cases (1.001 with multipleOf 0.001) valid.

Fixes eclipse-vertx#106
@jnbdz
jnbdz force-pushed the fix-multipleof-precision branch from 90642b3 to 742d9a2 Compare August 9, 2026 17:16
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

Incorrect Vert.x Open API 'multipleOf' validation

1 participant