• web第三节


    一.跨域问题:

      能够正常请求,但是没有办法获取到响应结果

      1.设置请求头

        response.setHeader("Access-Control-Allow-Origin", "*");

      代码如下:

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
            //1.接受数据
            String username=request.getParameter("username");
            System.out.println("接受的数据:"+username);
            //接受Ajax传递的数据
            //2.响应结果,数据必须为JSON格式
            response.getWriter().write("success");
            //3.设置请求头
            response.setHeader("Access-Control-Allow-Origin", "*");
        }

      2.JSONP解决跨域问题

        普通的跨域访问问题,浏览器会进行拦截,凡是src属性的都不会拦截

        ajax:http://localhost:8080/a/AServlet

        JSONP实现原理:动态加载<script>标签,利用src属性进行服务器资源的访问,但是只支持Get请求
        1.在我们的Ajax请求当中,需要以JSONP方式请求(通过jquery手段,动态生成sript)

        jsonp:"代表的时前台传给后台,后台再传递给你 jsonpCallBack"

        2.再AJAX请求当中需要将返回的数据格式指定为jsonp
          dataType:"JSONP"

        3.JSONP需要以Get请求发送 ?username=zhangsan
        4.后台需要做的事情:
          1.正常接收数据
          2.返回数据
          前台传递过来的jsonp需要原路返回

          String jsonp=request.getP("jsonpCallBack");

          需要将返回的数据转换为JSON success
          response.getWirter.write(jsonp+"("+返回的数据+")");

      修改Ajax请求:

    $("#button").click(function () {
                //获取到文本框的值
                var username=$("#username").val();
                //发送Ajax请求www.a.com的A工程
                $.ajax({
                  url:"http://www.a.com:8080/a/AServlet?username="+username,
                  type:"GET",
                  jsonp:"jsonpCallBack",      //回调函数
                  dataType:"JSONP",
                  success:function (result) {
                       alert(result);
                  },
                  error:function () {
                       alert('系统错误~')
                  }
            });
      });

        更改后台请求,需要将JSONP原路返回

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
                                //1.接受数据
                                String username=request.getParameter("username");
                                System.out.println("接受的数据:"+username);
    
                                //接受Ajax传递的数据
                                String jsonpCallBack = request.getParameter("jsonpCallBack");
                                System.out.println("jsonpCallBack:"+jsonpCallBack);
    
                                String success = JSON.toJSONString("success");
                                //2.响应结果,数据必须为JSON格式
                                response.getWriter().write(jsonpCallBack+"("+success+")");
                                //3.设置请求头
                                /*response.setHeader("Access-Control-Allow-Origin", "*");*/
                            }

      3.使用HTTPClient解决:就是不通过浏览器发送请求

        B工程的页面发送的Ajax没有办法请求到A工程,因为浏览器会拦截,走后台,后台通过HTTPClient请求请求到A工程,获取到响应结果
        1.B工程的Bindex.jsp页面请求到B工程的Servlet

    $("#button").click(function () {
                        //获取到文本框的值
                        var username=$("#username").val();
                        //发送Ajax请求www.a.com的A工程
                        $.ajax({
                            url:"BServlet?username="+username,
                            type:"GET",
                            success:function (result) {
                                alert(result);
                            },
                            error:function () {
                                alert('系统错误~')
                            }
                        });
                    });

        2.B工程的BServlet去模拟HTTP请求到A工程

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
                        //内部通过HTTPClient进行转发
                        //构建一个连接
                        CloseableHttpClient client = HttpClients.createDefault();
                        //构建请求
                        HttpGet get=new HttpGet("http://www.a.com:8080/a/AServlet?username="+request.getParameter("username"));
                        //发送请求
                        CloseableHttpResponse httpResponse = client.execute(get);
                        //获取返回结果
                        String result = EntityUtils.toString(httpResponse.getEntity());
                        //将A工程响应结果给页面
                        response.getWriter().write(result);
    
                    }

        3.A工程处理请求

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
                        //1.接受数据
                        String username=request.getParameter("username");
                        System.out.println("接受的数据:"+username);
    
                        //2.响应结果
                        response.getWriter().write("success");
                        
                        
    
                    }

    2.防止表单重复提交

      1.网络延迟,再网络延迟时间内,频繁的提交表单

        只能提交一次,监控表单的提交事件,通过一个boolean类型的变量来区分已经点击过还是没有点击,如果已经点击过,表单就不提交,没有点击过再提交

      2.重新加载或者后退页面
        思路如下:在我访问登录页面的时候,创建一个 Token令牌(当作一个标识) ,保存到session当中,然后再表单提交的时候将令牌一起提交后台Servlet去判断session当中的令牌和表单提交的令牌是否相等,如果相等代表正常提交(session清空),如果不相等,代表非正常提交

      Form.jsp页面

    <body>
                        <form action="FormServlet" onsubmit="return formSubmit()" method="post">
                            <input type="hidden" id="hiddenToken" name="formToken"/>
                            <input type="text" name="username"/>
                            <input type="submit" value="提交"/>
                        </form>
                    </body>
                    
                    
                    <script type="text/javascript">
                        //创建一个变量   false代表没有点击过,true代表已经点击过
                        var flag=false;
                        function formSubmit() {
                            if(!flag){      //取反值为false
                                flag=true;
                                return true;
                            }else {
                                return false;
                            }
                        }
    
                        $(function () {
                            //生成令牌
                            $.ajax({
                                url:"TokenServlet",
                                type:"POST",
                                success:function (token) {
                                    $("#hiddenToken").val(token);
                                }
                            })
                        })
                    </script>

      TokenServlet:

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
                        //生成令牌
                        String token = UUID.randomUUID().toString();
                        //令牌保存到session当中
                        request.getSession().setAttribute("sessionToken",token);
                        //响应
                        response.getWriter().write(token);
                    }

      FormServlet:

    protected void doGet(HttpServletRequest request, HttpServletResponse response) throws ServletException, IOException {
                        //验证令牌
                        //获取页面提交的隐藏域数据
                        String formToken = request.getParameter("formToken");
                        //获取Session中的Token
                        String sessionToken = (String)request.getSession().getAttribute("sessionToken");
                        //如果页面中获取的和session中不一致,代表已经提交过了,不要重复提交
                        if(!formToken.equals(sessionToken)){
                            response.getWriter().write("不要重复提交~");
                            return;
                        }
    
                        //接收数据
                        String username = request.getParameter("username");
                        System.out.println("接收的数据为:"+username);
                        //必须将token清空,不然永远是一致的
                        request.getSession().removeAttribute("sessionToken");
    
                        try {
                            //模拟网络延迟
                            Thread.sleep(300);
                        } catch (InterruptedException e) {
                            e.printStackTrace();
                        }
                        //返回数据
                        response.getWriter().write("success");
                    }

    3.防止XSS攻击:

      大部分浏览器都已经解决了该问题

      脚本注入
      防止XSS攻击:后台创建Filter过滤器,过滤所植入的脚本数据<script>,使用正则表达式匹配提交数据的格式

  • 相关阅读:
    软件测试基础5 ——系统测试之软件质量
    软件测试基础4 ——系统测试之测试方法
    软件测试基础3 ——系统测试之系统测试类型
    软件测试基础2 ——系统测试之测试对象与测试级别
    软件测试基础1 ——系统测试之测试基础
    《软件测试方法和技术》-读书笔记(三)
    《软件测试方法和技术》-读书笔记(二)软件缺陷的产生
    《软件测试方法和技术》-读书笔记(一)
    bug的一些事
    开发版速达-提供在线帐套配置功能
  • 原文地址:https://www.cnblogs.com/ws1149939228/p/12269422.html
Copyright © 2020-2023  润新知