You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何在Kotlin中格式化Firestore服务器Timestamp时间戳

问题原因

你当前的写法存在两个核心错误:

  • DateTimeFormatter 是Java 8引入的java.time系列时间类的专用格式化工具,不能直接用于java.util.Date类或者字符串的格式化
  • 先把Date转成默认字符串再截取拼接的方式严重依赖系统默认的输出格式,时区、系统语言变化时都会出错,完全不建议使用
正确实现方案

推荐直接用java.time系列API完成转换,不需要借助旧的Date类,代码更稳定,修正后的完整代码如下:

override fun onBindViewHolder(holder: OrderListViewHolder, position: Int) {
    val item = orderList[position]

    orderViewModel.setOrderProduct(item.foodItem)
    orderViewModel.setStatus(item.status)

    val foodItem = item.foodItem?.map { it.itemName }

    // 修正后的日期格式化逻辑
    val formattedDate = item.date?.let { timestamp ->
        // 将Firestore Timestamp转成带时区的时间对象,此处用系统默认时区
        val zonedDateTime = timestamp.toDate().toInstant().atZone(ZoneId.systemDefault())
        // 创建格式化器,指定Locale.ENGLISH保证月份为英文缩写,不需要可删除该参数
        val formatter = DateTimeFormatter.ofPattern("dd MMM yyyy, HH:mm", Locale.ENGLISH)
        formatter.format(zonedDateTime)
    } ?: "" // 为空时的兜底值

    Log.d("dates", formattedDate)

    holder.orderDate.text = formattedDate
    holder.foodName.text = foodItem.toString().removeSurrounding("[", "]")
    holder.status.text = orderViewModel.status.value.toString()
}
注意事项
  • 如果你的App需要适配安卓7.1及以下版本,需要在模块级build.gradle中开启核心库脱糖(coreLibraryDesugaring)来支持java.time API
  • 代码中去掉了非空断言!!,改用空安全调用避免空指针异常

可选兼容方案(不推荐)

如果你不想开启脱糖,也可以用旧的SimpleDateFormat实现:

val formattedDate = item.date?.let { timestamp ->
    val formatter = SimpleDateFormat("dd MMM yyyy, HH:mm", Locale.ENGLISH)
    formatter.format(timestamp.toDate())
} ?: ""

注意SimpleDateFormat是非线程安全的,不要声明成全局静态变量重复使用,避免多线程场景下出现格式异常。

内容的提问来源于stack exchange,提问作者Tea

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.09.27 11:06:04