当前位置:
首页 > 工程科技 > 材料科学 > 07完善前端系统功能项目开发文档资料文档.docx
07完善前端系统功能项目开发文档资料文档.docx
- 文档编号:6060427
- 上传时间:2023-01-03
- 格式:DOCX
- 页数:21
- 大小:47.15KB
07完善前端系统功能项目开发文档资料文档.docx
《07完善前端系统功能项目开发文档资料文档.docx》由会员分享,可在线阅读,更多相关《07完善前端系统功能项目开发文档资料文档.docx(21页珍藏版)》请在冰豆网上搜索。
07完善前端系统功能项目开发文档资料文档
登录控制
创建一个用户控制登录的注解:
@Target(ElementType.METHOD)
@Retention(RetentionPolicy.RUNTIME)
public@interfaceRequireLogin{
}
创建一个SpringMVC拦截器,用于登录的拦截
publicclassLoginCheckInterceptorextendsHandlerInterceptorAdapter{
@Override
publicbooleanpreHandle(HttpServletRequestrequest,HttpServletResponseresponse,Objecthandler)throwsException{
if(handlerinstanceofHandlerMethod){
HandlerMethodhm=(HandlerMethod)handler;
RequireLoginrl=hm.getMethodAnnotation(RequireLogin.class);
if(rl!
=null){
if(request.getSession().getAttribute(UserContext.LOGININFO_IN_SESSION)==null){
response.sendRedirect("/login.html");
returnfalse;
}
}
}
returnsuper.preHandle(request,response,handler);
}
}
在applicationContext-uiweb.xml中配置该拦截器:
interceptors>
interceptor>
mappingpath="/**"/>
interceptor>
interceptors>
在需要登录的controller的method上添加@RequiredLogin注解即可:
注销
在loginController中直接添加一个logout方法:
@RequestMapping("/logout")
publicStringlogout(){
UserContext.setLoginInfo(null);
return"redirect:
main.do";
}
直接使用redirect:
前缀完成响应的跳转;
绑定手机
绑定手机前端
1,创建一个BitStatesUtils来处理用户的状态码;
/**
*@paramstates所有状态值
*@paramvalue需要判断状态值
*@return是否存在
*/
publicstaticbooleanhasState(longstates,longvalue){
return(states&value)!
=0;
}
/**
*@paramstates已有状态值
*@paramvalue需要添加状态值
*@return新的状态值
*/
publicstaticlongaddState(longstates,longvalue){
if(hasState(states,value)){
returnstates;
}
return(states|value);
}
/**
*@paramstates已有状态值
*@paramvalue需要删除状态值
*@return新的状态值
*/
publicstaticlongremoveState(longstates,longvalue){
if(!
hasState(states,value)){
returnstates;
}
returnstates^value;
}
在该类中创建一个静态值,用于标记用户状态和手机绑定状态;
publicfinalstaticLongOP_BASIC_INFO=1L;/用户注册成功的标示,及为默认初始状态
publicfinalstaticLongOP_BIND_PHONE=2L<<0;//是否已经绑定了手机号码
修改Userinfo的empty方法,在用户注册的时候需要给用户绑定一个初始状态:
publicstaticUserinfoempty(longid){
Userinfoempty=newUserinfo();
empty.setId(id);
empty.setBitState(BitStatesUtils.OP_BASIC_INFO);
returnempty;
}
2,给userinfo对象添加一个方法用于判断用户是否已经绑定手机
publicbooleangetHasBindPhone(){
returnBitStatesUtils.hasState(this.bitState,BitStatesUtils.OP_BIND_PHONE);
}
3,修改personal.ftl,根据用户手机绑定状态显示不同内容:
<#ifuserinfo.hasBindPhone>
已认证查看
<#else>
未绑定;">马上绑定
#if>
4,创建绑定手机模式窗口
--绑定手机模式框-->
<#if!
userinfo.hasBindPhone>
×
绑定手机
手机号:
发送验证码
验证码:
取消
保存
#if>
5,给绑定连接添加事件,点击绑定后弹出绑定手机模式窗口
if($("#openBindPhoneModal").size()>0){
$("#openBindPhoneModal").click(function(){
$('#bindPhoneModal').modal('show');
});
}
6,给发送验证码添加事件:
$("#sendVerifyCode").click(function(){
varphoneNumber=$("#phoneNumber").val();
var_me=$(this);
if(phoneNumber){
_me.attr("disabled",true);
$.ajax({
dataType:
"json",
type:
"post",
data:
{phoneNumber:
phoneNumber},
url:
"/sendVerifyCode.do",
success:
function(){
varsec=120;
vartimer=window.setInterval(function(){
sec--;
_me.text(sec+"秒重新发送");
if(sec==0){
window.clearInterval(timer);
_me.attr("disabled",false);
_me.text("重新发送验证码");
}
},1000);
}
});
}
});
7,后台添加发送短信的方法,在PersonalController中添加方法:
@RequestMapping("/sendVerifyCode")
@ResponseBody
publicStringsendVerifyCode(Modelmodel){
Logininfocurrent=UserContext.getLoginInfo();
System.out.println("发送手机验证码");
return"true";
}
完成短信发送逻辑
添加一个专门的VerifyCodeServiceImpl用来完成验证码服务,包括验证码发送,验证码验证,验证码时间验证;
首先,在该方法中需要传入本系统的发送短信的相关信息,比如username,password,apikey等内容,这些内容是随时可以配置的,所以我们也采用properties文件的方式,
添加m5c.properties:
m5c.username=xiaomage
m5c.password=1234
m5c.apikey=xiaomage1234
m5c.url=http:
//localhost:
8082/send.do
在applicationContext-core.xml中,要引入多个properties文件,因为要引入多个配置文件,所以我们修改引入配置文件的方式:
--配置属性资源文件-->
classpath:
datasource.properties
classpath:
m5c.properties
因为我们使用的是全注解方式,所以VerifyCodeServiceImpl是不配置在xml文件中的,那么我们怎么添加属性的值呢?
使用@Value标签:
@Service
publicclassVerifyCodeServiceImplimplementsIVerifyCodeService{
@Value("${m5c.username}")
privateStringusername;
@Value("${m5c.password}")
privateStringpassword;
@Value("${m5c.apikey}")
privateStringapikey;
@Value("${m5c.url}")
privateStringurl;
实现发送短信的逻辑
@Override
publicvoidsendVerifyCode(StringphoneNumber){
if(this.checkCanSendVerifyCode()){
try{
StringrandCode=UUID.randomUUID().toString().substring(0,4);
HttpURLConnectionconn=(HttpURLConnection)newURL(url).openConnection();
//必须大写
conn.setRequestMethod("POST");
conn.setDoOutput(true);
StringBuilderparams=newStringBuilder(100).append("username=").append(username).append("&password=").append(password)
.append("&apikey=").append(apikey).append("&mobile=").append(phoneNumber).append("&content=").append("你的验证码是:
")
.append(randCode).append(",有效期3分钟!
");
conn.getOutputStream().write(params.toString().getBytes());
InputStreamis=conn.getInputStream();
Stringret=StreamUtils.copyToString(is,Charset.forName("UTF-8"));
if("success".equals(ret.substring(0,ret.indexOf(":
")))){
VerifyCodevc=newVerifyCode(phoneNumber,randCode,newDate());
UserContext.setVerifyCode(vc);
}else{
thrownewLogicException("短信发送失败,平台管理员!
");
}
}catch(IOExceptione){
e.printStackTrace();
thrownewLogicException("短信发送失败,平台管理员!
");
}
}
}
其中的checkCanSendVerifyCode方法用于验证当前是否能再次发短信:
privatebooleancheckCanSendVerifyCode(){
Datenow=newDate();
VerifyCodevc=UserContext.getVerifyCode();
if(vc==null){
returntrue;
}else{
DatelastTime=vc.getLastSendTime();
if(DateUtil.getSecondBetween(lastTime,now)>=120){
returntrue;
}
}
returnfalse;
}
为了让service和web相关API脱离,我们把当前用户发送的验证码信息的存取逻辑都放到了UserContext中:
publicstaticvoidsetVerifyCode(VerifyCodevc){
getRequest().getSession().setAttribute(VERIFYCODE_IN_SESSION,vc);
}
publicstaticVerifyCodegetVerifyCode(){
return(VerifyCode)getRequest().getSession().getAttribute(VERIFYCODE_IN_SESSION);
}
测试之前请部署好eloan-mockserver;
完成手机绑定逻辑
在发送完验证码之后,就是用户输入验证码,并点击保存之后的逻辑。
首先修改前端页面,添加提交手机绑定信息:
$("#bindPhone").click(function(){
$("#bindForm").ajaxSubmit(function(data){
if(data.success){
$.messager.confirm("提示","绑定手机成功!
",function(){
window.location.reload();
});
}else{
$.messager.alert("提示",data.msg);
}
});
});
在PersonalController中添加绑定手机方法:
@RequestMapping("/bindPhone")
@ResponseBody
publicResultJSONbindPhone(StringphoneNumber,StringverifyCode,Modelmodel){
ResultJSONjson=newResultJSON(true);
try{
this.userInfoService.bindPhone(phoneNumber,verifyCode);
json.setSuccess(true);
}catch(LogicExceptionle){
json.setSuccess(false);
json.setMsg(le.getMessage());
}
returnjson;
}
在userInfoService中添加bindPhone方法:
publicvoidbindPhone(StringphoneNumber,StringverifyCode){
if(this.verifyCodeService.checkVerifyCode(phoneNumber,verifyCode)){
Logininfocurrent=UserContext.getLoginInfo();
Userinfoui=this.userInfoMapper.selectByPrimaryKey(current.getId());
if(!
ui.getHasBindPhone()){
ui.addBitState(BitStatesUtils.OP_BIND_PHONE);
ui.setPhoneNumber(phoneNumber);
this.update(ui);
}
}else{
thrownewLogicException("验证码错误或者过期!
");
}
}
注意,因为我们的userinfo对象需要乐观锁修改,所以我们专门在service中写了一个update方法来处理乐观锁问题:
privatevoidupdate(Userinfoui){
intret=this.userInfoMapper.updateByPrimaryKey(ui);
if(ret==0){
System.out.println("userinfo对象更新失败");
thrownewLogicException("系统正忙,请稍后再试!
如果多次看到该提示,平台管理员!
");
}
}
为了方便操作,在Userinfo对象中添加一个增加状态的方法:
publicvoidaddBitState(LongnewState){
this.bitState=BitStatesUtils.addState(this.bitState,newState);
}
在VerifyCodeService中添加检查验证码的方法:
publicbooleancheckVerifyCode(StringphoneNumber,Stringcode){
VerifyCodevc=UserContext.getVerifyCode();
if(vc!
=null){
if(vc.getPhoneNumber().equals(phoneNumber)&&//判断电话号码是否相同
vc.getRandomCode().equals(code)&&//判断验证码是否相同
DateUtil.getSecondBetwee
- 配套讲稿:
如PPT文件的首页显示word图标,表示该PPT已包含配套word讲稿。双击word图标可打开word文档。
- 特殊限制:
部分文档作品中含有的国旗、国徽等图片,仅作为作品整体效果示例展示,禁止商用。设计者仅对作品中独创性部分享有著作权。
- 关 键 词:
-
07
完善
前端
系统
功能
项目
开发
文档
资料
冰豆网所有资源均是用户自行上传分享,仅供网友学习交流,未经上传用户书面授权,请勿作他用。