第一行代码

这篇总结其实上周就打算写了。

讲两件事,第一件事关于工作和生活的一些交集,第二件事是工作中的小心得。

第一件事

上周去外地出差,在用户那边现场调试软件。在临近出差结束的前一天晚上十点半,用户提出了一个涉及到软件核心功能的更改需求。从单一功能开发的角度来说并不麻烦,大概半小时就可以加上这个需求。

从现场回酒店的路上梳理了一下思路,然后在第二天早晨,向用户指出这个需求有一定风险,短时间现场开发以及身边没有配套的测试人员,都会可能对整个系统带来未知的bug,导致现场测试通过,但是后期技术人员不在开发现场,会冒出各种奇怪的问题。说难听点就是纠缠不清。用户反馈说这个功能很关键。那好吧,花了半小时编码,半小时测试,功能就交付了。

当天结束了现场开发,收拾行李准备返京,心里被搞的很嗷滔。晚上买了张电影票,发现沉浸进入电影情节后,糟糕的心情很容易丢掉,看的是《谈判专家》,看主角从谈判专家到被专家谈判,最后位置互换又成为谈判者的过程,蛮有趣。

工作就是工作,别让他影响自己下来的生活。

btw,关于我的意见,可以参考《Continuous Delivery: Reliable Software Releases through Build, Test, and Deployment Automation》 by Jez Humble and David Farley中的内容:

在敏捷和DevOps文化强调快速迭代和持续交付的环境中,通常会有回归测试和自动化测试来确保代码的稳定性。对核心代码的任何修改都会通过CI/CD(持续集成/持续交付)管道进行彻底的测试,以保证系统的可靠性。

第二件事

还是这次现场开发,不过事情发生在今天,也就是出差回来的第一周。用户反馈现场软件经常陷入崩溃或者暂停运行的异常。我心里咯噔一下,不仅因为这个异常听起来是偶现,更因为我在现场时候这个问题并没有出现过。另外我在软件日志中并没有发现任何异常。

Bug 复现过程就不再赘述,总而言之就是我给用户更新的软件用户并没有及时更新在现场测试的机器上。

作为技术人员,在离开现场时我已经将软件依赖环境和可执行程序全部部署在用户的笔记本电脑上,后期更新版本只需要替换其中一个动态库,但是是通过其他方式传递的。为避免后期更新无法追踪,每发送一次更新库,我都会文字告诉用户这次更新了哪些内容。

问题就出在这儿。当天我告诉用户我新增了A功能,用户没有将更新版本部署到测试环境,在两天后用户面对自己上游的测试,测试A功能发现上述的异常。

所以我想说的是软件工程师第一行代码未必是"hello word!",有可能更需要学会写Release Note。应该将每次的Update以准确的软件发布更新内容的形式告知用户,还是那句话,免得扯皮。

总结如下。

我去某hub上搜了下Trending比较靠前的仓库,大致总结了一个简化的Release Note模版:

## [1.0.0] - 2024-06-29
### Added
- 新增用户登录功能
- 添加用户配置文件页面

### Changed
- 改进了首页加载速度
- 更新了第三方依赖库版本

### Fixed
- 修复了用户注册时的表单验证错误
- 修复了在某些情况下崩溃的bug

对于使用git的开发者来说(坚守svn的不多了吧?)semantic-release是一个不错的工具,一个完全自动化的版本管理工具,依据Git commit消息来生成发行说明。另外release-it是一个用于发布版本的命令行工具,可以自动生成Release Notes并更新版本号。两个工具限制和依赖比较多,不方便使用如上两个工具的话一定一定一定要手动编写好更新文档

如果手动编写Release Note的话,可以使用预处理器指令来检测编译选项并发出编译器警告以起到提示手动撰写Release Note的目的。在检测到编译模式为release时,生成Target的同时生成一个编译器警告,提示工程师填写Release Note。

#include <iostream>

#if defined(NDEBUG)
    #pragma message("Warning: Please fill in the Release Note.")
#endif

int main() {
    std::cout << "Hello, World!" << std::endl;
    return 0;
}

经历这次事情,感觉程序员和工程师,完全是两码事,慢慢体会成长,希望对各位同仁有借鉴意义。