规范!!规范!!!

lxf2023-05-21 01:46:43

规范是开发绕不开的一个话题,不管是新项目或者是重构,规范都是十分重要的。它决定了你的项目是凌乱的,还是齐整的。当然,如果你定义的细一些的话,在排查问题上,也会轻松不少。闲话少叙,让我们开始吧

好吧,根据 eslint 里的规范,其实是分为 3 类,error、warn、off。但是,我个人觉得,一个规则,要不就是按照规则走,要不就是不按照规则走。没有什么第三种情况。所以,所有的规则,我都是采用 error or off,thanks

对了,我们可以把 lint 规则,最有价值的是业务 lint 规则,配置到 CI / CD 的流程上。在 CI 过的时候,再进行 CR。这样,我们的项目规范性就可以杠杠哒,而且一些业务错误也可以轻松规避了

最后再提一句哈,在我认为所有的规范,都是为了代码可读性,毕竟代码是给人卡看的,顺便在电脑上运行的。至于性能问题,等遇到了,我们再 case by case 吧

规则

camelcase:'off'

为了兼容 server 的接口返回

代码规范

不使用不常见的操作符

// 好了,我摊牌了,就是不要用 位运算符
~、^、|、&、>>、<<

尽量使用解构来获取属性,且在函数内部解构

// ❌
const getFullName = (user) => {
    const firstName = user.firstName;
    const lastName = user.lastName;
    return `${firstName} ${lastName}`
}

// ❌
const getFullName = ({ firstName, lastName } = {}) => {
    return `${firstName} ${lastName}`
}

// ✅
const getFullName = (user) => {
    const { firstName, lastName } = user || {};
    return `${firstName} ${lastName}`
}

// 数组也是一样的哈

const arr = [0, 1, 2, 3];

// ❌
const first = arr[0];
const second = arr[1];

// ✅
const [first, second] = arr

使用箭头函数,不使用函数声明(个人喜好

// ❌
function test() {
    ...
}

// ✅
const test = () => {
    ...
}

Immutability and Pure Function

// ❌
const func = params => {
    params.aaa = 1;
}

// ❌
let a = 1;
const func = () => {
    a++;
}

// 依赖透明,同样的输入有同样输出
const map = {
    bar: 2
}

// ❌
const test = () => {
    const { bar } = map || {};
}

// ✅
const test = (map) => {
    const { bar } = map || {}
}

参数超过 3 个,可选参数超过 2 个,使用 Object

// ❌
const test = (a: string, b: string, c:number, d: boolean) => {
    ...
}

// ✅
const test = (params:{
    a: string,
    b: string,
    c: number,
    d: boolean
}) => {
    ...
}

// ❌
const test = (title:string, options1?:any, options2?:any) => {
    ...
}

// ✅
const test = (params: {
    title: string,
    options1?: any,
    options2?: any
}) => {
    ...
}

函数的参数,尽可能的粒子化

// ❌
const getLevel = (task) => {
    const { talent_level_list } = task?.data?.requirement || {}
    ...
}

// ✅
const talentLevel = task?.data?.requirement?.talent_level_list 
const getLevel = (level) => {
    ...
}

及时删除无用代码

// ❌
useEffect(() => {
    // TODO: 这个弹窗逻辑在 2022-01-21 下线
    const isNotice = localStorage.getItem('notice');
    if(!isNotice){
        showModel();
    }  
}, [])

React 规范

组件名称追求简单,文件夹以及文件名采用小写的 kebab-case

// ❌
import Header from './header/header'

// ✅
import Header from './header'

// ❌
import TabItem from './tab/tab-item'

// ✅
import TabItem from './tab/item'

定时器在组件销毁时跟着销毁

// ❌
useEffect(() => {
    const timer = setInterval(() => {
        ...
    },1000)
}, [])

// ✅
useEffect(() => {
    const timer = setInterval(() => {
        ...
    },1000)
    return () => {
        clearInterval(timer)
    }
}, [])

钩子函数中的依赖不超过 3 个

// ❌
useEffect(() => {
    ...
}, [propA, propB, propC, propD])

// ✅
useEffect(() => {
    ...
}, [propA, propB])

useEffect(() => {
    ...
}, [propC, propD])

不用 useCallback,根据情况使用 useMemo

// ❌
const add = useCallback(() => {
    // useCallback 用来固定函数,但是那里有那么多很复杂的函数需要去固定,到最后可读性 down down down
    xx.xxx({
        task_id: taskDetail.task_id;
    }).then(() => {
        ...
    }).catch(() => {
        ...
    })
}, [taskDetail])

// ❌
const counters = useMemo(() => [    // 固定个锤子