Zastanawiałem się, czy można wyłączyć atrybut Required validation w niektórych akcjach kontrolera. Zastanawiam się nad tym, ponieważ w jednym z moich formularzy edycji nie wymagam od użytkownika wprowadzania wartości pól, które już wcześniej określił. Jednak potem implementuję logikę, że kiedy wprowadzają wartość, używa specjalnej logiki do aktualizacji modelu, takiej jak haszowanie wartości itp.
Jakieś sugestie, jak obejść ten problem?
EDYCJA:
I tak, walidacja klienta jest tutaj problemem, ponieważ nie pozwoli im przesłać formularza bez wpisania wartości.
c#
asp.net-mvc
asp.net-mvc-3
data-annotations
Alex Hope O'Connor
źródło
źródło
RequiredAttr
całkowite usunięcie i wykonanie sprawdzenia po stronie serwera, gdy zajdzie taka potrzeba. Ale to byłoby trudne dla klientaOdpowiedzi:
Ten problem można łatwo rozwiązać za pomocą modeli widoków. Modele widoków to klasy, które są specjalnie dostosowane do potrzeb danego widoku. Na przykład w twoim przypadku możesz mieć następujące modele widoku:
które zostaną użyte w odpowiednich akcjach kontrolera:
źródło
Update(FormCollection collection)
, a przynajmniej ja nigdy. I zawsze definiować i używać konkretnego widoku modelu:Update(UpdateViewView model)
.Insert
. Dziękuję za zwrócenie uwagi.Jeśli chcesz tylko wyłączyć sprawdzanie poprawności dla pojedynczego pola po stronie klienta, możesz zastąpić atrybuty walidacji w następujący sposób:
źródło
@Html.TexBoxFor(model => model.SomeValue, new { data_val = false })
- łatwiejsze do odczytania IMO.$(".search select").attr('data-val', false);
Wiem, że na to pytanie udzielono już dawno odpowiedzi i zaakceptowana odpowiedź faktycznie zadziała. Ale przeszkadza mi jedna rzecz: kopiowanie 2 modeli tylko w celu wyłączenia walidacji.
Oto moja sugestia:
W ten sposób nie musisz zawracać sobie głowy walidacją po stronie klienta / serwera, framework będzie zachowywał się tak, jak powinien. Ponadto, jeśli zdefiniujesz
[Display]
atrybut w klasie bazowej, nie musisz ponownie definiować go w plikuUpdateModel
.Nadal możesz używać tych klas w ten sam sposób:
źródło
Możesz usunąć całą weryfikację z właściwości za pomocą następujących elementów w akcji kontrolera.
@ Komentarz Iana dotyczący MVC5
Nadal jest możliwe
Trochę denerwujące, że tracisz statyczne wpisywanie dzięki zaktualizowanemu interfejsowi API. Możesz osiągnąć coś podobnego do starego sposobu, tworząc instancję pomocnika HTML i używając metod NameExtensions .
źródło
ModelState
pasującej do tego podpisu. Przynajmniej nie w MVC 5.Strona klienta Aby wyłączyć walidację formularza, poniżej podano wiele opcji opartych na moich badaniach. Mam nadzieję, że jeden z nich będzie dla ciebie pracował.
opcja 1
Wolę to i to działa idealnie dla mnie.
i wzywając to jak
Opcja 2
Wariant 3
Opcja 4
Opcja 5
Po stronie serwera
Utwórz atrybut i oznacz swoją metodę akcji tym atrybutem. Dostosuj to, aby dostosować się do swoich konkretnych potrzeb.
Lepsze podejście zostało opisane tutaj. Włącz / wyłącz dynamicznie sprawdzanie poprawności po stronie serwera MVC
źródło
Osobiście skłaniałbym się do podejścia, które Darin Dimitrov pokazał w swoim rozwiązaniu. Dzięki temu możesz korzystać z adnotacji danych z walidacją ORAZ mieć osobne atrybuty danych w każdym ViewModel odpowiadające wykonywanemu zadaniu. Aby zminimalizować ilość pracy związanej z kopiowaniem między modelem i modelem widoku, należy spojrzeć na AutoMapper lub ValueInjecter . Obie mają swoje mocne strony, więc sprawdź je obie.
Innym możliwym podejściem byłoby wyprowadzenie modelu widoku lub modelu z IValidatableObject. Daje to możliwość zaimplementowania funkcji Validate. W walidacji można zwrócić listę elementów ValidationResult lub wydać zwrot wydajności dla każdego problemu wykrytego podczas walidacji.
ValidationResult składa się z komunikatu o błędzie i listy ciągów z nazwami pól. Komunikaty o błędach zostaną wyświetlone w miejscu w pobliżu pól wprowadzania.
źródło
Uważam, że najczystszym sposobem jest wyłączenie weryfikacji po stronie klienta, a po stronie serwera będziesz musiał:
Wydaje się, że nawet niestandardowy model widoku nie rozwiąże problemu, ponieważ liczba tych pól z wstępnie wypełnionymi odpowiedziami może się różnić. Jeśli tego nie zrobią, niestandardowy model widoku może być najłatwiejszym sposobem, ale używając powyższej techniki, możesz obejść problemy z walidacją.
źródło
to była odpowiedź kogoś innego w komentarzach ... ale powinna to być odpowiedź prawdziwa:
$("#SomeValue").removeAttr("data-val-required")
testowane na MVC 6 z polem mającym
[Required]
atrybutodpowiedź skradziona z https://stackoverflow.com/users/73382/rob powyżej
źródło
Miałem ten problem podczas tworzenia widoku edycji dla mojego modelu i chcę zaktualizować tylko jedno pole.
Moje rozwiązanie na najprostszy sposób polega na umieszczeniu dwóch pól za pomocą:
Komentarze to pole, które aktualizuję tylko w widoku edycji, które nie ma wymaganego atrybutu.
Jednostka ASP.NET MVC 3
źródło
AFAIK nie możesz usunąć atrybutu w czasie wykonywania, ale tylko zmienić ich wartości (np. Tylko do odczytu prawda / fałsz) szukaj tutaj czegoś podobnego . Jako inny sposób robienia tego, co chcesz, bez mieszania się z atrybutami, użyję ViewModel dla twojej konkretnej akcji, abyś mógł wstawić całą logikę bez łamania logiki potrzebnej innym kontrolerom. Jeśli spróbujesz uzyskać jakiś kreator (formularz wieloetapowy), możesz zamiast tego serializować już skompilowane pola i za pomocą TempData zabrać je ze sobą. (aby uzyskać pomoc w serializacji deserializacji, możesz użyć kontraktów futures MVC )
źródło
To, co powiedział @Darin, jest tym, co polecam. Dodam jednak do tego (i w odpowiedzi na jeden z komentarzy), że w rzeczywistości można również użyć tej metody dla typów pierwotnych, takich jak bit, bool, a nawet struktur, takich jak Guid, po prostu ustawiając je na wartość null. Gdy to zrobisz,
Required
atrybut będzie działał zgodnie z oczekiwaniami.źródło
Od MVC 5 można to łatwo osiągnąć, dodając to do pliku
global.asax
.źródło
Szukałem rozwiązania, w którym mógłbym użyć tego samego modelu do wstawiania i aktualizacji w webowym api. W mojej sytuacji jest to zawsze treść ciała. Te
[Requiered]
atrybuty muszą być pomijane, jeśli jest to metoda aktualizacji. W moim rozwiązaniu umieszczasz atrybut[IgnoreRequiredValidations]
nad metodą. Jest to następujące:Co jeszcze trzeba zrobić? Podczas uruchamiania należy utworzyć i dodać własny BodyModelValidator. To jest w HttpConfiguration i wygląda następująco:
config.Services.Replace(typeof(IBodyModelValidator), new IgnoreRequiredOrDefaultBodyModelValidator());
Mój własny BodyModelValidator pochodzi z DefaultBodyModelValidator. I doszedłem do wniosku, że musiałem zastąpić metodę „ShallowValidate”. W tym zastąpieniu filtruję wymagane walidatory modelu. A teraz klasa IgnoreRequiredOrDefaultBodyModelValidator i klasa atrybutów IgnoreRequiredValidations:
Źródła:
string debug = new StackTrace().ToString()
aby dowiedzieć się, kto obsługuje walidację modelu.źródło
Jeśli nie chcesz używać innego ViewModel, możesz wyłączyć sprawdzanie poprawności klienta w widoku, a także usunąć walidacje na serwerze dla tych właściwości, które chcesz zignorować. Sprawdź tę odpowiedź, aby uzyskać głębsze wyjaśnienie https://stackoverflow.com/a/15248790/1128216
źródło
W moim przypadku ten sam Model był używany na wielu stronach do celów ponownego wykorzystania. Stworzyłem więc atrybut niestandardowy, który sprawdza wykluczenia
i w kontrolerze
Powiedz, że Model jest
źródło
Tak, można wyłączyć wymagany atrybut. Utwórz własny atrybut klasy niestandardowej (przykładowy kod o nazwie ChangeableRequired) do rozszerzenia z RequiredAtribute i Dodaj właściwość Disabled i Zastąp metodę IsValid, aby sprawdzić, czy jest wyłączona. Użyj odbicia, aby ustawić wyłączone poperty, na przykład:
Atrybut niestandardowy:
Zaktualizuj usługę, aby używać nowego atrybutu niestandardowego:
gdzie musisz wyłączyć właściwość, użyj odbicia, aby ją ustawić:
Czy to przyjemne i czyste?
Uwaga: powyższa weryfikacja zostanie wyłączona, gdy instancja obiektu będzie żyła \ aktywna ...
źródło