前言一般在团队开发中每个人的代码习惯都不太一样,这样就会导致代码风格不一致,以致于维护和修改bug的时候看别人的代码成为一种痛苦…这种情况尤其在前端开发中尤为明显。因为关于前端的开发规范貌似也没有行业权威标准。这几天在网上看了下,基本上在开发中通过eslint进行约束,airbnb的标准貌似颇为推崇,今天稍微整理下,准备在日后开发中形成习惯。基本规则每个文件只包含一个React组件。eslint: react/no-multi-comp;(官方表示在无状态,或者Pure组件允许一个文件包含多个组件,但是我个人觉得一个文件只包含一个组件比较浅显易懂)始终使用JSX语法;不要始终React.createElement方法,除非初始化app的文件不是JSX格式;Class vs React.createClass vs stateless如果组件拥有内部的state或者refs时,更推荐使用class extends Component,除非有更好的理由使用mixin。eslint:react/prefer-es6-class// badconst Listing = React.createClass({ // … render() { return <div>{this.state.hello}</div>; }});// goodclass Listing extends React.Component { // … render() { return <div>{this.state.hello}</div>; }}如果组件没有拥有内部的state或者refs,那么普通函数(不要使用箭头函数)比类的写法更好:// badclass Listing extends React.Component { render() { return <div>{this.props.hello}</div>; }}// bad (因为箭头函数没有“name”属性)const Listing = ({ hello }) => ( <div>{hello}</div>);// goodfunction Listing({ hello }) { return <div>{hello}</div>;}命名拓展名:React组件使用.jsx扩展名;文件名:文件名使用帕斯卡命名:HomePage.jsx引用命名:React组件使用帕斯卡命名,引用实例采用驼峰式命名:eslint: react/jsx-pascal-case)(个人不喜欢这样,引用命名还是按照帕斯卡命名)// badimport reservationCard from ‘./ReservationCard’;// goodimport ReservationCard from ‘./ReservationCard’;// badconst ReservationItem = <ReservationCard />;// goodconst reservationItem = <ReservationCard />;声明不要使用displayName属性来命名组件,应该使用类的引用名称。// badexport default React.createClass({ displayName: ‘ReservationCard’, // stuff goes here});// goodexport default class ReservationCard extends React.Component {}对齐为JSX语法使用下列的对齐方式:eslint: react/jsx-closing-bracket-location// bad<Foo superLongParam=“bar” anotherSuperLongParam=“baz” />// good<Foo superLongParam=“bar” anotherSuperLongParam=“baz”/>// 如果组件的属性可以放在一行就保持在当前一行中,(个人觉得如果只有一个属性就放在一行)<Foo bar=“bar” />// 多行属性采用缩进<Foo superLongParam=“bar” anotherSuperLongParam=“baz”> <Quux /></Foo>引号JSX的属性都采用双引号,其他的JS都使用单引号:jsx-quotes。为什么这样做?JSX 属性 不能包含转义的引号, 所以当输入"don’t"这类的缩写的时候用双引号会更方便。// bad<Foo bar=‘bar’ />// good<Foo bar=“bar” />// bad<Foo style={{ left: “20px” }} />// good<Foo style={{ left: ‘20px’ }} />空格始终在自闭和标签前添加一个空格。// bad<Foo/>// very bad<Foo />// bad<Foo />// good<Foo />属性属性名称始终使用驼峰命名法。// bad<Foo UserName=“hello” phone_number={12345678}/>// good<Foo userName=“hello” phoneNumber={12345678}/>当属性值等于true的时候,省略该属性的赋值。eslint:react/jsx-boolean-value// bad<Foo hidden={true}/>// good<Foo hidden/>括号使用括号包裹多行JSX标签,react/wrap-multilines// badrender() { return <MyComponent className=“long body” foo=“bar”> <MyChild /> </MyComponent>;}// goodrender() { return ( <MyComponent className=“long body” foo=“bar”> <MyChild /> </MyComponent> );}// good, when single linerender() { const body = <div>hello</div>; return <MyComponent>{body}</MyComponent>;}标签当标签没有子元素的时候,始终使用自闭合的标签:eslint: react/self-closing-comp// bad<Foo className=“stuff”></Foo>// good<Foo className=“stuff” />如果控件有多行属性,关闭标签要另起一行。 eslint: react/jsx-closing-bracket-location// bad<Foo bar=“bar” baz=“baz” />// good<Foo bar=“bar” baz=“baz”/>方法在 render 方法中事件的回调函数,应该在构造函数中进行bind绑定。 eslint: react/jsx-no-bind。为什么这样做? 在 render 方法中的 bind 调用每次调用 render 的时候都会创建一个全新的函数。// badclass extends React.Component { onClickDiv() { // do stuff } render() { return <div onClick={this.onClickDiv.bind(this)} /> }}// goodclass extends React.Component { constructor(props) { super(props); this.onClickDiv = this.onClickDiv.bind(this); } onClickDiv() { // do stuff } render() { return <div onClick={this.onClickDiv} /> }}React 组件的内部方法命名不要使用下划线前缀。// badReact.createClass({ _onClickSubmit() { // do stuff }, // other stuff});// goodclass extends React.Component { onClickSubmit() { // do stuff } // other stuff}排序class extends React.Component的顺序:static静态方法constructorgetChildContextcomponentWillMountcomponentDidMountcomponentWillReceivePropsshouldComponentUpdatecomponentWillUpdatecomponentDidUpdatecomponentWillUnmount点击回调或者事件回调 比如 onClickSubmit() 或者 onChangeDescription()render函数中的 getter 方法 比如 getSelectReason() 或者 getFooterContent()可选的 render 方法 比如 renderNavigation() 或者 renderProfilePicture()render怎么定义propTypes, defaultProps, contextTypes等import React, { PropTypes } from ‘react’;const propTypes = { id: PropTypes.number.isRequired, url: PropTypes.string.isRequired, text: PropTypes.string,};const defaultProps = { text: ‘Hello World’,};class Link extends React.Component { static methodsAreOk() { return true; } render() { return <a href={this.props.url} data-id={this.props.id}>{this.props.text}</a> }}Link.propTypes = propTypes;Link.defaultProps = defaultProps;export default Link;关于这个开发规范差不多就这样吧,eslint的配置个人在研究下,下次再放出来