一.先說思路javascript
//1.數據庫加三個字段,state:(0:未激活,1:激活成功),ActiCode:(放激活碼),token_exptime(過時時間,用來驗證激活郵件是否過時)html
//2.用戶填寫資料,點擊註冊,插入數據成功,state字段默認是0,同時生成一個ActiCode(用傳過來的郵箱、密碼、和當前時間加密造成)也存入數據庫java
//3.發送郵件。。。提示用戶登陸郵箱激活。。。郵件中帶一個激活成功頁的URL,URL裏有兩個參數(1,用戶ID,2:激活碼)web
//4.用戶登陸郵箱點擊連接,來處處理激活的業務邏輯頁面或Servlet,獲得URL中兩個參數,以這兩個參數爲條件查詢數據庫裏的數據,若是有,取當前時間和以前存入數據庫的過時時間做比較,看是否過時,過時,刪除數據庫中該條記錄,並轉到失敗頁面,沒過時,查看連接傳過來的激活碼與數據庫字段激活碼是否一致,不一致,一樣刪除數據庫中該條記錄,並跳轉到激活失敗界面,一致,則將字段state爲1,激活成功,轉到激活成功頁。。。sql
2、具體實現代碼數據庫
1.首先,準備一個簡單的測試頁面瀏覽器
<body> <div id="main" style="margin:0 auto;width:500px;"> <form id="reg" action="user.action?op=reg" method="post"> <p> E-mail:<input type="text" class="input" name="email" id="email"> </p> <p> 密 碼:<input type="password" class="input" name="pwd" id="pwd"> </p> <p> <input type="submit" class="btn" value="提交註冊" > </p> </form> </div> </body>
2.點擊提交註冊,來到user.action?op=reg,注意帶的參數op指我要作的操做,用於後面的Servlet作判斷該作什麼操做,下面的代碼完成了造成激活碼、過時時間等表示當前註冊用戶的狀態的信息存入數據庫併發送郵件的過程。(郵件內容自定義,能夠忽略個人)服務器
1 package com.nh.web.servlets; 2 3 import java.io.IOException; 4 import java.io.PrintWriter; 5 import java.sql.SQLException; 6 import java.text.SimpleDateFormat; 7 import java.util.ArrayList; 8 import java.util.Calendar; 9 import java.util.Date; 10 import java.util.List; 11 import java.util.UUID; 12 13 import javax.naming.NamingException; 14 import javax.servlet.ServletException; 15 import javax.servlet.http.HttpServlet; 16 import javax.servlet.http.HttpServletRequest; 17 import javax.servlet.http.HttpServletResponse; 18 19 import com.nh.dao.DBHelper; 20 import com.nh.utils.Encrypt; 21 import com.nh.utils.SendEmail; 22 23 public class UserServlet extends CommonServlet { 24 25 public void doPost(HttpServletRequest request, HttpServletResponse response) 26 throws ServletException, IOException { 27 // 取出op 28 String op = request.getParameter("op"); 29 // 判斷op是什麼,調用不一樣的方法作處理 30 try { 31 if (op != null && !"".equals(op)) { 32 if ("reg".equals(op)) { 33 regOP(request, response); 34 } 35 } else { 36 37 } 38 } catch (Exception e) { 39 e.printStackTrace(); 40 response.sendRedirect("common/500.jsp"); 41 } 42 } 43 44 private void regOP(HttpServletRequest request, HttpServletResponse response) throws IOException, SQLException, NamingException { 45 // 1.數據庫加兩個字,state字段(0:未激活,1:激活成功),ActiCode:(放激活碼) 46 // 2.用戶填寫資料,插入數據成功,state字段默認是0,同時生成一個ActiCode也存入數據庫 47 // 3.提示用戶激活。。。發送郵件。。。郵件中帶一個激活成功頁的URL,URL裏有兩個參數(1,用戶ID,2:激活碼) 48 // 4.用戶點擊連接,回到激活成功頁。。。激活成功頁的Load事件,獲得兩個參數,以這兩個參數爲條件查詢數據庫裏的數據,若是有,修改字段state爲1,反之。。提示激活失敗,從新激活。。 49 50 String email=request.getParameter("email"); 51 String pwd=Encrypt.md5(request.getParameter("pwd")); 52 Calendar c = Calendar.getInstance(); 53 //如今的時間(單位:毫秒) 54 //TODO:時間換算問題,如何處理int和long之間的關係 55 long time = c.getTimeInMillis(); 56 57 //建立激活碼 58 String token=Encrypt.md5(email+pwd+time); 59 //過時時間爲24小時後 60 // int token_exptime=(int)(time+1000*60*60*24); 61 String token_exptime=(time+1000*20)+""; //這裏測試是用的20秒 62 63 String id=UUID.randomUUID().toString(); 64 String sql="insert into tb_user(id,username,pwd,token,token_exptime,regtime,status) values (?,?,?,?,?,sysdate,0)"; 65 66 List<Object> params=new ArrayList<Object>(); 67 params.add(id); 68 params.add(email); 69 params.add(pwd); 70 params.add(token); 71 params.add(token_exptime); 72 73 DBHelper db=new DBHelper(); 74 int r=db.doUpdate(sql, params); //保存註冊信息 75 76 if( r>0 ){ 77 //發送郵件 78 ///郵件的內容 79 SimpleDateFormat sdf=new SimpleDateFormat("yyyy-MM-dd"); 80 81 StringBuffer sb=new StringBuffer("<div style=\"width:660px;overflow:hidden;border-bottom:1px solid #bdbdbe;\"><div style=\"height:52px;overflow:hidden;border:1px solid #464c51;background:#353b3f url(http://www.lofter.com/rsc/img/email/hdbg.png);\"><a href=\"http://www.lofter.com?mail=qbclickbynoticemail_20120626_01\" target=\"_blank\" style=\"display:block;width:144px;height:34px;margin:10px 0 0 20px;overflow:hidden;text-indent:-2000px;background:url(http://www.lofter.com/rsc/img/email/logo.png) no-repeat;\">LOFTER</a></div>"+"<div style=\"padding:24px 20px;\">您好,"+email+"<br/><br/>LOFTER是一款\"專一興趣、分享創做\"的輕博客產品,旨在爲\"熱愛記錄生活、追求時尚品質、崇尚自由空間\"的你,打造一個全新而定展現平臺!<br/><br/>請點擊下面連接激活帳號,24小時生效,不然從新註冊帳號,連接只能使用一次,請儘快激活!</br>"); 82 sb.append("<a href=\"http://localhost:8080/mailtest/emailcheck.action?op=activate&id="); 83 sb.append(id); 84 sb.append("&token="); 85 sb.append(token); 86 sb.append("\">http://localhost:8080/mailtest/emailcheck.action?op=activate&id="); 87 sb.append(id); 88 sb.append("&token="); 89 sb.append(token); 90 sb.append("</a>"+"<br/>若是以上連接沒法點擊,請把上面網頁地址複製到瀏覽器地址欄中打開<br/><br/><br/>LOFTER,專一興趣,分享創做<br/>"+sdf.format(new Date())+ "</div></div>" ); 91 92 //發送郵件 93 SendEmail.send(email, sb.toString()); 94 } 95 96 response.sendRedirect("doEmail.action?op=emaillogin&email="+email+"&pwd="+pwd); 97 98 } 99 100 }
發送郵件的代碼,這裏須要導入javax.mail的包,即mail.jar,若是發件人郵箱是QQ郵箱還要去QQ郵箱開啓smtp和其餘兩個協議,我這裏用的163郵箱就不須要設置session
1 package com.nh.utils; 2 3 import java.util.Date; 4 import java.util.Properties; 5 6 import javax.mail.Authenticator; 7 import javax.mail.Message; 8 import javax.mail.MessagingException; 9 import javax.mail.PasswordAuthentication; 10 import javax.mail.Session; 11 import javax.mail.Transport; 12 import javax.mail.internet.InternetAddress; 13 import javax.mail.internet.MimeMessage; 14 15 16 /** 17 * 18 * @author Qixuan.Chen 19 */ 20 public class SendEmail { 21 22 public static final String HOST = "smtp.163.com"; 23 // public static final String PROTOCOL = "smtp"; 24 // public static final int PORT = 25; 25 26 public static final String FROM = "xxxx@163.com";//發件人的email 27 public static final String PWD = "xxxx";//發件人密碼 28 29 30 /** 31 * 獲取Session 32 * @return 33 */ 34 private static Session getSession() { 35 Properties props = new Properties(); 36 props.put("mail.smtp.host", HOST);//設置服務器地址 37 // props.put("mail.store.protocol" , PROTOCOL);//設置協議 38 // props.put("mail.smtp.port", PORT);//設置端口 39 props.put("mail.smtp.auth" , "true"); 40 41 Authenticator authenticator = new Authenticator() { 42 43 @Override 44 protected PasswordAuthentication getPasswordAuthentication() { 45 return new PasswordAuthentication(FROM, PWD); 46 } 47 48 }; 49 Session session = Session.getDefaultInstance(props , authenticator); 50 51 return session; 52 } 53 54 public static void send(String toEmail , String content) { 55 Session session = getSession(); 56 try { 57 // System.out.println("--send--"+content); 58 // Instantiate a message 59 Message msg = new MimeMessage(session); 60 61 //Set message attributes 62 msg.setFrom(new InternetAddress(FROM)); 63 InternetAddress[] address = {new InternetAddress(toEmail)}; 64 msg.setRecipients(Message.RecipientType.TO, address); 65 msg.setSubject("帳號激活郵件"); 66 msg.setSentDate(new Date()); 67 msg.setContent(content , "text/html;charset=utf-8"); 68 69 //Send the message 70 Transport.send(msg); 71 } 72 catch (MessagingException mex) { 73 mex.printStackTrace(); 74 } 75 } 76 77 }
這是收到的激活郵件併發
根據用戶所填郵箱跳轉相應郵箱登陸地址的代碼
1 package com.nh.web.servlets; 2 3 import java.io.IOException; 4 import java.io.PrintWriter; 5 6 import javax.servlet.ServletException; 7 import javax.servlet.http.HttpServlet; 8 import javax.servlet.http.HttpServletRequest; 9 import javax.servlet.http.HttpServletResponse; 10 11 public class DoEmailLoginServlet extends CommonServlet { 12 13 public void doPost(HttpServletRequest request, HttpServletResponse response) 14 throws ServletException, IOException { 15 String op = request.getParameter("op"); 16 // 判斷op是什麼,調用不一樣的方法作處理 17 try { 18 if (op != null && !"".equals(op)) { 19 if ("emaillogin".equals(op)) { 20 emailloginOP(request, response); 21 } 22 } else { 23 24 } 25 } catch (Exception e) { 26 e.printStackTrace(); 27 response.sendRedirect("common/500.jsp"); 28 } 29 } 30 31 private void emailloginOP(HttpServletRequest request, 32 HttpServletResponse response) throws IOException { 33 //判斷用戶郵箱是什麼,跳到指定郵箱登錄界面 34 String email=request.getParameter("email"); //572480349@qq.com 35 String pwd=request.getParameter("pwd"); 36 String addrstr=email.split("@")[1]; //qq.com 37 38 if( "qq.com".equals(addrstr)){ 39 addrstr="https://mail.qq.com"; 40 }else if( "163.com".equals(addrstr)){ 41 addrstr="http://mail.163.com/"; 42 }else if( "126.com".equals(addrstr)){ 43 addrstr="http://www.126.com/"; 44 }else if( "sina.com".equals(addrstr)){ 45 addrstr="http://mail.sina.com.cn/"; 46 }else if( "hotmail.com".equals(addrstr)){ 47 addrstr="https://login.live.com"; 48 } 49 50 response.sendRedirect("emailaction.jsp?email="+email+"&pwd="+pwd+"&addrstr="+addrstr); 51 } 52 53 }
具體頁面我就不一一給了,直接上激活驗證代碼吧
1 package com.nh.web.servlets; 2 3 import java.io.IOException; 4 import java.io.PrintWriter; 5 import java.lang.reflect.InvocationTargetException; 6 import java.sql.SQLException; 7 import java.util.ArrayList; 8 import java.util.Calendar; 9 import java.util.List; 10 11 import javax.naming.NamingException; 12 import javax.servlet.ServletException; 13 import javax.servlet.http.HttpServlet; 14 import javax.servlet.http.HttpServletRequest; 15 import javax.servlet.http.HttpServletResponse; 16 17 import com.lofter.bean.User; 18 import com.nh.dao.DBHelper; 19 import com.nh.utils.DataExistAlreadyException; 20 21 public class EmailActivateCheckServlet extends CommonServlet { 22 23 public void doPost(HttpServletRequest request, HttpServletResponse response) 24 throws ServletException, IOException { 25 // 取出op 26 String op = request.getParameter("op"); 27 // 判斷op是什麼,調用不一樣的方法作處理 28 try { 29 if (op != null && !"".equals(op)) { 30 if( "activate".equals(op)){ 31 activateOP(request,response); 32 } 33 } else { 34 35 } 36 } catch (Exception e) { 37 e.printStackTrace(); 38 response.sendRedirect("common/500.jsp"); 39 } 40 } 41 42 private void activateOP(HttpServletRequest request, 43 HttpServletResponse response) throws InstantiationException, IllegalAccessException, IllegalArgumentException, InvocationTargetException, Exception { 44 //獲取參數token的值,即激活識別碼。 45 //將它與數據表中的用戶信息進行查詢對比,若是有相應的數據集,判斷是否過時,若是在有效期內則將對應的用戶表中字段status設置1,即已激活,這樣就完成了激活功能。 46 47 String id=request.getParameter("id"); 48 String token=request.getParameter("token"); 49 Calendar c = Calendar.getInstance(); 50 //如今的時間(單位:毫秒) 51 long curtime = c.getTimeInMillis(); 52 53 String sql="select id,token_exptime,token,username,pwd from tb_user where status=0 and token=?"; 54 List<Object> params=new ArrayList<Object>(); 55 params.add( token ); 56 57 DBHelper db=new DBHelper(); 58 User u=db.findSingleObject(User.class, sql, params); 59 String email=u.getUsername(); 60 String pwd=u.getPwd(); 61 if( u!=null ){ 62 long token_exptime=Long.parseLong(u.getToken_exptime()); 63 if( curtime>token_exptime ){ 64 //激活碼過時,先刪除該用戶記錄,而後從新發送郵件 65 sql="delete from tb_user where id='"+u.getId()+"'"; 66 db.doUpdate(sql, null); 67 response.sendRedirect("actionfailer.jsp?email="+email+"&pwd="+pwd); 68 // throw new DataExistAlreadyException("激活碼已過時!"); 69 return; 70 }else{ 71 //驗證激活碼是否正確 72 if( token.equals(u.getToken())){ 73 //激活成功, //並更新用戶的激活狀態,爲已激活 74 sql="update tb_user set status=1 where id='"+u.getId()+"'"; 75 db.doUpdate(sql, null); 76 response.sendRedirect("actionsuccess.jsp"); 77 }else{ 78 sql="delete from tb_user where id='"+u.getId()+"'"; 79 db.doUpdate(sql, null); 80 response.sendRedirect("actionfailer.jsp?email="+email+"&pwd="+pwd); 81 return; 82 // throw new DataExistAlreadyException("激活碼不正確"); 83 } 84 } 85 } 86 87 } 88 89 } 90 91 92 93 package com.nh.web.servlets; 94 95 import java.io.IOException; 96 import java.io.PrintWriter; 97 98 import javax.servlet.ServletContext; 99 import javax.servlet.ServletException; 100 import javax.servlet.http.HttpServlet; 101 import javax.servlet.http.HttpServletRequest; 102 import javax.servlet.http.HttpServletResponse; 103 import javax.servlet.http.HttpSession; 104 105 106 public abstract class CommonServlet extends HttpServlet { 107 private static final long serialVersionUID = 3893961453320250657L; 108 109 private String saveFilePath=""; 110 protected String basePath=""; 111 112 113 @Override 114 protected void doGet(HttpServletRequest req, HttpServletResponse resp) 115 throws ServletException, IOException { 116 doPost(req,resp); 117 } 118 119 @Override 120 protected void service(HttpServletRequest req, HttpServletResponse resp) 121 throws ServletException, IOException { 122 123 saveFilePath=req.getRealPath("/"); 124 HttpSession session=req.getSession(); 125 ServletContext application=session.getServletContext(); 126 if( application.getAttribute("basePath")!=null ){ 127 basePath=(String) application.getAttribute("basePath"); 128 } 129 130 super.service(req, resp); 131 } 132 133 134 } 135 136 137 package com.lofter.bean; 138 139 import java.io.Serializable; 140 import java.util.Date; 141 142 public class User implements Serializable { 143 144 private static final long serialVersionUID = -1989259749641485708L; 145 146 private String id; 147 private String username; // --帳戶 148 private String pwd; // --密碼 149 private String nickname; // --名稱 150 private String autograph; // --我的簽名 151 private String head; // --頭像 152 private Date regtime; // --註冊時間 153 154 private String token; // --帳號激活碼 155 private String token_exptime; // --激活碼有效期 156 private Integer status; // --激活狀態 ,0-未激活,1-已激活 157 158 public User() { 159 super(); 160 } 161 162 163 164 public User(String id, String username, String pwd, String nickname, 165 String autograph, String head, Date regtime, String token, 166 String token_exptime, Integer status) { 167 super(); 168 this.id = id; 169 this.username = username; 170 this.pwd = pwd; 171 this.nickname = nickname; 172 this.autograph = autograph; 173 this.head = head; 174 this.regtime = regtime; 175 this.token = token; 176 this.token_exptime = token_exptime; 177 this.status = status; 178 } 179 180 181 182 public String getId() { 183 return id; 184 } 185 186 public void setId(String id) { 187 this.id = id; 188 } 189 190 public String getUsername() { 191 return username; 192 } 193 194 public void setUsername(String username) { 195 this.username = username; 196 } 197 198 public String getPwd() { 199 return pwd; 200 } 201 202 public void setPwd(String pwd) { 203 this.pwd = pwd; 204 } 205 206 public String getNickname() { 207 return nickname; 208 } 209 210 public void setNickname(String nickname) { 211 this.nickname = nickname; 212 } 213 214 public String getAutograph() { 215 return autograph; 216 } 217 218 public void setAutograph(String autograph) { 219 this.autograph = autograph; 220 } 221 222 public String getHead() { 223 return head; 224 } 225 226 public void setHead(String head) { 227 this.head = head; 228 } 229 230 public Date getRegtime() { 231 return regtime; 232 } 233 234 public void setRegtime(Date regtime) { 235 this.regtime = regtime; 236 } 237 238 public static long getSerialversionuid() { 239 return serialVersionUID; 240 } 241 242 public String getToken() { 243 return token; 244 } 245 246 public void setToken(String token) { 247 this.token = token; 248 } 249 250 public String getToken_exptime() { 251 return token_exptime; 252 } 253 254 public void setToken_exptime(String token_exptime) { 255 this.token_exptime = token_exptime; 256 } 257 258 public Integer getStatus() { 259 return status; 260 } 261 262 public void setStatus(Integer status) { 263 this.status = status; 264 } 265 266 267 268 }