@Controller
@RequestMapping("/ops/hbase/cluster")
public class HBaseClusterManageController {
private List<String> inComputerRooms = Arrays.asList(/*replaced by i18n tool*/
ApplicationContextHolder.getApplicationContext().getMessage("java.HBaseClusterManageController.inComputerRooms.yìn_ní", null, "印尼", LocaleContextHolder.getLocale()),
ApplicationContextHolder.getApplicationContext().getMessage("java.HBaseClusterManageController.inComputerRooms.mĕi_guó", null, "美国", LocaleContextHolder.getLocale()));
private List<String> hkComputerRooms = Arrays.asList(
ApplicationContextHolder.getApplicationContext().getMessage("java.HBaseClusterManageController.hkComputerRooms.xiāng_găng", null, "香港", LocaleContextHolder.getLocale()));
}
springmvc的不分离项目前端vm,做的国际化,通过en和zh启动后,这个list调用之后会出现异常,如果正常的使用Arrays.asList("香港"),就不报错。
报错信息为:
org.springframework.beans.factory.BeanCreationException: Error creating bean with name 'xxx.ops.web.controller.ops.hbase_v2.HBaseClusterManageController' defined in file [xxx]: Instantiation of bean failed; nested exception is org.springframework.beans.BeanInstantiationException: Could not instantiate bean class [xxx.ops.hbase_v2.HBaseClusterManageController]: Constructor threw exception; nested exception is java.lang.NullPointerException
因为这个会进行配置文件的交互,会走messages_en.properties啥的,我就在本地的private List<String> inComputerRooms 上刚刚加了@Autowired,发现结果还是这样。
初步解决方案:
发现这个list在类的公共区域会报错,把list初始化信息放入正在使用的方法中,没有问题,缺点代码冗余。
多个方法都存在一份副本。
专业人士推荐方案:
这个异常可能是由于在初始化 HBaseClusterManageController 控制器时,尝试访问 ApplicationContextHolder 上下文之前,LocaleContextHolder 上下文尚未设置 Locale 导致的。
因为在创建 HBaseClusterManageController 实例时,会立即执行其构造函数,而在构造函数中引用了 LocaleContextHolder.getLocale(),如果此时 LocaleContextHolder 上下文尚未设置 Locale,则可能会返回 null。
可以尝试将这些 List 的初始化代码移动到 @PostConstruct 方法中,这样可以确保 Locale 在初始化 List 之前正确设置
List<String> hkComputerRooms =null;
List<String> inComputerRooms =null;
@PostConstruct
private void init() {
inComputerRooms = Arrays.asList(
ApplicationContextHolder.getApplicationContext().getMessage("java.HBaseClusterManageController.inComputerRooms.yìn_ní", null, "印尼", LocaleContextHolder.getLocale()),
ApplicationContextHolder.getApplicationContext().getMessage("java.HBaseClusterManageController.inComputerRooms.mĕi_guó", null, "美国", LocaleContextHolder.getLocale())
);
hkComputerRooms = Arrays.asList(
ApplicationContextHolder.getApplicationContext().getMessage("java.HBaseClusterManageController.hkComputerRooms.xiāng_găng", null, "香港", LocaleContextHolder.getLocale())
);
}
试了不好使。