Skip to content

Commit 0293429

Browse files
committed
Fix nanosecond timestamp scaling
Some datetime formats passed to `string_to_timestamp_nanos` were parsing milliseconds as nanoseconds. E.g. `1970-01-01 00:00:00.123` would parse as `123` nanoseconds instead of milliseconds.
1 parent 5b90bc9 commit 0293429

File tree

1 file changed

+8
-10
lines changed

1 file changed

+8
-10
lines changed

arrow/src/compute/kernels/cast_utils.rs

Lines changed: 8 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -16,10 +16,8 @@
1616
// under the License.
1717

1818
use crate::error::{ArrowError, Result};
19-
use chrono::format::Fixed::{Nanosecond as FixedNanosecond, TimezoneOffsetColon};
20-
use chrono::format::Item::{Fixed, Literal, Numeric};
21-
use chrono::format::Numeric::Nanosecond;
22-
use chrono::format::Pad::Zero;
19+
use chrono::format::Fixed::{Nanosecond, TimezoneOffsetColon};
20+
use chrono::format::Item::{Fixed, Literal};
2321
use chrono::format::{Item, Parsed};
2422
use chrono::prelude::*;
2523

@@ -107,7 +105,7 @@ pub fn string_to_timestamp_nanos(s: &str) -> Result<i64> {
107105
// timezone offset, using ' ' as a separator
108106
// Example: 2020-09-08 13:42:29.190855-05:00
109107
// Full format string: "%Y-%m-%d %H:%M:%S%.f%:z".
110-
const FORMAT1: [Item; 2] = [Fixed(FixedNanosecond), Fixed(TimezoneOffsetColon)];
108+
const FORMAT1: [Item; 2] = [Fixed(Nanosecond), Fixed(TimezoneOffsetColon)];
111109
if let Ok(ts) = chrono::format::parse(&mut p, rest, FORMAT1.iter())
112110
.and_then(|()| p.to_datetime())
113111
{
@@ -117,7 +115,7 @@ pub fn string_to_timestamp_nanos(s: &str) -> Result<i64> {
117115
// with an explicit Z, using ' ' as a separator
118116
// Example: 2020-09-08 13:42:29Z
119117
// Full format string: "%Y-%m-%d %H:%M:%S%.fZ".
120-
const FORMAT2: [Item; 2] = [Fixed(FixedNanosecond), Literal("Z")];
118+
const FORMAT2: [Item; 2] = [Fixed(Nanosecond), Literal("Z")];
121119
if let Ok(ts) = chrono::format::parse(&mut p, rest, FORMAT2.iter())
122120
.and_then(|()| p.to_datetime_with_timezone(&Utc))
123121
{
@@ -126,8 +124,8 @@ pub fn string_to_timestamp_nanos(s: &str) -> Result<i64> {
126124

127125
// without a timezone specifier as a local time, using ' ' as a separator
128126
// Example: 2020-09-08 13:42:29.190855
129-
const FORMAT5: [Item; 2] = [Literal("."), Numeric(Nanosecond, Zero)];
130-
// Full format string: "%Y-%m-%d %H:%M:%S.%f".
127+
const FORMAT5: [Item; 1] = [Fixed(Nanosecond)];
128+
// Full format string: "%Y-%m-%d %H:%M:%S%.f".
131129
if let Ok(ts) = chrono::format::parse(&mut p, rest, FORMAT5.iter())
132130
.and_then(|()| p.to_naive_datetime_with_offset(0))
133131
{
@@ -152,8 +150,8 @@ pub fn string_to_timestamp_nanos(s: &str) -> Result<i64> {
152150
{
153151
// without a timezone specifier as a local time, using T as a separator
154152
// Example: 2020-09-08T13:42:29.190855
155-
// Full format string: "%Y-%m-%dT%H:%M:%S.%f".
156-
const FORMAT3: [Item; 2] = [Literal("."), Numeric(Nanosecond, Zero)];
153+
// Full format string: "%Y-%m-%dT%H:%M:%S%.f".
154+
const FORMAT3: [Item; 1] = [Fixed(Nanosecond)];
157155
if let Ok(ts) = chrono::format::parse(&mut p, rest, FORMAT3.iter())
158156
.and_then(|()| p.to_naive_datetime_with_offset(0))
159157
{

0 commit comments

Comments
 (0)