| 205 | } |
| 206 | |
| 207 | static Status GetTimestampMetadata(const ::arrow::TimestampType& type, |
| 208 | const WriterProperties& properties, |
| 209 | const ArrowWriterProperties& arrow_properties, |
| 210 | ParquetType::type* physical_type, |
| 211 | std::shared_ptr<const LogicalType>* logical_type) { |
| 212 | const bool coerce = arrow_properties.coerce_timestamps_enabled(); |
| 213 | const auto target_unit = |
| 214 | coerce ? arrow_properties.coerce_timestamps_unit() : type.unit(); |
| 215 | const auto version = properties.version(); |
| 216 | |
| 217 | // The user is explicitly asking for Impala int96 encoding, there is no |
| 218 | // logical type. |
| 219 | if (arrow_properties.support_deprecated_int96_timestamps()) { |
| 220 | *physical_type = ParquetType::INT96; |
| 221 | return Status::OK(); |
| 222 | } |
| 223 | |
| 224 | *physical_type = ParquetType::INT64; |
| 225 | *logical_type = TimestampLogicalTypeFromArrowTimestamp(type, target_unit); |
| 226 | |
| 227 | // The user is explicitly asking for timestamp data to be converted to the |
| 228 | // specified units (target_unit). |
| 229 | if (coerce) { |
| 230 | if (version == ::parquet::ParquetVersion::PARQUET_1_0 || |
| 231 | version == ::parquet::ParquetVersion::PARQUET_2_4) { |
| 232 | switch (target_unit) { |
| 233 | case ::arrow::TimeUnit::MILLI: |
| 234 | case ::arrow::TimeUnit::MICRO: |
| 235 | break; |
| 236 | case ::arrow::TimeUnit::NANO: |
| 237 | case ::arrow::TimeUnit::SECOND: |
| 238 | return Status::NotImplemented("For Parquet version ", |
| 239 | ::parquet::ParquetVersionToString(version), |
| 240 | ", can only coerce Arrow timestamps to " |
| 241 | "milliseconds or microseconds"); |
| 242 | } |
| 243 | } else { |
| 244 | switch (target_unit) { |
| 245 | case ::arrow::TimeUnit::MILLI: |
| 246 | case ::arrow::TimeUnit::MICRO: |
| 247 | case ::arrow::TimeUnit::NANO: |
| 248 | break; |
| 249 | case ::arrow::TimeUnit::SECOND: |
| 250 | return Status::NotImplemented("For Parquet version ", |
| 251 | ::parquet::ParquetVersionToString(version), |
| 252 | ", can only coerce Arrow timestamps to " |
| 253 | "milliseconds, microseconds, or nanoseconds"); |
| 254 | } |
| 255 | } |
| 256 | return Status::OK(); |
| 257 | } |
| 258 | |
| 259 | // The user implicitly wants timestamp data to retain its original time units, |
| 260 | // however the ConvertedType field used to indicate logical types for Parquet |
| 261 | // version <= 2.4 fields does not allow for nanosecond time units and so nanoseconds |
| 262 | // must be coerced to microseconds. |
| 263 | if ((version == ::parquet::ParquetVersion::PARQUET_1_0 || |
| 264 | version == ::parquet::ParquetVersion::PARQUET_2_4) && |
no test coverage detected