Część 9. Dodawanie walidacji do aplikacji MVC platformy ASP.NET Core
Uwaga
Nie jest to najnowsza wersja tego artykułu. Aby zapoznać się z bieżącą wersją, zapoznaj się z wersją tego artykułu platformy .NET 8.
Ostrzeżenie
Ta wersja ASP.NET Core nie jest już obsługiwana. Aby uzyskać więcej informacji, zobacz .NET i .NET Core Support Policy (Zasady obsługi platformy .NET Core). Aby zapoznać się z bieżącą wersją, zapoznaj się z wersją tego artykułu platformy .NET 8.
Ważne
Te informacje odnoszą się do produktu w wersji wstępnej, który może zostać znacząco zmodyfikowany, zanim zostanie wydany komercyjnie. Firma Microsoft nie udziela żadnych gwarancji, jawnych lub domniemanych, w odniesieniu do informacji podanych w tym miejscu.
Aby zapoznać się z bieżącą wersją, zapoznaj się z wersją tego artykułu platformy .NET 8.
Autor: Rick Anderson
W tej sekcji:
- Logika walidacji jest dodawana do
Movie
modelu. - Upewnij się, że reguły walidacji są wymuszane za każdym razem, gdy użytkownik tworzy lub edytuje film.
Utrzymywanie suchych elementów
Jednym z zestawów projektu MVC jest DRY ("Nie powtarzaj siebie"). ASP.NET Core MVC zachęca do określenia funkcjonalności lub zachowania tylko raz, a następnie ich odzwierciedlenia wszędzie w aplikacji. Zmniejsza to ilość kodu potrzebnego do zapisania i sprawia, że kod, który zapisujesz mniej podatny na błędy, ułatwia testowanie i ułatwia konserwację.
Obsługa walidacji zapewniana przez MVC i Entity Framework Core jest dobrym przykładem zasady DRY w działaniu. Reguły walidacji można deklaratywne określić w jednym miejscu (w klasie modelu), a reguły są wymuszane wszędzie w aplikacji.
Usuń wcześniej edytowane dane
W następnym kroku zostaną dodane reguły sprawdzania poprawności, które nie zezwalają na wartości null.
Uruchom aplikację, przejdź do /Movies/Index
pozycji , usuń wszystkie wymienione filmy i zatrzymaj aplikację. Aplikacja użyje danych inicjujowych przy następnym uruchomieniu.
Dodawanie reguł walidacji do modelu filmu
Przestrzeń nazw DataAnnotations udostępnia zestaw wbudowanych atrybutów weryfikacji, które są stosowane deklaratywnie do klasy lub właściwości. Przestrzeń nazw DataAnnotations zawiera również atrybuty formatowania, takie jak DataType
, które pomagają w formatowaniu i nie zapewniają żadnej walidacji.
Zaktualizuj klasęMovie
, aby korzystać z wbudowanych atrybutów Required
weryfikacji , StringLength
, RegularExpression
Range
i DataType
atrybutu formatowania.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
[Required]
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$")]
[Required]
[StringLength(30)]
public string? Genre { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$")]
[StringLength(5)]
[Required]
public string? Rating { get; set; }
}
Atrybuty weryfikacji określają zachowanie, które chcesz wymusić na właściwościach modelu, do których są stosowane:
Atrybuty
Required
iMinimumLength
wskazują, że właściwość musi mieć wartość, ale nic nie uniemożliwia użytkownikowi wprowadzania białych znaków w celu spełnienia tej weryfikacji.Atrybut
RegularExpression
służy do ograniczania liczby znaków, które mogą być wprowadzane jako dane wejściowe. W poprzednim kodzie w polu „Genre” (Gatunek):- Muszą być używane tylko litery.
- Pierwsza litera musi być wielką literą. Białe spacje są dozwolone, gdy liczby i znaki specjalne są niedozwolone.
W atrybucie
RegularExpression
„Rating” (Klasyfikacja):- Pierwszy znak musi być wielką literą.
- Kolejne znaki mogą być znakami specjalnymi i cyframi. W atrybucie Rating wartość „PG-13” jest prawidłowa, ale w przypadku atrybutu Genre — nie.
Atrybut
Range
ogranicza wartość do określonego zakresu.Atrybut
StringLength
umożliwia ustawienie maksymalnej długości właściwości ciągu i opcjonalnie jego minimalnej długości.Typy wartości (takie jak
decimal
,int
,float
,DateTime
) są z natury wymagane i nie wymagają atrybutu[Required]
.
Automatyczne wymuszanie reguł weryfikacji przez platformę ASP.NET Core pomaga zwiększyć niezawodność aplikacji. Gwarantuje to również, że nie można zapomnieć o zweryfikowaniu czegoś i przypadkowo niech złych danych w bazie danych.
Interfejs użytkownika błędu walidacji
Uruchom aplikację i przejdź do kontrolera Filmy.
Wybierz link Utwórz nowy, aby dodać nowy film. Wypełnij formularz kilkoma nieprawidłowymi wartościami. Gdy tylko walidacja po stronie klienta jQuery wykryje błąd, zostanie wyświetlony komunikat o błędzie.
Uwaga
Może nie być możliwe wprowadzenie przecinków dziesiętnych w polach dziesiętnych. Aby obsługiwać walidację jQuery dla ustawień regionalnych innych niż angielski, które używają przecinka (",") dla przecinka dziesiętnego i formatów dat innych niż angielskie stany USA, należy wykonać kroki w celu globalizacji aplikacji. Zobacz ten komentarz usługi GitHub 4076 , aby uzyskać instrukcje dotyczące dodawania przecinka dziesiętnego.
Zwróć uwagę, że formularz automatycznie renderował odpowiedni komunikat o błędzie weryfikacji w każdym polu zawierającym nieprawidłową wartość. Błędy są wymuszane po stronie klienta (przy użyciu języków JavaScript i jQuery) i po stronie serwera (w przypadku wyłączenia języka JavaScript przez użytkownika).
Ważną korzyścią jest to, że nie trzeba zmieniać pojedynczego wiersza kodu w MoviesController
klasie lub w Create.cshtml
widoku, aby włączyć ten interfejs użytkownika weryfikacji. Kontroler i widoki utworzone wcześniej w tym samouczku automatycznie podniosły reguły weryfikacji określone przy użyciu atrybutów weryfikacji we właściwościach Movie
klasy modelu. Przetestuj walidację Edit
przy użyciu metody akcji i zastosowano tę samą walidację.
Dane formularza nie są wysyłane do serwera, dopóki nie wystąpią żadne błędy weryfikacji po stronie klienta. Możesz to sprawdzić, umieszczając punkt przerwania w metodzie HTTP Post
przy użyciu narzędzia Fiddler lub Narzędzia programistyczne F12.
Jak działa walidacja
Możesz się zastanawiać, jak interfejs użytkownika weryfikacji został wygenerowany bez żadnych aktualizacji kodu w kontrolerze lub widokach. Poniższy kod przedstawia dwie Create
metody.
// GET: Movies/Create
public IActionResult Create()
{
return View();
}
// POST: Movies/Create
// To protect from overposting attacks, enable the specific properties you want to bind to.
// For more details, see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Create([Bind("Id,Title,ReleaseDate,Genre,Price,Rating")] Movie movie)
{
if (ModelState.IsValid)
{
_context.Add(movie);
await _context.SaveChangesAsync();
return RedirectToAction(nameof(Index));
}
return View(movie);
}
Pierwsza metoda akcji (HTTP GET) Create
wyświetla początkowy formularz Utwórz. Druga wersja ([HttpPost]
) obsługuje wpis formularza. Druga Create
metoda (wersja [HttpPost]
) wywołuje metodę ModelState.IsValid
w celu sprawdzenia, czy film ma jakiekolwiek błędy walidacji. Wywołanie tej metody ocenia wszystkie atrybuty walidacji, które zostały zastosowane do obiektu. Jeśli obiekt zawiera błędy weryfikacji, Create
metoda ponownie wyświetli formularz. Jeśli nie ma żadnych błędów, metoda zapisuje nowy film w bazie danych. W naszym przykładzie filmu formularz nie jest publikowany na serwerze, gdy występują błędy walidacji wykryte po stronie klienta; druga Create
metoda nigdy nie jest wywoływana, gdy występują błędy weryfikacji po stronie klienta. Jeśli wyłączysz język JavaScript w przeglądarce, walidacja klienta jest wyłączona i możesz przetestować metodę ModelState.IsValid
HTTP POSTCreate
, wykrywając błędy walidacji.
Możesz ustawić punkt przerwania w metodzie [HttpPost] Create
i sprawdzić, czy metoda nigdy nie jest wywoływana, walidacja po stronie klienta nie będzie przesyłać danych formularza po wykryciu błędów walidacji. Jeśli wyłączysz język JavaScript w przeglądarce, prześlij formularz z błędami, punkt przerwania zostanie trafiony. Nadal uzyskujesz pełną walidację bez języka JavaScript.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Firefox.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Chrome.
Po wyłączeniu języka JavaScript opublikuj nieprawidłowe dane i przejdź przez debuger.
Część szablonu Create.cshtml
widoku jest wyświetlana w następującym znaczniku:
<h4>Movie</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Create">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="Title" class="control-label"></label>
<input asp-for="Title" class="form-control" />
<span asp-validation-for="Title" class="text-danger"></span>
</div>
@*Markup removed for brevity.*@
Powyższy znacznik jest używany przez metody akcji do wyświetlania początkowego formularza i ponownego redysponowania go w przypadku błędu.
Pomocnik tagów wejściowych używa atrybutów DataAnnotations i tworzy atrybuty HTML wymagane do weryfikacji jQuery po stronie klienta. Pomocnik tagu weryfikacji wyświetla błędy walidacji. Aby uzyskać więcej informacji, zobacz Walidacja .
Naprawdę miło jest to, że ani kontroler, ani Create
szablon widoku nie wie nic o rzeczywistych regułach walidacji, które są wymuszane, ani o wyświetlanych konkretnych komunikatach o błędach. Reguły walidacji i ciągi błędów są określone tylko w Movie
klasie. Te same reguły sprawdzania poprawności są automatycznie stosowane do Edit
widoku i wszystkich innych szablonów widoków, które można utworzyć, aby edytować model.
Jeśli musisz zmienić logikę weryfikacji, możesz to zrobić w dokładnie jednym miejscu, dodając atrybuty weryfikacji do modelu (w tym przykładzie Movie
klasa). Nie trzeba martwić się o niespójność różnych części aplikacji ze sposobem wymuszania reguł — cała logika walidacji zostanie zdefiniowana w jednym miejscu i używana wszędzie. Dzięki temu kod jest bardzo czysty i ułatwia konserwację i rozwijanie. Oznacza to, że będziesz w pełni przestrzegać zasady DRY.
Używanie atrybutów Typu danych
Movie.cs
Otwórz plik i sprawdź klasęMovie
. System.ComponentModel.DataAnnotations
Przestrzeń nazw udostępnia atrybuty formatowania oprócz wbudowanego zestawu atrybutów weryfikacji. Zastosowaliśmy DataType
już wartość wyliczenia do daty wydania i pól ceny. Poniższy kod przedstawia ReleaseDate
właściwości i Price
z odpowiednim DataType
atrybutem.
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
Atrybuty DataType
zawierają tylko wskazówki dla aparatu wyświetlania, aby sformatować dane i dostarczyć elementy/atrybuty, takie jak <a>
adres URL i <a href="mailto:EmailAddress.com">
adres e-mail. Możesz użyć atrybutu RegularExpression
, aby zweryfikować format danych. Atrybut DataType
służy do określania typu danych, który jest bardziej szczegółowy niż typ wewnętrzny bazy danych, nie są atrybutami walidacji. W tym przypadku chcemy śledzić tylko datę, a nie godzinę. Wyliczenie DataType
zawiera wiele typów danych, takich jak Data, Godzina, Numer telefonu, Waluta, Adres e-mail i inne. Atrybut DataType
może również umożliwić aplikacji automatyczne udostępnianie funkcji specyficznych dla typu. Na przykład mailto:
można utworzyć link dla DataType.EmailAddress
elementu , a selektor dat można udostępnić DataType.Date
w przeglądarkach obsługujących kod HTML5. Atrybuty DataType
emitują atrybuty HTML 5 data-
(wymawiane kreski danych), które przeglądarki HTML 5 mogą zrozumieć. Atrybuty DataType
nie zapewniają żadnej walidacji.
DataType.Date
nie określa formatu wyświetlanej daty. Domyślnie pole danych jest wyświetlane zgodnie z domyślnymi formatami na podstawie serwera CultureInfo
.
Atrybut DisplayFormat
jest używany do jawnego określenia formatu daty:
[DisplayFormat(DataFormatString = "{0:yyyy-MM-dd}", ApplyFormatInEditMode = true)]
public DateTime ReleaseDate { get; set; }
Ustawienie ApplyFormatInEditMode
określa, że formatowanie powinno być również stosowane, gdy wartość jest wyświetlana w polu tekstowym do edycji. (Możesz nie chcieć tego dla niektórych pól — na przykład w przypadku wartości walutowych prawdopodobnie nie chcesz, aby symbol waluty w polu tekstowym był edytowany).
Atrybut można użyć DisplayFormat
samodzielnie, ale zazwyczaj dobrym pomysłem jest użycie atrybutu DataType
. Atrybut DataType
przekazuje semantyka danych, w przeciwieństwie do sposobu renderowania ich na ekranie, i zapewnia następujące korzyści, które nie są uzyskiwane za pomocą elementu DisplayFormat:
Przeglądarka może włączyć funkcje HTML5 (na przykład w celu wyświetlania kontrolki kalendarza, symbolu waluty odpowiedniego dla ustawień regionalnych, linków poczty e-mail itp.)
Domyślnie przeglądarka będzie renderować dane przy użyciu poprawnego formatu na podstawie ustawień regionalnych.
Atrybut
DataType
może umożliwić MVC wybranie odpowiedniego szablonu pola w celu renderowania danych (DisplayFormat
jeśli jest używany przez siebie przy użyciu szablonu ciągu).
Uwaga
Sprawdzanie poprawności zapytania jQuery nie działa z atrybutem Range
i DateTime
. Na przykład następujący kod zawsze wyświetla błąd weryfikacji po stronie klienta, nawet jeśli data znajduje się w określonym zakresie:
[Range(typeof(DateTime), "1/1/1966", "1/1/2020")]
Aby użyć atrybutu z atrybutem , należy wyłączyć walidację Range
daty zapytania jQuery.DateTime
Zazwyczaj nie jest dobrym rozwiązaniem do kompilowania dat twardych w modelach, dlatego użycie atrybutu Range
i DateTime
jest zniechęcane.
Poniższy kod przedstawia łączenie atrybutów w jednym wierszu:
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
public string Title { get; set; }
[Display(Name = "Release Date"), DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$"), Required, StringLength(30)]
public string Genre { get; set; }
[Range(1, 100), DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$"), StringLength(5)]
public string Rating { get; set; }
}
W następnej części serii przejrzymy aplikację i wprowadzimy pewne ulepszenia w automatycznie wygenerowanych Details
metodach i Delete
.
Dodatkowe zasoby
W tej sekcji:
- Logika walidacji jest dodawana do
Movie
modelu. - Upewnij się, że reguły walidacji są wymuszane za każdym razem, gdy użytkownik tworzy lub edytuje film.
Utrzymywanie suchych elementów
Jednym z zestawów projektu MVC jest DRY ("Nie powtarzaj siebie"). ASP.NET Core MVC zachęca do określenia funkcjonalności lub zachowania tylko raz, a następnie ich odzwierciedlenia wszędzie w aplikacji. Zmniejsza to ilość kodu potrzebnego do zapisania i sprawia, że kod, który zapisujesz mniej podatny na błędy, ułatwia testowanie i ułatwia konserwację.
Obsługa walidacji zapewniana przez MVC i Entity Framework Core Code First jest dobrym przykładem zasady DRY w działaniu. Reguły walidacji można deklaratywne określić w jednym miejscu (w klasie modelu), a reguły są wymuszane wszędzie w aplikacji.
Usuń wcześniej edytowane dane
W następnym kroku zostaną dodane reguły sprawdzania poprawności, które nie zezwalają na wartości null.
Uruchom aplikację, przejdź do /Movies/Index
pozycji , usuń wszystkie wymienione filmy i zatrzymaj aplikację. Aplikacja użyje danych inicjujowych przy następnym uruchomieniu.
Dodawanie reguł walidacji do modelu filmu
Przestrzeń nazw DataAnnotations udostępnia zestaw wbudowanych atrybutów weryfikacji, które są stosowane deklaratywnie do klasy lub właściwości. Przestrzeń nazw DataAnnotations zawiera również atrybuty formatowania, takie jak DataType
, które pomagają w formatowaniu i nie zapewniają żadnej walidacji.
Zaktualizuj klasęMovie
, aby korzystać z wbudowanych atrybutów Required
weryfikacji , StringLength
, RegularExpression
Range
i DataType
atrybutu formatowania.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
[Required]
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$")]
[Required]
[StringLength(30)]
public string? Genre { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$")]
[StringLength(5)]
[Required]
public string? Rating { get; set; }
}
Atrybuty weryfikacji określają zachowanie, które chcesz wymusić na właściwościach modelu, do których są stosowane:
Atrybuty
Required
iMinimumLength
wskazują, że właściwość musi mieć wartość, ale nic nie uniemożliwia użytkownikowi wprowadzania białych znaków w celu spełnienia tej weryfikacji.Atrybut
RegularExpression
służy do ograniczania liczby znaków, które mogą być wprowadzane jako dane wejściowe. W poprzednim kodzie w polu „Genre” (Gatunek):- Muszą być używane tylko litery.
- Pierwsza litera musi być wielką literą. Białe spacje są dozwolone, gdy liczby i znaki specjalne są niedozwolone.
W atrybucie
RegularExpression
„Rating” (Klasyfikacja):- Pierwszy znak musi być wielką literą.
- Kolejne znaki mogą być znakami specjalnymi i cyframi. W atrybucie Rating wartość „PG-13” jest prawidłowa, ale w przypadku atrybutu Genre — nie.
Atrybut
Range
ogranicza wartość do określonego zakresu.Atrybut
StringLength
umożliwia ustawienie maksymalnej długości właściwości ciągu i opcjonalnie jego minimalnej długości.Typy wartości (takie jak
decimal
,int
,float
,DateTime
) są z natury wymagane i nie wymagają atrybutu[Required]
.
Automatyczne wymuszanie reguł weryfikacji przez platformę ASP.NET Core pomaga zwiększyć niezawodność aplikacji. Gwarantuje to również, że nie można zapomnieć o zweryfikowaniu czegoś i przypadkowo niech złych danych w bazie danych.
Interfejs użytkownika błędu walidacji
Uruchom aplikację i przejdź do kontrolera Filmy.
Wybierz link Utwórz nowy, aby dodać nowy film. Wypełnij formularz kilkoma nieprawidłowymi wartościami. Gdy tylko walidacja po stronie klienta jQuery wykryje błąd, zostanie wyświetlony komunikat o błędzie.
Uwaga
Może nie być możliwe wprowadzenie przecinków dziesiętnych w polach dziesiętnych. Aby obsługiwać walidację jQuery dla ustawień regionalnych innych niż angielski, które używają przecinka (",") dla przecinka dziesiętnego i formatów dat innych niż angielskie stany USA, należy wykonać kroki w celu globalizacji aplikacji. Zobacz ten komentarz usługi GitHub 4076 , aby uzyskać instrukcje dotyczące dodawania przecinka dziesiętnego.
Zwróć uwagę, że formularz automatycznie renderował odpowiedni komunikat o błędzie weryfikacji w każdym polu zawierającym nieprawidłową wartość. Błędy są wymuszane po stronie klienta (przy użyciu języków JavaScript i jQuery) i po stronie serwera (w przypadku wyłączenia języka JavaScript przez użytkownika).
Ważną korzyścią jest to, że nie trzeba zmieniać pojedynczego wiersza kodu w MoviesController
klasie lub w Create.cshtml
widoku, aby włączyć ten interfejs użytkownika weryfikacji. Kontroler i widoki utworzone wcześniej w tym samouczku automatycznie podniosły reguły weryfikacji określone przy użyciu atrybutów weryfikacji we właściwościach Movie
klasy modelu. Przetestuj walidację Edit
przy użyciu metody akcji i zastosowano tę samą walidację.
Dane formularza nie są wysyłane do serwera, dopóki nie wystąpią żadne błędy weryfikacji po stronie klienta. Możesz to sprawdzić, umieszczając punkt przerwania w metodzie HTTP Post
przy użyciu narzędzia Fiddler lub Narzędzia programistyczne F12.
Jak działa walidacja
Możesz się zastanawiać, jak interfejs użytkownika weryfikacji został wygenerowany bez żadnych aktualizacji kodu w kontrolerze lub widokach. Poniższy kod przedstawia dwie Create
metody.
// GET: Movies/Create
public IActionResult Create()
{
return View();
}
// POST: Movies/Create
// To protect from overposting attacks, enable the specific properties you want to bind to.
// For more details, see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Create([Bind("Id,Title,ReleaseDate,Genre,Price,Rating")] Movie movie)
{
if (ModelState.IsValid)
{
_context.Add(movie);
await _context.SaveChangesAsync();
return RedirectToAction(nameof(Index));
}
return View(movie);
}
Pierwsza metoda akcji (HTTP GET) Create
wyświetla początkowy formularz Utwórz. Druga wersja ([HttpPost]
) obsługuje wpis formularza. Druga Create
metoda (wersja [HttpPost]
) wywołuje metodę ModelState.IsValid
w celu sprawdzenia, czy film ma jakiekolwiek błędy walidacji. Wywołanie tej metody ocenia wszystkie atrybuty walidacji, które zostały zastosowane do obiektu. Jeśli obiekt zawiera błędy weryfikacji, Create
metoda ponownie wyświetli formularz. Jeśli nie ma żadnych błędów, metoda zapisuje nowy film w bazie danych. W naszym przykładzie filmu formularz nie jest publikowany na serwerze, gdy występują błędy walidacji wykryte po stronie klienta; druga Create
metoda nigdy nie jest wywoływana, gdy występują błędy weryfikacji po stronie klienta. Jeśli wyłączysz język JavaScript w przeglądarce, walidacja klienta jest wyłączona i możesz przetestować metodę ModelState.IsValid
HTTP POSTCreate
, wykrywając błędy walidacji.
Możesz ustawić punkt przerwania w metodzie [HttpPost] Create
i sprawdzić, czy metoda nigdy nie jest wywoływana, walidacja po stronie klienta nie będzie przesyłać danych formularza po wykryciu błędów walidacji. Jeśli wyłączysz język JavaScript w przeglądarce, prześlij formularz z błędami, punkt przerwania zostanie trafiony. Nadal uzyskujesz pełną walidację bez języka JavaScript.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Firefox.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Chrome.
Po wyłączeniu języka JavaScript opublikuj nieprawidłowe dane i przejdź przez debuger.
Część szablonu Create.cshtml
widoku jest wyświetlana w następującym znaczniku:
<h4>Movie</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Create">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="Title" class="control-label"></label>
<input asp-for="Title" class="form-control" />
<span asp-validation-for="Title" class="text-danger"></span>
</div>
@*Markup removed for brevity.*@
Powyższy znacznik jest używany przez metody akcji do wyświetlania początkowego formularza i ponownego redysponowania go w przypadku błędu.
Pomocnik tagów wejściowych używa atrybutów DataAnnotations i tworzy atrybuty HTML wymagane do weryfikacji jQuery po stronie klienta. Pomocnik tagu weryfikacji wyświetla błędy walidacji. Aby uzyskać więcej informacji, zobacz Walidacja .
Naprawdę miło jest to, że ani kontroler, ani Create
szablon widoku nie wie nic o rzeczywistych regułach walidacji, które są wymuszane, ani o wyświetlanych konkretnych komunikatach o błędach. Reguły walidacji i ciągi błędów są określone tylko w Movie
klasie. Te same reguły sprawdzania poprawności są automatycznie stosowane do Edit
widoku i wszystkich innych szablonów widoków, które można utworzyć, aby edytować model.
Jeśli musisz zmienić logikę weryfikacji, możesz to zrobić w dokładnie jednym miejscu, dodając atrybuty weryfikacji do modelu (w tym przykładzie Movie
klasa). Nie trzeba martwić się o niespójność różnych części aplikacji ze sposobem wymuszania reguł — cała logika walidacji zostanie zdefiniowana w jednym miejscu i używana wszędzie. Dzięki temu kod jest bardzo czysty i ułatwia konserwację i rozwijanie. Oznacza to, że będziesz w pełni przestrzegać zasady DRY.
Używanie atrybutów Typu danych
Movie.cs
Otwórz plik i sprawdź klasęMovie
. System.ComponentModel.DataAnnotations
Przestrzeń nazw udostępnia atrybuty formatowania oprócz wbudowanego zestawu atrybutów weryfikacji. Zastosowaliśmy DataType
już wartość wyliczenia do daty wydania i pól ceny. Poniższy kod przedstawia ReleaseDate
właściwości i Price
z odpowiednim DataType
atrybutem.
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
Atrybuty DataType
zawierają tylko wskazówki dla aparatu wyświetlania, aby sformatować dane i dostarczyć elementy/atrybuty, takie jak <a>
adres URL i <a href="mailto:EmailAddress.com">
adres e-mail. Możesz użyć atrybutu RegularExpression
, aby zweryfikować format danych. Atrybut DataType
służy do określania typu danych, który jest bardziej szczegółowy niż typ wewnętrzny bazy danych, nie są atrybutami walidacji. W tym przypadku chcemy śledzić tylko datę, a nie godzinę. Wyliczenie DataType
zawiera wiele typów danych, takich jak Data, Godzina, Numer telefonu, Waluta, Adres e-mail i inne. Atrybut DataType
może również umożliwić aplikacji automatyczne udostępnianie funkcji specyficznych dla typu. Na przykład mailto:
można utworzyć link dla DataType.EmailAddress
elementu , a selektor dat można udostępnić DataType.Date
w przeglądarkach obsługujących kod HTML5. Atrybuty DataType
emitują atrybuty HTML 5 data-
(wymawiane kreski danych), które przeglądarki HTML 5 mogą zrozumieć. Atrybuty DataType
nie zapewniają żadnej walidacji.
DataType.Date
nie określa formatu wyświetlanej daty. Domyślnie pole danych jest wyświetlane zgodnie z domyślnymi formatami na podstawie serwera CultureInfo
.
Atrybut DisplayFormat
jest używany do jawnego określenia formatu daty:
[DisplayFormat(DataFormatString = "{0:yyyy-MM-dd}", ApplyFormatInEditMode = true)]
public DateTime ReleaseDate { get; set; }
Ustawienie ApplyFormatInEditMode
określa, że formatowanie powinno być również stosowane, gdy wartość jest wyświetlana w polu tekstowym do edycji. (Możesz nie chcieć tego dla niektórych pól — na przykład w przypadku wartości walutowych prawdopodobnie nie chcesz, aby symbol waluty w polu tekstowym był edytowany).
Atrybut można użyć DisplayFormat
samodzielnie, ale zazwyczaj dobrym pomysłem jest użycie atrybutu DataType
. Atrybut DataType
przekazuje semantyka danych, w przeciwieństwie do sposobu renderowania ich na ekranie, i zapewnia następujące korzyści, które nie są uzyskiwane za pomocą elementu DisplayFormat:
Przeglądarka może włączyć funkcje HTML5 (na przykład w celu wyświetlania kontrolki kalendarza, symbolu waluty odpowiedniego dla ustawień regionalnych, linków poczty e-mail itp.)
Domyślnie przeglądarka będzie renderować dane przy użyciu poprawnego formatu na podstawie ustawień regionalnych.
Atrybut
DataType
może umożliwić MVC wybranie odpowiedniego szablonu pola w celu renderowania danych (DisplayFormat
jeśli jest używany przez siebie przy użyciu szablonu ciągu).
Uwaga
Sprawdzanie poprawności zapytania jQuery nie działa z atrybutem Range
i DateTime
. Na przykład następujący kod zawsze wyświetla błąd weryfikacji po stronie klienta, nawet jeśli data znajduje się w określonym zakresie:
[Range(typeof(DateTime), "1/1/1966", "1/1/2020")]
Aby użyć atrybutu z atrybutem , należy wyłączyć walidację Range
daty zapytania jQuery.DateTime
Zazwyczaj nie jest dobrym rozwiązaniem do kompilowania dat twardych w modelach, dlatego użycie atrybutu Range
i DateTime
jest zniechęcane.
Poniższy kod przedstawia łączenie atrybutów w jednym wierszu:
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
public string Title { get; set; }
[Display(Name = "Release Date"), DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$"), Required, StringLength(30)]
public string Genre { get; set; }
[Range(1, 100), DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$"), StringLength(5)]
public string Rating { get; set; }
}
W następnej części serii przejrzymy aplikację i wprowadzimy pewne ulepszenia w automatycznie wygenerowanych Details
metodach i Delete
.
Dodatkowe zasoby
W tej sekcji:
- Logika walidacji jest dodawana do
Movie
modelu. - Upewnij się, że reguły walidacji są wymuszane za każdym razem, gdy użytkownik tworzy lub edytuje film.
Utrzymywanie suchych elementów
Jednym z zestawów projektu MVC jest DRY ("Nie powtarzaj siebie"). ASP.NET Core MVC zachęca do określenia funkcjonalności lub zachowania tylko raz, a następnie ich odzwierciedlenia wszędzie w aplikacji. Zmniejsza to ilość kodu potrzebnego do zapisania i sprawia, że kod, który zapisujesz mniej podatny na błędy, ułatwia testowanie i ułatwia konserwację.
Obsługa walidacji zapewniana przez MVC i Entity Framework Core Code First jest dobrym przykładem zasady DRY w działaniu. Reguły walidacji można deklaratywne określić w jednym miejscu (w klasie modelu), a reguły są wymuszane wszędzie w aplikacji.
Dodawanie reguł walidacji do modelu filmu
Przestrzeń nazw DataAnnotations udostępnia zestaw wbudowanych atrybutów weryfikacji, które są stosowane deklaratywnie do klasy lub właściwości. Przestrzeń nazw DataAnnotations zawiera również atrybuty formatowania, takie jak DataType
, które pomagają w formatowaniu i nie zapewniają żadnej walidacji.
Zaktualizuj klasęMovie
, aby korzystać z wbudowanych atrybutów Required
weryfikacji , StringLength
, RegularExpression
Range
i DataType
atrybutu formatowania.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
[Required]
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$")]
[Required]
[StringLength(30)]
public string? Genre { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$")]
[StringLength(5)]
[Required]
public string? Rating { get; set; }
}
Atrybuty weryfikacji określają zachowanie, które chcesz wymusić na właściwościach modelu, do których są stosowane:
Atrybuty
Required
iMinimumLength
wskazują, że właściwość musi mieć wartość, ale nic nie uniemożliwia użytkownikowi wprowadzania białych znaków w celu spełnienia tej weryfikacji.Atrybut
RegularExpression
służy do ograniczania liczby znaków, które mogą być wprowadzane jako dane wejściowe. W poprzednim kodzie w polu „Genre” (Gatunek):- Muszą być używane tylko litery.
- Pierwsza litera musi być wielką literą. Białe spacje są dozwolone, gdy liczby i znaki specjalne są niedozwolone.
W atrybucie
RegularExpression
„Rating” (Klasyfikacja):- Pierwszy znak musi być wielką literą.
- Kolejne znaki mogą być znakami specjalnymi i cyframi. W atrybucie Rating wartość „PG-13” jest prawidłowa, ale w przypadku atrybutu Genre — nie.
Atrybut
Range
ogranicza wartość do określonego zakresu.Atrybut
StringLength
umożliwia ustawienie maksymalnej długości właściwości ciągu i opcjonalnie jego minimalnej długości.Typy wartości (takie jak
decimal
,int
,float
,DateTime
) są z natury wymagane i nie wymagają atrybutu[Required]
.
Automatyczne wymuszanie reguł weryfikacji przez platformę ASP.NET Core pomaga zwiększyć niezawodność aplikacji. Gwarantuje to również, że nie można zapomnieć o zweryfikowaniu czegoś i przypadkowo niech złych danych w bazie danych.
Interfejs użytkownika błędu walidacji
Uruchom aplikację i przejdź do kontrolera Filmy.
Wybierz link Utwórz nowy, aby dodać nowy film. Wypełnij formularz kilkoma nieprawidłowymi wartościami. Gdy tylko walidacja po stronie klienta jQuery wykryje błąd, zostanie wyświetlony komunikat o błędzie.
Uwaga
Może nie być możliwe wprowadzenie przecinków dziesiętnych w polach dziesiętnych. Aby obsługiwać walidację jQuery dla ustawień regionalnych innych niż angielski, które używają przecinka (",") dla przecinka dziesiętnego i formatów dat innych niż angielskie stany USA, należy wykonać kroki w celu globalizacji aplikacji. Zobacz ten komentarz usługi GitHub 4076 , aby uzyskać instrukcje dotyczące dodawania przecinka dziesiętnego.
Zwróć uwagę, że formularz automatycznie renderował odpowiedni komunikat o błędzie weryfikacji w każdym polu zawierającym nieprawidłową wartość. Błędy są wymuszane po stronie klienta (przy użyciu języków JavaScript i jQuery) i po stronie serwera (w przypadku wyłączenia języka JavaScript przez użytkownika).
Ważną korzyścią jest to, że nie trzeba zmieniać pojedynczego wiersza kodu w MoviesController
klasie lub w Create.cshtml
widoku, aby włączyć ten interfejs użytkownika weryfikacji. Kontroler i widoki utworzone wcześniej w tym samouczku automatycznie podniosły reguły weryfikacji określone przy użyciu atrybutów weryfikacji we właściwościach Movie
klasy modelu. Przetestuj walidację Edit
przy użyciu metody akcji i zastosowano tę samą walidację.
Dane formularza nie są wysyłane do serwera, dopóki nie wystąpią żadne błędy weryfikacji po stronie klienta. Możesz to sprawdzić, umieszczając punkt przerwania w metodzie HTTP Post
przy użyciu narzędzia Fiddler lub Narzędzia programistyczne F12.
Jak działa walidacja
Możesz się zastanawiać, jak interfejs użytkownika weryfikacji został wygenerowany bez żadnych aktualizacji kodu w kontrolerze lub widokach. Poniższy kod przedstawia dwie Create
metody.
// GET: Movies/Create
public IActionResult Create()
{
return View();
}
// POST: Movies/Create
// To protect from overposting attacks, enable the specific properties you want to bind to.
// For more details, see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Create([Bind("Id,Title,ReleaseDate,Genre,Price,Rating")] Movie movie)
{
if (ModelState.IsValid)
{
_context.Add(movie);
await _context.SaveChangesAsync();
return RedirectToAction(nameof(Index));
}
return View(movie);
}
Pierwsza metoda akcji (HTTP GET) Create
wyświetla początkowy formularz Utwórz. Druga wersja ([HttpPost]
) obsługuje wpis formularza. Druga Create
metoda (wersja [HttpPost]
) wywołuje metodę ModelState.IsValid
w celu sprawdzenia, czy film ma jakiekolwiek błędy walidacji. Wywołanie tej metody ocenia wszystkie atrybuty walidacji, które zostały zastosowane do obiektu. Jeśli obiekt zawiera błędy weryfikacji, Create
metoda ponownie wyświetli formularz. Jeśli nie ma żadnych błędów, metoda zapisuje nowy film w bazie danych. W naszym przykładzie filmu formularz nie jest publikowany na serwerze, gdy występują błędy walidacji wykryte po stronie klienta; druga Create
metoda nigdy nie jest wywoływana, gdy występują błędy weryfikacji po stronie klienta. Jeśli wyłączysz język JavaScript w przeglądarce, walidacja klienta jest wyłączona i możesz przetestować metodę ModelState.IsValid
HTTP POSTCreate
, wykrywając błędy walidacji.
Możesz ustawić punkt przerwania w metodzie [HttpPost] Create
i sprawdzić, czy metoda nigdy nie jest wywoływana, walidacja po stronie klienta nie będzie przesyłać danych formularza po wykryciu błędów walidacji. Jeśli wyłączysz język JavaScript w przeglądarce, prześlij formularz z błędami, punkt przerwania zostanie trafiony. Nadal uzyskujesz pełną walidację bez języka JavaScript.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Firefox.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Chrome.
Po wyłączeniu języka JavaScript opublikuj nieprawidłowe dane i przejdź przez debuger.
Część szablonu Create.cshtml
widoku jest wyświetlana w następującym znaczniku:
<h4>Movie</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Create">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="Title" class="control-label"></label>
<input asp-for="Title" class="form-control" />
<span asp-validation-for="Title" class="text-danger"></span>
</div>
@*Markup removed for brevity.*@
Powyższy znacznik jest używany przez metody akcji do wyświetlania początkowego formularza i ponownego redysponowania go w przypadku błędu.
Pomocnik tagów wejściowych używa atrybutów DataAnnotations i tworzy atrybuty HTML wymagane do weryfikacji jQuery po stronie klienta. Pomocnik tagu weryfikacji wyświetla błędy walidacji. Aby uzyskać więcej informacji, zobacz Walidacja .
Naprawdę miło jest to, że ani kontroler, ani Create
szablon widoku nie wie nic o rzeczywistych regułach walidacji, które są wymuszane, ani o wyświetlanych konkretnych komunikatach o błędach. Reguły walidacji i ciągi błędów są określone tylko w Movie
klasie. Te same reguły sprawdzania poprawności są automatycznie stosowane do Edit
widoku i wszystkich innych szablonów widoków, które można utworzyć, aby edytować model.
Jeśli musisz zmienić logikę weryfikacji, możesz to zrobić w dokładnie jednym miejscu, dodając atrybuty weryfikacji do modelu (w tym przykładzie Movie
klasa). Nie trzeba martwić się o niespójność różnych części aplikacji ze sposobem wymuszania reguł — cała logika walidacji zostanie zdefiniowana w jednym miejscu i używana wszędzie. Dzięki temu kod jest bardzo czysty i ułatwia konserwację i rozwijanie. Oznacza to, że będziesz w pełni przestrzegać zasady DRY.
Używanie atrybutów Typu danych
Movie.cs
Otwórz plik i sprawdź klasęMovie
. System.ComponentModel.DataAnnotations
Przestrzeń nazw udostępnia atrybuty formatowania oprócz wbudowanego zestawu atrybutów weryfikacji. Zastosowaliśmy DataType
już wartość wyliczenia do daty wydania i pól ceny. Poniższy kod przedstawia ReleaseDate
właściwości i Price
z odpowiednim DataType
atrybutem.
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
Atrybuty DataType
zawierają tylko wskazówki dla aparatu wyświetlania, aby sformatować dane i dostarczyć elementy/atrybuty, takie jak <a>
adres URL i <a href="mailto:EmailAddress.com">
adres e-mail. Możesz użyć atrybutu RegularExpression
, aby zweryfikować format danych. Atrybut DataType
służy do określania typu danych, który jest bardziej szczegółowy niż typ wewnętrzny bazy danych, nie są atrybutami walidacji. W tym przypadku chcemy śledzić tylko datę, a nie godzinę. Wyliczenie DataType
zawiera wiele typów danych, takich jak Data, Godzina, Numer telefonu, Waluta, Adres e-mail i inne. Atrybut DataType
może również umożliwić aplikacji automatyczne udostępnianie funkcji specyficznych dla typu. Na przykład mailto:
można utworzyć link dla DataType.EmailAddress
elementu , a selektor dat można udostępnić DataType.Date
w przeglądarkach obsługujących kod HTML5. Atrybuty DataType
emitują atrybuty HTML 5 data-
(wymawiane kreski danych), które przeglądarki HTML 5 mogą zrozumieć. Atrybuty DataType
nie zapewniają żadnej walidacji.
DataType.Date
nie określa formatu wyświetlanej daty. Domyślnie pole danych jest wyświetlane zgodnie z domyślnymi formatami na podstawie serwera CultureInfo
.
Atrybut DisplayFormat
jest używany do jawnego określenia formatu daty:
[DisplayFormat(DataFormatString = "{0:yyyy-MM-dd}", ApplyFormatInEditMode = true)]
public DateTime ReleaseDate { get; set; }
Ustawienie ApplyFormatInEditMode
określa, że formatowanie powinno być również stosowane, gdy wartość jest wyświetlana w polu tekstowym do edycji. (Możesz nie chcieć tego dla niektórych pól — na przykład w przypadku wartości walutowych prawdopodobnie nie chcesz, aby symbol waluty w polu tekstowym był edytowany).
Atrybut można użyć DisplayFormat
samodzielnie, ale zazwyczaj dobrym pomysłem jest użycie atrybutu DataType
. Atrybut DataType
przekazuje semantyka danych, w przeciwieństwie do sposobu renderowania ich na ekranie, i zapewnia następujące korzyści, które nie są uzyskiwane za pomocą elementu DisplayFormat:
Przeglądarka może włączyć funkcje HTML5 (na przykład w celu wyświetlania kontrolki kalendarza, symbolu waluty odpowiedniego dla ustawień regionalnych, linków poczty e-mail itp.)
Domyślnie przeglądarka będzie renderować dane przy użyciu poprawnego formatu na podstawie ustawień regionalnych.
Atrybut
DataType
może umożliwić MVC wybranie odpowiedniego szablonu pola w celu renderowania danych (DisplayFormat
jeśli jest używany przez siebie przy użyciu szablonu ciągu).
Uwaga
Sprawdzanie poprawności zapytania jQuery nie działa z atrybutem Range
i DateTime
. Na przykład następujący kod zawsze wyświetla błąd weryfikacji po stronie klienta, nawet jeśli data znajduje się w określonym zakresie:
[Range(typeof(DateTime), "1/1/1966", "1/1/2020")]
Aby użyć atrybutu z atrybutem , należy wyłączyć walidację Range
daty zapytania jQuery.DateTime
Zazwyczaj nie jest dobrym rozwiązaniem do kompilowania dat twardych w modelach, dlatego użycie atrybutu Range
i DateTime
jest zniechęcane.
Poniższy kod przedstawia łączenie atrybutów w jednym wierszu:
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models;
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
public string Title { get; set; }
[Display(Name = "Release Date"), DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$"), Required, StringLength(30)]
public string Genre { get; set; }
[Range(1, 100), DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$"), StringLength(5)]
public string Rating { get; set; }
}
W następnej części serii przejrzymy aplikację i wprowadzimy pewne ulepszenia w automatycznie wygenerowanych Details
metodach i Delete
.
Dodatkowe zasoby
W tej sekcji:
- Logika walidacji jest dodawana do
Movie
modelu. - Upewnij się, że reguły walidacji są wymuszane za każdym razem, gdy użytkownik tworzy lub edytuje film.
Utrzymywanie suchych elementów
Jednym z zestawów projektu MVC jest DRY ("Nie powtarzaj siebie"). ASP.NET Core MVC zachęca do określenia funkcjonalności lub zachowania tylko raz, a następnie ich odzwierciedlenia wszędzie w aplikacji. Zmniejsza to ilość kodu potrzebnego do zapisania i sprawia, że kod, który zapisujesz mniej podatny na błędy, ułatwia testowanie i ułatwia konserwację.
Obsługa walidacji zapewniana przez MVC i Entity Framework Core Code First jest dobrym przykładem zasady DRY w działaniu. Reguły walidacji można deklaratywne określić w jednym miejscu (w klasie modelu), a reguły są wymuszane wszędzie w aplikacji.
Dodawanie reguł walidacji do modelu filmu
Przestrzeń nazw DataAnnotations udostępnia zestaw wbudowanych atrybutów weryfikacji, które są stosowane deklaratywnie do klasy lub właściwości. Przestrzeń nazw DataAnnotations zawiera również atrybuty formatowania, takie jak DataType
, które pomagają w formatowaniu i nie zapewniają żadnej walidacji.
Zaktualizuj klasę Movie
, aby korzystać z wbudowanych Required
atrybutów , StringLength
, RegularExpression
i Range
walidacji.
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models
{
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
[Required]
public string? Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$")]
[Required]
[StringLength(30)]
public string? Genre { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$")]
[StringLength(5)]
[Required]
public string? Rating { get; set; }
}
}
Atrybuty weryfikacji określają zachowanie, które chcesz wymusić na właściwościach modelu, do których są stosowane:
Atrybuty
Required
iMinimumLength
wskazują, że właściwość musi mieć wartość, ale nic nie uniemożliwia użytkownikowi wprowadzania białych znaków w celu spełnienia tej weryfikacji.Atrybut
RegularExpression
służy do ograniczania liczby znaków, które mogą być wprowadzane jako dane wejściowe. W poprzednim kodzie w polu „Genre” (Gatunek):- Muszą być używane tylko litery.
- Pierwsza litera musi być wielką literą. Białe spacje są dozwolone, gdy liczby i znaki specjalne są niedozwolone.
W atrybucie
RegularExpression
„Rating” (Klasyfikacja):- Pierwszy znak musi być wielką literą.
- Kolejne znaki mogą być znakami specjalnymi i cyframi. W atrybucie Rating wartość „PG-13” jest prawidłowa, ale w przypadku atrybutu Genre — nie.
Atrybut
Range
ogranicza wartość do określonego zakresu.Atrybut
StringLength
umożliwia ustawienie maksymalnej długości właściwości ciągu i opcjonalnie jego minimalnej długości.Typy wartości (takie jak
decimal
,int
,float
,DateTime
) są z natury wymagane i nie wymagają atrybutu[Required]
.
Automatyczne wymuszanie reguł weryfikacji przez platformę ASP.NET Core pomaga zwiększyć niezawodność aplikacji. Gwarantuje to również, że nie można zapomnieć o zweryfikowaniu czegoś i przypadkowo niech złych danych w bazie danych.
Interfejs użytkownika błędu walidacji
Uruchom aplikację i przejdź do kontrolera Filmy.
Wybierz link Utwórz nowy, aby dodać nowy film. Wypełnij formularz kilkoma nieprawidłowymi wartościami. Gdy tylko walidacja po stronie klienta jQuery wykryje błąd, zostanie wyświetlony komunikat o błędzie.
Uwaga
Może nie być możliwe wprowadzenie przecinków dziesiętnych w polach dziesiętnych. Aby obsługiwać walidację jQuery dla ustawień regionalnych innych niż angielski, które używają przecinka (",") dla przecinka dziesiętnego i formatów dat innych niż angielskie stany USA, należy wykonać kroki w celu globalizacji aplikacji. Zobacz ten komentarz usługi GitHub 4076 , aby uzyskać instrukcje dotyczące dodawania przecinka dziesiętnego.
Zwróć uwagę, że formularz automatycznie renderował odpowiedni komunikat o błędzie weryfikacji w każdym polu zawierającym nieprawidłową wartość. Błędy są wymuszane po stronie klienta (przy użyciu języków JavaScript i jQuery) i po stronie serwera (w przypadku wyłączenia języka JavaScript przez użytkownika).
Ważną korzyścią jest to, że nie trzeba zmieniać pojedynczego wiersza kodu w MoviesController
klasie lub w Create.cshtml
widoku, aby włączyć ten interfejs użytkownika weryfikacji. Kontroler i widoki utworzone wcześniej w tym samouczku automatycznie podniosły reguły weryfikacji określone przy użyciu atrybutów weryfikacji we właściwościach Movie
klasy modelu. Przetestuj walidację Edit
przy użyciu metody akcji i zastosowano tę samą walidację.
Dane formularza nie są wysyłane do serwera, dopóki nie wystąpią żadne błędy weryfikacji po stronie klienta. Możesz to sprawdzić, umieszczając punkt przerwania w metodzie HTTP Post
przy użyciu narzędzia Fiddler lub Narzędzia programistyczne F12.
Jak działa walidacja
Możesz się zastanawiać, jak interfejs użytkownika weryfikacji został wygenerowany bez żadnych aktualizacji kodu w kontrolerze lub widokach. Poniższy kod przedstawia dwie Create
metody.
// GET: Movies/Create
public IActionResult Create()
{
return View();
}
// POST: Movies/Create
// To protect from overposting attacks, enable the specific properties you want to bind to.
// For more details, see http://go.microsoft.com/fwlink/?LinkId=317598.
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Create([Bind("Id,Title,ReleaseDate,Genre,Price,Rating")] Movie movie)
{
if (ModelState.IsValid)
{
_context.Add(movie);
await _context.SaveChangesAsync();
return RedirectToAction(nameof(Index));
}
return View(movie);
}
Pierwsza metoda akcji (HTTP GET) Create
wyświetla początkowy formularz Utwórz. Druga wersja ([HttpPost]
) obsługuje wpis formularza. Druga Create
metoda (wersja [HttpPost]
) wywołuje metodę ModelState.IsValid
w celu sprawdzenia, czy film ma jakiekolwiek błędy walidacji. Wywołanie tej metody ocenia wszystkie atrybuty walidacji, które zostały zastosowane do obiektu. Jeśli obiekt zawiera błędy weryfikacji, Create
metoda ponownie wyświetli formularz. Jeśli nie ma żadnych błędów, metoda zapisuje nowy film w bazie danych. W naszym przykładzie filmu formularz nie jest publikowany na serwerze, gdy występują błędy walidacji wykryte po stronie klienta; druga Create
metoda nigdy nie jest wywoływana, gdy występują błędy weryfikacji po stronie klienta. Jeśli wyłączysz język JavaScript w przeglądarce, walidacja klienta jest wyłączona i możesz przetestować metodę ModelState.IsValid
HTTP POSTCreate
, wykrywając błędy walidacji.
Możesz ustawić punkt przerwania w metodzie [HttpPost] Create
i sprawdzić, czy metoda nigdy nie jest wywoływana, walidacja po stronie klienta nie będzie przesyłać danych formularza po wykryciu błędów walidacji. Jeśli wyłączysz język JavaScript w przeglądarce, prześlij formularz z błędami, punkt przerwania zostanie trafiony. Nadal uzyskujesz pełną walidację bez języka JavaScript.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Firefox.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Chrome.
Po wyłączeniu języka JavaScript opublikuj nieprawidłowe dane i przejdź przez debuger.
Część szablonu Create.cshtml
widoku jest wyświetlana w następującym znaczniku:
<h4>Movie</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Create">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="Title" class="control-label"></label>
<input asp-for="Title" class="form-control" />
<span asp-validation-for="Title" class="text-danger"></span>
</div>
@*Markup removed for brevity.*@
Powyższy znacznik jest używany przez metody akcji do wyświetlania początkowego formularza i ponownego redysponowania go w przypadku błędu.
Pomocnik tagów wejściowych używa atrybutów DataAnnotations i tworzy atrybuty HTML wymagane do weryfikacji jQuery po stronie klienta. Pomocnik tagu weryfikacji wyświetla błędy walidacji. Aby uzyskać więcej informacji, zobacz Walidacja .
Naprawdę miło jest to, że ani kontroler, ani Create
szablon widoku nie wie nic o rzeczywistych regułach walidacji, które są wymuszane, ani o wyświetlanych konkretnych komunikatach o błędach. Reguły walidacji i ciągi błędów są określone tylko w Movie
klasie. Te same reguły sprawdzania poprawności są automatycznie stosowane do Edit
widoku i wszystkich innych szablonów widoków, które można utworzyć, aby edytować model.
Jeśli musisz zmienić logikę weryfikacji, możesz to zrobić w dokładnie jednym miejscu, dodając atrybuty weryfikacji do modelu (w tym przykładzie Movie
klasa). Nie trzeba martwić się o niespójność różnych części aplikacji ze sposobem wymuszania reguł — cała logika walidacji zostanie zdefiniowana w jednym miejscu i używana wszędzie. Dzięki temu kod jest bardzo czysty i ułatwia konserwację i rozwijanie. Oznacza to, że będziesz w pełni przestrzegać zasady DRY.
Używanie atrybutów Typu danych
Movie.cs
Otwórz plik i sprawdź klasęMovie
. System.ComponentModel.DataAnnotations
Przestrzeń nazw udostępnia atrybuty formatowania oprócz wbudowanego zestawu atrybutów weryfikacji. Zastosowaliśmy DataType
już wartość wyliczenia do daty wydania i pól ceny. Poniższy kod przedstawia ReleaseDate
właściwości i Price
z odpowiednim DataType
atrybutem.
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
Atrybuty DataType
zawierają tylko wskazówki dla aparatu wyświetlania, aby sformatować dane i dostarczyć elementy/atrybuty, takie jak <a>
adres URL i <a href="mailto:EmailAddress.com">
adres e-mail. Możesz użyć atrybutu RegularExpression
, aby zweryfikować format danych. Atrybut DataType
służy do określania typu danych, który jest bardziej szczegółowy niż typ wewnętrzny bazy danych, nie są atrybutami walidacji. W tym przypadku chcemy śledzić tylko datę, a nie godzinę. Wyliczenie DataType
zawiera wiele typów danych, takich jak Data, Godzina, Numer telefonu, Waluta, Adres e-mail i inne. Atrybut DataType
może również umożliwić aplikacji automatyczne udostępnianie funkcji specyficznych dla typu. Na przykład mailto:
można utworzyć link dla DataType.EmailAddress
elementu , a selektor dat można udostępnić DataType.Date
w przeglądarkach obsługujących kod HTML5. Atrybuty DataType
emitują atrybuty HTML 5 data-
(wymawiane kreski danych), które przeglądarki HTML 5 mogą zrozumieć. Atrybuty DataType
nie zapewniają żadnej walidacji.
DataType.Date
nie określa formatu wyświetlanej daty. Domyślnie pole danych jest wyświetlane zgodnie z domyślnymi formatami na podstawie serwera CultureInfo
.
Atrybut DisplayFormat
jest używany do jawnego określenia formatu daty:
[DisplayFormat(DataFormatString = "{0:yyyy-MM-dd}", ApplyFormatInEditMode = true)]
public DateTime ReleaseDate { get; set; }
Ustawienie ApplyFormatInEditMode
określa, że formatowanie powinno być również stosowane, gdy wartość jest wyświetlana w polu tekstowym do edycji. (Możesz nie chcieć tego dla niektórych pól — na przykład w przypadku wartości walutowych prawdopodobnie nie chcesz, aby symbol waluty w polu tekstowym był edytowany).
Atrybut można użyć DisplayFormat
samodzielnie, ale zazwyczaj dobrym pomysłem jest użycie atrybutu DataType
. Atrybut DataType
przekazuje semantyka danych, w przeciwieństwie do sposobu renderowania ich na ekranie, i zapewnia następujące korzyści, które nie są uzyskiwane za pomocą elementu DisplayFormat:
Przeglądarka może włączyć funkcje HTML5 (na przykład w celu wyświetlania kontrolki kalendarza, symbolu waluty odpowiedniego dla ustawień regionalnych, linków poczty e-mail itp.)
Domyślnie przeglądarka będzie renderować dane przy użyciu poprawnego formatu na podstawie ustawień regionalnych.
Atrybut
DataType
może umożliwić MVC wybranie odpowiedniego szablonu pola w celu renderowania danych (DisplayFormat
jeśli jest używany przez siebie przy użyciu szablonu ciągu).
Uwaga
Sprawdzanie poprawności zapytania jQuery nie działa z atrybutem Range
i DateTime
. Na przykład następujący kod zawsze wyświetla błąd weryfikacji po stronie klienta, nawet jeśli data znajduje się w określonym zakresie:
[Range(typeof(DateTime), "1/1/1966", "1/1/2020")]
Aby użyć atrybutu z atrybutem , należy wyłączyć walidację Range
daty zapytania jQuery.DateTime
Zazwyczaj nie jest dobrym rozwiązaniem do kompilowania dat twardych w modelach, dlatego użycie atrybutu Range
i DateTime
jest zniechęcane.
Poniższy kod przedstawia łączenie atrybutów w jednym wierszu:
using System;
using System.ComponentModel.DataAnnotations;
using System.ComponentModel.DataAnnotations.Schema;
namespace MvcMovie.Models
{
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
public string Title { get; set; }
[Display(Name = "Release Date"), DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$"), Required, StringLength(30)]
public string Genre { get; set; }
[Range(1, 100), DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$"), StringLength(5)]
public string Rating { get; set; }
}
}
W następnej części serii przejrzymy aplikację i wprowadzimy pewne ulepszenia w automatycznie wygenerowanych Details
metodach i Delete
.
Dodatkowe zasoby
W tej sekcji:
- Logika walidacji jest dodawana do
Movie
modelu. - Upewnij się, że reguły walidacji są wymuszane za każdym razem, gdy użytkownik tworzy lub edytuje film.
Utrzymywanie suchych elementów
Jednym z zestawów projektu MVC jest DRY ("Nie powtarzaj siebie"). ASP.NET Core MVC zachęca do określenia funkcjonalności lub zachowania tylko raz, a następnie ich odzwierciedlenia wszędzie w aplikacji. Zmniejsza to ilość kodu potrzebnego do zapisania i sprawia, że kod, który zapisujesz mniej podatny na błędy, ułatwia testowanie i ułatwia konserwację.
Obsługa walidacji zapewniana przez MVC i Entity Framework Core Code First jest dobrym przykładem zasady DRY w działaniu. Reguły walidacji można deklaratywne określić w jednym miejscu (w klasie modelu), a reguły są wymuszane wszędzie w aplikacji.
Dodawanie reguł walidacji do modelu filmu
Przestrzeń nazw DataAnnotations udostępnia zestaw wbudowanych atrybutów weryfikacji, które są stosowane deklaratywnie do klasy lub właściwości. Przestrzeń nazw DataAnnotations zawiera również atrybuty formatowania, takie jak DataType
, które pomagają w formatowaniu i nie zapewniają żadnej walidacji.
Zaktualizuj klasę Movie
, aby korzystać z wbudowanych Required
atrybutów , StringLength
, RegularExpression
i Range
walidacji.
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
[Required]
public string Title { get; set; }
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$")]
[Required]
[StringLength(30)]
public string Genre { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$")]
[StringLength(5)]
[Required]
public string Rating { get; set; }
}
Atrybuty weryfikacji określają zachowanie, które chcesz wymusić na właściwościach modelu, do których są stosowane:
Atrybuty
Required
iMinimumLength
wskazują, że właściwość musi mieć wartość, ale nic nie uniemożliwia użytkownikowi wprowadzania białych znaków w celu spełnienia tej weryfikacji.Atrybut
RegularExpression
służy do ograniczania liczby znaków, które mogą być wprowadzane jako dane wejściowe. W poprzednim kodzie w polu „Genre” (Gatunek):- Muszą być używane tylko litery.
- Pierwsza litera musi być wielką literą. Dozwolone są białe spacje, a liczby i znaki specjalne nie są dozwolone.
W atrybucie
RegularExpression
„Rating” (Klasyfikacja):- Pierwszy znak musi być wielką literą.
- Kolejne znaki mogą być znakami specjalnymi i cyframi. W atrybucie Rating wartość „PG-13” jest prawidłowa, ale w przypadku atrybutu Genre — nie.
Atrybut
Range
ogranicza wartość do określonego zakresu.Atrybut
StringLength
umożliwia ustawienie maksymalnej długości właściwości ciągu i opcjonalnie jego minimalnej długości.Typy wartości (takie jak
decimal
,int
,float
,DateTime
) są z natury wymagane i nie wymagają atrybutu[Required]
.
Automatyczne wymuszanie reguł weryfikacji przez platformę ASP.NET Core pomaga zwiększyć niezawodność aplikacji. Gwarantuje to również, że nie można zapomnieć o zweryfikowaniu czegoś i przypadkowo niech złych danych w bazie danych.
Interfejs użytkownika błędu walidacji
Uruchom aplikację i przejdź do kontrolera Filmy.
Naciśnij link Utwórz nowy, aby dodać nowy film. Wypełnij formularz kilkoma nieprawidłowymi wartościami. Gdy tylko walidacja po stronie klienta jQuery wykryje błąd, zostanie wyświetlony komunikat o błędzie.
Uwaga
Może nie być możliwe wprowadzenie przecinków dziesiętnych w polach dziesiętnych. Aby obsługiwać walidację jQuery dla ustawień regionalnych innych niż angielski, które używają przecinka (",") dla przecinka dziesiętnego i formatów dat innych niż angielskie stany USA, należy wykonać kroki w celu globalizacji aplikacji. Zobacz ten komentarz usługi GitHub 4076 , aby uzyskać instrukcje dotyczące dodawania przecinka dziesiętnego.
Zwróć uwagę, że formularz automatycznie renderował odpowiedni komunikat o błędzie weryfikacji w każdym polu zawierającym nieprawidłową wartość. Błędy są wymuszane po stronie klienta (przy użyciu języków JavaScript i jQuery) i po stronie serwera (w przypadku wyłączenia języka JavaScript przez użytkownika).
Ważną korzyścią jest to, że nie trzeba zmieniać pojedynczego wiersza kodu w MoviesController
klasie lub w Create.cshtml
widoku, aby włączyć ten interfejs użytkownika weryfikacji. Kontroler i widoki utworzone wcześniej w tym samouczku automatycznie podniosły reguły weryfikacji określone przy użyciu atrybutów weryfikacji we właściwościach Movie
klasy modelu. Przetestuj walidację Edit
przy użyciu metody akcji i zastosowano tę samą walidację.
Dane formularza nie są wysyłane do serwera, dopóki nie wystąpią żadne błędy weryfikacji po stronie klienta. Możesz to sprawdzić, umieszczając punkt przerwania w metodzie HTTP Post
przy użyciu narzędzia Fiddler lub Narzędzia programistyczne F12.
Jak działa walidacja
Możesz się zastanawiać, jak interfejs użytkownika weryfikacji został wygenerowany bez żadnych aktualizacji kodu w kontrolerze lub widokach. Poniższy kod przedstawia dwie Create
metody.
// GET: Movies/Create
public IActionResult Create()
{
return View();
}
// POST: Movies/Create
[HttpPost]
[ValidateAntiForgeryToken]
public async Task<IActionResult> Create(
[Bind("ID,Title,ReleaseDate,Genre,Price, Rating")] Movie movie)
{
if (ModelState.IsValid)
{
_context.Add(movie);
await _context.SaveChangesAsync();
return RedirectToAction("Index");
}
return View(movie);
}
Pierwsza metoda akcji (HTTP GET) Create
wyświetla początkowy formularz Utwórz. Druga wersja ([HttpPost]
) obsługuje wpis formularza. Druga Create
metoda (wersja [HttpPost]
) wywołuje metodę ModelState.IsValid
w celu sprawdzenia, czy film ma jakiekolwiek błędy walidacji. Wywołanie tej metody ocenia wszystkie atrybuty walidacji, które zostały zastosowane do obiektu. Jeśli obiekt zawiera błędy weryfikacji, Create
metoda ponownie wyświetli formularz. Jeśli nie ma żadnych błędów, metoda zapisuje nowy film w bazie danych. W naszym przykładzie filmu formularz nie jest publikowany na serwerze, gdy występują błędy walidacji wykryte po stronie klienta; druga Create
metoda nigdy nie jest wywoływana, gdy występują błędy weryfikacji po stronie klienta. Jeśli wyłączysz język JavaScript w przeglądarce, walidacja klienta jest wyłączona i możesz przetestować metodę ModelState.IsValid
HTTP POSTCreate
, wykrywając błędy walidacji.
Możesz ustawić punkt przerwania w metodzie [HttpPost] Create
i sprawdzić, czy metoda nigdy nie jest wywoływana, walidacja po stronie klienta nie będzie przesyłać danych formularza po wykryciu błędów walidacji. Jeśli wyłączysz język JavaScript w przeglądarce, prześlij formularz z błędami, punkt przerwania zostanie trafiony. Nadal uzyskujesz pełną walidację bez języka JavaScript.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Firefox.
Na poniższej ilustracji przedstawiono sposób wyłączania języka JavaScript w przeglądarce Chrome.
Po wyłączeniu języka JavaScript opublikuj nieprawidłowe dane i przejdź przez debuger.
Część szablonu Create.cshtml
widoku jest wyświetlana w następującym znaczniku:
<h4>Movie</h4>
<hr />
<div class="row">
<div class="col-md-4">
<form asp-action="Create">
<div asp-validation-summary="ModelOnly" class="text-danger"></div>
<div class="form-group">
<label asp-for="Title" class="control-label"></label>
<input asp-for="Title" class="form-control" />
<span asp-validation-for="Title" class="text-danger"></span>
</div>
@*Markup removed for brevity.*@
Powyższy znacznik jest używany przez metody akcji do wyświetlania początkowego formularza i ponownego redysponowania go w przypadku błędu.
Pomocnik tagów wejściowych używa atrybutów DataAnnotations i tworzy atrybuty HTML wymagane do weryfikacji jQuery po stronie klienta. Pomocnik tagu weryfikacji wyświetla błędy walidacji. Aby uzyskać więcej informacji, zobacz Walidacja .
Naprawdę miło jest to, że ani kontroler, ani Create
szablon widoku nie wie nic o rzeczywistych regułach walidacji, które są wymuszane, ani o wyświetlanych konkretnych komunikatach o błędach. Reguły walidacji i ciągi błędów są określone tylko w Movie
klasie. Te same reguły sprawdzania poprawności są automatycznie stosowane do Edit
widoku i wszystkich innych szablonów widoków, które można utworzyć, aby edytować model.
Jeśli musisz zmienić logikę weryfikacji, możesz to zrobić w dokładnie jednym miejscu, dodając atrybuty weryfikacji do modelu (w tym przykładzie Movie
klasa). Nie trzeba martwić się o niespójność różnych części aplikacji ze sposobem wymuszania reguł — cała logika walidacji zostanie zdefiniowana w jednym miejscu i używana wszędzie. Dzięki temu kod jest bardzo czysty i ułatwia konserwację i rozwijanie. Oznacza to, że będziesz w pełni przestrzegać zasady DRY.
Używanie atrybutów Typu danych
Movie.cs
Otwórz plik i sprawdź klasęMovie
. System.ComponentModel.DataAnnotations
Przestrzeń nazw udostępnia atrybuty formatowania oprócz wbudowanego zestawu atrybutów weryfikacji. Zastosowaliśmy DataType
już wartość wyliczenia do daty wydania i pól ceny. Poniższy kod przedstawia ReleaseDate
właściwości i Price
z odpowiednim DataType
atrybutem.
[Display(Name = "Release Date")]
[DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[Range(1, 100)]
[DataType(DataType.Currency)]
public decimal Price { get; set; }
Atrybuty DataType
zawierają tylko wskazówki dla aparatu wyświetlania w celu formatowania danych (i dostarcza elementy/atrybuty, takie jak <a>
adres URL i <a href="mailto:EmailAddress.com">
adres e-mail. Możesz użyć atrybutu RegularExpression
, aby zweryfikować format danych. Atrybut DataType
służy do określania typu danych, który jest bardziej szczegółowy niż typ wewnętrzny bazy danych, nie są atrybutami walidacji. W tym przypadku chcemy śledzić tylko datę, a nie godzinę. Wyliczenie DataType
zawiera wiele typów danych, takich jak Data, Godzina, Numer telefonu, Waluta, Adres e-mail i inne. Atrybut DataType
może również umożliwić aplikacji automatyczne udostępnianie funkcji specyficznych dla typu. Na przykład mailto:
można utworzyć link dla DataType.EmailAddress
elementu , a selektor dat można udostępnić DataType.Date
w przeglądarkach obsługujących kod HTML5. Atrybuty DataType
emitują atrybuty HTML 5 data-
(wymawiane kreski danych), które przeglądarki HTML 5 mogą zrozumieć. Atrybuty DataType
nie zapewniają żadnej walidacji.
DataType.Date
nie określa formatu wyświetlanej daty. Domyślnie pole danych jest wyświetlane zgodnie z domyślnymi formatami na podstawie serwera CultureInfo
.
Atrybut DisplayFormat
jest używany do jawnego określenia formatu daty:
[DisplayFormat(DataFormatString = "{0:yyyy-MM-dd}", ApplyFormatInEditMode = true)]
public DateTime ReleaseDate { get; set; }
Ustawienie ApplyFormatInEditMode
określa, że formatowanie powinno być również stosowane, gdy wartość jest wyświetlana w polu tekstowym do edycji. (Możesz nie chcieć tego dla niektórych pól — na przykład w przypadku wartości walutowych prawdopodobnie nie chcesz, aby symbol waluty w polu tekstowym był edytowany).
Atrybut można użyć DisplayFormat
samodzielnie, ale zazwyczaj dobrym pomysłem jest użycie atrybutu DataType
. Atrybut DataType
przekazuje semantyka danych, w przeciwieństwie do sposobu renderowania ich na ekranie, i zapewnia następujące korzyści, które nie są uzyskiwane za pomocą elementu DisplayFormat:
Przeglądarka może włączyć funkcje HTML5 (na przykład w celu wyświetlania kontrolki kalendarza, symbolu waluty odpowiedniego dla ustawień regionalnych, linków poczty e-mail itp.)
Domyślnie przeglądarka będzie renderować dane przy użyciu poprawnego formatu na podstawie ustawień regionalnych.
Atrybut
DataType
może umożliwić MVC wybranie odpowiedniego szablonu pola w celu renderowania danych (DisplayFormat
jeśli jest używany przez siebie przy użyciu szablonu ciągu).
Uwaga
Sprawdzanie poprawności zapytania jQuery nie działa z atrybutem Range
i DateTime
. Na przykład następujący kod zawsze wyświetla błąd weryfikacji po stronie klienta, nawet jeśli data znajduje się w określonym zakresie:
[Range(typeof(DateTime), "1/1/1966", "1/1/2020")]
Aby użyć atrybutu z atrybutem , należy wyłączyć walidację Range
daty zapytania jQuery.DateTime
Zazwyczaj nie jest dobrym rozwiązaniem do kompilowania dat twardych w modelach, dlatego użycie atrybutu Range
i DateTime
jest zniechęcane.
Poniższy kod przedstawia łączenie atrybutów w jednym wierszu:
public class Movie
{
public int Id { get; set; }
[StringLength(60, MinimumLength = 3)]
public string Title { get; set; }
[Display(Name = "Release Date"), DataType(DataType.Date)]
public DateTime ReleaseDate { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z\s]*$"), Required, StringLength(30)]
public string Genre { get; set; }
[Range(1, 100), DataType(DataType.Currency)]
[Column(TypeName = "decimal(18, 2)")]
public decimal Price { get; set; }
[RegularExpression(@"^[A-Z]+[a-zA-Z0-9""'\s-]*$"), StringLength(5)]
public string Rating { get; set; }
}
W następnej części serii przejrzymy aplikację i wprowadzimy pewne ulepszenia w automatycznie wygenerowanych Details
metodach i Delete
.