v42-0001-minor-refactor-SQL-JSON-query-functions-based.no-cfbot
application/octet-stream
Filename: v42-0001-minor-refactor-SQL-JSON-query-functions-based.no-cfbot
Type: application/octet-stream
Part: 0
Message:
Re: remaining sql/json patches
From 94725e35d0c36c19c3d729294e264b410232ab08 Mon Sep 17 00:00:00 2001
From: jian he <jian.universality@gmail.com>
Date: Thu, 7 Mar 2024 21:38:30 +0800
Subject: [PATCH v42 1/2] minor refactor SQL/JSON query functions based on v24.
---
src/backend/executor/execExprInterp.c | 25 +++++++++++++++++++
src/backend/parser/parse_expr.c | 19 ++++++++++++++
.../regress/expected/sqljson_queryfuncs.out | 2 +-
3 files changed, 45 insertions(+), 1 deletion(-)
diff --git a/src/backend/executor/execExprInterp.c b/src/backend/executor/execExprInterp.c
index dad424ba..fc36b086 100644
--- a/src/backend/executor/execExprInterp.c
+++ b/src/backend/executor/execExprInterp.c
@@ -4325,6 +4325,31 @@ ExecEvalJsonExprPath(ExprState *state, ExprEvalStep *op,
*op->resvalue = JsonbPGetDatum(JsonbValueToJsonb(jbv));
*op->resnull = false;
}
+ else if (jbv->type == jbvNumeric)
+ {
+ switch (jexpr->returning->typid)
+ {
+ /*
+ * we need to handle these cases seperately.
+ * because cast from numeric to int2, int4,
+ * int8, float4, float8 cannot handle error
+ * softly. See coerceJsonFuncExprOutput.
+ */
+ case INT2OID:
+ case INT4OID:
+ case INT8OID:
+ case FLOAT4OID:
+ case FLOAT8OID:
+ *op->resvalue = JsonbPGetDatum(JsonbValueToJsonb(jbv));
+ *op->resnull = false;
+ break;
+ default:
+ ExecPrepareJsonItemCoercion(jbv, jsestate, throw_error,
+ &jump_eval_coercion,
+ op->resvalue, op->resnull);
+ break;
+ }
+ }
else
{
/*
diff --git a/src/backend/parser/parse_expr.c b/src/backend/parser/parse_expr.c
index 6557b07f..f4d5ef53 100644
--- a/src/backend/parser/parse_expr.c
+++ b/src/backend/parser/parse_expr.c
@@ -4535,6 +4535,25 @@ coerceJsonFuncExprOutput(ParseState *pstate, JsonExpr *jsexpr)
break;
}
}
+ /*
+ * the JsonbValue returned by JsonPathValue maybe a jbvType is jbvNumeric
+ * in that case, we need to use JsonCoercion node to handle error softly.
+ *
+ */
+ if (jsexpr->op == JSON_VALUE_OP)
+ {
+ switch (returning->typid)
+ {
+ case INT2OID:
+ case INT4OID:
+ case INT8OID:
+ case FLOAT4OID:
+ case FLOAT8OID:
+ return (Node *) makeJsonCoercion(returning, omit_quotes, NULL);
+ default:
+ break;
+ }
+ }
default_typid = JsonFuncExprDefaultReturnType(jsexpr);
default_typmod = -1;
diff --git a/src/test/regress/expected/sqljson_queryfuncs.out b/src/test/regress/expected/sqljson_queryfuncs.out
index f5b57465..23054d9a 100644
--- a/src/test/regress/expected/sqljson_queryfuncs.out
+++ b/src/test/regress/expected/sqljson_queryfuncs.out
@@ -213,7 +213,7 @@ SELECT JSON_VALUE(jsonb '1.23', '$');
SELECT JSON_VALUE(jsonb '1.23', '$' RETURNING int);
json_value
------------
- 1
+
(1 row)
SELECT JSON_VALUE(jsonb '"1.23"', '$' RETURNING numeric);
--
2.34.1