关于技术选型,我现在的判断标准
刚开始工作的时候,选技术主要看哪个"更先进"、社区更热、面试更常问。现在标准完全变了。
一、先看团队里有没有人真的用过
这条听起来很不技术,但影响最大。
我们去年要给一个服务选消息队列。候选是 Kafka 和 RabbitMQ。Kafka 吞吐高、生态好、业界主流,从技术指标上完胜。
但我们团队没人上过 Kafka 生产环境。Kafka 的运维复杂度在于分区再平衡、消费者组管理、磁盘规划、监控指标解读,这些文档里不会细讲,只有踩过才知道。
最后选了 RabbitMQ。吞吐对我们够用(峰值每秒几千条),而且有人用过。
后来有次消费端积压,从发现到定位到解决用了四十分钟。如果当时是 Kafka,我怀疑要搞一整天。
技术选型里,"团队会不会用"这个权重,比大多数人给的高。
二、看"出错的时候好不好排查"
我现在的评估清单里有一条:这个技术出问题时,我能不能快速知道发生了什么。
具体地问:
- 有没有清晰的日志?
- 有没有能看内部状态的手段(状态页、pprof、metrics)?
- 错误信息是"something went wrong"还是能指出具体原因?
- 社区里搜错误信息,能不能搜到有用的答案?
Kubernetes 就是个典型例子。它的能力很强,但出问题时那个错误信息经常让人摸不着头脑。相比之下 systemd 的日志清楚得多。
这不是说 Kubernetes 不好,而是说它的学习成本要算进选型成本里。
三、看"如果我要换掉它,成本多大"
没有技术能用一辈子。所以我会问:它是不是把我和别的东西绑死了?
好例子:用标准库的 database/sql 接口,换数据库驱动只改一行;用某个 ORM 的专有特性,换 ORM 就要重写查询层。
好例子:业务逻辑写成不依赖框架的普通类,换框架的时候能直接搬走。
我的做法是在边界上做隔离:
// 定义自己的接口
interface CacheStore {
public function get(string $key): ?string;
public function set(string $key, string $value, int $ttl): void;
}
// 具体实现包一层框架
final class RedisCacheStore implements CacheStore { /* ... */ }
多写几十行,但换来的是"换掉 Redis 只改一个类"。
四、看"这块业务以后会变得多快"
需求变化快的地方,选改起来快的技术。
我有个运营后台,一年改了三十多个需求,平均每个需求改动不超过一天。它用的是最"土"的 PHP + 模板,没有任何前端框架、没有前后端分离。
同期另一个项目用了前后端分离 + SPA,虽然技术上更"现代",但每次改个字段要动三个仓库、走两次发布。运营那边抱怨了很久。
需求稳定的地方,选"跑得省心"的技术。 反过来,需求天天变的地方,别追求架构优雅,追求改得快。
五、警惕"以后可能会需要"
这是我最常犯的错误。
有个项目一开始就按"以后要支持百万用户"设计:分了服务、上了消息队列、做了读写分离、加了缓存层。结果两年过去,日活三千。
那些为了扩展性付出的复杂度,全部变成了维护负担。而且因为业务方向变了,有些服务压根没用上,删又不舍得删。
现在的原则:为未来预留接口,但不为未来实现。
比如:数据访问包一层接口(预留),但先不实现多数据源(不实现)。等真的需要了,替换实现就行。
六、看"这个决定可逆吗"
可逆的决定可以快,不可逆的决定要慢。
可逆的:选哪个日志库、用哪个 HTTP 客户端、目录怎么分。这些改起来成本低,凭直觉选,不合适再换。
不可逆的:数据库选型、数据格式、对外 API 的形状、核心领域模型的划分。这些一旦定了,改起来动全身。
我在可逆的决定上花的时间变少了,在不可逆的决定上花的时间变多了。
七、一个具体的反例
有次要给一个内部工具选前端方案。我花了三天比较 Vue 和 React 的生态、性能、学习曲线,最后选了 Vue。
结果那个工具总代码量不到 2000 行,只有三个页面,用哪个框架根本没区别。真正花时间的部分是我调 CSS 布局。
决策成本应该和决策影响成正比。 现在我遇到小决定,会给自己设个时间上限(比如 15 分钟),到点就选。
现在的清单
写下来大概是这七条,按我实际使用的权重排:
- 团队有没有人会(权重最高)
- 出问题了好不好查
- 换掉它的成本
- 这块业务变化快不快
- 是不是在为想象中的未来买单
- 这个决定可逆吗
- 技术指标(性能、生态、活跃度)
性能排在最后不是因为它不重要,而是因为大部分项目根本到不了性能瓶颈。真到了,再针对性优化。
最后
有句话我挺认同:架构决策的代价,往往在决定之后的两年里慢慢显现。
技术选型也是。选的时候觉得无所谓的东西,两年后可能变成"当时怎么想的"。
所以我现在做稍微重要一点的选型时,会写一段决策记录:当时有哪些选项、为什么选这个、假设是什么、什么情况下应该重新评估。
那个"假设是什么"很重要——它让你以后能判断这个决定还成不成立。