一、简介

在开发中,属性变量类型的验证,几乎是任何语言都必须关注的问题,因为如果传入的数据类型不对,轻者程序运行仅仅是给出警告⚠️,严重的会直接导致程序中断,APP闪退或者web页面挂掉,这是很严重的bug问题。如我们所知,JavaScript是一种弱类型的语言,这意味着开发者可以随意地修改变量值的数据类型,而且JavaScript虚拟机对此操作并不会产生异议,虽然这种机制大大地提高了编程的灵活性,但是也隐藏了一个极大的crash风险。React组件为此提供了一种声明和验证属性类型的方法,称为自动属性验证机制。这种机制将会大幅度减少调试时间,能够及时把不正确的属性类型触发警告⚠️,以便开发者准确快速的定位bug,然后进行修复。

二、验证器类型

React内置了自动属性验证器,如下所示:

数组类型     React.PropTyps.array

布尔类型     React.PropTyps.bool

函数类型     React.PropTyps.func

数字类型     React.PropTyps.number

对象类型     React.PropTyps.object

字符串类型   React.PropTyps.string

React也支持自定义属性验证器,可以使用typeof字段和“===”进行判断并抛出异常,例如:

布尔类型 (props, propName) => (typeof props[propName] === "boolean") ?  null : new Error(`${propName} is not boolean`)

函数类型 (props, propName) => (typeof props[propName] === "function") ?  null : new Error(`${propName} is not function`)

数字类型 (props, propName) => (typeof props[propName] === "number") ?  null : new Error(`${propName} is not number`)

对象类型 (props, propName) => (typeof props[propName] === "object") ?  null : new Error(`${propName} is not object`)

字符串类型 (props, propName) => (typeof props[propName] === "string") ?  null : new Error(`${propName} is not string`)
字符类类型和长度限制嵌套 (props, propName) => (typeof props[propName] === 'string') ?
((props[propName].length > 5) ? new Error("长度超过5") : null) : new Error(`${propName} is not sring`)

三、验证器声明

React中对属性类型的声明使用了关键字propTypes。对于createClass组件、ES6类组件和无状态函数式组件,它们的声明方式有所区别,如下所示:

createClass组件:

//创建组件
const Component = React.createClass({
//属性验证声明
propTypes: {
title: React.PropTypes.string,
items: React.PropTypes.array
}
   .........  
})

ES6类组件:

//创建组件
class Component extends React.Component{
.........
}
//属性验证声明
Component.propTypes = {
title: React.PropTypes.string,
items: React.PropTypes.array
}

无状态函数式组件:

//创建组件
const Component = ({title,items}) => {
.......
}
//属性验证声明
Component.propTypes = {
title: React.PropTypes.string,
items: React.PropTypes.array
}

四、验证器属性限制

React中,在没有提供属性数据的情况下渲染组件会导致JavaScript报错,从而拖垮整个Web应用。对于这种数据缺少的错误,React属性验证器提供了isRequired字段要求属性数据是必须项,如果不填或者为空,React将会在触发错误之前就在控制台发出警告信息,提醒开发者异常原因。如下:

//创建组件
const Component = React.createClass({
//属性验证声明
propTypes: {
title: React.PropTypes.string.isRequired,
items: React.PropTypes.array.isRequired
}
   .........  
})

五、简单示例

需求: 定一个动物组件,拥有种族类型属性type,动物数组属性kinds,在Web页面上展示type标题和kinds个数。

1、传入正确的数据,动物数组个数显示正常:

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>Hello React</title>
<script src="react/react.js"></script>
<script src="react/react-dom.js"></script>
<script src="react/browser.min.js"></script>
</head>
<body>
<div id="container"></div>
<script type="text/babel"> const AnimalComponent = React.createClass({
render(){
const {type, kinds} = this.props
const divStyle = {
width:400,
height:100,
backgroundColor:"#DAE",
color:"red",
textAlign:"center"
}
return (
<div className="animal" style={divStyle}>
<h1>{type}</h1>
<p>
<span>{kinds.length} kinds animals</span>
</p>
</div>
)
}
}) const kinds = ["cat","dog","pig","Cattle","sheep"]
ReactDOM.render(
<AnimalComponent type="Breastfeeding animation" kinds={kinds} />,
document.getElementById("container")
) </script>
</body>
</html>

2、如果将数组kinds当做字符串传入,Web页面虽然没有挂掉,但是动物数组个数却显示异常,如果开发者检查不仔细,那就是线上的bug了:

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>Hello React</title>
<script src="react/react.js"></script>
<script src="react/react-dom.js"></script>
<script src="react/browser.min.js"></script>
</head>
<body>
<div id="container"></div>
<script type="text/babel"> const AnimalComponent = React.createClass({
render(){
const {type, kinds} = this.props
const divStyle = {
width:400,
height:100,
backgroundColor:"#DAE",
color:"red",
textAlign:"center"
}
return (
<div className="animal" style={divStyle}>
<h1>{type}</h1>
<p>
<span>{kinds.length} kinds animals</span>
</p>
</div>
)
}
}) const kinds = "this is a cat"
ReactDOM.render(
<AnimalComponent type="Breastfeeding animation" kinds={kinds} />,
document.getElementById("container")
) </script>
</body>
</html>

3、如果此时添加属性验证器,再将数组kinds当做字符串传入,Web页面没有挂掉的同时,控制台还会爆出警告,可以及时发现数据问题:

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>Hello React</title>
<script src="react/react.js"></script>
<script src="react/react-dom.js"></script>
<script src="react/browser.min.js"></script>
</head>
<body>
<div id="container"></div>
<script type="text/babel"> const AnimalComponent = React.createClass({ propTypes: {
type: React.PropTypes.string,
kinds: React.PropTypes.array
}, render(){
const {type, kinds} = this.props
const divStyle = {
width:400,
height:100,
backgroundColor:"#DAE",
color:"red",
textAlign:"center"
}
return (
<div className="animal" style={divStyle}>
<h1>{type}</h1>
<p>
<span>{kinds.length} kinds animals</span>
</p>
</div>
)
}
}) const kinds = "this is a cat"
ReactDOM.render(
<AnimalComponent type="Breastfeeding animation" kinds={kinds} />,
document.getElementById("container")
) </script>
</body>
</html>

4、如果此时添加属性验证器的同时,还限制属性是isRequried,那么在渲染组件时,不传递参数,Web页面直接会挂掉成空白页了,当然可以提前设置默认参数避免这种问题:

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>Hello React</title>
<script src="react/react.js"></script>
<script src="react/react-dom.js"></script>
<script src="react/browser.min.js"></script>
</head>
<body>
<div id="container"></div>
<script type="text/babel"> const AnimalComponent = React.createClass({ propTypes: {
type: React.PropTypes.string.isRequired,
kinds: React.PropTypes.array.isRequired
}, render(){
const {type, kinds} = this.props
const divStyle = {
width:400,
height:100,
backgroundColor:"#DAE",
color:"red",
textAlign:"center"
}
return (
<div className="animal" style={divStyle}>
<h1>{type}</h1>
<p>
<span>{kinds.length} kinds animals</span>
</p>
</div>
)
}
}) ReactDOM.render(
<AnimalComponent/>,
document.getElementById("container")
) </script>
</body>
</html>

5、如果此时添加自定义的属性验证器,再将数组kinds当做字符串传入,Web页面没有挂掉的同时,控制台还可以弹出自定义的警告信息:

<!DOCTYPE html>
<html>
<head lang="en">
<meta charset="UTF-8">
<title>Hello React</title>
<script src="react/react.js"></script>
<script src="react/react-dom.js"></script>
<script src="react/browser.min.js"></script>
</head>
<body>
<div id="container"></div>
<script type="text/babel"> const AnimalComponent = React.createClass({ propTypes: {
type: React.PropTypes.string,
kinds: (props, propName) =>
(typeof props[propName] === 'string') ? new Error(`${propName} is not array`) : null
}, render(){
const {type, kinds} = this.props
const divStyle = {
width:400,
height:100,
backgroundColor:"#DAE",
color:"red",
textAlign:"center"
}
return (
<div className="animal" style={divStyle}>
<h1>{type}</h1>
<p>
<span>{kinds.length} kinds animals</span>
</p>
</div>
)
}
}) const kinds = "this is a cat"
ReactDOM.render(
<AnimalComponent type="Breastfeeding animation" kinds={kinds} />,
document.getElementById("container")
) </script>
</body>
</html>

React: React的属性验证机制的更多相关文章

  1. React 学习(二) ---- props验证与默认属性

    在上一节中, 我们提到了props, 组件之间数据的传递使用props. 我们调用组件时可以设置props, 组件内部通过props获取. 为了props 使用更加友好, React 提供了简单的验证 ...

  2. React库protypes属性

    Prop 验证 随着应用不断变大,保证组件被正确使用变得非常有用.为此我们引入propTypes.React.PropTypes 提供很多验证器 (validator) 来验证传入数据的有效性.当向 ...

  3. 【React系列】Props 验证

    Props 验证使用 propTypes,它可以保证我们的应用组件被正确使用,React.PropTypes 提供很多验证器 (validator) 来验证传入数据是否有效.当向 props 传入无效 ...

  4. React组件的防呆机制(propTypes)

    Prop验证 随着应用不断变大,为了保证组件被正确使用变得越来越重要.为此我们引入propsTypes.React.PropTypes提供很多验证器(valodator)来验证传入的数据的有效性.当向 ...

  5. react第九单元(propTypes验证)

    第九单元(propTypes验证) #课程目标 理解类型验证的必要性 灵活掌握类型验证的使用 #知识点 在给react组件传属性的的时候,我们可以定义属性的类型,此时我们需要下载prop-types这 ...

  6. 从零开始学前端,React框架背后的核心机制和原理JSX

    什么是React React是起源于Facebook的一个前端框架,用于构建用户界面的JavaScript库,Facebook用来探索一种更加高效优雅的Javascript MVC框架来架设Insta ...

  7. HTML5 number类型文本框step属性的验证机制——张鑫旭

    我在下一盘很大的棋,本文只是其中的一个棋子. 需要提前知道的: 目前而言,对step雄起的浏览器为IE10+, Chrome以及Opera浏览器. 需要预先知道number类型input的一些基本知识 ...

  8. React Native声明属性和属性确认

    属性声明 因为用React Native创建的自定义组件可以复用, 我们开发过程中可能一个项目组有多个人同时开发,其他同事可能会用到我们自定义的组件, 但是他们使用的时候很容易忘记使用某些属性,这时候 ...

  9. react的三大属性

    react的三大属性 state props  refs props 来自外部属性 states 来自内部状态 refs 用于表示组件内某个元素 state基础(最重要的属性) state是组件对象最 ...

随机推荐

  1. MATLAB实例:新建文件夹,保存.mat文件并保存数据到.txt文件中

    MATLAB实例:新建文件夹,保存.mat文件并保存数据到.txt文件中 作者:凯鲁嘎吉 - 博客园 http://www.cnblogs.com/kailugaji/ 用MATLAB实现:指定路径下 ...

  2. java之类的构造方法

    构造器的特征: 具有和类相同的名称: 不声明返回值的类型: 不能被static.final.synchronized.abstract.native修饰,不能有return语句返回值: 构造器的作用: ...

  3. C++入门到理解之文件操作(文本文件的读写+二进制文件的读写)

    原文地址http://www.javayihao.top/detail/168 一:概述 1.程序在运行中产生的数据都是临时数据,程序一旦运行结束会被释放,可以通过文件相关的操作将数据持久保存. 2. ...

  4. Python三级菜单作业实现

    数据结构: menu = { '北京':{ '海淀':{ '五道口':{ 'soho':{}, '网易':{}, 'google':{} }, '中关村':{ '爱奇艺':{}, '汽车之家':{}, ...

  5. c++.net学习笔记

    Notes for c++ learning 程序根据什么特征来区分调用哪个重载函数? 只能靠参数而不能靠返回值类型的不同来区分重载函数. 编译器根据参数为每个重载函数产生不同的内部标识符 在Visu ...

  6. SpringBoot2.0 整合 JWT 框架,解决Token跨域验证问题

    本文源码:GitHub·点这里 || GitEE·点这里 一.传统Session认证 1.认证过程 1.用户向服务器发送用户名和密码. 2.服务器验证后在当前对话(session)保存相关数据. 3. ...

  7. 干货:.net core实现读取appsettings.json配置文件(建议收藏)

    看好多人不懂在.NET CORE中如何读取配置文件,我这里分两篇,这一篇介绍怎样通过appsettings.json配置读取文件信息.这里我会教大家两种方式: 第一种直接放到通用类库,那里想调往那调. ...

  8. 资深架构师教你String 常量池、 String.itern()

    什么是常量 用final修饰的成员变量表示常量,值一旦给定就无法改变! final修饰的变量有三种:静态变量.实例变量和局部变量,分别表示三种类型的常量. Class文件中的常量池 在Class文件结 ...

  9. 使用elementUI的日期选择框,两选择框关联时间限值

    elementui 本身也提供了在一个输入框内关联选择时间的组件,非常好使,但无奈项目需要用两个输入框去关联的选择: <el-date-picker class="datepicker ...

  10. Beyond Compare 4.X 破解方法(亲测有效)

    Windows下Beyond Compare 4 30天评估到期了的话,可以尝试下面两种方式: 破解方式把Beyond Compare 4安装文件夹下面的BCUnrar.dll文件删掉就行了,但是这种 ...