精华内容
下载资源
问答
  • Web前端黑客技术揭秘

    2018-06-13 16:17:31
    本书适合前端工程师阅读,同时也适合对Web前端各类安全问题或黑客攻防过程充满好奇的读者阅读,书中的内容可以让读者重新认识到Web的危险,并知道该如何去保护自己以免受黑客的攻击。 作者简介 · · · · · · ...
  • web前端面试之vue

    2020-08-18 16:20:43
    vue-router如何做用户登录权限等? axios取消请求 vuex原理 mvc与mvvm mvc View:视图层 ui界面 controller:控制器 接受并处理用户请求通知Model改变,并将Model返回给 View Model:模型 数据 MVVM分为..

    目录

    mvc与mvvm

    vue生命周期

    vue 的双向绑定的原理是什么 

    vue组件通信

    vue服务器渲染

    vue性能优化

    ue-router 有哪几种导航钩子?

    vue-router如何做历史返回提示?

    vue-router如何做用户登录权限等?

    axios取消请求

    vuex原理


    mvc与mvvm

    mvc

    • View:视图层 ui界面
    • controller:控制器 接受并处理用户请求通知Model改变,并将Model返回给 View
    • Model:模型 数据

     

    MVVM分为Model、View、ViewModel三者。

    • Model:代表数据模型,数据和业务逻辑都在Model层中定义;
    • View:代表UI视图,负责数据的展示;
    • ViewModel:就是与界面(view)对应的Model,ViewModel的职责就是把model对象封装成可以显示和接受输入的界面数据对象。

    Model和ViewModel之间有着双向数据绑定的联系。因此当Model中的数据改变时会触发View层的刷新,View中由于用户交互操作而改变的数据也会在Model中同步。

    简单的说,ViewModel就是View与Model的连接器,View与Model通过ViewModel实现双向绑定。

    MVVM与MVC最大的区别就是:

    它实现了View和Model的自动同步,也就是当Model的属性改变时,我们不用再自己手动操作Dom元素,来改变View的显示,而是改变属性后该属性对应View层显示会自动改变

    vue生命周期

    加载渲染过程 父 beforeCreate -> 父 created -> 父 beforeMount ->
    子 beforeCreate -> 子 created -> 子 beforeMount -> 子 mounted -> 父 mounted 子组件更新过程
    父 beforeUpdate -> 子 beforeUpdate -> 子 updated -> 父 updated

    父组件更新过程
    父 beforeUpdate -> 父 updated

    销毁过程
    父 beforeDestroy -> 子 beforeDestroy -> 子 destroyed -> 父 destroyed

    vue 的双向绑定的原理是什么 

    vue.js 是采用数据劫持结合发布者-订阅者模式的方式,通过 Object.defineProperty()来劫持各个属性的 setter,getter, 在数据变动时发布消息给订阅者,触发相应的监听回调。

    具体步骤:

    第一步:需要 observe 的数据对象进行递归遍历,包括子属性对象的属性,都加上 setter 和 getter 这样的话, 给这个对象的某个值赋值,就会触发 setter,那么就能监听到了数据变化

    第二步:compile 解析模板指令,
    将模板中的变量替换成数据,然后初始化渲染页面视图,并将每个指令对应的节点绑定更新函数,添加监听数据的订阅者,
    一旦数据有变动,收到通知,更新视图

    第三步:Watcher 订阅者是 Observer 和 Compile 之间通信的桥梁,主要做的事情是:在自身实例化时往属性订阅器(dep)里面
    添加自己自身必须有一个 update()方法待属性变动 dep.notice()通知时,能调用自身的 update() 方法,并触发 Compile 中绑定的回调,则功成身退。

    第四步:MVVM 作为数据绑定的入口,整合 Observer、Compile 和 Watcher 三者,通过 Observer 来监听自己的 model 数据变化,通过 Compile 来解析编译模板指令,最终利用 Watcher 搭起 Observer 和 Compile 之间的通信桥梁,达到数据变化 -> 视图更新;视图交互变化(input) -> 数据 model 变更的双向绑定效果。

    vue组件通信

    父组件向子组件传值

    父组件通过props向下传递数据给子组件。注:组件中的数据共有三种形式:data、props、computed

    子组件向父组件传值(通过事件形式)

    子组件通过events给父组件发送消息,实际上就是子组件把自己的数据发送到父组件。($emit)

    常见使用场景可以分为三类:

     

    • 父子通信:

    父向子传递数据是通过 props,子向父是通过 events($emit);通过父链 / 子链也可以通信($parent / $children);ref 也可以访问组件实例;provide / inject API;$attrs/$listeners

    • 兄弟通信:

    Bus;Vuex

    • 跨级通信:

    Bus;Vuex;provide / inject API、$attrs/$listeners

    vue服务器渲染

     

    vue性能优化

    ue-router 有哪几种导航钩子?

    三种全局导航钩子:

    • router.beforeEach(to, from, next),
    • router.beforeResolve(to, from, next),
    • router.afterEach(to, from ,next)

    组件内钩子

    • beforeRouteEnter,
    • beforeRouteUpdate,
    • beforeRouteLeave

    单独路由独享组件

    • beforeEnter

    vue-router如何做历史返回提示?

    vue-router如何做用户登录权限等?

    axios取消请求

    原理 将正在请求的ajax放入一个数组中 名称为url+请求方式+参数字符串=>[{ajaxName:'http://crm/login&post',fun:xxx}]
    在请求的时候先去这个数组中找是否有这个ajax,如果有就调用这个ajax的fun函数,取消了上一次请求,如果没有就 在这个数组中添加上这个ajax,结束的时候将这个ajax从数组中清除了

    vuex原理

    Vuex实现了一个单向数据流,在全局拥有一个State存放数据,当组件要更改State中的数据时,必须通过Mutation进行,Mutation同时提供了订阅者模式供外部插件调用获取State数据的更新。而当所有异步操作(常见于调用后端接口异步获取更新数据)或批量的同步操作需要走Action,但Action也是无法直接修改State的,还是需要通过Mutation来修改State的数据。最后,根据State的变化,渲染到视图上

    展开全文
  • 不需要关心它如何存取文件、如何进行权限控制,所以对象存储对前端工程师来说是 Serverless。甚至一些第三方的 API 服务,也是 Serverless,因为我们使用的时候,不需要去关心服务器。 当然...
  • 第(5)节与第(6)节仔细研究了eladmin对于后端与前端权限控制机制,本节主要讨论如何在系统中进行异常控制,一般都是根据源码来寻找答案,仔细研究eladmin的官网对于异常处理的说明后,我们首先来看盾异常实体...

    第(5)节与第(6)节仔细研究了eladmin对于后端与前端的权限控制,本节主要讨论如何在系统中进行异常控制。

    1. 后端异常定义

    我们还是根据源码来寻找答案,仔细研究eladmin的官网对于异常处理的说明后,我们首先来看后端异常实体类ApiError
    在这里插入图片描述
    这个实体中主要封装三个信息

    • 状态status,默认是400;
    • timestamp,默认是当前的时间;
    • String类型的message。
      然后再看看通用异常BadRequestException的定义
      在这里插入图片描述
      由上图可知,BadRequestException封装了status与message,message需要传入,status默认是BAD_REQUEST,我们在IDEA中按住ctrl键点击可以看到
      在这里插入图片描述
      默认BAD_REQUEST的值为400。
      官方给了两个自定义异常的实例,我们来看其中一个,EntityNotFoundException,看到名子就知道这是一个实体不存在异常,看看它的结构
      在这里插入图片描述
      这个异常类很简单,传入对象对应class类(其实主要就是获取类的名子,看箭头指示),再传入这个类的字段名,再传入字段中该类的值,然后输出消息"这个类的field字段值 val 不存在"。我们来举一个例子吧!

    2. 后端已有异常类测试

    首先在后端找到我们之前创建的“我的岗位管理”的gen模块,不清楚怎么利用代码生成器自动创建gen模块的请回看第(2)节与第(3)节的内容,打开MyJob这个类
    在这里插入图片描述
    我们发现有name字段属性,于是我们用EntityNotFoundException做一个测试,打开eladmin-system模块下的测试类EladminSystemApplicationTests,这部分代码,eladmin已经自动为我们配置好了,我们利用@Test测试方法抛出一个异常,如图:
    在这里插入图片描述
    利用junit运行该函数contextLoads,可以得到如下结果
    在这里插入图片描述
    使用就是这么简单。这里重点注意两个注解的使用
    在这里插入图片描述
    这两个注解保证在junit运行时会自动加载系统的上下文,这样EladminSystemApplicationTests才能识别出MyJob这个类,以后我们自己写系统的测试类时,一定要加上这两个注解。
    官方还提供了一些默认的异常类(如下图),大家可以按照上面的方法自己测一下。
    在这里插入图片描述

    3. 后端全局异常拦截

    参照官网,全局异常拦截定义在GlobalExceptionHandler中
    在这里插入图片描述
    这里一定要记住这两个关键注解:

    • @RestControllerAdvice:默认会扫描指定包中所有@RequestMapping注解
    • @ExceptionHandler:通过@ExceptionHandler的 value 属性可过滤拦截的条件,即按照抛出异常的类型分别进行处理
      我们来做两个例子走一下全部的流程,深刻理解一下。

    3.1 测试EntityNotFoundException

    首先在进入“我的岗位管理”界面查询所有岗位时,抛出异常
    在这里插入图片描述
    在全局异常拦截类中GlobalExceptionHandler对EntityNotFoundException相应的方法entityNotFoundException设置断点
    在这里插入图片描述
    运行程序,进入“我的岗位管理界面”,如下图
    在这里插入图片描述
    这会触发查询所有岗位的函数,于是会抛出EntityNotFoundException,可以看到
    在这里插入图片描述
    成功拦截到我们定义的EntityNotFoundException。

    3.2 测试 MethodArgumentNotValidException

    我们故意在Myjob类对于创建时间的字段中加上@NotNull,如下图
    在这里插入图片描述
    然后重启后端,在”我的岗位管理“新增界面中,故意在创建日期中不进行填写
    在这里插入图片描述
    在GlobalExceptionHandler中的 handleMethodArgumentNotValidException方法中加断点,运行过程中可以看到全局拦截器拦截到了MethodArgumentNotValidException
    在这里插入图片描述

    4. 前端异常拦载

    官网,前端的异常拦载都在src/utils/request.js中

    // response 拦截器
    service.interceptors.response.use(
      response => {
        const code = response.status
        if (code < 200 || code > 300) {         
          Notification.error({
            title: response.message
          })
          return Promise.reject('error')
        } else {
          return response.data
        }
      },
      error => {
        let code = 0
        try {
          code = error.response.data.status
        } catch (e) {
          if (error.toString().indexOf('Error: timeout') !== -1) {
            Notification.error({
              title: '网络请求超时',
              duration: 5000
            })
            return Promise.reject(error)
          }
        }
        if (code) {
          if (code === 401) {
            store.dispatch('LogOut').then(() => {
              // 用户登录界面提示
              Cookies.set('point', 401)
              location.reload()
            })
          } else if (code === 403) {
            router.push({ path: '/401' })
          } else {
            const errorMsg = error.response.data.message
            if (errorMsg !== undefined) {
              Notification.error({
                title: errorMsg,
                duration: 5000
              })
            }
          }
        } else {
          Notification.error({
            title: '接口请求失败',
            duration: 5000
          })
        }
        return Promise.reject(error)
      }
    )
    

    看这段源代码很好理解,就是这样的逻辑:

    1. 如果 code < 200 || code > 300 输出错误error
    2. 如果输出error,code = error.response.data.status:
      3. 如果code存在 且 code === 401: 让重新登录
      4. 如果code存在 且 code === 403: 跳转到"/401"对应的界面
      5. 如果code存在 code为其他数值:界面以通知的形式输出erro中的message
      6. 如果code不存在,界面以通知的形式输出“接口请求失败”

    参照上述流程,我们做两个例子,一个让界面以通知的形式输出我们定义的错误消息,一个让界面跳转到指定页,这两个都是我们常用的。

    3.1 界面输出错误消息

    按照2.1定义异常EntityNotFoundException,在进入“我的岗位管理时”,抛出EntityNotFoundException异常,观察GlobalExceptionHandler拦截器中对于该异常的处理
    在这里插入图片描述
    按照1ApiError的定义,我们已经知道ApiError中code默认为400,按照上述前端异常处理的逻辑,如果code=400会以通知的形式输出我们定义的message,如下图
    在这里插入图片描述

    3.2 错误跳转页面

    还是按照2.1定义异常EntityNotFoundException,我们直接去修改GlobalExceptionHandler拦截器中对应该异常的处理方法entityNotFoundException,让其code为403
    在这里插入图片描述
    再次重启后端,进入“我们岗位管理”页面时,触发异常,可以看到这时就跳转到了eladmin定义的异常页面了,如下图:
    在这里插入图片描述
    当然你可以定义自己的异常处理页面,通过参看前面路由,我们知道”/401“路径对应的页面是:
    在这里插入图片描述
    你完全可以自定义一个异常处理界面替换@/views/features/401,或者重新定义一个路由指向别的页面。

    4 总结

    本节主要讲解了eladmin中关于前后端异常处理的机制,其实非常简单,就是spring-boot中一些基本的异常处理方法,我们完全可以直接复用eladmin的代码,如果做项目时对异常处理不熟或记得不全,完全可以回去看看eladmin源代码中异常处理的内容,如果还不懂,记得回来看我的博客,算是讲得非常清楚了。如果看了本节觉得有收获记得给我点赞,你们的支持是我更新的动力。下节还有更重要的内容,请继续关注。

    展开全文
  • 如何从零开始,使用Springboot开发项目 开发前的一些准备工作,以及思考项目整体结构与思路 记录开发过程中遇到的一些难题以及bug 总结目前博客网站的一些优缺点 思考整个项目有哪些可以优化的地方,以及有哪些可...
  • 2.如何控制权限? 在 Access 表配置校验规则,默认不允许访问,需要对 每张表、每种角色、每种操作 做相应的配置,粒度细分到行级 https://github.com/Tencent/APIJSON/issues/12 3.如何校验参数? 在 Request 表...
  • 进行负责的业务/数据接口,前端负责展现/交互逻辑,前逐步开发对于同时份数数据接口,我们可以自定义开发多个客户端,可以选择web和app就可以使用同一个接口,多个前端展示。 2,如何实现前阶段分离 简单来说,前端...
  • dev_modules分支采用rpc架构,html在simplenote-web里面,适合学习spring如何构建html.dev_modules不再作为开发分支。 已dev_1.1为主,专注服务端接口。 前端页面见: 目标: 做一个发日志,问答的小网站 可以基于...
  • 前端包含最佳实践,用于构建出色的Web应用程序。 登录,注册,注销和检查身份验证流程(管理员可以为目标用户断开会话)。 内部化。 您的客户将感谢您的关注。 现在征服不同的市场。 用于请求/响应的通用错误...
  • 日志对一个系统的安全和开发运营的重要性是不言而喻的,本章将为大家带来Web日志的分类和处理方式,首先课程会为大家讲解Yii2框架的日志组件的使用,其次将讲解到如何使用Sentry进行错误日志的收集和开发人员处理...
  • 02 什么是异常处理及异常处理的两种方式对比 03 多分支与万能异常 04 异常处理的其他内容 05 什么时候用异常处理 06 什么是socket 07 套接字发展及分类 08 基于tcp协议的套接字编程 09 socket底层工作原理解释 10 ...
  • 顺便问一下,我用weblint上传文件,前端如何前端选定文件的绝对路径传道一般处理程序 ``` string title = context.Request.Form["title"]; HttpPostedFile upFile = HttpContext.Current.Request.Files[...
  • mall-admin-web项目的安装及部署请参考:mall前端项目的安装与部署。 Docker环境部署 使用虚拟机安装CentOS7.6请参考:虚拟机安装及使用Linux,看这一篇就够了; Docker环境的安装请参考:开发者必备Docker命令; ...

空空如也

空空如也

1 2 3 4
收藏数 62
精华内容 24
关键字:

web前端如何处理权限