Überprüfen mit der IDataErrorInfo-Schnittstelle (VB)
von Stephen Walther
Stephen Walther zeigt Ihnen, wie Sie benutzerdefinierte Validierungsfehlermeldungen anzeigen, indem Sie die IDataErrorInfo-Schnittstelle in einer Modellklasse implementieren.
Das Ziel dieses Tutorials besteht darin, einen Ansatz zum Durchführen der Validierung in einer ASP.NET MVC-Anwendung zu erläutern. Sie erfahren, wie Sie verhindern können, dass jemand ein HTML-Formular übermittelt, ohne Werte für erforderliche Formularfelder bereitzustellen. In diesem Tutorial erfahren Sie, wie Sie die Überprüfung mithilfe der IErrorDataInfo-Schnittstelle durchführen.
Annahmen
In diesem Tutorial verwende ich die MoviesDB-Datenbank und die Movies-Datenbanktabelle. Diese Tabelle weist die folgenden Spalten auf:
Spaltenname | Datentyp | NULL-Werte zulassen |
---|---|---|
Id | Int | False |
Titel | Nvarchar(100) | False |
Regisseur | Nvarchar(100) | False |
DateReleased | Datetime | False |
In diesem Tutorial verwende ich microsoft Entity Framework, um meine Datenbankmodellklassen zu generieren. Die vom Entity Framework generierte Movie-Klasse wird in Abbildung 1 angezeigt.
Abbildung 01: Die Movie-Entität(Klicken Sie hier, um das Bild in voller Größe anzuzeigen)
Hinweis
Weitere Informationen zur Verwendung von Entity Framework zum Generieren Ihrer Datenbankmodellklassen finden Sie in meinem Tutorial zum Erstellen von Modellklassen mit dem Entity Framework.
Die Controllerklasse
Wir verwenden den Home-Controller, um Filme auflisten und neue Filme zu erstellen. Der Code für diese Klasse ist in Listing 1 enthalten.
Auflistung 1: Controllers\HomeController.vb
Public Class HomeController
Inherits Controller
Private _db As New MoviesDBEntities()
Public Function Index() As ActionResult
Return View(_db.MovieSet.ToList())
End Function
Public Function Create() As ActionResult
Return View()
End Function
<AcceptVerbs(HttpVerbs.Post)> _
Public Function Create(<Bind(Exclude := "Id")> ByVal movieToCreate As Movie) As ActionResult
' Validate
If (Not ModelState.IsValid) Then
Return View()
End If
' Add to database
Try
_db.AddToMovieSet(movieToCreate)
_db.SaveChanges()
Return RedirectToAction("Index")
Catch
Return View()
End Try
End Function
End Class
Die Home-Controllerklasse in Listing 1 enthält zwei Create()-Aktionen. Die erste Aktion zeigt das HTML-Formular zum Erstellen eines neuen Films an. Die zweite Create()-Aktion führt die tatsächliche Einfügung des neuen Films in die Datenbank aus. Die zweite Create()-Aktion wird aufgerufen, wenn das formular, das von der ersten Create()-Aktion angezeigt wird, an den Server übermittelt wird.
Beachten Sie, dass die zweite Create()-Aktion die folgenden Codezeilen enthält:
' Validate
If (Not ModelState.IsValid) Then
Return View()
End If
Die IsValid-Eigenschaft gibt false zurück, wenn ein Validierungsfehler vorliegt. In diesem Fall wird die Ansicht Erstellen, die das HTML-Formular zum Erstellen eines Films enthält, erneut angezeigt.
Erstellen einer partiellen Klasse
Die Movie-Klasse wird vom Entity Framework generiert. Sie können den Code für die Movie-Klasse sehen, wenn Sie die Datei MoviesDBModel.edmx im fenster Projektmappen-Explorer erweitern und moviesDBModel.Designer öffnen. vb-Datei im Code-Editor (siehe Abbildung 2).
Abbildung 02: Der Code für die Movie-Entität (Klicken Sie hier, um das Bild in voller Größe anzuzeigen)
Die Movie-Klasse ist eine partielle Klasse. Das bedeutet, dass wir eine weitere partielle Klasse mit demselben Namen hinzufügen können, um die Funktionalität der Movie-Klasse zu erweitern. Wir fügen die Validierungslogik der neuen partiellen Klasse hinzu.
Fügen Sie die -Klasse in Listing 2 zum Ordner Models hinzu.
Auflistung 2: Models\Movie.vb
Public Partial Class Movie
End Class
Beachten Sie, dass die Klasse in Listing 2 den Teilmodifizierer enthält. Alle Methoden oder Eigenschaften, die Sie dieser Klasse hinzufügen, werden Teil der Movie-Klasse, die vom Entity Framework generiert wird.
Hinzufügen von Partiellen OnChanging- und OnChanged-Methoden
Wenn Entity Framework eine Entitätsklasse generiert, fügt Entity Framework der Klasse automatisch Partielle Methoden hinzu. Das Entity Framework generiert partielle OnChanging- und OnChanged-Methoden, die den einzelnen Eigenschaften der -Klasse entsprechen.
Im Fall der Movie-Klasse erstellt Entity Framework die folgenden Methoden:
- OnIdChanging
- OnIdChanged
- OnTitleChanging
- OnTitleChanged
- OnDirectorChanging
- OnDirectorChanged
- OnDateReleasedChanging
- OnDateReleasedChanged
Die OnChanging-Methode wird direkt vor der Änderung der entsprechenden Eigenschaft aufgerufen. Die OnChanged-Methode wird direkt nach dem Ändern der Eigenschaft aufgerufen.
Sie können diese partiellen Methoden nutzen, um der Movie-Klasse Validierungslogik hinzuzufügen. Mit der Movie-Klasse in Listing 3 wird überprüft, ob den Eigenschaften Title und Director nicht leere Werte zugewiesen sind.
Hinweis
Eine partielle Methode ist eine Methode, die in einer Klasse definiert ist, die Sie nicht implementieren müssen. Wenn Sie keine partielle Methode implementieren, entfernt der Compiler die Methodensignatur und alle Aufrufe der -Methode, sodass keine Laufzeitkosten für die Partielle Methode anfallen. Im Visual Studio Code-Editor können Sie eine partielle Methode hinzufügen, indem Sie die Schlüsselwort (keyword) teil eingeben, gefolgt von einem Leerzeichen, um eine Liste der zu implementierenden Teilelemente anzuzeigen.
Auflistung 3: Models\Movie.vb
Imports System.ComponentModel
Partial Public Class Movie
Implements IDataErrorInfo
Private _errors As New Dictionary(Of String, String)()
Private Sub OnTitleChanging(ByVal value As String)
If value.Trim().Length = 0 Then
_errors.Add("Title", "Title is required.")
End If
End Sub
Private Sub OnDirectorChanging(ByVal value As String)
If value.Trim().Length = 0 Then
_errors.Add("Director", "Director is required.")
End If
End Sub
End Class
Wenn Sie beispielsweise versuchen, der Title-Eigenschaft eine leere Zeichenfolge zuzuweisen, wird einem Wörterbuch mit dem Namen _errors eine Fehlermeldung zugewiesen.
An diesem Punkt geschieht nichts, wenn Sie der Title-Eigenschaft eine leere Zeichenfolge zuweisen und dem Feld "Private _errors" ein Fehler hinzugefügt wird. Wir müssen die IDataErrorInfo-Schnittstelle implementieren, um diese Validierungsfehler für das ASP.NET MVC-Framework verfügbar zu machen.
Implementieren der IDataErrorInfo-Schnittstelle
Die IDataErrorInfo-Schnittstelle ist seit der ersten Version Teil des .NET Frameworks. Diese Schnittstelle ist eine sehr einfache Schnittstelle:
Public Interface IDataErrorInfo
Default ReadOnly Property Item(ByVal columnName As String) As String
ReadOnly Property [Error]() As String
End Interface
Wenn eine Klasse die IDataErrorInfo-Schnittstelle implementiert, verwendet das ASP.NET MVC-Framework diese Schnittstelle beim Erstellen eines instance der Klasse. Die Aktion Create() des Startcontrollers akzeptiert beispielsweise eine instance der Movie-Klasse:
<AcceptVerbs(HttpVerbs.Post)> _
Public Function Create(<Bind(Exclude := "Id")> ByVal movieToCreate As Movie) As ActionResult
' Validate
If (Not ModelState.IsValid) Then
Return View()
End If
' Add to database
Try
_db.AddToMovieSet(movieToCreate)
_db.SaveChanges()
Return RedirectToAction("Index")
Catch
Return View()
End Try
End Function
Das ASP.NET MVC-Framework erstellt die instance des Films, der an die Create()-Aktion übergeben wird, mithilfe einer Modellbindung (DefaultModelBinder). Die Modellbindung ist für das Erstellen einer instance des Movie-Objekts verantwortlich, indem die HTML-Formularfelder an eine instance des Movie-Objekts gebunden werden.
DefaultModelBinder erkennt, ob eine Klasse die IDataErrorInfo-Schnittstelle implementiert oder nicht. Wenn eine Klasse diese Schnittstelle implementiert, ruft die Modellbindung den Indexer IDataErrorInfo.this für jede Eigenschaft der Klasse auf. Wenn der Indexer eine Fehlermeldung zurückgibt, fügt die Modellbindung diese Fehlermeldung automatisch dem Modellzustand hinzu.
Der DefaultModelBinder überprüft auch die IDataErrorInfo.Error-Eigenschaft. Diese Eigenschaft soll nicht-eigenschaftsspezifische Validierungsfehler darstellen, die der -Klasse zugeordnet sind. Beispielsweise können Sie eine Validierungsregel erzwingen, die von den Werten mehrerer Eigenschaften der Movie-Klasse abhängt. In diesem Fall würden Sie einen Validierungsfehler von der Error-Eigenschaft zurückgeben.
Die aktualisierte Movie-Klasse in Listing 4 implementiert die IDataErrorInfo-Schnittstelle.
Auflistung 4: Models\Movie.vb (implementiert IDataErrorInfo)
Imports System.ComponentModel
Partial Public Class Movie
Implements IDataErrorInfo
Private _errors As New Dictionary(Of String, String)()
Private Sub OnTitleChanging(ByVal value As String)
If value.Trim().Length = 0 Then
_errors.Add("Title", "Title is required.")
End If
End Sub
Private Sub OnDirectorChanging(ByVal value As String)
If value.Trim().Length = 0 Then
_errors.Add("Director", "Director is required.")
End If
End Sub
#Region "IDataErrorInfo Members"
Public ReadOnly Property [Error]() As String Implements IDataErrorInfo.Error
Get
Return String.Empty
End Get
End Property
Default Public ReadOnly Property Item(ByVal columnName As String) As String Implements IDataErrorInfo.Item
Get
If _errors.ContainsKey(columnName) Then
Return _errors(columnName)
End If
Return String.Empty
End Get
End Property
#End Region
End Class
In Listing 4 überprüft die Indexereigenschaft die _errors Auflistung, um festzustellen, ob sie einen Schlüssel enthält, der dem an den Indexer übergebenen Eigenschaftennamen entspricht. Wenn der -Eigenschaft kein Validierungsfehler zugeordnet ist, wird eine leere Zeichenfolge zurückgegeben.
Sie müssen den Home-Controller in keiner Weise ändern, um die geänderte Movie-Klasse zu verwenden. Die in Abbildung 3 angezeigte Seite veranschaulicht, was geschieht, wenn kein Wert für die Formularfelder Titel oder Director eingegeben wird.
Abbildung 03: Ein Formular mit fehlenden Werten (Klicken Sie hier, um das Bild in voller Größe anzuzeigen)
Beachten Sie, dass der DateReleased-Wert automatisch überprüft wird. Da die DateReleased-Eigenschaft keine NULL-Werte akzeptiert, generiert defaultModelBinder automatisch einen Überprüfungsfehler für diese Eigenschaft, wenn sie keinen Wert aufweist. Wenn Sie die Fehlermeldung für die DateReleased-Eigenschaft ändern möchten, müssen Sie einen benutzerdefinierten Modellbinder erstellen.
Zusammenfassung
In diesem Tutorial haben Sie gelernt, wie Sie die IDataErrorInfo-Schnittstelle verwenden, um Validierungsfehlermeldungen zu generieren. Zunächst haben wir eine partielle Movie-Klasse erstellt, die die Funktionalität der teilweisen Movie-Klasse erweitert, die vom Entity Framework generiert wird. Als Nächstes haben wir validierungslogik zu den partiellen Methoden der Movie-Klasse OnTitleChanging() und OnDirectorChanging() hinzugefügt. Schließlich haben wir die IDataErrorInfo-Schnittstelle implementiert, um diese Validierungsmeldungen für das ASP.NET MVC-Framework verfügbar zu machen.