ajax

ajax:async javascript and xml - 异步的js和xml

作用:发送http请求
浏览器 -> 服务器 请求
服务器 -> 浏览器 响应

 

xml:extension markup language - 可扩展的标记语言 - 自定义标签

通过button点击使用ajax

// 点击按钮发送http请求到demo.php,获取demo.php中的时间,放在div中
document.querySelector("button").onclick = function(){
    // 发送请求
    // 1.创建ajax对象
    var ajax = new XMLHttpRequest()
    // 2.监听请求状态
    ajax.onreadystatechange = function(){
        // 判断请求完成
        if(ajax.readyState==4){
            // 判断是否请求成功
            if(ajax.status>=200 && ajax.status<300){
                // 接收服务器响应的数据
                var res = ajax.responseText;
                console.log(res);
            }
        }
    }
    // 3.设置请求
    ajax.open('get','demo.php')
    // 4.发送
    ajax.send()
}

ajax的写法

// ajax写的时候需要4个步骤
// 1.创建对象
var xhr = new XMLHttpRequest()
// console.log(xhr.readyState);
// 2.监听状态
xhr.onreadystatechange = function(){
    // 输出状态
    // console.log(xhr.readyState); // 状态是4的时候表示请求完成
    // 不能在这里直接接收数据 - 只能在状态是4的时候再接收
    if(xhr.readyState===4){
        // 接收数据
        // console.log(xhr.responseText);
        // 通常会在请求成功的时候接收数据
        // console.log(xhr.status) // 响应状态码
        if(parseInt(xhr.status/100)===2){ //判断状态码是不是200到300之间也可以这么写——if(xhr.status>=200 && xhr.status<300)
            console.log(xhr.responseText);
        }else{
            console.log("请求出问题了");
        }
    }
// 3.设置
// get请求的数据都在地址栏后面
xhr.open('get','demo.php?id=2')
// 4.发送
xhr.send()

}

post请求方式的写法

var xhr = new XMLHttpRequest()

xhr.onreadystatechange = function(){
    if(xhr.readyState===4){
        if(xhr.status>=200 && xhr.status<300){
            var res = xhr.responseText;
            console.log(res);
        }
    }
}

xhr.open('post','demo.php')
// 设置请求头
xhr.setRequestHeader('content-type','application/x-www-form-urlencoded')
xhr.send("id=2")

总结:

设置 - 请求方式、请求路径
是否有数据需要发送
有 - get请求还是post请求
get:修改请求路径,把数据放到地址后面
post:设置请求头

send()
没有数据:send

 

ajax的特点

1.可以同步 可以异步

xhr.onreadystatechange = function(){
    if(xhr.readyState===4){
        if(xhr.status>=200 && xhr.status<300){
            // var res = xhr.responseText;
            // 专门用来获取xml数据
            var res = xhr.responseXML;
            // 获取xml中的数据,就像操作dom节点一样去操作就好
            var students = res.querySelectorAll('student')
            for(let i=0;i<students.length;i++){
                let nameTag = students[i].firstElementChild;
                console.log(nameTag);
            }
       }
    }
}
// open方法有第三个参数:布尔值,默认是true,代表是否是异步请求
xhr.open('get','demo.xml',false)
xhr.send()

2.可以请求任意类型文件 - php/txt/css/js/xml/json  例子同上

3.将数组/对象 转成字符串

var str = JSON.stringify([1,2,3])
var str = JSON.stringify({name:"张三",age:12})
console.log(str); // json字符串
var xhr = new XMLHttpRequest()
xhr.onreadystatechange = function(){
    if(xhr.readyState===4){
        if(xhr.status>=200 && xhr.status<300){
            var res = xhr.responseText;
            // 可以将长的像数组或对象的字符串转成数组或对象
            res = JSON.parse(res) // JSON.parse只能转换json字符串和数字,如果不是json字符串,也不是数字,转换失败报错
            // 
            console.log(res);
        }
    }
}
xhr.open('get','demo.php')
xhr.send()

若想要获取数据库中的数据 js代码同上,php代码为

<?php
header("content-type:text/html;charset=utf8");
// date_default_timezone_set("PRC");
// echo date("Y-m-d H:i:s",time());

// 在php中输出 - 就是给ajax做响应
// echo 123;



$con = mysqli_connect("localhost","root","root","2008");
mysqli_query($con,"set names utf8");
$res = mysqli_query($con,"select * from user");
$arr = [];
while($row = mysqli_fetch_assoc($res)){
    $arr[] = $row;
}
// ajax接收到的数据,都是字符串类型的,所以php给ajax响应的时候,如果是数组,就要转成json字符串响应
echo json_encode($arr); // 将数组转成json字符串

// php给ajax响应的时候,不要输出多次,不要使用var_dump和print_r进行输出,就使用echo 给响应一次就好

 

封装的ajax函数

// 测试函数
document.querySelector("button").onclick = function(){
    sendAjax({
        url:'demo.php',
        success:function(res){
            console.log(res);
        },
        method:'post',
        async:true,
        dataType:"json",
        // data:'name=张三&age=12'
        data:{
            name:"张三",
            age:12
        }
    })
}


// 将请求方式、是否异步、数据、设置为默认值
// 每个数据传进来进行判断 - method:'aaa'    url:123456
// 传入参数的时候,希望能使用对象传入,字符串也可以
function sendAjax(obj){
    // 请求地址
    /*
    1.是否传入地址
    2.传入地址后,地址的类型是否是字符串
    */
    // if(obj.url){
    //     // 传值了
    //     // 判断类型
    //     if(Object.prototype.toString.call(obj.url) !== '[object String]'){
    //         throw new Error('地址类型不对')
    //     }
    // }else{
    //     // 没有传
    //     throw new Error('地址必填')
    // }

    if(!obj.url){ // 没有传值
        throw new Error('地址必填')
    }
    // 代码能走到这里,说明传值了
    // 判断类型
    if(Object.prototype.toString.call(obj.url) !== '[object String]'){
        throw new Error('地址类型不对')
    }
    // 请求方式
    /*
    1.是否传入请求方式
    2.没有传入 - 默认值是get
    3.如果传入了 - 判断是否是get或post
    */
    if(!obj.method){ // 没有传入请求方式
        obj.method = 'get';
    }
    // 判断请求方式必须是字符串
    if(Object.prototype.toString.call(obj.method) !== '[object String]'){
        throw new Error('请求方式类型不对')
    }
    // 判断请求方式是否是get或post
    if(obj.method.toLowerCase()!=='get' && obj.method.toLowerCase()!=='post'){
        throw new Error('请求方式只能是get或post')
    }
    // 请求是否异步
    /*
    1.判断是否传入
    2.传入了 - 判断必须是布尔值
    3.没传入 - 设置默认true
    */
    if(obj.async === undefined){ // 没传
        obj.async = true
    }
    // 判断类型必须是布尔值
    if(Object.prototype.toString.call(obj.async) !== '[object Boolean]'){
        throw new Error('是否异步的参数必须是布尔值')
    }
    // 请求的参数
    /*
    1.是否传入
    2.如果传入了
    3.类型允许是object和string
    4.如果string
        判断请求方式
    5.如果是object
        将object转成string
        再判断请求方式
    */
    if(obj.data){ // 如果传入了
        var data = '';
        // 判断类型
        // 如果是字符串
        if(Object.prototype.toString.call(obj.data) === '[object String]'){
            data = obj.data
        }
        // 再如果是object
        else if(Object.prototype.toString.call(obj.data) === '[object Object]'){
            // 转成string
            var arr = []
            for(var attr in obj.data){
                arr.push(attr + '=' + obj.data[attr])
            }
            data = arr.join('&')
        }
        // 否则报错
        else{
            throw new Error('数据类型不对')
        }
        // data - 就是能直接使用的数据 字符串
        // 如果是get请求,就把数据拼接在地址后面
        if(obj.method.toLowerCase()=='get'){
            obj.url += '?' + data
        }
    }
    // 请求成功的函数
    /*
    1.有没有传
    2.没有传就报错
    3.如果传了,类型必须是一个函数
    */
    if(!obj.success){
        throw new Error('成功的处理函数必填')
    }
    if(Object.prototype.toString.call(obj.success) !== '[object Function]'){
        throw new Error('成功的处理函数必须是函数类型')
    }
    // 请求失败的函数
    if(!obj.error){
        obj.error = function(){}
    }
    if(Object.prototype.toString.call(obj.error) !== '[object Function]'){
        throw new Error('失败的处理函数必须是函数类型')
    }
    // 判断希望返回的数据类型是否传入
    if(!obj.dataType){
        obj.dataType = 'json';
    }
    // 创建ajax对象
    var xhr = new XMLHttpRequest();
    // 监听状态
    xhr.onreadystatechange = function(){
        // 判断是否完成
        if(xhr.readyState === 4){
            // 判断是否成功
            if(xhr.status>=200 && xhr.status<300){
                // 成功了
                // 希望返回的数据类型 - 默认值是json
                /*
                1.判断是否传入
                2.没有传入给默认值 - json
                3.如果传入了
                */
                switch(obj.dataType){
                    case 'json':
                        var res = xhr.responseText;
                        res = JSON.parse(res);
                        break;
                    case 'string':
                        var res = xhr.responseText;
                        break;
                    case 'xml':
                        var res = xhr.responseXML;
                        break;
                    default:
                        throw new Error('希望返回的数据类型不对')
                }
                obj.success(res)
            }else{
                // 失败了
                obj.error()
            }
        }
    }
    // 设置请求方式和地址
    xhr.open(obj.method,obj.url,obj.async)
    // 判断是否有数据
    if(data){
        // 判断请求方式是否是post
        if(obj.method.toLowerCase() === 'post'){
            // 设置请求头
            xhr.setRequestHeader('content-type','application/x-www-form-urlencoded');
            xhr.send(data)
            return;
        }
    }
    // 发送请求
    xhr.send()
}
/************************** 请求模板 ****************************/
/*
sendAjax({
    url:'demo.php',
    success:function(res){
        console.log(res);
    },
    method:'post',
    async:true,
    dataType:"json",
    // data:'name=张三&age=12'
    data:{
        name:"张三",
        age:12
    }
})
*/

 

 

posted @ 2021-01-27 19:37  技术活当赏  阅读(55)  评论(0)    收藏  举报