konform-kt / konform

Portable validations for Kotlin
https://www.konform.io
MIT License
651 stars 39 forks source link

Custom validations called with `run(...)` do not set a `dataPath` in the `ValidationResult` #37

Closed cies closed 2 years ago

cies commented 2 years ago
    val validator = Validation<FormDto> {

      val validateDiscountedUntil = Validation<FormDto> {
        addConstraint("When specifying a discount until date, it should be in the future") {
          if (it.discountUntil == null) {
              true
          } else {
              it.discountUntil > LocalDate.now()
          }
        }
      }
      FormDto::discountUntil {
        run(validateDiscountedUntil)
      }
    }

Gives me:

Invalid(errors=[ValidationError(dataPath=, message=When specifying a discount until date, it should be in the future)])

I find this weird behavior as I do specify it on FormDto::discountUntil

YokiToki commented 2 years ago

@cies That is problem. You add constraint in the ValidationBuilder<FormDto> context, but run add validation to prebuiltValidations without property context. I have the same problem, and since the library is no longer maintained, a fork seems to be the best solution.

nlochschmidt commented 2 years ago

Something isn't quite right here.

The validateDiscountedUntil is defined as a Validation on FormDto. However in this case the intended use seems to be to validate the discountUntil field, so it should be a LocalDate?

e.g. this works as expected:

val validator = Validation<FormDto> {
    val validateDiscountedUntil = Validation<LocalDate?> {
        addConstraint("When specifying a discount until date, it should be in the future") {
            if (it == null) {
                true
            } else {
                it > LocalDate.now()
            }
        }
    }
    FormDto::discountUntil {
        run(validateDiscountedUntil)
    }
}

and gives back:

 Invalid(errors=[ValidationError(dataPath=.discountUntil, message=When specifying a discount until date, it should be in the future)])

The bug here is that there is a missing a dsl marker to prevent the inner run to access the run of the outer scope opened by Validation<FormDto> { in the first line.