博客园  :: 首页  :: 新随笔  :: 联系 :: 订阅 订阅  :: 管理

使用option 链式调用来代替异步方法幂调用

Posted on 2021-01-11 20:33  liufu627  阅读(124)  评论(0编辑  收藏  举报

场景

0. 当前目录下有jquery-3.4.1.min.js,option.html,ajax.html,子目录School下要有student.json,class.json和techer.json文件

  • student.json
[
    {"id":1,"classid":1,"name":"张三"}
]
  • class.json
[{
    "id":1,
    "name":"初一班",
    "techerid":1
}]
  • techer.json
[{"id":1, "name":"张老师"}]

希望先得学生信息,再找班级信息(根据classid),再找老师信息(根据techerid),需要使用ajax来动态调用。

1. 传统代码实现ajax.html如下:

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <script src="jquery-3.4.1.min.js">
    </script>
</head>

<body>
    <script>
        
        var m3 = (input, link_obj) => {
            $.ajax({
                url: "school/techer.json",
                dataType: "json",
                success: function (data) {
                    let found = false;
                    for (var key in data) {
                        if (data[key].id == input) {

                            var name = data[key].name;
                            console.log(`techer(id:${input},name=${name})`);
                            found = true;
                            break;
                        }
                    }

                    if (!found) {
                        var err = `techer query failed:${input}`;
                        console.log(err);
                    }
                },
                error(err) {
                    var err = `request techer query failed.`;
                    console.log(err);
                }
            })
        }


        var m2 = (input) => {
            $.ajax({
                url: "school/class.json",
                dataType: "json",
                success: function (data) {
                    let found = false;
                    for (var key in data) {
                        if (data[key].id == input) {

                            var techerid = data[key].techerid;
                            var name = data[key].name;
                            console.log(`class(id:${input},techerid:${techerid},name=${name})`);
                            found = true;
                            m3(techerid);
                            break;
                        }
                    }

                    if (!found) {
                        var err = `class query failed:${input}`;
                        console.log(err);
                        Fail(err, link_obj);
                    }
                },
                error(err) {
                    var err = `request class query failed.`;
                    console.log(err);
                }
            })
        }

        var m1 = (input) => {
            $.ajax({
                url: "school/student.json",
                dataType: "json",
                success: function (data) {
                    let found = false;
                    for (var key in data) {
                        if (data[key].id == input) {

                            var classid = data[key].classid;
                            var name = data[key].name;
                            console.log(`student(id:${input},classid:${classid},name=${name})`);                            
                            found = true;
                            m2(classid);
                            break;
                        }
                    }

                    if (!found) {
                        var err = `student query failed:${input}`;
                        console.log(err);
                    }
                },
                error(err) {
                    var err = `request student query failed.`;
                    console.log(err);
                }
            })
        }
       
        m1(1);

    </script>
</body>

</html>

显示结果为:

student(id:1,classid:1,name=张三)
ajax.html:55 class(id:1,techerid:1,name=初一班)
ajax.html:25 techer(id:1,name=张老师)

我们发现,m1调用m2,m2调用m3,每个方法都是ajax调用,主逻辑:m1(1),只有查看代码才知道实际的逻辑关系,这不是很好的方法。

2.以下便是我的解决方案 option.html:

具体代码如下:

<!DOCTYPE html>
<html lang="en">

<head>
    <meta charset="UTF-8">
    <meta name="viewport" content="width=device-width, initial-scale=1.0">
    <title>Document</title>
    <script src="jquery-3.4.1.min.js">
    </script>
</head>

<body>
    <script>
        (function link_enter(window) {

            function Link(fn, input) {
                this.listfn = [{ obj: this, fn, input }];

                this.option = function (fn, input) {
                    this.listfn.push({ obj: this, fn, input });
                    return this;
                },
                    this.run = function (arg) {
                        if (this.listfn && this.listfn.length <= 0)
                            return;

                        let { obj, fn, input } = this.listfn.shift();
                        if (typeof fn !== 'function')
                            return;
                        if (!obj) {
                            console.log("obj is null");
                            return;
                        }

                        if (!arg) {
                            fn(input, obj);
                            return;
                        }

                        let { success, output } = arg;

                        if (success) {
                            fn(output, obj);
                        }
                    }
            }

            window.Link = {
                init: function (fn, input) {
                    return new Link(fn,input);
                }
            }

            window.Ok = function (data,link_obj) {
                link_obj.run({ success: true, output: data });
            }
            window.Fail = function (err,link_obj) {
                link_obj.run({ success: false, output: err });
            }
        })(window);

        var m1 = (input, link_obj) => {
            $.ajax({
                url: "school/student.json",
                dataType:"json",
                success:function(data) {
                    let found = false;
                    for (var key in data) {
                        if (data[key].id == input) {

                            var classid=data[key].classid;
                            var name=data[key].name;
                            console.log(`student(id:${input},classid:${classid},name=${name})`);
                            window.Ok(classid,link_obj)
                            found = true;
                        }
                    }

                    if (!found) {
                        var err = `student query failed:${input}`;
                        console.log(err);
                        Fail(err,link_obj);
                    }

                },
                error(err) {
                    var err = `request student query failed.`;
                    console.log(err);
                    window.Fail(err,link_obj);
                }
            })
        }

        var m2 = (input, link_obj) => {
            $.ajax({
                url: "school/class.json",
                dataType:"json",
                success:function(data) {
                    let found = false;
                    for (var key in data) {
                        if (data[key].id == input) {

                            var techerid=data[key].techerid;
                            var name=data[key].name;
                            console.log(`class(id:${input},techerid:${techerid},name=${name})`);
                            window.Ok(techerid,link_obj)
                            found = true;
                        }
                    }

                    if (!found) {
                        var err = `class query failed:${input}`;
                        console.log(err);
                        Fail(err,link_obj);
                    }

                },
                error(err) {
                    var err = `request class query failed.`;
                    console.log(err);
                    window.Fail(err,link_obj);
                }
            })
        }

        var m3 = (input, link_obj) => {
            $.ajax({
                url: "school/techer.json",
                dataType:"json",
                success:function(data) {
                    let found = false;
                    for (var key in data) {
                        if (data[key].id == input) {

                            var name=data[key].name;
                            console.log(`techer(id:${input},name=${name})`);
                            window.Ok(input,link_obj)
                            found = true;
                        }
                    }

                    if (!found) {
                        var err = `techer query failed:${input}`;
                        console.log(err);
                        Fail(err,link_obj);
                    }

                },
                error(err) {
                    var err = `request techer query failed.`;
                    console.log(err);
                    window.Fail(err,link_obj);
                }
            })
        }


        
        var m = Link.init(m1, 1).option(m2).option(m3).run();        
        var m2 = Link.init(m1, 2).option(m2).option(m3).run();        
        var m3 = Link.init(m1, 3    ).option(m2).option(m3).run();        
        var m4 = Link.init(m1, 4    ).option(m2).option(m3).run();        
        //var m2 = Link.init(m1, "5").option(m2).option(m3).run();

    </script>
</body>

</html>

打开浏览器控制台,出现以下输出:

option.html:73 student(id:1,classid:1,name=张三)
option.html:81 student query failed:2
option.html:81 student query failed:3
option.html:81 student query failed:4
option.html:105 class(id:1,techerid:1,name=初一班)
option.html:136 techer(id:1,name=张老师)