一、背景

前端即使是小团队,偶尔也是会冒出多人合作问题。

  • 编码风格不能保证统一
  • git使用不规范,某些不规范的代码推送造成历史代码丢失
  • 新人对他人代码上下文不熟悉改动产生bug

等等。

问题的避免要求到个人是不可靠的,分散精力到琐碎如缩进格式的细节也会降低生产力。

因此,思考使用自动化加上流程改进的方案,有效拦截问题。

二、目标

规范流程

  • 产品、项目的代码都设成保护分支,禁止force push等危险操作
  • git提交可控,如当冲突解决失误、无意覆盖多个文件,检查人员能够方便看出来,避免合入主分支
  • 功能修改commit必须带上jira id,方便开发日后看git历史了解上下文、QA分析

代码保持优雅

  • 编码风格统一

    如文件陈列规则一致

  • 增加可维护性、可读性

    如变量表意,没有大段无用代码,尽量使用新的稳定语法糖,减少冗余代码

  • 避免潜在bug

     如相等判断应该使用全等符号,而不是仅仅比较值

质量保证

避免低级错误,如把编译不过、导致白屏的代码合并到主分支

保证单元测试覆盖的代码功能不被破坏

三、流程

四:审核方式:Merge Request

代码合并到项目/产品主分支前一定要通过merge request的方式进行合并。

  1. 把所有项目/产品分支设置为保护分支,能禁止force push(🈲️)这种危险操作。
  2. 可以添加一系列自动检查,让代码规范检查成为强制、常态、自动的。
  3. 天然给code review提供方便
  4. 对于初级持续集成方案,构建、实践的时间成本很低

自动检查:流水线

把本地提交合并到远程主干分支前,需要通过一系列检查。

为什么需要流水线

避免本地检查因为种种原因被跳过(如代码很急跳过检查,习惯不好不喜欢检查,环境配置不对导致本地检查不生效等等)

检查内容

检查不通过,如提交的修改新增了lint错误,流水线会失败。

人工检查: Code Review

MR流水线通过后,需要经过其他人确认没有看出问题。才能由有权限的人进行合并。

Review基本规则

  1. 严格遵照MR/git/代码风格的规范
  2. 不允许错误使用git导致提别人的代码 (比如一个非重命名提交几十个文件改动)
  3. Reviewer提出有潜在的bug,作者要提交新的修复commit才通过review

前置条件:自审

自己才是MR的最终负责人,避免错误提交。

  1. commit是否只包含有效提交

    1. 不包含别人的提交
    2. 如本次MR个人只提交了5个commit,就应该只有5个commit

      如多出一个无用的merge commit,普通修改逻辑不该有这样的提交

  2. change是不是都是符合预期

    1. 可以很清楚地看到文件改动数量,大量文件变动是不正常的
    2. 左侧变动导航可以清楚看到改动了那些文件,是否包含自己未主动变动过的文件修改
  3. 流水线跑过后再请人review,避免来来回回浪费时间

这些都是一眼能扫出来的问题。

Code Review 利弊分析

好处:

  • 提前减少问题
  • 可以碰撞思想,让代码更加健壮优雅。

顾虑Q&A:

  • Q: 开发风格不一样,如果reviewer有个人喜好(如一个时间转换工具叫做DateUtil还是DateTransfromer),很难花时间去讨论、迁就

    • A: 不要提个人喜好,主要按个人的建议另外找时间和所有人拉通,放在开发规范里。
    • A: 强烈的建议可以提gitlab issue,找时间集中整理issue,列为技术债指定人一一解决
    • A: 对于没有写在规范文档里的,但是社区公认的不好实践,不予通过,如被废弃的方法
  • Q: review别人代码会不会太耗费精力,看不出问题是否承受压力。

    • A: 对于熟悉的代码,很快就知道干了什么
    • A: 对于不熟悉的代码,不明白的请对方说明,可以增加自己对项目的基本了解。在时间紧的情况下,可以不关心逻辑,只检查一些原则问题。
    • A: reviewer只是规避风险,提出建议。作者才是最终负责人。
  • Q: 一个人负责的项目,且非新人、合作伙伴、实习生,合并前需要code review吗?

    • A: 合并到主分支里的代码需要,其他灵活变通。

五、提交MR步骤

如小明需要向产品分支feature-AAA贡献代码,对应jira任务JIRA-1001

  1. 基于最新feature-AAA分支checkout一个新的本地分支xiaoming,更推荐以jira号命名JIRA-1001。个人分支名不能和主产品、项目分支命名类似,其他如果没有规范看个人习惯。

    git checkout feature-AAA
    git pull --rebase
    git checkout -b JIRA-1001
  2. 在本地分支JIRA-1001上提交修改。
  3. push到对应远程分支

    git push --set-upstream origin JIRA-1001
  4. 命令行可自动提示创建merge-request链接

    或点击gitlab网站上创建merge request。注意选对【待合并分支】和【待合入的分支】

  5. 点击流水线跑过后后立即merge按钮,则跑过后会合并。默认远程分支会删除。

上述操作完成后,如果要在同一个本地分支上继续提交代码,确保在提merge request之前,本地代码和待合入的代码保持同步。

git fetch origin feature-AAA (或干脆 git fetch --all)
git rebase origin feature-AAA 

如果有冲突,先在本地解决了再push。避免重复提交、或提了MR后才发现有冲突,浪费时间。

MR格式要求

  1. 是否合并多个commit 为一个

    1. 对于很小变动的提交(比如所有MR都做的同一件事情,选择压缩所有commit到一个)。保持主分支变更历史清晰。
    2. 每个commit做了独立的事情,不squash
  2. 对于功能修改代码,变更历史需要包含jira id。

    如果压缩commit:MR title带 jira id

    不压缩:commit需要带jira id

    保证主分支代码历史有变更依据。

问题

  • 提交merge request后,合并之前又有人提交了新的代码怎么办?

    点击rebase即可线上更新代码,如果没有冲突,则可继续流程

  • 为什么同步了最新的代码提交merge request,过了一会儿又发现有冲突?

    可能是其他人合入了与你的MR产生冲突的代码。

    此时把远程分支删除,更新本地代码,解决冲突后重新提交。

    //把远程分支删除
    git push origin JIRA-1001 --delete
    
    //更新本地代码
    git fetch origin feature-AAA (或干脆 git fetch --all)
    git rebase origin feature-AAA

六、贴士💡

  • 在本地IDE配置自动格式化代码,自动修复工具🔧

    配置保存时自动格式化。

    简单的错误可以也可以自动修复。

  • 功能代码提交后运行自动修复命令。如果有自动修复造成的更改,再提交一个修复的commit。

七、更进一步的期望

更多的补充检查

静态检查 / 代码扫描

  • 如sonar,能够发现更多问题。

功能性测试

初级功能测试,保证运行正确

作用:开发确保页面可访问,至少能访问首页(或默认页面),避免低级错误(如页面拦截逻辑写错导致项目白屏)

测试撰写:前端开发

环境维护人:前端开发,集成到前端流水线

成本:较小。要为功能测试做配置,至少要搭建一个含有基本API访问的mock server,需要花费一些时间。

初级功能测试,保证前端功能

作用:从前端单方面保证所有基本稳定的页面交互正确,避免新代码合入改坏旧功能以及修复旧功能造成QA重复工作

测试撰写:QA撰写自己维护的测试用例,前端开发撰写一些白盒用例

环境维护人:前端开发,集成到前端流水线

成本:较大。需要搭建自动化同步更新后端接口+人工mock数据合并的mock server,要花费较多的时间。维护起来可以变成开源项目。每个项目要单独准备一些初始数据。

比较完善的功能测试,端到端

作用:还原真实的测试场景,测试稳定的重要功能,保证测试到的场景下所有链路功能正常。

比如测试某个页面时,可以等待几秒后截图,截图邮件发给QA,可以定期检查,截图是否符合预期。甚至可以留一个底图做像素比对,相似度低于一定程度时才发告警邮件。

版本开发完成,提交测试后,修复性代码合并前应该通过功能测试。

测试撰写:QA撰写自己维护的测试用例,前端开发撰写一些白盒用例

环境维护人:所有开发、运维。单独成一条流水线,不影响提测前代码合并。流水线失败也能够看到。

成本:很大。对于前端和测试只需要准备自己的测试用例,对于前端所有的上层开发都要准备一些初始数据,保证测试环境的稳定,运维需要准备和重置测试环境,准备流水线。每个项目要单独准备一些初始数据。

可能存在的问题分析

  • 提测后,修复代码可能造成新的bug

    解决方案:

    • 人工方式:

      提测后,相关分支除了通过流水线外,必须被其他人review 批准后才可合并。

      review新人(对项目完全不熟)、合作伙伴、实习生的代码,除了基本准则,一定检查明白代码逻辑。

    • 自动化的方式:跑功能测试后才可合并(等待未来搭建)
  • 流水线有时比较慢,需要运维同事帮忙优化

    解决方案:

    • 优化CI配置,前置依赖下载给多个job使用。
    • 配置缓存,至少减少重复下载依赖的时间。

更好地形成闭环

  • 流程可视化,如在办公室设立一个公用大屏(投影,或者电视挂在墙上),流水线失败会显示挂掉的UI
  • 主分支流水线失败及时通知,用邮件、群机器人🤖️、扩音器播音的方式提醒对应提交人
  • 如果有自动化功能测试,功能测试失败会自动发邮件给QA

imirror707
45 声望2 粉丝