Apache Superset查询TIMESTAMP WITH TIME ZONE列比较报错问题咨询
问题根因
该报错不是查询逻辑导致,也和数据录入的时间取值逻辑无关,问题出在Singer TAP的输出格式不符合协议要求:
Singer协议规定datetime类型字段必须传递ISO 8601格式的字符串,你当前直接将Python原生datetime对象随记录yield,下游写入PostgreSQL的Target组件无法正确识别该对象类型,错误将其解析为datetime.timedelta类型后写入,导致表中该字段存储值类型异常,执行查询时触发类型比较报错。
排查步骤
- 打印TAP的标准输出,查看
datetime_downloaded_from_api字段的输出格式,正常合规的输出应为类似2024-01-01T12:00:00.123Z的字符串,若为<datetime object at 0x...>的对象标识则说明格式错误。 - 连接PostgreSQL执行查询
SELECT pg_typeof(datetime_downloaded_from_api), datetime_downloaded_from_api FROM your_table LIMIT 1;,验证字段实际存储值是否为合法的带时区时间类型。 - 检查你使用的PostgreSQL Target组件版本,确认是否存在已知的datetime类型解析Bug。
解决方案
- 调整数据生成逻辑,在yield记录前将datetime对象序列化为ISO 8601标准字符串,修改代码如下:
creation_datetime = datetime.now(timezone.utc) # 新增序列化步骤,输出带UTC标识的ISO格式字符串 creation_datetime = creation_datetime.isoformat().replace("+00:00", "Z") new_record = { "key": valid_value.contract.symbol.lower(), "datetime_downloaded_from_api": creation_datetime } yield new_record
- 若修改后仍有报错,可在Meltano的PostgreSQL Target配置中添加参数
datetime_timezone: UTC,强制统一时间解析时区,避免跨时区转换异常。 - 若使用的是低于1.8.0版本的
target-postgres,建议升级到最新稳定版,修复已知的时间类型解析漏洞。
内容的提问来源于stack exchange,提问作者Erik
相关产品推荐
相关产品推荐

