[JAVA] Übergeben eines anderen Werts als des Annotation-Attributs an die Nachricht Hibernate Validator (Bean Validation) (Einbettungsmethode)

Sie können den in der Einschränkungsanmerkung angegebenen Attributwert wie folgt in die Bean-Validierungsfehlermeldung einbetten. (Beachten Sie, dass der in diesem Eintrag behandelte Inhalt von der Verwendung des Hibernate Validator abhängt.)

Beispiel für eine Constraint-Annotation-Spezifikation


@Size(min = 4, max = 16)
private String foo;

Beispiel für die Ausführung der Validierung


// ...
Bean bean = new Bean();
bean.foo = "123";
Set<ConstraintViolation<Bean>> violations = vb.validate(bean);
// ...

Die im obigen Fall generierte Fehlermeldung lautet "Größe muss zwischen 4 und 16 liegen".

Der Hintergrund, den ich anders als den Wert des Anmerkungsattributs einbetten wollte, ist ...

In dem Fall, an dem ich gerade arbeite, musste ich den Referenzwert, auf den zum Zeitpunkt der Eingabeprüfung verwiesen werden sollte, von der externen Einstellung (eigentlich der Eigenschaftendatei) abrufen. Es gab eine Option zum Überprüfen mit Logik ohne Verwendung der Bean-Validierung, aber ich wollte den Bean-Validierungsmechanismus so weit wie möglich für die Eingabeprüfung verwenden, daher habe ich untersucht, wie dies mit der Bean-Validierung realisiert werden kann.

Welche Art von Einschränkungsanmerkung haben Sie speziell vorgenommen?

Obwohl es nicht tatsächlich erstellt wurde, habe ich beschlossen, eine Anmerkung zu erstellen, die überprüft, ob das Datum nach der angegebenen Anzahl von Tagen liegt, und eine Einschränkungsanmerkung zu erstellen, die den Teil mit der angegebenen Anzahl von Tagen aus der Eigenschaftendatei abruft. ..

Beispiel für das Erstellen einer Einschränkungsanmerkung


@DaysLater(days = "foo.daysLater", defaultValue = 5)
private LocalDate fooDate;

Beispiel für die Einstellung von Eigenschaftendateien


foo.daysLater=10

src/main/resources/ValidationMessages.Beispiel für die Einstellung von Eigenschaften


com.example.validation.DaysLater.message = must be {days} days later

Ich konnte es überprüfen, aber die Nachricht ist enttäuschend ...

Ich möchte sagen "muss 10 Tage später sein" als Fehlermeldung, wenn die Einschränkung verletzt wird ... Leider ist das Standardverhalten "muss foo.daysLater Tage später sein". Nun, es ist ein natürliches Ergebnis ...

Ist es möglich, die Bean Validation-Spezifikationen einzuhalten?

Ich habe es nicht richtig recherchiert, aber als ich mir die Spezifikationen ansah, schien es keine Möglichkeit zu geben, innerhalb der Bean Validation-Spezifikationen damit umzugehen. Da die EL-Formel jedoch beim Zusammenstellen der Nachricht verwendet werden kann, kann sie möglicherweise durch Beherrschen der EL-Formel verarbeitet werden.

Es kann mithilfe der Erweiterungsfunktion von Hibernate Validator unterstützt werden!

Bei Verwendung von Erweiterung von Hibernate Validation wird die Nachricht angezeigt Sie können die Werte ändern, auf die in der Definition verwiesen werden kann.


private int value; //Speichern Sie den Eigenschaftswert aus dem Attributwert (Eigenschaftsschlüssel) der Anmerkung

// ...

public boolean isValid(LocalDate targetValue, ConstraintValidatorContext context) {

  boolean result = //Überprüfen Sie, ob der Inhalt weggelassen wurde...
  
    //Wenn die Prüfung NG lautet, wird die Standardoperation ungültig und es werden Informationen zu willkürlichen Einschränkungsverletzungen generiert.
  if (!result) {
    //Konvertieren Sie in die von Hibernate Validator bereitgestellte Schnittstelle, um die Erweiterung von Hibernate Validator zu verwenden
    HibernateConstraintValidatorContext hibernateContext =
        context.unwrap(HibernateConstraintValidatorContext.class);

    //Deaktivieren Sie die Generierung von Informationen zu Standardbeschränkungsverletzungen
    hibernateContext.disableDefaultConstraintViolation();

    //Generieren Sie Informationen zu Verstößen gegen beliebige Einschränkungen
    hibernateContext
        //In der Nachrichtendefinition{value}Um auf den Wert mit verweisen zu können
        .addMessageParameter("days", this.days)
        //Ermöglichen Sie, dass der Wert durch den Wert des Variablennamens im EL-Ausdruck in der Nachrichtendefinition referenziert wird
        .addExpressionVariable("days", this.days)
        //Die Nachrichtenvorlage verwendet die in der Anmerkung angegebene Vorlage (wie das Standardverhalten).
        .buildConstraintViolationWithTemplate(hibernateContext.getDefaultConstraintMessageTemplate())
        //Informationen zu Einschränkungsverletzungen hinzufügen
        .addConstraintViolation();
  }
  return result;
}

Mit der obigen Implementierung ist es möglich, den dem Eigenschaftsschlüssel entsprechenden Wert anstelle des Eigenschaftsschlüssels in die Nachricht einzubetten. Durch Verwendung dieses Mechanismus ist es auch möglich, ein "Datum, an dem die Prüfung in Ordnung ist" in die Nachricht einzubetten.

public boolean isValid(LocalDate targetValue, ConstraintValidatorContext context) {

  LocalDate validMinDate = LocalDate.now().plusDays(value);
  boolean result = //Überprüfen Sie, ob der Inhalt weggelassen wurde...
  
  if (!result) {
    HibernateConstraintValidatorContext hibernateContext =
        context.unwrap(HibernateConstraintValidatorContext.class);
    hibernateContext.disableDefaultConstraintViolation();
    hibernateContext
        .addMessageParameter("days", this.days)
        .addExpressionVariable("days", this.days)
        //Das Datum hinzugefügt, an dem die Prüfung in Ordnung ist
        .addMessageParameter("validMinDate", validMinDate)
        .addExpressionVariable("validMinDate", validMinDate)
        .buildConstraintViolationWithTemplate(hibernateContext.getDefaultConstraintMessageTemplate())
        .addConstraintViolation();
  }
  return result;
}

src/main/resources/ValidationMessages.properties


com.example.validation.DaysLater.message = must be {validMinDate} or later

Die Fehlermeldung bei Verletzung der Einschränkung lautet "muss 2018-09-26 oder höher sein". Dies kann eine intuitivere Meldung sein.

Zusammenfassung

Wenn es eine Voraussetzung ist, auf Hibernate Validator ausgeführt zu werden, ist es mit der diesmal eingeführten Erweiterung einfacher, Nachrichten mit hoher Benutzerfreundlichkeit zu verfassen. Das Projekt, an dem ich gerade arbeite, kann auf dem Hivernate Validator ausgeführt werden. Daher denke ich darüber nach, diesen Mechanismus effektiv zu nutzen.

Recommended Posts

Übergeben eines anderen Werts als des Annotation-Attributs an die Nachricht Hibernate Validator (Bean Validation) (Einbettungsmethode)
So erstellen Sie eine Methode
[Swift5] So kommunizieren Sie von ViewController zu Model und übergeben einen Wert
So übergeben Sie den Wert an einen anderen Bildschirm