登录模块点击一次登录按钮发起了两次请求
2018-03-04 11:21
483 查看
前言
我还在想这个情况会不会跟上一篇博文一样,是因为某种问题导致页面生成了多个id一样的表单,但是发现并不是这样。目前这个问题暂时通过提交前禁用按钮提交功能,返回结果后恢复按钮提交功能来解决。根本原因还没找到。问题描述
使用360浏览器
通过浏览器地址栏发起一个能登录成功的请求:http://localhost:8080/user/login?loginId=liweizhi&password=liweizhi
查看后台,发现,只发起了一次访问:
09:09:28.246 [http-nio-8080-exec-32] INFO hrm.controller.UserController - 进到了login方法 09:09:28.247 [http-nio-8080-exec-32] DEBUG org.mybatis.spring.SqlSessionUtils - Creating a new SqlSession 09:09:28.247 [http-nio-8080-exec-32] DEBUG org.mybatis.spring.SqlSessionUtils - SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@71c627a5] was not registered for synchronization because synchronization is not active 09:09:28.248 [http-nio-8080-exec-32] DEBUG o.m.s.t.SpringManagedTransaction - JDBC Connection [com.mchange.v2.c3p0.impl.NewProxyConnection@72dd5e26] will not be managed by Spring 09:09:28.249 [http-nio-8080-exec-32] DEBUG h.d.E.queryByLoginIdAndPassword - ==> Preparing: SELECT login_id,password,identity FROM employee_inf WHERE login_id=? AND password = ?; 09:09:28.250 [http-nio-8080-exec-32] DEBUG h.d.E.queryByLoginIdAndPassword - ==> Parameters: liweizhi(String), liweizhi(String) 09:09:28.253 [http-nio-8080-exec-32] DEBUG h.d.E.queryByLoginIdAndPassword - <== Total: 1 09:09:28.254 [http-nio-8080-exec-32] DEBUG org.mybatis.spring.SqlSessionUtils - Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@71c627a5] 09:09:28.254 [http-nio-8080-exec-32] INFO hrm.controller.UserController - 登录成功,准备跳往主界面
通过浏览器地址栏发起登录不成功的请求:
http://localhost:8080/user/login?loginId=liweizhi1&password=liweizhi1
却发起了两次访问:
09:11:24.892 [http-nio-8080-exec-38] INFO hrm.controller.UserController - 进到了login方法 09:11:24.893 [http-nio-8080-exec-38] DEBUG org.mybatis.spring.SqlSessionUtils - Creating a new SqlSession 09:11:24.893 [http-nio-8080-exec-38] DEBUG org.mybatis.spring.SqlSessionUtils - SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@67e3089a] was not registered for synchronization because synchronization is not active 09:11:24.894 [http-nio-8080-exec-38] DEBUG o.m.s.t.SpringManagedTransaction - JDBC Connection [com.mchange.v2.c3p0.impl.NewProxyConnection@6d1b63ea] will not be managed by Spring 09:11:24.894 [http-nio-8080-exec-38] DEBUG h.d.E.queryByLoginIdAndPassword - ==> Preparing: SELECT login_id,password,identity FROM employee_inf WHERE login_id=? AND password = ?; 09:11:24.895 [http-nio-8080-exec-38] DEBUG h.d.E.queryByLoginIdAndPassword - ==> Parameters: liweizhi1(String), liweizhi1(String) 09:11:24.903 [http-nio-8080-exec-38] DEBUG h.d.E.queryByLoginIdAndPassword - <== Total: 0 09:11:24.903 [http-nio-8080-exec-38] DEBUG org.mybatis.spring.SqlSessionUtils - Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@67e3089a] 09:11:24.904 [http-nio-8080-exec-38] INFO hrm.controller.UserController - 登录失败,账号密码错误 09:11:25.499 [http-nio-8080-exec-39] INFO hrm.controller.UserController - 进到了login方法 09:11:25.500 [http-nio-8080-exec-39] DEBUG org.mybatis.spring.SqlSessionUtils - Creating a new SqlSession 09:11:25.500 [http-nio-8080-exec-39] DEBUG org.mybatis.spring.SqlSessionUtils - SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5281d24e] was not registered for synchronization because synchronization is not active 09:11:25.501 [http-nio-8080-exec-39] DEBUG o.m.s.t.SpringManagedTransaction - JDBC Connection [com.mchange.v2.c3p0.impl.NewProxyConnection@5879b93e] will not be managed by Spring 09:11:25.501 [http-nio-8080-exec-39] DEBUG h.d.E.queryByLoginIdAndPassword - ==> Preparing: SELECT login_id,password,identity FROM employee_inf WHERE login_id=? AND password = ?; 09:11:25.503 [http-nio-8080-exec-39] DEBUG h.d.E.queryByLoginIdAndPassword - ==> Parameters: liweizhi1(String), liweizhi1(String) 09:11:25.506 [http-nio-8080-exec-39] DEBUG h.d.E.queryByLoginIdAndPassword - <== Total: 0 09:11:25.506 [http-nio-8080-exec-39] DEBUG org.mybatis.spring.SqlSessionUtils - Closing non transactional SqlSession [org.apache.ibatis.session.defaults.DefaultSqlSession@5281d24e] 09:11:25.507 [http-nio-8080-exec-39] INFO hrm.controller.UserController - 登录失败,账号密码错误
如果url参数为空:
http://localhost:8080/user/login?loginId=1&password=
如果上一次发起的是带参数值的url请求访问了两次,那么这次带参数值的url请求也是发起两次访问。
09:26:34.607 [http-nio-8080-exec-50] INFO hrm.controller.UserController - 进到了login方法 09:26:34.607 [http-nio-8080-exec-50] INFO hrm.controller.UserController - 账号或密码为空,不访问数据库,直接返回null 09:26:34.851 [http-nio-8080-exec-44] INFO hrm.controller.UserController - 进到了login方法 09:26:34.852 [http-nio-8080-exec-44] INFO hrm.controller.UserController - 账号或密码为空,不访问数据库,直接返回null
如果上一次访问url请求参数为空,那么这次请求参数为空的url请求就只访问一次:
09:29:16.214 [http-nio-8080-exec-48] INFO hrm.controller.UserController - 进到了login方法 09:29:16.214 [http-nio-8080-exec-48] INFO hrm.controller.UserController - 账号或密码为空,不访问数据库,直接返回null
上面那一段我并不能很好的表达,因为出现的情况很怪异,为什么会这样。
也就是说,只有账号密码填写正确的情况,才能确定只发起一次请求。其他情况均不能确定。通常是发起两次请求。
一开始我以为是前端的问题,但是我通过url直接访问也会出现这个问题,说明不是前端代码的问题。这就让我很郁闷了。
但是假如前端代码我在执行提交方法时,先禁用按钮点击功能,等返回结果后再恢复按钮的点击功能,就能保证只发起一次请求:
<script> function submitForm() { //$("#btn").attr("disabled",true);//禁用按钮 $('#form').form('submit',{ url:'/user/login', success:function (data) { if(data){ window.location.href=data;//页面跳转 }else{ $('#p').text("您输入的账号或密码不正确,请重新输入");//给出提示 } //$("#btn").attr("disabled",false);//恢复按钮 } }); } </script>
郁闷。。。为什么会这样。。。
这是我的表单:
<div class="easyui-window" title="Login" style="width:320px;height:220px;" collapsible="false" minimizable="false" maximizable="false" closable="false" draggable="false" resizable="false"> <form id="form" method="post" style="padding:10px 20px 10px 40px;"> <p id="p">欢迎登录</p> <p>账号:<input class="easyui-textbox" name="loginId" data-options="prompt:'请输入账号'"></p> <p>密码:<input class="easyui-textbox" name="password" data-options="prompt:'请输入密码'" type="password"></p> <div style="padding:5px;text-align:center;"> <button id="btn" class="easyui-linkbutton" onclick="submitForm()">登录</button> </div> </form> </div>
这是我的后台代码:
@ResponseBody @RequestMapping(value = "/login") public String login(@RequestParam("loginId") String loginId, @RequestParam("password") String password, //@RequestParam("token") String clientToken, HttpSession session){ logger.info("进到了login方法"); if("".equals(loginId) || "".equals(password)) { logger.info("账号或密码为空,不访问数据库,直接返回null"); return null; } User user = employeeService.getUserByLoginIdAndPassword(new User(loginId,password)); if(user!=null){ logger.info("登录成功,准备跳往主界面"); session.setAttribute("user_session",user); return "/user/main";//login方法用@ResponseBody注解修饰了,因此这里是直接返回字符串到浏览器 }else{ logger.info("登录失败,账号密码错误"); return null; } }
我想这也不是前端easyui框架的bug吧,毕竟我通过浏览器直接访问url是没有涉及到前端的。但是上面又说了前端代码提交前禁用按钮请求返回结果后恢复按钮功能就不会发起多次请求。
使用其他浏览器
我又换了火狐浏览器,发现,在火狐浏览器上通过url进行访问,任何情况都是发起一次请求!!!(ps:我上面的例子用的是360浏览器)但是用火狐浏览器访问登录界面,当账号密码填写错误,出现的结果跟使用360浏览器一样,都是页面变成一片空白,如图:
奇怪的是!!!!当账号密码填写正确,没有进行页面的跳转,如图:
很不理解,我的脚本代码是这么写的:
function submitForm() { //$("#btn").attr("disabled",true);//禁用按钮 $('#form').form('submit',{ url:'/user/login', success:function (data) { if(data){ window.location.href=data;//页面跳转 }else{ $('#p').text("您输入的账号或密码不正确,请重新输入");//给出提示 } //$("#btn").attr("disabled",false);//恢复按钮 } }); }
控制台也没报错说,无法识别window.location.href,没有报错。但是却莫名其妙的将后台返回的结果显示在界面上。
而使用谷歌浏览器,通过url进行访问的话,任何情况都是发起一次请求。但是如果通过登录界面进行访问的话,如果账号密码填写正确,是能进到主界面的。如果账号密码填写错误的情况,就会发起两次请求。跟360浏览器一样,页面变得一片空白。
整理一下
我使用url进行访问,就没涉及到前端,使用360登录成功的话就只发起一次请求,失败的话就发起两次请求。使用火狐、谷歌,账号密码正确与否都只发起一次请求。通过界面进行访问,就涉及到前端。360和谷歌,账号密码正确的话能正确跳转到主界面,而火狐却只是返回返回的字符串。账号密码填写错误,三种浏览器都一样,发起两次请求,且页面变得一片空白。
目前解决方案
通过在脚本方法中,提交前禁用按钮点击功能,返回结果后恢复点击功能,就能实现只发起一次请求:function submitForm() { $("#btn").attr("disabled",true);//禁用按钮 $('#form').form('submit',{ url:'/user/login', success:function (data) { if(data){ window.location.href=data;//页面跳转 }else{ $('#p').text("您输入的账号或密码不正确,请重新输入");//给出提示 } $("#btn").attr("disabled",false);//恢复按钮 } }); }
但是火狐浏览器却还是有问题,当账号密码正确时,界面没有跳转到主界面,而是返回一个字符串显示在界面上。
我的看法
当我发现通过上面的脚本代码可以解决问题的时候,我猜想问题是出在前端。可是当我通过直接url进行进行访问,就没涉及到前端,但通过360浏览器的地址栏发起请求,在登录失败的时候也会发起两次请求。这又让我觉得问题不是出在前端。我觉得问题就只能出在浏览器了,这锅暂时就让浏览器背着吧。暂时就这样吧。
至于为什么通过上面的脚本代码就能避开那个问题,我也不知道。这是我在前端处理表单”由于网络延迟重复点击提交按钮造成的发起多次请求“问题时碰巧解决的。
最后
记下这个问题,看看什么时候才有能力去解决。相关文章推荐
- 点击按钮一次,请求两次问题解决
- 按钮的Ajax请求时一次点击两次提交的解决方法
- 按钮的ajax请求时,一次点击两次提交的问题
- 按钮的ajax请求时,一次点击两次提交的问题
- 利用HttpClient的POST方式发起带参数的请求时,点击注册按钮无反应状态分析
- div模拟收藏按钮,连续点击两次导致重复请求两次接口
- 如果某个页面上点击按钮发起了一个http url请求,去执行一个action,但是还没等这个action完成,我就刷新了这个页面,然后又点击了这个按钮,这样之前的那次http url请求还在执行吗?
- 怎么解决重复提交的问题,即网络不好的时候,提交按钮点了一次,但是却发起了多次http url请求,数据库中写入了多条重复记录(当然ID是不重复的,因为毕竟是多条http url记录)
- 按钮点击不起作用和点击一次执行两次问题解决
- Exchange2010 OWA登录后,点击任何按钮提示“出现意外错误,无法处理您的请求”
- ajax请求时,一次点击两次提交的问题
- 点击按钮一次,多次请求的问题
- 给button绑定click事件时,出现ajax请求时,一次点击两次提交的问题解决
- 动态创建添加按钮后,解决开始需要点击两次才能触发,之后点击一次就可以了
- 为什么查询时总是点击查询按钮两次才会有结果,而以后只要点击一次就可以有查询结果了?
- 点击页面上的普通按钮(没有任何逻辑),可每次都重新请求一次
- js调用浏览器打印模块实现点击按钮触发自定义函数
- javascript设置连续两次点击按钮时间间隔的方法
- Spring mvc 一次请求Controller执行两次的问题
- 利用pywinauto模块打开一个应用,输入参数,点击应用中的按钮,获取数据