个人博客网站编写(05)--注冊功能的編寫(邮件激活、Redis 缓存、Ajax 异步获取)

本文介绍了个人博客网站注册功能的编写过程,涉及邮件激活、Redis缓存和Ajax异步获取验证码。首先准备资源文件,设置注册页面布局。接着讲解了验证码的生成和验证,包括前端页面的JavaScript实现和后端Servlet处理。然后,阐述了手机号的验证,使用Ajax发送请求到后台检查手机号是否已注册。最后提到了邮箱验证,但由于篇幅原因,将在后续专题中详细介绍。
摘要由CSDN通过智能技术生成

 个人博客网站编写(05)--注冊功能的編寫(邮件激活、Redis 缓存、Ajax 异步获取)

 

前言:上一篇我們將介紹了如何編寫接口及測試的編寫,這一篇我們將開始從最基礎的功能開始寫!

 


最近兩天沒有寫博客,第一:最近滿著去將我買的服務器備案。真是一個麻煩的事情。第二:最近兩天有開發任務。效率真低哦!拖了很久的時間。

好吧開始!

前期準備:

第一步,在webapp頁面下放入jsp、css、js、images。等資源文件,在文末我會將對應的資源放入網盤。

第二步,將register.jsp直接放入webapp的頁面,activeFail.jsp、activeSuccess、registerSuccess、文件放入web-inf目錄下。

在這我需要解釋一下,在webapp頁面下,是可以直接通過超連接就能訪問的,而web-info下面的目錄是需要通過controller跳轉才能訪問,所以更加安全!因此一般的做法是將不需要權限訪問的,放在WEBAPP下!

第三步,將register.jsp頁面打開,並輸入下面的代碼。

<%@ page contentType="text/html;charset=UTF-8"%>//設計編碼為utf-8
<%@ taglib prefix="c" uri="http://java.sun.com/jsp/jstl/core" %>//使用Jstl的c標簽
<%@ taglib prefix="fn" uri="http://java.sun.com/jsp/jstl/functions" %> //使用jstl的函數標簽
<c:set var="ctx" value="${pageContext.request.contextPath }"/> //定義全局的獲取路徑啊?

在 head 标签内引入 CSS 和 JS 文件:

  <link type="text/css" rel="stylesheet" href="${ctx}/css/dreamland.css">//css文件
    <script type="text/javascript" src="${ctx}/js/jquery.min.js"></script>//js文件

第四步,在index.jsp中添加超鏈接跳轉到登陸界面。

<h2><a href=''register.jsp">注冊</a></h2>

然後運行項目,點擊注冊。

OJBK,現在開始來咯!

首先是驗證碼。

验证码

1.在 id 为 nickName_span 的 span 标签下加入 input 输入框和验证码图片(src 属性引入图片):

//首先是加入一個輸入框。
<input id="code" name="code" type="text" class="kuang_txt yanzm" placeholder="验证码" onblur="checkCode()">
      <div>
         <IMG id="captchaImg" style="CURSOR: pointer"
                           onclick="changeCaptcha()"
                           title="看不清楚?请点击刷新验证码!" align='absmiddle' src="${ctx}/captchaServlet"
                           height="18" width="55">
                      <a href="javascript:;"
                         onClick="changeCaptcha()" style="color: #666;">看不清楚</a> <span id="code_span" style="color: red"></span>
                  </div>

代碼解釋:

(1)其中 onclick 点击事件 changeCaptcha,点击之后更换验证码,具体方法如下:

     //更换验证码
    function changeCaptcha() {
        $("#captchaImg").attr('src', '${ctx}/captchaServlet?t=' + (new Date().getTime()));
    }

根据 id(captchaImg) 获取 image 标签对象,将它的 src 属性值替换成新的验证码图片。

(2)src 属性值对应的是一个 Servlet,Servlet 对应的URL是 /captchaServlet,当页面加载的时候它会调用该 Servlet 的方法,返回一个验证码图片。

 

2.在 web.xml 文件中配置 captchaServlet。

    <!--验证码-->
  <servlet>
    <servlet-name>CaptchaServlet</servlet-name>
    <servlet-class>
      com.liwei.blog.common.CodeCaptchaServlet
    </servlet-class>
  </servlet>
  <servlet-mapping>
    <servlet-name>CaptchaServlet</servlet-name>
    <url-pattern>/captchaServlet</url-pattern>
  </servlet-mapping>

 captchaServlet執行過程。

1、點擊看不清,然後代碼執行找到WEB.XML中servlet-name為 CaptchaServlet的servlt.

2、然後servlet通過servlet-mapping找到項目中servlet的實際位置。

 

3、SO,現在我們要去寫驗證碼的servlet了。

在 common 包下引入 CodeCaptchaServlet.java,制作验证码的类,主要是通过 Graphics 设置图片大小,然后随机生成干扰点和4位随机验证码,并保存到 Session 中,用于注册时验证。生成验证码的 CodeCaptchaServlet.java 文件我已放在了文末的百度网盘链接中,可以当作工具类来直接使用。

4.重新启动 Tomcat,点击 index.jsp 内的链接“点我注册”查看效果:

嗯,很不錯我們現在有了驗證碼了!

注册

页面表单校验

 

这里主要说下手机号的校验、验证码的校验、勾选用户协议的校验和表单提交,其他校验方法参考源码中的方法。

1.手机号的校验:

      <input id="phone" name="phone" type="text" class="kuang_txt phone" placeholder="手机号" onblur="checkPhone();"><span id="phone_ok"></span>
       <br/>
       <span id="phone_span" style="color: red"></span>

其中 br 标签代表换行,给手机号的 input 框添加一个离焦事件 onblur="checkPhone();", 具体方法如下:

    //校验手机号
    var v = 0;
    var flag2 = false;
    function checkPhone(){
        var phone = $("#phone").val();
        phone = phone.replace(/^\s+|\s+$/g,"");
        if(phone == ""){
            $("#phone_span").text("请输入手机号码!");
            $("#phone_ok").text("");
            var hgt = $("#regist-left").height();

            if(v==0){
                $("#regist-left").height(hgt+30);
                $("#regist-right").height(hgt+30);
                v++;
            }

            flag2 =  false;
        }
        if(!(/^1[3|4|5|8|7][0-9]\d{8}$/.test(phone))){
            $("#phone_span").text("手机号码非法,请重新输入!");
            $("#phone_ok").text("");
            var hgt = $("#regist-left").height();
            if(v==0){
                $("#regist-left").height(hgt+30);
                $("#regist-right").height(hgt+30);
                v++;
            }
            flag2 = false;
        }else{
            $.ajax({
                type:'post',
                url:'/checkPhone',
                data: {"phone":phone},
                dataType:'json',
                success:function(data){
                    var val = data['message'];
                    if(val=="success"){
                        $("#phone_span").text("");
                        $("#reg_span").text("");
                        $("#phone_ok").text("√").css("color","green");

                        var content = $("#phone_ok").text();
                        if(content=="√" ){
                            var hgt = $("#regist-left").height();
                            if(v==1){
                                $("#regist-left").height(hgt-30);
                                $("#regist-right").height(hgt-30);
                            }
                            v=0;
                        }
                        flag2 =  true;

                    }else{

                        $("#phone_span").text("该手机号已经注册!");
                        $("#phone_ok").text("");
                        var hgt = $("#regist-left").height();
                        if(v==0){
                            $("#regist-left").height(hgt+30);
                            $("#regist-right").height(hgt+30);
                            v++;
                        }
                        flag2 =  false;
                    }
                }
            });

        }

        return flag2;
    }


     //根据内容增加而增加高度
    function increaseHeight() {

           var hgt = $("#regist-left").height();
            $("#regist-left").height(hgt+30);
            $("#regist-right").height(hgt+30);

    }
    //根据内容减少而减少高度
    function reduceHeight() {
        var hgt = $("#regist-left").height();
        $("#regist-left").height(hgt-30);
        $("#regist-right").height(hgt-30);
    }

代码解读如下:

(1)通过 var 定义两个变量,一个变量 v 赋初始值为0,方法中可以根据 v 的值控制外部 div 的高度。另一个变量 flag2 赋初始值 false,代表手机号 input 框的状态,false 情况下不能提交表单。

(2)jQuery 获取对象的方式为:$("#phone"),根据 $+("#id") 的方式获取该 id 的标签对象,记得通过 id 获取对象要加 #,通过 class 获取标签对象要加 .,还有其他获取对象的方法,不会的同学可搜索 CSS 标签选择器进行学习。

(3)获取 input 框对象之后,可通过对象 .val() 方法获取该对象的值,即鼠标离焦后该 input 框内的值,赋值给变量 phone。

(4)接下来通过 replace 方法去掉前后空格,该方法的第一个参数是一个正则表达式,表示以空格开头或者以空格结尾。

(5)判断该手机号是否为空,如果为空则在 id=phone_span 的 span 标签中进行提示,span 标签中有内容后,整个 div 会向下扩张,所以要动态增加外部 div 的高度,通过 id=regist-left 获取左边 div 的高度,右边的 div 和左边一样,如果变量 v=0,则将左边和右边的 div 高度都加30,v 自增1。

(6)对手机号进行正则匹配,判断手机号是否正确合法,如果不正确给予错误提示,动态增加外部 div 高度,原理同上。

(7)手机号码判断正确以后,发送 AJAX 请求到后台,请求方式为 post ,请求 URL 为 /checkPhone,映射后台的某个 Controller 的方法,请求参数 data 是手机号,数据类型是 JSON 格式,success 回调函数返回后台处理结果,放在 data 中,通过 data['message'] 取出放在 data 中的数据,如果是“success”,说明该手机号未被注册,则在 input 后的 span 标签中打“√”,并且如果 v=1,则将外部 div 减去30,动态缩短 div 高度,将变量 v 重置为0,并将 flag2 赋值为 true,表示手机号的 input 框状态已正确。

(8)如果返回结果不是“success”,说明该手机号已被注册,则给予提示,然后将外部 div 高度动态增加30,v自增 1,将 flag2 赋值为 false,表示 input 框状态错误,不能提交表单。

(9)最后将 flag2 返回。

(10)后面两个方法是将动态增加和缩短 div 的高度封装成了方法,直接调用方法即可。

其中 $("#reg_span").text("") 用来对点击注册时出现的错误进行错误提示,默认情况下都为空。

手机号校验 AJAX 请求对应的后台代码:

在 wang.dreamland.www.controller 包下新建 RegisterController.java,将关于注册的方法都放在此 Controller 下:

    @Controller
    public class RegisterController {
    private final static Logger log = Logger.getLogger(RegisterController.class);
    @Autowired
    private UserService userService;
    @RequestMapping("/checkPhone")
    @ResponseBody
    public Map<String, Object> checkPhone(Model model, @RequestParam(value = "phone", required = false) String phone) {
        log.debug("注册-判断手机号" + phone + "是否可用");
        Map map = new HashMap<String, Object>();
        User user = userService.findByPhone(phone);
        if (user == null) {
            //未注册
            map.put("message", "success");
        } else {
            //已注册
            map.put("message", "fail");
        }

        return map;
    }
    }

代码解读如下:

(1)在类上加上 @Controller 注解代表这是 Controller 层。

(2)通过 Logger.getLogger 方法获取日志对象 Logger,参数就是要打印的类的字节码文件。

(3)通过 @Autowired 注解注入 UserService 对象,可调用其中的方法。

(4)@RequestMapping 注解映射前端访问的 URL 路径,这里对应的就是 AJAX 请求的 URL。

(5)@ResponseBody 注解作用是返回 JSON 格式的数据。

(6)@RequestParam 注解接收前台传来的参数,value 对应参数的名字,required=false 代表该参数是非必须的,可以没有,后面的 String phone 用来接收参数的值,类型为 String 类型。

(7)打印 Log 日志。

(8)new 一个 HashMap 集合,将数据以 key-value 的形式存入 map 中。

(9)根据手机号码查询用户,如果用户为 null 则代表未注册,则以“message”为键,“success”为值存入 map 集合。

(10)如果用户不为 null,则代表该手机号已被注册,则把“fail”作为值存入 map 集合,最后将 map 集合返回。

2.验证码的校验

     <input id="code" name="code" type="text" class="kuang_txt yanzm" placeholder="验证码" onblur="checkCode()">

验证码 input 框的离焦事件 checkCode 方法如下:

    //验证码校验
    var flag_c = false;
    function checkCode() {
        var code = $("#code").val();
        code = code.replace(/^\s+|\s+$/g,"");
        if(code == ""){
            $("#code_span").text("请输入验证码!").css("color","red");
            flag_c = false;
        }else{
            $.ajax({
                type: 'post',
                url: '/checkCode',
                data: {"code": code},
                dataType: 'json',
                success: function (data) {
                    var val = data['message'];
                    if (val == "success") {
                        $("#code_span").text("√").css("color","green");
                        $("#reg_span").text("");
                        flag_c = true;
                    }else {
                        $("#code_span").text("验证码错误!").css("color","red");
                        flag_c = false;
                    }
                }
            });

        }
        return flag_c;
    }

代码解读如下:

(1)定义一个变量 flag_c = false,默认状态为错误状态,不可提交表单。

(2)根据标签 id 获取标签对象,通过对象的 val() 方法取得该标签对象的值,即用户输入的验证码。

(3)将验证码去空格后,判断该验证码是否为空,为空则给予错误提示,因为错误提示是加在验证码右侧,所以不用增加 div 高度。

(4)如果验证码不为空,则发送 AJAX 请求给后台,后台将处理后的结果放在 data 中,通过 data["message"] 获取放入 data 中的数据,如果是“success”,则代表验证码正确,打个“√”,flag_c 赋值为 true,代表该 input 框状态正确。

(5)如果 AJAX 返回的结果不是“success”,则说明输入的验证码错误,则给出错误提示,flag_c赋值为 flase,代表状态错误。

(6)最后将 flag_c 返回。

验证码校验 AJAX 请求对应的后台代码:

在 RegisterController.java 中添加如下方法:

    @RequestMapping("/checkCode")
    @ResponseBody
    public Map<String, Object> checkCode(Model model, @RequestParam(value = "code", required = false) String code) {
        log.debug("注册-判断验证码" + code + "是否可用");
        Map map = new HashMap<String, Object>();
        ServletRequestAttributes attrs = (ServletRequestAttributes) RequestContextHolder.getRequestAttributes();
        String vcode = (String) attrs.getRequest().getSession().getAttribute(CodeCaptchaServlet.VERCODE_KEY);

         if (code.equals(vcode)) {
            //验证码正确
            map.put("message", "success");
        } else {
            //验证码错误
            map.put("message", "fail");
        }

        return map;
    }

代码解读如下:

(1)通过 ServletRequestAttributes 获取 Request 对象,然后通过 Request 获取 Session 对象。

(2)通过 session.getAttribute 方法获取之前生成验证码时存入 session 中的验证码,赋值给 vcode。

(3)判断前台传来的验证码和 Session 中存入的验证码是否相同。如果相同则代表验证码输入正确,将“success”返回给前台,否则代表验证码输入错误,将“fail”返回给前台。

勾选用户协议的校验:

    <input id="protocol" type="checkbox" onclick="checkProtocol();"><span>已阅读并同意<a href="#" target="_blank" ><span class="lan">《梦境网用户协议》</span></a></span>

选择框 checkbox 的点击事件 checkProtocol 方法如下:

    //勾选用户协议校验
    function checkProtocol() {
        if($('#protocol').prop("checked"))
        {
            $("#reg_span").text("");
            return true;
        }
        else{
            return false;
        }

    }

如上面的代码,通过 id 获取 input 框对象,通过该对象的 prop 方法返回 checked 属性的值,如果为 true 则将 id=reg_span 的 span 标签的错误内容清空,返回 true,否则返回 false。

表单提交

所有的 input 框被 form 标签包裹着,成功提交表单后,后台通过 input 框的 name 属性获取 value 中的值。

     <form action="${ctx}/doRegister" method="post" id="registerForm">

action 对应后台 Controller 中的映射 URL,method 请求方式是 post 请求,form 表单的 id 是 registerForm。

通过点击注册按钮提交表单:

     <input name="注册" type="button" class="btn_zhuce" id ="to_register" value="注册">

注册按钮的点击事件如下:

     //提交注册信息
    $("#to_register").click (function(){
        if(!checkProtocol()){
            $("#protocol_span").text("请勾选\"阅读并接受梦境网用户协议\"!").css("color","red");
        }else{
            $("#protocol_span").text("");
        }

        if(checkPhone()  &&  checkPassword()&& checkEmail() && checkNickName()&& checkCode() && checkProtocol()){
            $("#registerForm").submit();
        }else {
            $("#reg_span").text("请将信息填写完整!").css("color","red");
        }

    });

代码解读如下:

(1)通过 id 获取对象,对象.click(function(){}); 即该对象的点击事件函数。

(2)判断是否勾选用户协议,没有的话给予错误提示,勾选则将 span 标签内容清空。

(3)判断手机号、密码、邮箱、昵称、验证码、勾选用户协议都正确后,则通过 form 表单对象的 submit() 方法提交表单,否则有一个错误,则提示错误信息。

 

接下來是重頭戲,關於郵箱的驗證。不過限於本篇的篇幅。我決定寫個小專題,專門記錄。

郵箱驗證請點擊這裏。郵箱驗證

链接:https://pan.baidu.com/s/1e1k05lX6_PwGrey82v3Gdw 密码:3gd3

 

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值