github-actions[bot] commented on code in PR #69987:
URL: https://github.com/apache/doris/pull/69987#discussion_r4441065272


##########
fe/fe-connector/fe-connector-jdbc/src/main/java/org/apache/doris/connector/jdbc/JdbcQueryBuilder.java:
##########
@@ -840,10 +853,9 @@ private String literalToSql(ConnectorLiteral lit) {
             return formatBooleanLiteral((Boolean) val);
         } else if (val instanceof Double) {
             double d = (Double) val;
-            if (d == Math.floor(d) && !Double.isInfinite(d)) {
-                return Long.toString((long) d);
-            }
-            return val.toString();
+            // Narrowing integral-looking doubles to long corrupts values 
outside the long range.
+            // Non-finite literals have no portable SQL spelling; evaluate 
their predicates locally.
+            return Double.isFinite(d) ? Double.toString(d) : null;

Review Comment:
   [P1] Preserve exact integer spelling for in-range doubles
   
   With default JDBC CAST pushdown, a PostgreSQL BIGINT row 
`id=9223372036854774784` matches `CAST(id AS DOUBLE) = 
CAST('9223372036854774784' AS DOUBLE)`. The converter strips the column CAST, 
and this line now emits `"id" = 9.2233720368547748E18`. PostgreSQL treats the 
exponent literal as exact NUMERIC value `9223372036854774800` and compares the 
BIGINT exactly, so it discards the matching row before Doris can evaluate its 
residual. The previous long rendering emitted the actual integer 
`9223372036854774784`. Preserve exact in-range integer text, use appropriate 
typed floating SQL, or keep this predicate local; the new Java 
`Double.parseDouble` round-trip test cannot catch this. See PostgreSQL's 
[numeric constant 
typing](https://www.postgresql.org/docs/current/sql-syntax-lexical.html#SQL-SYNTAX-CONSTANTS-NUMERIC)
 and [operator 
resolution](https://www.postgresql.org/docs/current/typeconv-oper.html).



##########
fe/fe-connector/fe-connector-jdbc/src/main/java/org/apache/doris/connector/jdbc/JdbcQueryBuilder.java:
##########
@@ -840,10 +853,9 @@ private String literalToSql(ConnectorLiteral lit) {
             return formatBooleanLiteral((Boolean) val);
         } else if (val instanceof Double) {
             double d = (Double) val;
-            if (d == Math.floor(d) && !Double.isInfinite(d)) {
-                return Long.toString((long) d);
-            }
-            return val.toString();
+            // Narrowing integral-looking doubles to long corrupts values 
outside the long range.
+            // Non-finite literals have no portable SQL spelling; evaluate 
their predicates locally.
+            return Double.isFinite(d) ? Double.toString(d) : null;

Review Comment:
   [P2] Use Oracle floating literal syntax for large finite doubles
   
   Oracle `BINARY_DOUBLE` columns map to Doris DOUBLE, but finiteness does not 
guarantee that this untyped spelling is valid remote SQL. For example, `d < 
CAST('1e200' AS DOUBLE)` now becomes `"d" < 1.0E200`. Oracle interprets 
unsuffixed literals as NUMBER, whose range excludes `1e200`, so the scan fails 
even for a matching `d=0` row; that case previously succeeded with the bounded 
long spelling. Render a BINARY_DOUBLE literal using the `D` suffix (or 
equivalent lossless conversion), or return null so the predicate stays local. 
Oracle's [numeric literal 
rules](https://docs.oracle.com/en/database/oracle/oracle-database/19/sqlrf/Literals.html)
 specify the default NUMBER type, binary-double suffix and out-of-range error.



-- 
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

To unsubscribe, e-mail: [email protected]

For queries about this service, please contact Infrastructure at:
[email protected]


---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]

Reply via email to