1. 服务器端渲染(ssr:service side render)
优点:
- 解决白屏问题,提高首屏渲染速度
- 可以直接渲染页面,利于seo优化
主要技术:
通过react提供的renderToString方法,接受一个react组件,返回一段html结构字符串
renderToString:渲染时带data-reacId,这样会增增加流量,但是在客户端对比就会重新渲染
re7ynderToStaticMarkUp:渲染时不带data-raectId,节省流量,但是在客户端重新渲染时会出现闪屏
https://yq.aliyun.com/articles/641674
https://www.cnblogs.com/Coding-net/p/5024756.html
2. react-redux实现原理
- redux作为一个通用模块,主要用来处理应用中state的变更,通过react-redux做连接
- react-redux两个核心方法
provider: 在最外层封装了整个应用,并向connect模块传递store
connect: 1. 监听原组件,将state和action通过props的方式擦混入到原组件内部。2. 监听store tree变化,使其包装的原组建可以响应state变化
3. react 高阶组件
- 属性代理:通过被包裹的react组件来操作props
- 反向继承: 高阶组件继承于被包裹的react组件
- 组合多个高阶组件可以使用compose(xxx,xxx)
高阶组件使用方法详解:
https://segmentfault.com/a/1190000010371752
https://www.jianshu.com/p/68c6ab7c35dc
4. router4 withRouter
withRouter其实就是为了获取location,history, maatch 这些参数,其本质上就是一个高阶组件,提供一个context
本文参考:https://segmentfault.com/a/1190000017140200
webpack 参考资料https://www.jianshu.com/p/c395ec989abd
4. 面向对象
面向对象的两大概念:类和实例
类:对象的类型模板
实例: 根据类创建的对象
虽然js没有类的概念,但是它使用构造函数(constructor)作为对象的模板
new 创建一个对象都进行了哪些操作
- 创建一个空对象,用this变量引用该对象并继承该函数的原型
- 属性和方法加入到this的引用对象中
- 新创建的对象由this所引用,最后隐式的返回this
function newObj(fun,argument){
var obj = {};
if(fun && typeof fun === 'function'){
o.__proto__ == fun.prototype;
fun.apply(o,argument);
return o;
}
}
如果构造函数内部由return语句,且return后面跟着一个对象,new 命令返回retrun 指定的对象,否则直接返回this
5. 原型链
imageproto和prototype区别
- proto是普通对象的隐式属性,在new的时候,会指向prototype所指的对象
-
proto实际上是某个实体对象的属性,而prototype则是属于构造函数的属性
简而言之
- 构造函数通过prototype属性访问原型对象
- 实例对象通过[[prototype]]内部属性访问原型对象,浏览器实现了proto属性用于实例对象访问原型对象
- object为构造函数的时候,是function的实例对象;function为构造函数时,function.prototype是对象,那么它就是object的实例对象
5. 元素居中
1.文本居中:text-align:center
- 图片居中:父级:text-align:center
- 块级元素居中:margin-left:auto;margin-right:auto
- 单行文本竖直居中,让height和line-height相等(如果不确定高度,可以用padding)
6. vue双向绑定
通过数据劫持结合发布者-订阅者模式来实现的,vue通过object.defineProperty()来实现数据劫持
https://www.cnblogs.com/libin-1/p/6893712.html
7. web攻击正怎么防御
- xss(跨站脚本攻击):例如在表单中提交含有可执行的javascript的内容文本,如果服务器端没有过滤或转义这些脚本,而这些脚本由通过内容的形式发布到了页面上,这个时候如果有其他用户访问这个网页,那么浏览器就会执行这些脚本,从而被攻击,从而获取用户的cookie等信息
防御
对于敏感的cookie信息,使用HttpOnly,使document对象找不到cookie
对于用户输入的信息进行转义
- CSRF(跨站点请求伪造):CSRF攻击者在用户已经登录目标网站之后,诱使用户访问一个攻击页面,利用目标网站对用户的信任,以用户身份在攻击页面对目标网站发起伪造用户操作的请求,达到攻击目的。
防御
- 敏感信息使用验证码
- 验证http referer字段(referer字段会记录http请求的来源地址)
- 在请求地址中添加token验证(更多的是生成一个随机的token,在用户提交数据的同时提交这个token,服务器端比对后如果不正确,则拒绝执行操作。在用户登录之后,产生token 并放入session中,在每次请求时把token从session中拿出来,以参数的形式加入请求,在服务器端建立拦截器验证该token,token则通过,否则拒绝。但是这种方法也是有安全问题的,在某些网站支持用户发表链接的,那么黑客在该网站发布自己的个人网站地址,系统也会为这个地址后加上token,则黑客可以在自己的网站上得到这个token参数,从而发动CSRF攻击)
- 在http头中自定义token属性并验证(把token作为自定义属性放在HTTP的头中,通过封装XMLHttpRequest可以一次性给所有请求加上token 属性。这样子token就不会暴露在浏览器地址中。)
3.SQL注入:攻击者在提交表单的时候,在表单上面填写相关的sql语句,而系统把这些字段当成普通的变量发送给服务器端进行sql查询,则,由攻击者填写的sql会拼接在系统的sql语句上,从而进行数据库的某些操作。
防御 - 表单过滤,验证表单提交的合法性,对一些特殊字符进行转义处理
- 数据库权限最小化
- 查询语句使用数据库提供的参数化查询接口,不要直接拼接SQL
https://blog.csdn.net/qq_27855219/article/details/88796366
8. flex布局
flex(flexible box)其中心思想是给予容器控制内部元素高度和宽度的能力
https://www.cnblogs.com/nuannuan7362/p/5823381.html
- 利弊
布局更加精简,直接用css的方式,你不用再引入bootstraop,使用栅格系统。
瑕疵就是,IE10及IE10以上才支持,所以目前主要应用在移动端上。
flex默认存在两根轴:水平的主轴和垂直的交叉轴
flex项目默认沿主轴排列
在设置了flex布局之后子元素的float,clear, vertical-align都失效
grid:网格容器(display:grid)
9. 原型和原型链以及构造函数的关联
- js中所有函数都有一个prototype属性,这个属性引用一个对象(fun.prototype),即原型对象,简称为原型
- 所有原型都有constructor属性和proto属性
- constructor属性指向自己的继承父类(即它的构造函数的原型)
- js中一切皆对象,而对象都有一个proto属性,
- object.prototype的proto指向null(最顶级的原型对象),所有原型链的最顶层都是object.prototype
- 注意:A instanceof B 是检查A的原型链上是否存在B.prototype
function是最顶层的构造方法,所有对象都由function方法构造,包括object方法,function 方法
object对象和function方法是相互依赖的
原型链只有在索引值的时候才会用到,如果我们尝试获取对象的某个属性值,但该对象中并没有此属性值,那么js就会在其原型链对象中找,如果还没有,那么会一直在原型链中找,直到object.prototype,如果该对象原型链中没有找到,则返回undefined
9.柯里化函数
柯里化:又称为部分求值,是把接受多个参数的函数变化成一个接受一个单一参数的函数,并且返回一个新的函数的技,新函数接受余下参数并返回运算结果
其实质就是利用闭包的概念
10. 箭头函数不能使用的情况
- 定义字面量方法
const calculator = {
array: [1, 2, 3],
sum: () => {
console.log(this === window); // => true
return this.array.reduce((result, item) => result + item);
}
};
console.log(this === window); // => true
// Throws "TypeError: Cannot read property 'reduce' of undefined"
calculator.sum();
因为运行的时候this.array未定义,在执行calculator.sum()的时候this指向windo,原因是箭头函数把函数上下文绑定到了window上,解决方案:
const calculator = {
array: [1, 2, 3],
sum() {
console.log(this === calculator); // => true
return this.array.reduce((result, item) => result + item);
}
};
calculator.sum(); // => 6
把箭头函数变成普通函数
- 定义原型方法
箭头函数会陶制运行时的执行上下文错误
function Cat(name) {
this.name = name;
}
Cat.prototype.sayCatName = () => {
console.log(this === window); // => true
return this.name;
};
const cat = new Cat('Mew');
cat.sayCatName(); // => undefined
只要变成普通函数之后,被调用时的执行上下文就会指向新创建的cat实例
- 定义事件回调函数
const button = document.getElementById('myButton');
button.addEventListener('click', () => {
console.log(this === window); // => true
this.innerHTML = 'Clicked button';
});
应该修改为
const button = document.getElementById('myButton');
button.addEventListener('click', function() {
console.log(this === button); // => true
this.innerHTML = 'Clicked button';
});
在用户触发点击按钮的时候,事件回调函数中的this实际指向button
- 定义构造函数
因为箭头函数在创建时this对象就绑定了,并不会指向对象实例
const Message = (text) => {
this.text = text;
};
const helloMessage = new Message('Hello World!');
// Throws "TypeError: Message is not a constructor"
11. apply,call,bind
call,apply改变某个函数运行的上下文
call,apply区别就是接受参数的方式不太一样
call(this,arg1,arg2,...) -- call传递的是参数
apply(this,[arg1,arg2,...]) -- apply传递的是数组
bind会创建一个新函数,称为这个绑定函数时,绑定函数会以创建它时传入bind()方法的第一个参数作为this,
网友评论