diff --git a/app/server/conversion/converters_default.go b/app/server/conversion/converters_default.go index 34569deb..c06320fd 100644 --- a/app/server/conversion/converters_default.go +++ b/app/server/conversion/converters_default.go @@ -4,6 +4,8 @@ import ( "fmt" "time" + "github.com/phuslu/fasttime" + "github.com/ydb-platform/fq-connector-go/common" ) @@ -137,7 +139,7 @@ func (timestampToStringConverterUTC) Convert(in *time.Time) (string, error) { // ClickHouse - 1 nanosecond (10^-9 s) // Oracle - 1 nanosecond (10^-9 s) // Trailing zeros are omitted - return in.UTC().Format("2006-01-02T15:04:05.999999999Z"), nil + return fasttime.Strftime("%Y-%m-%dT%H:%M:%S%N:z", in.UTC()), nil } type timestampToStringConverterNaive struct{} diff --git a/go.mod b/go.mod index 9cb9f618..bf479b33 100644 --- a/go.mod +++ b/go.mod @@ -72,6 +72,7 @@ require ( github.com/google/uuid v1.6.0 // indirect github.com/hashicorp/go-cleanhttp v0.5.2 // indirect github.com/inconshreveable/mousetrap v1.1.0 // indirect + github.com/itchyny/timefmt-go v0.1.6 github.com/jackc/pgpassfile v1.0.0 // indirect github.com/jackc/pgservicefile v0.0.0-20221227161230-091c0ba34f0a // indirect github.com/jackc/puddle/v2 v2.2.1 // indirect @@ -79,10 +80,12 @@ require ( github.com/klauspost/asmfmt v1.3.2 // indirect github.com/klauspost/compress v1.16.7 // indirect github.com/klauspost/cpuid/v2 v2.2.3 // indirect + github.com/lestrrat-go/strftime v1.1.0 github.com/matttproud/golang_protobuf_extensions v1.0.4 // indirect github.com/minio/asm2plan9s v0.0.0-20200509001527-cdd76441f9d8 // indirect github.com/minio/c2goasm v0.0.0-20190812172519-36a3d3bbc4f3 // indirect github.com/paulmach/orb v0.11.1 // indirect + github.com/phuslu/fasttime v1.0.2 github.com/pierrec/lz4/v4 v4.1.18 // indirect github.com/pmezard/go-difflib v1.0.0 // indirect github.com/segmentio/asm v1.2.0 // indirect diff --git a/go.sum b/go.sum index a9aabf7f..b4b74b4f 100644 --- a/go.sum +++ b/go.sum @@ -780,6 +780,8 @@ github.com/ianlancetaylor/demangle v0.0.0-20181102032728-5e5cf60278f6/go.mod h1: github.com/ianlancetaylor/demangle v0.0.0-20200824232613-28f6c0f3b639/go.mod h1:aSSvb/t6k1mPoxDqO4vJh6VOCGPwU4O0C2/Eqndh1Sc= github.com/inconshreveable/mousetrap v1.1.0 h1:wN+x4NVGpMsO7ErUn/mUI3vEoE6Jt13X2s0bqwp9tc8= github.com/inconshreveable/mousetrap v1.1.0/go.mod h1:vpF70FUmC8bwa3OWnCshd2FqLfsEA9PFc4w1p2J65bw= +github.com/itchyny/timefmt-go v0.1.6 h1:ia3s54iciXDdzWzwaVKXZPbiXzxxnv1SPGFfM/myJ5Q= +github.com/itchyny/timefmt-go v0.1.6/go.mod h1:RRDZYC5s9ErkjQvTvvU7keJjxUYzIISJGxm9/mAERQg= github.com/jackc/pgerrcode v0.0.0-20220416144525-469b46aa5efa h1:s+4MhCQ6YrzisK6hFJUX53drDT4UsSW3DEhKn0ifuHw= github.com/jackc/pgerrcode v0.0.0-20220416144525-469b46aa5efa/go.mod h1:a/s9Lp5W7n/DD0VrVoyJ00FbP2ytTPDVOivvn2bMlds= github.com/jackc/pgpassfile v1.0.0 h1:/6Hmqy13Ss2zCq62VdNG8tM1wchn8zjSGOBJ6icpsIM= @@ -820,6 +822,8 @@ github.com/kr/pty v1.1.1/go.mod h1:pFQYn66WHrOpPYNljwOMqo10TkYh1fy3cYio2l3bCsQ= github.com/kr/text v0.1.0/go.mod h1:4Jbv+DJW3UT/LiOwJeYQe1efqtUx/iVham/4vfdArNI= github.com/kr/text v0.2.0 h1:5Nx0Ya0ZqY2ygV366QzturHI13Jq95ApcVaJBhpS+AY= github.com/kr/text v0.2.0/go.mod h1:eLer722TekiGuMkidMxC/pM04lWEeraHUUmBw8l2grE= +github.com/lestrrat-go/strftime v1.1.0 h1:gMESpZy44/4pXLO/m+sL0yBd1W6LjgjrrD4a68Gapyg= +github.com/lestrrat-go/strftime v1.1.0/go.mod h1:uzeIB52CeUJenCo1syghlugshMysrqUT51HlxphXVeI= github.com/lib/pq v1.2.0/go.mod h1:5WUZQaWbwv1U+lTReE5YruASi9Al49XbQIvNi/34Woo= github.com/lyft/protoc-gen-star v0.6.0/go.mod h1:TGAoBVkt8w7MPG72TrKIu85MIdXwDuzJYeZuUPFPNwA= github.com/lyft/protoc-gen-star v0.6.1/go.mod h1:TGAoBVkt8w7MPG72TrKIu85MIdXwDuzJYeZuUPFPNwA= @@ -842,6 +846,8 @@ github.com/paulmach/protoscan v0.2.1/go.mod h1:SpcSwydNLrxUGSDvXvO0P7g7AuhJ7lcKf github.com/phpdave11/gofpdf v1.4.2/go.mod h1:zpO6xFn9yxo3YLyMvW8HcKWVdbNqgIfOOp2dXMnm1mY= github.com/phpdave11/gofpdi v1.0.12/go.mod h1:vBmVV0Do6hSBHC8uKUQ71JGW+ZGQq74llk/7bXwjDoI= github.com/phpdave11/gofpdi v1.0.13/go.mod h1:vBmVV0Do6hSBHC8uKUQ71JGW+ZGQq74llk/7bXwjDoI= +github.com/phuslu/fasttime v1.0.2 h1:gmD27yB6vnQuhk4vtmoBOmjaXsF+wwmyjMtayoHHUko= +github.com/phuslu/fasttime v1.0.2/go.mod h1:1zflhZFowg3RSL0IpmWQ0AprKCKbTRKV9PEpVXDBZ7A= github.com/pierrec/lz4 v2.6.1+incompatible h1:9UY3+iC23yxF0UfGaYrGplQ+79Rg+h/q9FV9ix19jjM= github.com/pierrec/lz4 v2.6.1+incompatible/go.mod h1:pdkljMzZIN41W+lC3N2tnIh5sFi+IEE17M5jbnwPHcY= github.com/pierrec/lz4/v4 v4.1.15/go.mod h1:gZWDp/Ze/IJXGXf23ltt2EXimqmTUXEy0GFuRQyBid4= diff --git a/tools/misc/bench/benchmark_time_formatting_test.go b/tools/misc/bench/benchmark_time_formatting_test.go new file mode 100644 index 00000000..0c77097f --- /dev/null +++ b/tools/misc/bench/benchmark_time_formatting_test.go @@ -0,0 +1,32 @@ +// go test -v -cpu=4 -run=none -bench=. -benchmem strftime_test.go +package strftime_test + +import ( + "testing" + "time" + + "github.com/phuslu/fasttime" + "github.com/stretchr/testify/require" +) + +var now = time.Now().UTC() + +func TestEquivalence(t *testing.T) { + std1 := now.Format(time.RFC3339Nano) + std2 := now.Format("2006-01-02T15:04:05.999999999Z") + fast := fasttime.Strftime("%Y-%m-%dT%H:%M:%S.%N%:z", now) + require.Equal(t, std1, fast) + require.Equal(t, std2, fast) +} + +func BenchmarkRFC3339StdTime(b *testing.B) { + for i := 0; i < b.N; i++ { + now.Format(time.RFC3339Nano) + } +} + +func BenchmarkRFC3339Fasttime(b *testing.B) { + for i := 0; i < b.N; i++ { + fasttime.Strftime("%Y-%m-%dT%H:%M:%S%N:z", now) + } +}