diff --git a/pom.xml b/pom.xml
index 4b5489047..6adca2944 100644
--- a/pom.xml
+++ b/pom.xml
@@ -441,5 +441,10 @@
dingtalk-sdk
1.0-20210901
+
+ cn.hutool
+ hutool-core
+ 5.7.22
+
diff --git a/src/main/java/com/rebuild/core/service/trigger/aviator/AviatorDate.java b/src/main/java/com/rebuild/core/service/trigger/aviator/AviatorDate.java
index 941f7516a..0d1369af1 100644
--- a/src/main/java/com/rebuild/core/service/trigger/aviator/AviatorDate.java
+++ b/src/main/java/com/rebuild/core/service/trigger/aviator/AviatorDate.java
@@ -20,6 +20,7 @@ import java.util.Map;
public class AviatorDate extends AviatorObject {
private static final long serialVersionUID = 2930549924386648595L;
+ protected static final String DU_MINUTE= "I";
protected static final String DU_HOUR = "H";
protected static final String DU_DAY = "D";
protected static final String DU_MONTH = "M";
diff --git a/src/main/java/com/rebuild/core/service/trigger/aviator/DateAddFunction.java b/src/main/java/com/rebuild/core/service/trigger/aviator/DateAddFunction.java
index be8a1d54d..4247a79c6 100644
--- a/src/main/java/com/rebuild/core/service/trigger/aviator/DateAddFunction.java
+++ b/src/main/java/com/rebuild/core/service/trigger/aviator/DateAddFunction.java
@@ -10,6 +10,7 @@ package com.rebuild.core.service.trigger.aviator;
import cn.devezhao.commons.CalendarUtils;
import cn.devezhao.commons.ObjectUtils;
import com.googlecode.aviator.runtime.function.AbstractFunction;
+import com.googlecode.aviator.runtime.type.AviatorNil;
import com.googlecode.aviator.runtime.type.AviatorObject;
import java.util.Calendar;
@@ -30,28 +31,35 @@ public class DateAddFunction extends AbstractFunction {
public AviatorObject call(Map env, AviatorObject arg1, AviatorObject arg2) {
Object o = arg1.getValue(env);
Date date = o instanceof Date ? (Date) o : CalendarUtils.parse(o.toString());
+ if (date == null) {
+ return AviatorNil.NIL;
+ }
+
String interval = arg2.getValue(env).toString();
- int intervalUnit = Calendar.DATE;
+ int unit4Interval = Calendar.DATE; // default
- if (interval.endsWith(AviatorDate.DU_DAY)) {
+ if (interval.endsWith(AviatorDate.DU_MINUTE)) {
+ interval = interval.substring(0, interval.length() - 1);
+ unit4Interval = Calendar.MINUTE;
+ } else if (interval.endsWith(AviatorDate.DU_HOUR)) {
+ interval = interval.substring(0, interval.length() - 1);
+ unit4Interval = Calendar.HOUR_OF_DAY;
+ } else if (interval.endsWith(AviatorDate.DU_DAY)) {
interval = interval.substring(0, interval.length() - 1);
} else if (interval.endsWith(AviatorDate.DU_MONTH)) {
interval = interval.substring(0, interval.length() - 1);
- intervalUnit = Calendar.MONTH;
+ unit4Interval = Calendar.MONTH;
} else if (interval.endsWith(AviatorDate.DU_YEAR)) {
interval = interval.substring(0, interval.length() - 1);
- intervalUnit = Calendar.YEAR;
- } else if (interval.endsWith(AviatorDate.DU_HOUR)) {
- interval = interval.substring(0, interval.length() - 1);
- intervalUnit = Calendar.HOUR_OF_DAY;
+ unit4Interval = Calendar.YEAR;
}
- Date newDate = dateCalc(date, ObjectUtils.toInt(interval), intervalUnit);
+ Date newDate = dateAdd(date, ObjectUtils.toInt(interval), unit4Interval);
return new AviatorDate(newDate);
}
- protected Date dateCalc(Date date, int interval, int field) {
+ protected Date dateAdd(Date date, int interval, int field) {
return CalendarUtils.add(date, interval, field);
}
diff --git a/src/main/java/com/rebuild/core/service/trigger/aviator/DateDiffFunction.java b/src/main/java/com/rebuild/core/service/trigger/aviator/DateDiffFunction.java
index 5b9b35edd..51914b0b7 100644
--- a/src/main/java/com/rebuild/core/service/trigger/aviator/DateDiffFunction.java
+++ b/src/main/java/com/rebuild/core/service/trigger/aviator/DateDiffFunction.java
@@ -8,11 +8,16 @@ See LICENSE and COMMERCIAL in the project root for license information.
package com.rebuild.core.service.trigger.aviator;
import cn.devezhao.commons.CalendarUtils;
+import cn.devezhao.commons.ObjectUtils;
+import cn.hutool.core.date.DateUnit;
+import cn.hutool.core.date.DateUtil;
import com.googlecode.aviator.exception.ExpressionSyntaxErrorException;
import com.googlecode.aviator.runtime.function.AbstractFunction;
import com.googlecode.aviator.runtime.type.AviatorLong;
+import com.googlecode.aviator.runtime.type.AviatorNil;
import com.googlecode.aviator.runtime.type.AviatorObject;
import com.googlecode.aviator.runtime.type.AviatorString;
+import com.rebuild.core.Application;
import lombok.extern.slf4j.Slf4j;
import java.util.Date;
@@ -29,6 +34,17 @@ import java.util.Map;
public class DateDiffFunction extends AbstractFunction {
private static final long serialVersionUID = 5778729290544711131L;
+ private boolean isUseMysql;
+
+ protected DateDiffFunction() {
+ this(Boolean.FALSE);
+ }
+
+ protected DateDiffFunction(boolean isUseMysql) {
+ super();
+ this.isUseMysql = isUseMysql;
+ }
+
@Override
public AviatorObject call(Map env, AviatorObject arg1, AviatorObject arg2) {
return call(env, arg1, arg2, new AviatorString(AviatorDate.DU_DAY));
@@ -38,31 +54,50 @@ public class DateDiffFunction extends AbstractFunction {
public AviatorObject call(Map env, AviatorObject arg1, AviatorObject arg2, AviatorObject arg3) {
Object o1 = arg1.getValue(env);
Date date1 = o1 instanceof Date ? (Date) o1 : CalendarUtils.parse(o1.toString());
+ if (date1 == null) {
+ return AviatorNil.NIL;
+ }
+
Object o2 = arg2.getValue(env);
Date date2 = o2 instanceof Date ? (Date) o2 : CalendarUtils.parse(o2.toString());
+ if (date2 == null) {
+ return AviatorNil.NIL;
+ }
+
if (arg3.getValue(env) == null) {
throw new ExpressionSyntaxErrorException("`dateUnit` cannot be null");
}
+
String dateUnit = arg3.getValue(env).toString();
- if (date1 == null) {
- log.warn("Parseing date1 error : `{}`. Use default", o1);
- date1 = CalendarUtils.now();
+ if (isUseMysql) {
+ String mysqlUnit = "DAY";
+ if (AviatorDate.DU_YEAR.equalsIgnoreCase(dateUnit)) mysqlUnit = "YEAR";
+ else if (AviatorDate.DU_MONTH.equalsIgnoreCase(dateUnit)) mysqlUnit = "MONTH";
+ else if (AviatorDate.DU_HOUR.equalsIgnoreCase(dateUnit)) mysqlUnit = "HOUR";
+ else if (AviatorDate.DU_MINUTE.equalsIgnoreCase(dateUnit)) mysqlUnit = "MINUTE";
+
+ // 利用 MySQL 计算,可预期
+ String mysql = String.format("select TIMESTAMPDIFF(%s, '%s', '%s')",
+ mysqlUnit,
+ CalendarUtils.getUTCDateTimeFormat().format(date1),
+ CalendarUtils.getUTCDateTimeFormat().format(date2));
+ Object[] res = Application.getPersistManagerFactory().createNativeQuery(mysql).unique();
+
+ return AviatorLong.valueOf(ObjectUtils.toLong(res[0]));
+
+ } else {
+
+ long res = 0;
+
+ if (AviatorDate.DU_YEAR.equalsIgnoreCase(dateUnit)) res = DateUtil.betweenYear(date1, date2, true);
+ else if (AviatorDate.DU_MONTH.equalsIgnoreCase(dateUnit)) res = DateUtil.betweenMonth(date1, date2, true);
+ else if (AviatorDate.DU_DAY.equalsIgnoreCase(dateUnit)) res = DateUtil.betweenDay(date1, date2, true);
+ else if (AviatorDate.DU_HOUR.equalsIgnoreCase(dateUnit)) res = DateUtil.between(date1, date2, DateUnit.HOUR, false);
+ else if (AviatorDate.DU_MINUTE.equalsIgnoreCase(dateUnit)) res = DateUtil.between(date1, date2, DateUnit.MINUTE, false);
+
+ return AviatorLong.valueOf(res);
}
- if (date2 == null) {
- log.warn("Parseing date2 error : `{}`. Use default", o2);
- date2 = CalendarUtils.now();
- }
-
- long timeLeft = date1.getTime() - date2.getTime();
- timeLeft = timeLeft / 1000 / 60 / 60; // hours
-
- if (AviatorDate.DU_MONTH.equalsIgnoreCase(dateUnit)) timeLeft = timeLeft / 30; // FIXME 月固定30天
- else if (AviatorDate.DU_YEAR.equalsIgnoreCase(dateUnit)) timeLeft = timeLeft / 365; // FIXME 年固定365天
- else if (AviatorDate.DU_HOUR.equalsIgnoreCase(dateUnit)) ;
- else timeLeft = timeLeft / 24;
-
- return AviatorLong.valueOf(timeLeft);
}
@Override
diff --git a/src/main/java/com/rebuild/core/service/trigger/aviator/DateSubFunction.java b/src/main/java/com/rebuild/core/service/trigger/aviator/DateSubFunction.java
index 830801f48..c1bf957f6 100644
--- a/src/main/java/com/rebuild/core/service/trigger/aviator/DateSubFunction.java
+++ b/src/main/java/com/rebuild/core/service/trigger/aviator/DateSubFunction.java
@@ -20,8 +20,8 @@ public class DateSubFunction extends DateAddFunction {
private static final long serialVersionUID = -8857066285235050207L;
@Override
- protected Date dateCalc(Date date, int interval, int field) {
- return super.dateCalc(date, -interval, field);
+ protected Date dateAdd(Date date, int interval, int field) {
+ return super.dateAdd(date, -interval, field);
}
@Override
diff --git a/src/main/java/com/rebuild/core/service/trigger/aviator/LocationDistanceFunction.java b/src/main/java/com/rebuild/core/service/trigger/aviator/LocationDistanceFunction.java
index fab13b51b..ec37768b9 100644
--- a/src/main/java/com/rebuild/core/service/trigger/aviator/LocationDistanceFunction.java
+++ b/src/main/java/com/rebuild/core/service/trigger/aviator/LocationDistanceFunction.java
@@ -10,6 +10,7 @@ package com.rebuild.core.service.trigger.aviator;
import cn.devezhao.commons.ObjectUtils;
import com.googlecode.aviator.runtime.function.AbstractFunction;
import com.googlecode.aviator.runtime.type.AviatorDouble;
+import com.googlecode.aviator.runtime.type.AviatorNil;
import com.googlecode.aviator.runtime.type.AviatorObject;
import com.rebuild.core.metadata.MetadataHelper;
import lombok.extern.slf4j.Slf4j;
@@ -31,14 +32,12 @@ public class LocationDistanceFunction extends AbstractFunction {
public AviatorObject call(Map env, AviatorObject arg1, AviatorObject arg2) {
final double[] L1s = parseLngLat(arg1.getValue(env).toString());
if (L1s == null) {
- log.warn("Bad lnglat(1) format : {}", arg1.getValue(env));
- return AviatorDouble.valueOf(0);
+ return AviatorNil.NIL;
}
final double[] L2s = parseLngLat(arg2.getValue(env).toString());
if (L2s == null) {
- log.warn("Bad lnglat(2) format : {}", arg2.getValue(env));
- return AviatorDouble.valueOf(0);
+ return AviatorNil.NIL;
}
double LNG1 = L1s[0];
diff --git a/src/main/java/com/rebuild/core/service/trigger/aviator/RequestFunctuin.java b/src/main/java/com/rebuild/core/service/trigger/aviator/RequestFunctuin.java
index 66069b019..da20ad95d 100644
--- a/src/main/java/com/rebuild/core/service/trigger/aviator/RequestFunctuin.java
+++ b/src/main/java/com/rebuild/core/service/trigger/aviator/RequestFunctuin.java
@@ -8,6 +8,7 @@ See LICENSE and COMMERCIAL in the project root for license information.
package com.rebuild.core.service.trigger.aviator;
import com.googlecode.aviator.runtime.function.AbstractFunction;
+import com.googlecode.aviator.runtime.type.AviatorNil;
import com.googlecode.aviator.runtime.type.AviatorObject;
import com.googlecode.aviator.runtime.type.AviatorString;
import com.rebuild.utils.HttpUtils;
@@ -29,7 +30,7 @@ public class RequestFunctuin extends AbstractFunction {
@Override
public AviatorObject call(Map env, AviatorObject arg1) {
- return call(env, arg1, null);
+ return call(env, arg1, AviatorNil.NIL);
}
@Override
diff --git a/src/test/java/com/rebuild/core/service/trigger/aviator/AviatorUtilsTest.java b/src/test/java/com/rebuild/core/service/trigger/aviator/AviatorUtilsTest.java
index 88b7c344b..e71b494b5 100644
--- a/src/test/java/com/rebuild/core/service/trigger/aviator/AviatorUtilsTest.java
+++ b/src/test/java/com/rebuild/core/service/trigger/aviator/AviatorUtilsTest.java
@@ -33,14 +33,11 @@ class AviatorUtilsTest {
@Test
void func() {
- Object result = AviatorUtils.evalQuietly("DATEDIFF('2021-01-01 18:17:00', '2021-01-01 16:17:00', 'H')");
- System.out.println(result);
+ AviatorUtils.evalQuietly("p(DATEDIFF('2022-03-03 17:31:24', '2022-03-04 17:30:24', 'D'))");
- result = AviatorUtils.evalQuietly("DATEADD('2021-01-01 18:17:00', '2H')");
- System.out.println(result);
+ AviatorUtils.evalQuietly("p(DATEADD('2021-01-01 18:17:00', '2H'))");
- result = AviatorUtils.evalQuietly("DATESUB('2021-01-01 18:17:00', '1')");
- System.out.println(result);
+ AviatorUtils.evalQuietly("p(DATESUB('2021-01-01 18:17:00', '1'))");
}
@Test