Egg.js中Cookie和Session

Cookie

HTTP请求是无状态的,但是在开发时,有些情况是需要知道请求的人是谁的。为了解决这个问题,HTTP协议设计了一个特殊的请求头:Cookie。服务端可以通过响应头(set-cookie)将少量数据响应给客户端,浏览器会遵循协议将数据保留,并在下一次请求同一个服务的时候带上。

// html中插入DOM和JS方法
<div>
    <button onclick="add()">增加Cookie</button>
    <button onclick="del()">删除Cookie</button>
    <button onclick="editor()">修改Cookie</button>
    <button onclick="show()">查看Cookie</button>
</div>
<script>
    function add(){
        fetch("/add",{
            method:"post",
            headers:{
                "Content-type":"application/json"
            }
        });
    }
    function del(){
        fetch("/del",{
            method:"post",
            headers:{
                "Content-type":"application/json"
            }
        });
    }
    function editor(){
        fetch("/editor",{
            method:"post",
            headers:{
                "Content-type":"application/json"
            }
        });
    }
    function show(){
        fetch("/show",{
            method:"post",
            headers:{
                "Content-type":"application/json"
            }
        });
    }
</script>
async add() {
  const ctx = this.ctx
  ctx.cookies.set("user", "jspang.com")
  ctx.body = {
    status:200,
    data:'Cookie添加成功'
  }
}
async del() {
  const ctx = this.ctx
  ctx.cookies.set("user", null)
  ctx.body = {
    status:200,
    data:'Cookie删除成功'
  }
}
async editor() {
  const ctx = this.ctx
  ctx.cookies.set("user",'bilibili')
  ctx.body = {
    status:200,
    data:'Cookie修改成功'
  }
}
async show() {
  const ctx = this.ctx
  const user=ctx.cookies.get("user")
  console.log(user)
  ctx.body = {
    status:200,
    data:'Cookie显示成功'
  }
}

// 配置路由
router.post('/add', controller.zhuba.add);
router.post('/del', controller.zhuba.del);
router.post('/editor', controller.zhuba.editor);
router.post('/show', controller.zhuba.show);

Egg.js中Cookie和Session_第1张图片

image.png

配置和加密

一些配置选项,比如有效时间、服务端操作设置和中文编写加密这些操作。
ctx.cookies.set( ) 方法是有三个参数的,第一个参数是key,第二个参数是value,第三个参数就可以进行配置。比如你需要配置Cookie的有效时间,可以使用maxAge属性。(这个时间是毫秒。)

maxAge 时效设置

maxAge: 1000 * 2 (毫秒)

async add(){
  const ctx = this.ctx
  ctx.cookies.set("user","jspang.com",{
    maxAge:1000*2
  })
  ctx.body = {
    status:200,
    data:'Cookie添加成功'
  }
}
HhttpOnly 是否只允许服务端来操作Cookie

伪造Cookie来绕过登录是黑客经常使用的一种手段,所以为了安全,Egg.js默认设置只允许服务端来操作Cookie。
比如通过JS的方式document.cookie获取Cookie是不能获取的(需要在浏览器的控制台输入获取)。当我们想通过客户端操作Cookie时,可以通过下面的代码进行设置。

async add(){
  const ctx = this.ctx
  ctx.cookies.set("user","jspang.com",{
    maxAge:1000*60,
    httpOnly:false
  })
  ctx.body = {
    status:200,
    data:'Cookie添加成功'
  }
}
encrypt 设置中文Cookie (set加密 show解密)

加密只要在第三个参数中,加入encrypt:true,就可以加密成功。

ctx.cookies.set("user","zhuba",{
  encrypt:true
})

直接通过ctx.cookies.get( )方法获取,获取的是undefind,也就是无法获取的。这时候需要再次配置解密才可以使用, 在show( )方法里配置代码如下。

const user=ctx.cookies.get("user",{
  encrypt:true
})

Session

Cookie和Session非常类似,Egg中的Session就存储再Cookie中,但是Session比Cookie的安全性更高。所以在开发中经常使用Cookie来保存是否登录,而用Session来保存登录信息和用户信息。

添加、获取、删除

  • 添加:在add()方法中 ctx.session.username = ‘zhuba’
  • 获取:直接获取 const username = ctx.session.username
  • 删除:把值赋为空即可 ctx.session.username = null

session是支持中文的,不需要加密解密

配置项

config.session = {
    key :"PANG_SESS",   // 设置Key的默认值
    httpOnly:true,      // 设置服务端操作
    maxAge:1000*60  ,   // 设置最大有效时间
    renew: true,        // 页面有访问动作自动刷新session 
}

中间件的编写

Egg是对Koa的二次封装,所以中间件这部分和Koa框架是一样的,也追寻洋葱圈模型。

Egg.js约定中间件要写在/app/middleware文件夹下

module.exports = options => {
  return async (ctx, next) => {
    if (ctx.session.counter) { // 没学数据库先使用session
      ctx.session.counter++;
    } else {
      ctx.session.counter = 1;
    }
    await next();
  }
};

手动挂载:config/config.default.js config.middleware = [‘counter’];

在index()中使用, 可以发现中间件现在的作用域是全局的。

Egg.js中Cookie和Session_第2张图片

要想只在某一页面使用需要在router(路由)中配置中间件的使用,并去除全局挂载。

const counter = app.middleware.counter()
  const {
    router,
    controller,
  } = app;
  router.get('/', counter, controller.home.index);

在实际开发中中间件还是有很多用处的,比如日志的记录、比如所有页面的Gzip压缩展示、比如全局埋点的使用

你可能感兴趣的:(javascript,前端,开发语言)