如何远程验证电子邮件或检查电子邮件是不是存在

Posted

技术标签:

【中文标题】如何远程验证电子邮件或检查电子邮件是不是存在【英文标题】:How to Remote validate email or check if email exists如何远程验证电子邮件或检查电子邮件是否存在 【发布时间】:2012-12-31 13:19:51 【问题描述】:

我正在尝试检查注册时是否存在电子邮件,以便数据库中没有重复的电子邮件。我正在使用 MVC4 默认 Internet 应用程序执行此操作,但我已向 RegisterviewModel 添加了一个电子邮件字段。我还注意到,用户名字段做得很好,但我不知道他们是怎么做到的。我试图关注下面的这个博客,但没有运气,因为当我点击创建时没有响应。 Tug Berk。当我使用萤火虫时,当Json action excutes 时,我得到Status: 302 Found

这就是我所拥有的:

用户资料

[Table("UserProfile")]
public class UserProfile

    [Key]
    [DatabaseGeneratedAttribute(DatabaseGeneratedOption.Identity)]
    public int UserId  get; set; 
    public string UserName  get; set; 
    public string Email  get; set; 

注册视图模型

public class RegisterModel

    [Required]
    [Display(Name = "User name")]
    public string UserName  get; set; 

    [Required]
    [DataType(DataType.EmailAddress)]
    [Display(Name = "Email")]
    [Remote("DoesUserEmailExist", "Account", HttpMethod = "POST", ErrorMessage = "Email address already exists. Please enter a different Email address.")]
    public string Email  get; set; 

    [Required]
    [StringLength(100, ErrorMessage = "The 0 must be at least 2 characters long.",      MinimumLength = 6)]
    [DataType(DataType.Password)]
    [Display(Name = "Password")]
    public string Password  get; set; 

    [DataType(DataType.Password)]
    [Display(Name = "Confirm password")]
    [System.ComponentModel.DataAnnotations.Compare("Password", ErrorMessage = "The password and confirmation password do not match.")]
    public string ConfirmPassword  get; set; 

注册操作

    [HttpPost]
    [AllowAnonymous]
    [ValidateAntiForgeryToken]
    public ActionResult Register(RegisterModel model)
    
        if (ModelState.IsValid)
        
            try //CreateUserAndAccount
            
                WebSecurity.CreateUserAndAccount(model.UserName, model.Password, new  model.Email );
                WebSecurity.Login(model.UserName, model.Password);
                return RedirectToAction("Index", "Home");

            
            catch (MembershipCreateUserException e)
            
                ModelState.AddModelError("", ErrorCodeToString(e.StatusCode));
            
        

        // If we got this far, something failed, redisplay form
        return View(model);
    

Json 动作

[HttpPost]
    public JsonResult DoesUserEmailExist(string email)
    

        var user = Membership.GetUserNameByEmail(email);

        return Json(user == null);
    

编辑:添加注册视图

     @model Soccer.Models.RegisterModel

     @
     ViewBag.Title = "Register";
     

     <hgroup class="title">
     <h1>@ViewBag.Title.</h1>
     <h2>Create a new account.</h2>
     </hgroup>

 @using (html.BeginForm()) 
 @Html.AntiForgeryToken()
 @Html.ValidationSummary()

 <fieldset>
    <legend>Registration Form</legend>
    <ol>
        <li>
            @Html.LabelFor(m => m.UserName)
            @Html.TextBoxFor(m => m.UserName)
        </li>
        <li>
            @Html.LabelFor(m => m.Email)
            @Html.TextBoxFor(m => m.Email)
        </li>
        <li>
            @Html.LabelFor(m => m.Password)
            @Html.PasswordFor(m => m.Password)
        </li>
        <li>
            @Html.LabelFor(m => m.ConfirmPassword)
            @Html.PasswordFor(m => m.ConfirmPassword)
        </li>
    </ol>
    <input type="submit" value="Register" />
</fieldset>
 

 @section Scripts 
 @Scripts.Render("~/bundles/jqueryval")
 

有什么我不应该做的,或者我可以在这里采取其他更简单的选择吗?

【问题讨论】:

【参考方案1】:

首先,我要感谢JOBG 通过这个吸引我。如果您使用Database First,我在上面的问题中显示的内容应该仍然有效,因为它要求您在数据库中设置电子邮件列UNIQUE,但是要使其与EF Code First 一起使用,我必须对注册操作执行以下操作,还请注意,使用此解决方案,您不需要Remote Annotation in the model

注册操作

    [HttpPost]
    [AllowAnonymous]
    [ValidateAntiForgeryToken]
    public ActionResult Register(RegisterModel model)
    
        if (ModelState.IsValid)
        
            // Insert a new user into the database
            using (UsersContext db = new UsersContext())
            
                UserProfile email = db.UserProfiles.FirstOrDefault(u => u.Email.ToLower() == model.Email.ToLower());
                try
                
                    // Check if email already exists
                    if (email == null)
                    
                        WebSecurity.CreateUserAndAccount(model.UserName, model.Password, new  Email = model.Email );
                        WebSecurity.Login(model.UserName, model.Password);
                        return RedirectToAction("Index", "Home");
                    
                    else
                    
                        ModelState.AddModelError("Email", "Email address already exists. Please enter a different email address.");
                    
                
                catch (MembershipCreateUserException e)
                

                    ModelState.AddModelError("", ErrorCodeToString(e.StatusCode));
                
            
        

        // If we got this far, something failed, redisplay form
        return View(model);
    

注意:请注意,此操作会在 UserName 之前验证电子邮件,并且它要求您在创建对象之前至少访问数据库一次。

【讨论】:

【参考方案2】:

如果没有查看代码很难判断,但我的第一个嫌疑人是 js,请确保您已设置 jQuery 验证插件,它应该使用 .blur() 事件触发验证,使用 firebug(或类似的) 并查找当字段失去焦点时命中DoesUserEmailExist 的ajax POST,如果没有发生这种情况,则客户端缺少某些内容,因为Remote 属性和服务DoesUserEmailExist 看起来不错。

旁注:确保数据库中有电子邮件字段的UNIQUE 约束,这是确保没有重复的唯一真正方法电子邮件,即使使用DoesUserEmailExist 验证,因为并发性。

【讨论】:

我添加了一个注册视图。至于 UNIQUE 约束,我不确定代码优先实体框架是否可行。考虑到这一点,这已经分配给了 UserId 你说得对,EF5 不支持 UNIQUE 代码优先啊,也许这就是我不使用它的原因之一,我更喜欢 db 首先...至于问题,这个捆绑包@ 987654327@ 渲染了需要的 js,所以这不是问题,你试过 firebug 来检查请求吗? 我只是运行它,Status: 302 Found 这就是我得到的,这里肯定有问题 只是一个快速通知,我刚刚意识到在 Post 下只有电子邮件字符串的第一个字母被分配给电子邮件。应该是这样吗? Email=k 302 发现,你的路由有问题,Remote Attribute中的action和controller名称是否正确?如果你在DoesUserEmailExist 中设置断点,它会被击中吗?

以上是关于如何远程验证电子邮件或检查电子邮件是不是存在的主要内容,如果未能解决你的问题,请参考以下文章

如何检查电子邮件是不是确实存在

我应该如何在 javascript 或 nodeJs 中验证电子邮件地址是不是存在和域名是不是存在?

如何检查具有电子邮件的用户是不是已经存在?

检查电子邮件地址是不是存在[重复]

检查电子邮件是不是有效且存在

通过与客户端 (MVC) 一起使用 Web API 中的操作来验证电子邮件是不是存在于数据库中并进行远程验证?