公共组件库自定义异常需统一语义、便于复用、隔离影响、降低接入成本;命名以exception结尾且带组件域前缀,继承runtimeexception,设顶层基类componentexception,封装错误码、英文message、上下文参数及原始cause,并提供静态工厂方法和配套文档。

在公共组件库中设计自定义异常,核心目标是:**统一语义、便于复用、隔离影响、降低接入成本**。它不是简单写几个异常类,而是要作为组件对外契约的一部分,让所有使用方能“一看就懂、一用就对、一查就准”。
命名与继承体系要清晰
所有异常类名必须以 Exception 结尾,且前缀体现组件域(非业务域)。例如:CacheLoadException、IdGeneratorUnavailableException,而非 UserNotExistException(这是业务层该定义的)。
统一继承 RuntimeException,不引入受检异常(Checked Exception)。原因很实际:组件被多方调用,强制 throws 会污染上层方法签名,破坏透明性;而运行时异常更契合“组件不可用/参数非法/配置错误”等典型场景,也符合 Spring 等主流框架默认处理习惯。
建议设一个顶层基类(如 ComponentException),供所有组件异常继承。它可提供通用字段(如 componentName、errorCode)和标准化构造器,但本身不直接抛出。
必须封装结构化错误信息
每个异常实例应自带可解析的元数据,不能只靠 message 字符串。推荐包含:
-
唯一错误码(String 或 int):如
"CACHE-001",全局不重复,便于日志检索、监控告警、前端映射提示文案 -
简明英文 message:面向开发者,说明“什么错了”,如
"Failed to load key 'user_123' from remote cache" -
可选上下文参数(Map
) :比如缓存 key、请求 ID、超时毫秒数,方便问题定位,避免手动拼接字符串 - 原始 cause(Throwable):保留底层异常链,不丢失根因(如 RedisConnectionException 被包装为 CacheConnectException)
提供开箱即用的静态工厂方法
避免使用者反复 new 异常对象。在异常类中提供静态方法,例如:
在 Java 中初始化和管理阿里云 SDK客户端。包括单例模式、线程安全、endpoint 与 region 配置、VPC 终端节点、同步与异步等。
public static CacheLoadException forKey(String key) {
return new CacheLoadException("Failed to load key: " + key, "CACHE-002", Map.of("key", key));
}
这样调用方只需 throw CacheLoadException.forKey("user_123");,语义明确、参数安全、不易出错。
配套文档与使用示例不可少
在组件 README 或 Wiki 中单列一节《异常说明》,列出所有公开异常类、对应错误码、典型触发场景、推荐处理方式(重试?降级?记录日志?)。例如:
-
CacheTimeoutException (CACHE-003):当读取缓存超时时抛出 → 建议降级走 DB,不重试 -
ConfigInvalidException (CONFIG-101):配置项缺失或格式错误 → 启动阶段立即失败,不运行
附上真实代码片段,展示如何捕获并提取错误码做分支逻辑,而不是只写“请参考源码”。
禁止暴露内部实现细节
异常 message 和 context 中不得出现具体中间件名(如 “RedisCommandTimeoutException”)、线程名、堆栈路径、未脱敏的敏感参数(如完整 SQL、用户密码)。对外统一抽象为组件行为,例如:“缓存服务响应超时”、“ID 生成器当前不可用”。
所有异常类需标记 public 且 serialVersionUID 显式声明,确保跨版本序列化兼容(尤其用于 RPC 或消息传递场景)。
Java免费学习笔记:立即使用
解锁 Java 大师之旅:从入门到精通的终极指南










