ThreadLocalRandom生成随机ID重复 如何保证Firestore文档ID唯一
问题解决方案
问题根因
你遇到的非碰撞类ID重复问题,核心原因是伪随机数生成器的种子固定,安卓模拟器在应用重新编译安装、进程重启时,部分旧版本镜像会给ThreadLocalRandom返回固定的初始种子,如果你每次都是在应用启动后首次调用生成逻辑,就会得到完全相同的随机串。另外返回上一级布局后重复的场景,也可能是你的代码存在缓存旧ID、没有重新调用生成接口的逻辑问题。
最优解决方案
直接使用Firestore官方内置的文档ID生成能力,完全无需自行实现随机生成逻辑,官方生成逻辑已经做了唯一性适配,不会出现你遇到的重复问题:
// 调用无参document()方法,Firestore自动生成全局唯一ID DocumentReference newCommentRef = collectionReference.document(); Map<String, Object> newComment = new HashMap<>(); // -----ADDING SOME VALUES to newComment---- newCommentRef.set(newComment);
自定义ID生成的修复方案
如果你必须自行实现ID生成逻辑,做两处修改即可彻底避免重复:
- 替换随机源:用强随机生成器
SecureRandom替代ThreadLocalRandom,避免模拟器环境下种子固定的问题 - 增加时间戳维度:在随机串中拼接当前毫秒级时间戳,从业务层面保证ID不重复
修改后代码参考:
// 初始化强随机源 SecureRandom secureRandom = new SecureRandom(); RandomString gen = new RandomString(32, secureRandom); // 拼接时间戳+随机串,保证唯一性 String randomString = System.currentTimeMillis() + gen.nextString(); Map<String, Object> newComment = new HashMap<>(); // -----ADDING SOME VALUES to newComment---- collectionReference.document(randomString).set(newComment);
额外排查点
检查你的页面逻辑,确认返回上一级布局重新进入后,是否正确重新调用了随机字符串生成接口,而非复用了之前生成存储的旧ID变量。
内容的提问来源于stack exchange,提问作者Ben
相关产品推荐
相关产品推荐

