Copilot commented on code in PR #9095:
URL: https://github.com/apache/seatunnel/pull/9095#discussion_r2022464748


##########
seatunnel-connectors-v2/connector-iceberg/src/main/java/org/apache/seatunnel/connectors/seatunnel/iceberg/config/SQLToIcebergExprConverter.java:
##########
@@ -0,0 +1,222 @@
+/*
+ * Licensed to the Apache Software Foundation (ASF) under one
+ * or more contributor license agreements.  See the NOTICE file
+ * distributed with this work for additional information
+ * regarding copyright ownership.  The ASF licenses this file
+ * to you under the Apache License, Version 2.0 (the
+ * "License"); you may not use this file except in compliance
+ * with the License.  You may obtain a copy of the License at
+ *
+ *   http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing,
+ * software distributed under the License is distributed on an
+ * "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY
+ * KIND, either express or implied.  See the License for the
+ * specific language governing permissions and limitations
+ * under the License.
+ */
+
+package org.apache.seatunnel.connectors.seatunnel.iceberg.config;
+
+import org.apache.commons.lang3.StringUtils;
+import org.apache.iceberg.expressions.Expressions;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
+import net.sf.jsqlparser.JSQLParserException;
+import net.sf.jsqlparser.expression.DoubleValue;
+import net.sf.jsqlparser.expression.Expression;
+import net.sf.jsqlparser.expression.LongValue;
+import net.sf.jsqlparser.expression.NotExpression;
+import net.sf.jsqlparser.expression.NullValue;
+import net.sf.jsqlparser.expression.Parenthesis;
+import net.sf.jsqlparser.expression.StringValue;
+import net.sf.jsqlparser.expression.operators.conditional.AndExpression;
+import net.sf.jsqlparser.expression.operators.conditional.OrExpression;
+import net.sf.jsqlparser.expression.operators.relational.ComparisonOperator;
+import net.sf.jsqlparser.expression.operators.relational.EqualsTo;
+import net.sf.jsqlparser.expression.operators.relational.GreaterThan;
+import net.sf.jsqlparser.expression.operators.relational.GreaterThanEquals;
+import net.sf.jsqlparser.expression.operators.relational.InExpression;
+import net.sf.jsqlparser.expression.operators.relational.IsNullExpression;
+import net.sf.jsqlparser.expression.operators.relational.LikeExpression;
+import net.sf.jsqlparser.expression.operators.relational.MinorThan;
+import net.sf.jsqlparser.expression.operators.relational.MinorThanEquals;
+import net.sf.jsqlparser.expression.operators.relational.NotEqualsTo;
+import 
net.sf.jsqlparser.expression.operators.relational.ParenthesedExpressionList;
+import net.sf.jsqlparser.parser.CCJSqlParserUtil;
+import net.sf.jsqlparser.schema.Column;
+import net.sf.jsqlparser.statement.select.PlainSelect;
+import net.sf.jsqlparser.statement.select.Select;
+
+import java.util.ArrayList;
+import java.util.List;
+
+class SQLToIcebergExprConverter {
+    private static final Logger log = 
LoggerFactory.getLogger(SQLToIcebergExprConverter.class);
+
+    public static org.apache.iceberg.expressions.Expression 
parseWhereClauseToIcebergExpression(
+            String whereClauseStr) {
+        if (StringUtils.isNotBlank(whereClauseStr)) {
+            try {
+                // use the JsqlParser to parse the where clause
+                Select select =
+                        (Select) CCJSqlParserUtil.parse("SELECT * FROM t WHERE 
" + whereClauseStr);
+
+                PlainSelect plainSelect = (PlainSelect) select.getSelectBody();
+                net.sf.jsqlparser.expression.Expression whereClause = 
plainSelect.getWhere();
+
+                org.apache.iceberg.expressions.Expression icebergExpr =
+                        convertToIcebergExpression(whereClause);
+                return icebergExpr;
+            } catch (JSQLParserException e) {
+                log.error("Failed to parse where clause: {}", whereClauseStr, 
e);
+            }
+        }
+        return Expressions.alwaysTrue();
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
convertToIcebergExpression(
+            net.sf.jsqlparser.expression.Expression expr) {
+        if (expr instanceof Parenthesis) {
+            return convertToIcebergExpression(((Parenthesis) 
expr).getExpression());
+        }
+        if (expr instanceof AndExpression) {
+            return handleAndExpression((AndExpression) expr);
+        }
+        if (expr instanceof OrExpression) {
+            return handleOrExpression((OrExpression) expr);
+        }
+        if (expr instanceof NotExpression) {
+            return handleNotExpression((NotExpression) expr);
+        }
+        if (expr instanceof IsNullExpression) {
+            return handleIsNullExpression((IsNullExpression) expr);
+        }
+        if (expr instanceof InExpression) {
+            return handleInExpression((InExpression) expr);
+        }
+        if (expr instanceof LikeExpression) {
+            return handleLikeExpression((LikeExpression) expr);
+        }
+        if (expr instanceof ComparisonOperator) {
+            return handleComparisonOperator((ComparisonOperator) expr);
+        } else {
+            throw new UnsupportedOperationException(
+                    "Unsupported expression type: " + expr.getClass());
+        }
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
handleLikeExpression(
+            LikeExpression expr) {
+        String columnName = ((Column) 
expr.getLeftExpression()).getColumnName();
+        String value = ((StringValue) expr.getRightExpression()).getValue();
+        LikeExpression.KeyWord keyWord = expr.getLikeKeyWord();
+        if (keyWord == LikeExpression.KeyWord.LIKE) {
+            return Expressions.startsWith(columnName, value);
+        } else {
+            throw new UnsupportedOperationException("Unsupported like keyword: 
" + keyWord);
+        }
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
handleInExpression(InExpression expr) {
+        String columnName = ((Column) 
expr.getLeftExpression()).getColumnName();
+        ParenthesedExpressionList<Expression> list =
+                (ParenthesedExpressionList) expr.getRightExpression();
+        List<Object> values = extractValuesFromItemsList(list);
+
+        if (expr.isNot()) {
+            // handle NOT IN
+            return Expressions.notIn(columnName, values.toArray());
+        } else {
+            // handle IN
+            return Expressions.in(columnName, values.toArray());
+        }
+    }
+
+    private static List<Object> extractValuesFromItemsList(
+            ParenthesedExpressionList<Expression> list) {
+        List<Object> res = new ArrayList<>();
+        for (Expression expression : list) {
+            res.add(getValueFromExpression(expression));
+        }
+        return res;
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
handleAndExpression(
+            AndExpression expr) {
+        return Expressions.and(
+                convertToIcebergExpression(expr.getLeftExpression()),
+                convertToIcebergExpression(expr.getRightExpression()));
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
handleOrExpression(OrExpression expr) {
+        return Expressions.or(
+                convertToIcebergExpression(expr.getLeftExpression()),
+                convertToIcebergExpression(expr.getRightExpression()));
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
handleNotExpression(
+            NotExpression expr) {
+        return 
Expressions.not(convertToIcebergExpression(expr.getExpression()));
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
handleComparisonOperator(
+            ComparisonOperator expr) {
+        String columnName = ((Column) 
expr.getLeftExpression()).getColumnName();
+        Object value = getValueFromExpression(expr.getRightExpression());
+
+        if (expr instanceof EqualsTo) {
+            return Expressions.equal(columnName, value);
+        } else if (expr instanceof NotEqualsTo) {
+            return Expressions.notEqual(columnName, value);
+        } else if (expr instanceof GreaterThan) {
+            return Expressions.greaterThan(columnName, value);
+        } else if (expr instanceof GreaterThanEquals) {
+            return Expressions.greaterThanOrEqual(columnName, value);
+        } else if (expr instanceof MinorThan) {
+            return Expressions.lessThan(columnName, value);
+        } else if (expr instanceof MinorThanEquals) {
+            return Expressions.lessThanOrEqual(columnName, value);
+        } else {
+            throw new UnsupportedOperationException(
+                    "Unsupported comparison operator: " + expr.getClass());
+        }
+    }
+
+    private static org.apache.iceberg.expressions.Expression 
handleIsNullExpression(
+            IsNullExpression expr) {
+        String columnName = ((Column) 
expr.getLeftExpression()).getColumnName();
+        if (expr.isNot()) {
+            // handle IS NOT NULL
+            return Expressions.notNull(columnName);
+        } else {
+            // handle IS NULL
+            return Expressions.isNull(columnName);
+        }
+    }
+
+    private static Object 
getValueFromExpression(net.sf.jsqlparser.expression.Expression expr) {
+        if (expr instanceof LongValue) {
+            return ((LongValue) expr).getValue();
+        } else if (expr instanceof NullValue) {
+            return ((LongValue) expr).getValue();

Review Comment:
   Handling of NullValue in getValueFromExpression is incorrect; it casts a 
NullValue to LongValue instead of returning a proper null or handling the type 
appropriately. Consider returning null or explicitly processing NullValue.
   ```suggestion
               return null;
   ```



-- 
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]

Reply via email to