破坏双亲委派的经典场景
请说明SPI(Service Provider Interface)、Tomcat和热部署场景下如何破坏双亲委派模型并解释原因。
回答
小字辈
SPI机制(如JDBC驱动加载)
- 问题:DriverManager在rt.jar中由Bootstrap加载,但JDBC驱动实现类在classpath中,Bootstrap无法找到。
- 解决:使用线程上下文类加载器(TCCL),将父加载器无法加载的请求交由子加载器完成。
- 实现:ServiceLoader通过TCCL加载META-INF/services下的实现类。
Tomcat容器
- 每个Web App有独立的WebAppClassLoader,优先加载/WEB-INF/classes和/WEB-INF/lib下的类。
- 如果父加载器先加载,会导致不同Web App间类共享(如Spring版本冲突)。
- 机制:先尝试自己加载,失败才委派给父加载器(反向委派)。
热部署
- 创建新ClassLoader替换旧加载器加载修改后的类。
- 旧类加载器及加载的类共同被GC回收。
- Spring Boot DevTools使用RestartClassLoader实现快速重启。