6-2 接口的设计优劣
本节编程练习不计算学习进度,请电脑登录imooc.com操作

接口的设计优劣

从设计的层面上来考下,这种事件组合的方式是如何实现?有什么优势?

  1. Ajax 的参数回调
  2. 基于 deferred 方式的 done 回调
  3. 全局的自定义事件的回调

设计一:

tAjax({
    url: "php.html",
    complete: function(data) {
        console.log(data)
    }
})

如果要实现这种接口调用那么我们就需要封装下代码,把回调通过实参传递。

var tAjax = function(config) {
 //参考右图设计一
}

这样设计可以看做类似工厂模式的封装,好处不用多说在工厂模式里面包含了对象的创建等必要的逻辑,客户端根据传参选择动态的实例化相对的处理,对于客户端来去除了具体的依赖,当然 tAjax 你也可以看作一个外观模式提供的接口,其实就是隐藏了具体的复杂逻辑,提供一个简单的接口,从而降低耦合。


设计二:

tAjax({
    url: "php.html",
    complete: function(data) {
        console.log(data)
    }
}).done(function(data){
    console.log(data)
})

在之前加入了一个 done 链式处理,当然这里 done,其实是 deferred 的一个成功处理通知,如果之前没有接触,大家去了解一下关于 deferred 的概念,我们知道 jQuery 实现了链式,实现的原理无法就是返回本身对象的引用。

var ajax = tAjax({
    url: "php.html",
    complete: function(data) {
        console.log(data)
    }
})
ajax.done(function(){
    //.........
})

以上是分离的情况下,如果要合并成一条链式处理,只要在上一个方法中返回 this 即可。

var tAjax = function(config) {
   ///参考右图设计二
    return {
        done: function(ourfn) {
             doneFn = ourfn;
        }
    }
}

我们返回了一个 done 对象,这里一样要是对象,因为链式的原因我们看外部指定了内部的 done,从而把外部函数给引用到内部的 doneFn 上缓存起来 xhr.staturs 成功后一起执行,当然这种设计是有问题的,如果在 done 之后我再链式就肯定不行,因为对象的引用错了,那么 jQuery 是如何处理?

 

设计三:提供 document 对象的全局处理

$(document).ajaxComplete(function() {
    console.log('ajax请求成功')
})
tAjax({
    url: "php.html",
    complete: function(data) {
         console.log(data)
    }
}).done(function(data){
    console.log(data)
})

任务

  1. <!doctype html>
  2. <html>
  3. <head>
  4. <meta http-equiv="Content-type" content="text/html; charset=utf-8"/>
  5. <title>接口设计的优劣</title>
  6. </head>
  7. <body>
  8.  
  9.  
  10. <script type="text/javascript">
  11.  
  12. //伪代码,仅做参考
  13.  
  14. //设计一
  15. var tAjax1 = function(config) {
  16. var url = config.url;
  17. var complete = config.complete;
  18. var xhr = window.XMLHttpRequest ? new XMLHttpRequest() : new ActiveXObject('Microsoft.XMLHTTP');
  19. xhr.open('post', url);
  20. xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
  21. xhr.onreadystatechange = function() {
  22. if (xhr.readyState == 4) {
  23. if (xhr.status == 200) {
  24. complete(xhr.responseText);
  25. }
  26. }
  27. }
  28. xhr.send();
  29. }
  30.  
  31.  
  32. //设计二
  33. var tAjax2 = function(config) {
  34. var doneFn;
  35.  
  36. var url = config.url;
  37. var complete = config.complete;
  38. var xhr = window.XMLHttpRequest ? new XMLHttpRequest() : new ActiveXObject('Microsoft.XMLHTTP');
  39. xhr.open('post', url);
  40. xhr.setRequestHeader('Content-Type', 'application/x-www-form-urlencoded');
  41. xhr.onreadystatechange = function() {
  42. if (xhr.readyState == 4) {
  43. if (xhr.status == 200) {
  44. doneFn(xhr.responseText);
  45. complete(xhr.responseText);
  46. }
  47. }
  48. }
  49.  
  50. xhr.send(xhr.responseText);
  51.  
  52. return {
  53. /**
  54. * 返回一个done对象
  55. */
  56. done: function(ourfn) {
  57. doneFn = ourfn;
  58. }
  59. };
  60. }
  61.  
  62.  
  63. </script>
  64. </body>
  65. </html>
下一节