From d14360d1f8371bf33b7312567063f7b9fb3b4e70 Mon Sep 17 00:00:00 2001
From: Oliver Tan
current_timestamp(precision: int) → date
Returns the time of the current transaction.
+The value is based on a timestamp picked when the transaction starts +and which stays constant throughout the transaction. This timestamp +has no relationship with the commit order of concurrent transactions.
+current_timestamp(precision: int) → timestamp
Returns the time of the current transaction.
+The value is based on a timestamp picked when the transaction starts +and which stays constant throughout the transaction. This timestamp +has no relationship with the commit order of concurrent transactions.
+current_timestamp(precision: int) → timestamptz
Returns the time of the current transaction.
+The value is based on a timestamp picked when the transaction starts +and which stays constant throughout the transaction. This timestamp +has no relationship with the commit order of concurrent transactions.
+date_trunc(element: string, input: date) → timestamptz
Truncates input
to precision element
. Sets all fields that are less
significant than element
to zero (or one, for day and month)
Compatible elements: millennium, century, decade, year, quarter, month,
diff --git a/pkg/sql/logictest/testdata/logic_test/timestamp b/pkg/sql/logictest/testdata/logic_test/timestamp
index d83ecfdc7ebf..68d0f675e8e2 100644
--- a/pkg/sql/logictest/testdata/logic_test/timestamp
+++ b/pkg/sql/logictest/testdata/logic_test/timestamp
@@ -74,6 +74,11 @@ select '1-1-18 1:00:00.001-8':::TIMESTAMPTZ(6)
----
2001-01-18 01:00:00.001 -0800 PST
+query B
+select current_timestamp(3) - current_timestamp <= '1ms'::interval
+----
+true
+
statement ok
CREATE TABLE timestamp_test (
id integer PRIMARY KEY,
diff --git a/pkg/sql/parser/parse_test.go b/pkg/sql/parser/parse_test.go
index 17e5674eed07..a0743a46380f 100644
--- a/pkg/sql/parser/parse_test.go
+++ b/pkg/sql/parser/parse_test.go
@@ -1553,6 +1553,8 @@ func TestParse2(t *testing.T) {
`SELECT current_database()`},
{`SELECT CURRENT_TIMESTAMP`,
`SELECT current_timestamp()`},
+ {`SELECT current_timestamp(6)`,
+ `SELECT current_timestamp(6)`},
{`SELECT CURRENT_DATE`,
`SELECT current_date()`},
{`SELECT POSITION(a IN b)`,
diff --git a/pkg/sql/parser/sql.y b/pkg/sql/parser/sql.y
index 0a2a905432bf..0a16e681f97f 100644
--- a/pkg/sql/parser/sql.y
+++ b/pkg/sql/parser/sql.y
@@ -8238,6 +8238,10 @@ special_function:
{
$$.val = &tree.FuncExpr{Func: tree.WrapFunction($1)}
}
+| CURRENT_TIMESTAMP '(' a_expr ')'
+ {
+ $$.val = &tree.FuncExpr{Func: tree.WrapFunction($1), Exprs: tree.Exprs{$3.expr()}}
+ }
| CURRENT_TIMESTAMP '(' error { return helpWithFunctionByName(sqllex, $1) }
| CURRENT_TIME '(' ')'
{
diff --git a/pkg/sql/sem/builtins/builtins.go b/pkg/sql/sem/builtins/builtins.go
index 1ccce519f87d..cf6634edc04a 100644
--- a/pkg/sql/sem/builtins/builtins.go
+++ b/pkg/sql/sem/builtins/builtins.go
@@ -1675,7 +1675,7 @@ CockroachDB supports the following flags:
),
"now": txnTSImpl,
- "current_timestamp": txnTSImpl,
+ "current_timestamp": txnTSWithPrecisionImpl,
"transaction_timestamp": txnTSImpl,
"statement_timestamp": makeBuiltin(
@@ -3496,12 +3496,8 @@ has no relationship with the commit order of concurrent transactions.`
var txnTSDoc = `Returns the time of the current transaction.` + txnTSContextDoc
-var txnTSImpl = makeBuiltin(
- tree.FunctionProperties{
- Category: categoryDateAndTime,
- Impure: true,
- },
- tree.Overload{
+var txnTSOverloads = []tree.Overload{
+ {
Types: tree.ArgTypes{},
ReturnType: tree.FixedReturnType(types.TimestampTZ),
PreferredOverload: true,
@@ -3510,7 +3506,7 @@ var txnTSImpl = makeBuiltin(
},
Info: txnTSDoc,
},
- tree.Overload{
+ {
Types: tree.ArgTypes{},
ReturnType: tree.FixedReturnType(types.Timestamp),
Fn: func(ctx *tree.EvalContext, args tree.Datums) (tree.Datum, error) {
@@ -3518,12 +3514,71 @@ var txnTSImpl = makeBuiltin(
},
Info: txnTSDoc,
},
- tree.Overload{
+ {
Types: tree.ArgTypes{},
ReturnType: tree.FixedReturnType(types.Date),
Fn: currentDate,
Info: txnTSDoc,
},
+}
+
+var txnTSWithPrecisionOverloads = append(
+ []tree.Overload{
+ {
+ Types: tree.ArgTypes{{"precision", types.Int}},
+ ReturnType: tree.FixedReturnType(types.TimestampTZ),
+ PreferredOverload: true,
+ Fn: func(ctx *tree.EvalContext, args tree.Datums) (tree.Datum, error) {
+ prec := int32(tree.MustBeDInt(args[0]))
+ if prec < 0 || prec > 6 {
+ return nil, pgerror.Newf(pgcode.NumericValueOutOfRange, "precision %d out of range", prec)
+ }
+ return ctx.GetTxnTimestamp(tree.TimeFamilyPrecisionToRoundDuration(prec)), nil
+ },
+ Info: txnTSDoc,
+ },
+ {
+ Types: tree.ArgTypes{{"precision", types.Int}},
+ ReturnType: tree.FixedReturnType(types.Timestamp),
+ Fn: func(ctx *tree.EvalContext, args tree.Datums) (tree.Datum, error) {
+ prec := int32(tree.MustBeDInt(args[0]))
+ if prec < 0 || prec > 6 {
+ return nil, pgerror.Newf(pgcode.NumericValueOutOfRange, "precision %d out of range", prec)
+ }
+ return ctx.GetTxnTimestampNoZone(tree.TimeFamilyPrecisionToRoundDuration(prec)), nil
+ },
+ Info: txnTSDoc,
+ },
+ {
+ Types: tree.ArgTypes{{"precision", types.Int}},
+ ReturnType: tree.FixedReturnType(types.Date),
+ Fn: func(ctx *tree.EvalContext, args tree.Datums) (tree.Datum, error) {
+ prec := int32(tree.MustBeDInt(args[0]))
+ if prec < 0 || prec > 6 {
+ return nil, pgerror.Newf(pgcode.NumericValueOutOfRange, "precision %d out of range", prec)
+ }
+ return currentDate(ctx, args)
+ },
+ Info: txnTSDoc,
+ },
+ },
+ txnTSOverloads...,
+)
+
+var txnTSImpl = makeBuiltin(
+ tree.FunctionProperties{
+ Category: categoryDateAndTime,
+ Impure: true,
+ },
+ txnTSOverloads...,
+)
+
+var txnTSWithPrecisionImpl = makeBuiltin(
+ tree.FunctionProperties{
+ Category: categoryDateAndTime,
+ Impure: true,
+ },
+ txnTSWithPrecisionOverloads...,
)
func currentDate(ctx *tree.EvalContext, args tree.Datums) (tree.Datum, error) {
diff --git a/pkg/sql/sem/tree/normalize_test.go b/pkg/sql/sem/tree/normalize_test.go
index d52a612104ba..dbdd05294474 100644
--- a/pkg/sql/sem/tree/normalize_test.go
+++ b/pkg/sql/sem/tree/normalize_test.go
@@ -183,6 +183,7 @@ func TestNormalizeExpr(t *testing.T) {
{`clock_timestamp()`, `clock_timestamp()`},
{`now()`, `now()`},
{`current_timestamp()`, `current_timestamp()`},
+ {`current_timestamp(5)`, `current_timestamp(5)`},
{`transaction_timestamp()`, `transaction_timestamp()`},
{`statement_timestamp()`, `statement_timestamp()`},
{`cluster_logical_timestamp()`, `cluster_logical_timestamp()`},
From 2664b00de29c207089f33b047ffc3478fc27626a Mon Sep 17 00:00:00 2001
From: Andrei Matei