FirebaseMessageReceiver传Serializable对象到Activity取值为null如何解决
问题原因
- 关联类未实现Serializable接口:你的
FirmwareUpdate类包含FirmwareUrl类型的成员变量,仅FirmwareUpdate实现Serializable无效,若FirmwareUrl本身未实现Serializable接口,会导致整个对象序列化失败,存入Intent时直接丢失,取出时自然返回null。 - PendingIntent序列化兼容问题:Android系统对Intent中传递自定义Serializable对象的兼容性较差,尤其是通过PendingIntent传递时,部分系统版本、厂商ROM会主动丢弃自定义Serializable类型的Extra数据,仅保留String、Int等基础类型数据,这也是你能正常获取batteryId但拿不到完整对象的典型表现。
- 推送类型导致Intent被覆盖:如果你的Firebase推送属于通知消息而非纯数据消息,当应用处于后台时,系统会自动生成默认的启动PendingIntent,覆盖你在
FirebaseMessageReceiver中自定义的Extra参数,只有纯数据消息才会完全走你自定义的Receiver处理逻辑。 - 混淆导致反序列化失败:即使你给类加了
@Keep注解,若没有为Serializable类配置专门的混淆规则,ProGuard/R8混淆时可能修改类的字段名,导致反序列化时字段匹配失败,最终返回null。
解决方案
- 首先排查
FirmwareUrl类,确保它也实现了Serializable接口,如果其内部还有其他自定义类型的成员,需要逐层确保所有关联类都实现Serializable。 - 更稳妥的改造方案是将
FirmwareUpdate改为实现Parcelable接口,Android系统对Parcelable的传输优化和兼容性远高于Serializable,基本不会出现序列化丢失的问题。 - 如果不想修改序列化实现,可以先将
FirmwareUpdate对象转为JSON字符串,通过putExtra传递字符串,到目标Activity后再解析回对象,这种方式兼容性最高,不会出现自定义类型丢失的问题。 - 接收参数时使用安全类型转换,避免空指针崩溃:
val objFirmware = intent.getSerializableExtra(PUSH_NOTIFICATION_FIRMWARE_OBJ) as? FirmwareUpdate objFirmware?.let { // 仅对象非空时执行后续逻辑 }
- 调整Firebase推送为纯数据消息,避免系统默认通知逻辑覆盖你自定义的Intent Extra。
内容的提问来源于stack exchange,提问作者Jaimin Modi
相关产品推荐
相关产品推荐

