每日一题(js)

142 阅读3分钟

函数合成,从右到左合成函数

var compose = function () {
    var _arguments = arguments;  //缓存外层函数
    var length = _arguments.length;  //缓存长度
    var index = length;  //定义游标变量
    //检测函数,如果存在非函数参数,则抛出异常
    while (index --) {
        if (typeof _arguments[index] !== 'function') {
            throw new TypeError('参数必须为函数!');
        }
    }
    return function () {
        var index = length - 1;  //定位到最后一个参数下标
        //如果存在两个及以上参数,则调用最后一个参数函数,并传入内层函数;否则直接返回第 1 个参数函数。
        var result = length ? _arguments[index].apply(thisarguments) : arguments[0];
        //迭代参数函数
        while (index -- ) {
            //把右侧函数的执行结果作为参数传给左侧参数函数,并调用。
            result = _arguments[index](result);
           console.logthis)
        }
        return result;  //返回最左侧参数函数的执行结果
    }
}

var add = function (x) { return x + 5; } //加法允许

var mul= function (x) { return x * 5; } //乘法运算

var sub= function (x) { return x - 5; } //减法运算

var div = function (x) { return x / 5; } //除法运算

var fn = compose(compose(add, mul), sub, div);

//请问此时输出什么
console.log(fn(50))

说说什么是单点登录?如何实现?

什么是?

单点登录就是Single sign on,简称SSO,就是用户在一个应用中登录之后,其他受信任的相关应用也都能登录,举个例子,淘宝跟天猫是一家公司的不同部门开发的应用,我在淘宝登录后,我会发现天猫也随机登录了,这就是单点登录。

如何实现?

首先我们要明确:

  • cookie是不能跨域的
  • 每个网站对应的session也是不同的 所以针对这些情况,我们有两种场景需要面对:
  1. 同一个域名
    此时针对不同的域名,比如a.test.com,b.test.com。理论上来说,我们都会有一个登录界面login.test.com(没有也没有关系)。此时我们在login.test.com登录的时候,我们可以设置cookie的域为顶域,即test.com。这样就避免了跨域的问题,而对于session,我们可以做一个统一的common session(Spring Session等方案)
  2. 同一个域名
    对于不同的域名,我们有两种方法:
  • cookie应用间重定向
    如图

image.png
我们可以在一个域名下登录之后,不断用cookie向服务器重定向发送其他域名cookie的请求。但是这种方法在面对到比较多的域名的时候,将会非常耗时和消耗性能,建议站点较少时候使用。

  • 建立sso系统
    流程如下:
  1. 用户访问当前域名,此时是需要登录的,但用户现在没有登录。
  2. 跳转到CAS server,即SSO登录系统,SSO系统也没有登录,弹出用户登录页。
  3. 用户填写用户名、密码,SSO系统进行认证后,将登录状态写入SSO的session,浏览器(Browser)中写入SSO域下的Cookie。
  4. SSO系统登录完成后会生成一个ST(Service Ticket),然后跳转到app系统,同时将ST作为参数传递给当前域名。
  5. 当前域名拿到ST后,从后台向SSO发送请求,验证ST是否有效。
  6. 验证通过后,当前域名将登录状态写入session并设置当前域下的Cookie。 此时,如果有新的域名需要登录。就会走如下流程:
  7. 用户访问新的域名,此时是需要登录的,于是跳转到SSO。
  8. 此时SSO系统已经登录,生成一个ST,然后跳转到新的,同时将ST作为参数传递给新的域名。
  9. 新的域名拿到ST后,从后台向SSO发送请求,验证ST是否有效。
  10. 验证通过后,新的域名将登录状态写入session并设置新的域下的Cookie。

为什么还要发ST来验证,直接登录不好嘛?因为存在坏人,如果SSO并没有登录,而对方伪造了一个用户信息,发送到服务器,此时也会判断为登录,则就会造成账号的被盗