ElasticSqlMethodInvokeHelper.java 6.3 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112
  1. package org.elasticsearch.dsl.parser.helper;
  2. import com.alibaba.druid.sql.ast.SQLExpr;
  3. import com.alibaba.druid.sql.ast.expr.*;
  4. import org.apache.commons.collections.CollectionUtils;
  5. import org.elasticsearch.dsl.exception.ElasticSql2DslException;
  6. import org.elasticsearch.dsl.parser.QueryOrderConditionParser;
  7. public class ElasticSqlMethodInvokeHelper {
  8. public static final String DATE_METHOD = "date";
  9. public static final String NVL_METHOD = "nvl";
  10. public static final String INNER_DOC_METHOD = "inner_doc";
  11. public static final String NESTED_DOC_METHOD = "nested_doc";
  12. public static void checkDateMethod(SQLMethodInvokeExpr dateInvokeExpr) {
  13. if (!DATE_METHOD.equalsIgnoreCase(dateInvokeExpr.getMethodName())) {
  14. throw new ElasticSql2DslException("[syntax error] ElasticSql not support method:" + dateInvokeExpr.getMethodName());
  15. }
  16. if (CollectionUtils.isEmpty(dateInvokeExpr.getParameters()) || dateInvokeExpr.getParameters().size() != 2) {
  17. throw new ElasticSql2DslException(String.format("[syntax error] There is no %s args method named date",
  18. dateInvokeExpr.getParameters() != null ? dateInvokeExpr.getParameters().size() : 0));
  19. }
  20. SQLExpr patternArg = dateInvokeExpr.getParameters().get(0);
  21. SQLExpr timeValArg = dateInvokeExpr.getParameters().get(1);
  22. if (!(patternArg instanceof SQLCharExpr) && !(patternArg instanceof SQLVariantRefExpr)) {
  23. throw new ElasticSql2DslException("[syntax error] The first arg of date method should be a time pattern");
  24. }
  25. if (!(timeValArg instanceof SQLCharExpr) && !(timeValArg instanceof SQLVariantRefExpr)) {
  26. throw new ElasticSql2DslException("[syntax error] The second arg of date method should be a string of time");
  27. }
  28. }
  29. public static void checkInnerDocMethod(SQLMethodInvokeExpr innerDocInvokeExpr) {
  30. if (!INNER_DOC_METHOD.equalsIgnoreCase(innerDocInvokeExpr.getMethodName())) {
  31. throw new ElasticSql2DslException("[syntax error] ElasticSql not support method:" + innerDocInvokeExpr.getMethodName());
  32. }
  33. if (CollectionUtils.isEmpty(innerDocInvokeExpr.getParameters()) || innerDocInvokeExpr.getParameters().size() != 1) {
  34. throw new ElasticSql2DslException(String.format("[syntax error] There is no %s args method named inner_doc",
  35. innerDocInvokeExpr.getParameters() != null ? innerDocInvokeExpr.getParameters().size() : 0));
  36. }
  37. SQLExpr innerPropertyName = innerDocInvokeExpr.getParameters().get(0);
  38. if (!(innerPropertyName instanceof SQLPropertyExpr) && !(innerPropertyName instanceof SQLIdentifierExpr)) {
  39. throw new ElasticSql2DslException("[syntax error] The arg of inner_doc method should be field param name");
  40. }
  41. }
  42. public static void checkNestedDocMethod(SQLMethodInvokeExpr nestedDocInvokeExpr) {
  43. if (!NESTED_DOC_METHOD.equalsIgnoreCase(nestedDocInvokeExpr.getMethodName())) {
  44. throw new ElasticSql2DslException("[syntax error] ElasticSql not support method:" + nestedDocInvokeExpr.getMethodName());
  45. }
  46. if (CollectionUtils.isEmpty(nestedDocInvokeExpr.getParameters()) || nestedDocInvokeExpr.getParameters().size() != 1) {
  47. throw new ElasticSql2DslException(String.format("[syntax error] There is no %s args method named nested_doc",
  48. nestedDocInvokeExpr.getParameters() != null ? nestedDocInvokeExpr.getParameters().size() : 0));
  49. }
  50. SQLExpr innerPropertyName = nestedDocInvokeExpr.getParameters().get(0);
  51. if (!(innerPropertyName instanceof SQLPropertyExpr) && !(innerPropertyName instanceof SQLIdentifierExpr)) {
  52. throw new ElasticSql2DslException("[syntax error] The arg of nested_doc method should be field param name");
  53. }
  54. }
  55. public static void checkNvlMethod(SQLMethodInvokeExpr nvlInvokeExpr) {
  56. if (!NVL_METHOD.equalsIgnoreCase(nvlInvokeExpr.getMethodName())) {
  57. throw new ElasticSql2DslException("[syntax error] ElasticSql sort condition only support nvl method invoke");
  58. }
  59. if (CollectionUtils.isEmpty(nvlInvokeExpr.getParameters()) || nvlInvokeExpr.getParameters().size() > 3) {
  60. throw new ElasticSql2DslException(String.format("[syntax error] There is no %s args method named nvl",
  61. nvlInvokeExpr.getParameters() != null ? nvlInvokeExpr.getParameters().size() : 0));
  62. }
  63. SQLExpr fieldArg = nvlInvokeExpr.getParameters().get(0);
  64. SQLExpr valueArg = nvlInvokeExpr.getParameters().get(1);
  65. if (fieldArg instanceof SQLMethodInvokeExpr) {
  66. if (INNER_DOC_METHOD.equalsIgnoreCase(((SQLMethodInvokeExpr) fieldArg).getMethodName())) {
  67. checkInnerDocMethod((SQLMethodInvokeExpr) fieldArg);
  68. }
  69. if (NESTED_DOC_METHOD.equalsIgnoreCase(((SQLMethodInvokeExpr) fieldArg).getMethodName())) {
  70. checkNestedDocMethod((SQLMethodInvokeExpr) fieldArg);
  71. }
  72. } else if (!(fieldArg instanceof SQLPropertyExpr) && !(fieldArg instanceof SQLIdentifierExpr)) {
  73. throw new ElasticSql2DslException("[syntax error] The first arg of nvl method should be field param name");
  74. }
  75. if (!(valueArg instanceof SQLCharExpr) && !(valueArg instanceof SQLIntegerExpr) && !(valueArg instanceof SQLNumberExpr)) {
  76. throw new ElasticSql2DslException("[syntax error] The second arg of nvl method should be number or string");
  77. }
  78. if (nvlInvokeExpr.getParameters().size() == 3) {
  79. SQLExpr sortModArg = nvlInvokeExpr.getParameters().get(2);
  80. if (!(sortModArg instanceof SQLCharExpr)) {
  81. throw new ElasticSql2DslException("[syntax error] The third arg of nvl method should be string");
  82. }
  83. String sortModeText = ((SQLCharExpr) sortModArg).getText();
  84. if (!QueryOrderConditionParser.SortOption.AVG.mode().equalsIgnoreCase(sortModeText) && !QueryOrderConditionParser.SortOption.MIN.mode().equalsIgnoreCase(sortModeText)
  85. && !QueryOrderConditionParser.SortOption.MAX.mode().equalsIgnoreCase(sortModeText) && !QueryOrderConditionParser.SortOption.SUM.mode().equalsIgnoreCase(sortModeText)) {
  86. throw new ElasticSql2DslException("[syntax error] The third arg of nvl method should be one of the string[min,max,avg,sum]");
  87. }
  88. }
  89. }
  90. }