Ich habe ein merkwürdiges Problem mit der clientseitigen Validierung von ASP.NET MVC3. Ich habe folgende Klasse:
public class Instrument : BaseObject
{
public int Id { get; set; }
[Required(ErrorMessage = "Name is required.")]
[MaxLength(40, ErrorMessage = "Name cannot be longer than 40 characters.")]
public string Name { get; set; }
}
Aus meiner Sicht:
<div class="editor-field">
@Html.EditorFor(model => model.Name)
@Html.ValidationMessageFor(model => model.Name)
</div>
Und hier ist der generierte HTML-Code, den ich für das Textfeld für dieses Feld erhalte:
<input class="text-box single-line" data-val="true" data-val-required="Name is required." id="Name" name="Name" type="text" value="">
Keine Spur von MaxLengthAttribute
, aber alles andere scheint zu funktionieren.
Irgendwelche Ideen, was falsch läuft?
c#
asp.net-mvc
validation
asp.net-mvc-3
model-validation
Matt Jenkins
quelle
quelle
int.MaxValue
maximale Länge an und setzen die MinLength- Eigenschaft auf die gewünschte Mindestlänge. Nein, es ist nicht nur eine funktionale Problemumgehung. Es ist eines, das auch in der Praxis funktioniert.Ich habe nur einen Ausschnitt von jquery verwendet, um dieses Problem zu lösen.
$("input[data-val-length-max]").each(function (index, element) { var length = parseInt($(this).attr("data-val-length-max")); $(this).prop("maxlength", length); });
Der Selektor findet alle Elemente, für die ein Attributsatz data-val-length-max festgelegt ist. Dies ist das Attribut, das das StringLength-Validierungsattribut festlegt.
Jede Schleife durchläuft diese Übereinstimmungen und analysiert den Wert für dieses Attribut und weist ihn der Eigenschaft mxlength zu, die festgelegt werden sollte.
Fügen Sie dies einfach zu Ihrer Dokumentbereitschaftsfunktion hinzu, und schon kann es losgehen.
quelle
MaxLengthAttribute
funktioniert seit dem MVC 5.1-Update: Notizen ändernquelle
maxlength
Attribut immer noch nicht auf dasinput
Element an.In MVC 4 Wenn Sie eine maximale Länge im Eingabetyp Text wünschen? Sie können !
@Html.TextBoxFor(model => model.Item3.ADR_ZIP, new { @class = "gui-input ui-oblig", @maxlength = "5" })
quelle
Props an @ Nick-Harrison für seine Antwort:
$("input[data-val-length-max]").each(function (index, element) { var length = parseInt($(this).attr("data-val-length-max")); $(this).prop("maxlength", length); });
Ich habe mich gefragt, wozu parseInt () da ist. Ich habe es ohne Probleme vereinfacht ...
$("input[data-val-length-max]").each(function (index, element) { element.setAttribute("maxlength", element.getAttribute("data-val-length-max")) });
Ich hätte Nicks Antwort kommentiert, aber noch nicht genug Repräsentanten.
quelle
Ich hatte das gleiche Problem und konnte es lösen, indem ich die IValidatableObject-Schnittstelle in meinem Ansichtsmodell implementierte.
public class RegisterViewModel : IValidatableObject { /// <summary> /// Error message for Minimum password /// </summary> public static string PasswordLengthErrorMessage => $"The password must be at least {PasswordMinimumLength} characters"; /// <summary> /// Minimum acceptable password length /// </summary> public const int PasswordMinimumLength = 8; /// <summary> /// Gets or sets the password provided by the user. /// </summary> [Required] [DataType(DataType.Password)] [Display(Name = "Password")] public string Password { get; set; } /// <summary> /// Only need to validate the minimum length /// </summary> /// <param name="validationContext">ValidationContext, ignored</param> /// <returns>List of validation errors</returns> public IEnumerable<ValidationResult> Validate(ValidationContext validationContext) { var errorList = new List<ValidationResult>(); if ((Password?.Length ?? 0 ) < PasswordMinimumLength) { errorList.Add(new ValidationResult(PasswordLengthErrorMessage, new List<string>() {"Password"})); } return errorList; } }
Das Markup im Rasiermesser ist dann ...
<div class="form-group"> @Html.LabelFor(m => m.Password) @Html.PasswordFor(m => m.Password, new { @class = "form-control input-lg" } <div class="password-helper">Must contain: 8 characters, 1 upper-case, 1 lower-case </div> @Html.ValidationMessagesFor(m => m.Password, new { @class = "text-danger" }) </div>
Das funktioniert wirklich gut. Wenn ich stattdessen versuche, [StringLength] zu verwenden, ist der gerenderte HTML-Code einfach nicht korrekt. Die Validierung sollte wie folgt erfolgen:
<span class="text-danger field-validation-invalid field-validation-error" data-valmsg-for="Password" data-valmsg-replace="true"><span id="Password-error" class="">The Password should be a minimum of 8 characters long.</span></span>
Mit dem StringLengthAttribute wird der gerenderte HTML-Code als ValidationSummary angezeigt, was nicht korrekt ist. Das Lustige ist, dass wenn der Validator ausfällt, die Übermittlung immer noch blockiert ist!
quelle
StringLength
funktioniert super, ich habe es so benutzt:[StringLength(25,MinimumLength=1,ErrorMessage="Sorry only 25 characters allowed for ProductName")] public string ProductName { get; set; }
oder einfach
RegularExpression
ohne StringLength verwenden:[RegularExpression(@"^[a-zA-Z0-9'@&#.\s]{1,25}$", ErrorMessage = "Reg Says Sorry only 25 characters allowed for ProductName")] public string ProductName { get; set; }
aber für mich oben Methoden gaben Fehler in der Anzeigeansicht, weil ich bereits ProductName Feld in der Datenbank hatte, die mehr als 25 Zeichen hatte
Also bin ich endlich auf diesen und diesen Beitrag gestoßen und habe versucht, ohne dieses Modell zu validieren :
<div class="editor-field"> @Html.TextBoxFor(model => model.ProductName, new { @class = "form-control", data_val = "true", data_val_length = "Sorry only 25 characters allowed for ProductName", data_val_length_max = "25", data_val_length_min = "1" }) <span class="validation"> @Html.ValidationMessageFor(model => model.ProductName)</span> </div>
Dies hat mein Problem gelöst. Sie können die Validierung auch manuell mit jquery oder ModelState.AddModelError durchführen
Hoffnung hilft jemandem.
quelle
Ich weiß, dass ich sehr spät zur Party komme, aber ich habe endlich herausgefunden, wie wir die registrieren können
MaxLengthAttribute
.Zuerst brauchen wir einen Validator:
public class MaxLengthClientValidator : DataAnnotationsModelValidator<MaxLengthAttribute> { private readonly string _errorMessage; private readonly int _length; public MaxLengthClientValidator(ModelMetadata metadata, ControllerContext context, MaxLengthAttribute attribute) : base(metadata, context, attribute) { _errorMessage = attribute.FormatErrorMessage(metadata.DisplayName); _length = attribute.Length; } public override IEnumerable<ModelClientValidationRule> GetClientValidationRules() { var rule = new ModelClientValidationRule { ErrorMessage = _errorMessage, ValidationType = "length" }; rule.ValidationParameters["max"] = _length; yield return rule; } }
Nichts wirklich Besonderes. Im Konstruktor speichern wir einige Werte aus dem Attribut. In der setzen
GetClientValidationRules
wir eine Regel.ValidationType = "length"
wirddata-val-length
vom Framework zugeordnet.rule.ValidationParameters["max"]
ist für dasdata-val-length-max
Attribut.Jetzt, da Sie einen Validator haben, müssen Sie ihn nur noch registrieren in
global.asax
:protected void Application_Start() { //... //Register Validator DataAnnotationsModelValidatorProvider.RegisterAdapter(typeof(MaxLengthAttribute), typeof(MaxLengthClientValidator)); }
Et voila, es funktioniert einfach.
quelle
Ich habe dies für alle Eingaben in meinem HTML-Dokument (Textbereich, Eingaben usw.) versucht, die die Eigenschaft data-val-length-max hatten und ordnungsgemäß funktionieren.
$(document).ready(function () { $(":input[data-val-length-max]").each(function (index, element) { var length = parseInt($(this).attr("data-val-length-max")); $(this).prop("maxlength", length); }); });
quelle
Dies kann die MaxLength und die MinLength ersetzen
[StringLength(40, MinimumLength = 10 , ErrorMessage = "Name cannot be longer than 40 characters and less than 10")]
quelle
<input class="text-box single-line" data-val="true" data-val-required="Name is required." id="Name1" name="Name" type="text" value=""> $('#Name1').keypress(function () { if (this.value.length >= 5) return false; });
quelle