Copilot commented on code in PR #9342:
URL: https://github.com/apache/seatunnel/pull/9342#discussion_r2106459124
##########
docs/en/transform-v2/sql-functions.md:
##########
@@ -757,9 +757,59 @@ DAY_OF_YEAR(CREATED)
Returns a value of the specific time unit from a date/time value. This method
returns a numeric value with EPOCH field and an int for all other fields.
-Example:
-
-EXTRACT(SECOND FROM CURRENT_TIMESTAMP)
+The following are valid field names for EXTRACT:
+
+- `CENTURY`: The century; for interval values, the year field divided by 100
+- `DAY`: The day of the month (1-31); for interval values, the number of days
+- `DECADE`: The year field divided by 10
+- `DOW` or `DAYOFWEEK`: The day of the week as Sunday (0) to Saturday (6)
+- `DOY`: The day of the year (1-365/366)
+- `EPOCH`: For timestamp values, the number of seconds since 1970-01-01
00:00:00; for interval values, the total number of seconds
+- `HOUR`: The hour field (0-23)
+- `ISODOW`: The day of the week as Monday (1) to Sunday (7), matching ISO 8601
+- `ISOYEAR`: The ISO 8601 week-numbering year
+- `MICROSECONDS`: The seconds field, including fractional parts, multiplied by
1,000,000
+- `MILLENNIUM`: The millennium; for interval values, the year field divided by
1000
+- `MILLISECONDS`: The seconds field, including fractional parts, multiplied by
1,000
Review Comment:
The docs list the field as `MILLISECONDS` (plural), but the implementation
uses `MILLISECOND` (singular). Align the documentation with the actual field
name or update the code to accept the plural form.
```suggestion
- `MILLISECOND`: The seconds field, including fractional parts, multiplied
by 1,000
```
##########
seatunnel-transforms-v2/src/main/java/org/apache/seatunnel/transform/sql/zeta/functions/DateTimeFunction.java:
##########
@@ -400,11 +420,138 @@ public static Integer extract(List<Object> args) {
if (datetime instanceof LocalDateTime) {
return ((LocalDateTime) datetime).getNano() / 1000_000;
}
+ if (datetime instanceof OffsetDateTime) {
+ return ((OffsetDateTime) datetime).getNano() / 1000_000;
+ }
+ break;
+ case "MICROSECONDS":
+ if (datetime instanceof LocalTime) {
+ return ((LocalTime) datetime).getNano() / 1000;
+ }
+ if (datetime instanceof LocalDateTime) {
+ return ((LocalDateTime) datetime).getNano() / 1000;
+ }
+ if (datetime instanceof OffsetDateTime) {
+ return ((OffsetDateTime) datetime).getNano() / 1000;
+ }
+ break;
+ case "EPOCH":
+ if (datetime instanceof LocalDateTime) {
+ ZoneOffset offset = ZoneOffset.UTC;
+ return (int) ((LocalDateTime)
datetime).toEpochSecond(offset);
+ }
+ if (datetime instanceof LocalDate) {
+ LocalDateTime ldt = LocalDateTime.of((LocalDate) datetime,
LocalTime.MIDNIGHT);
+ ZoneOffset offset = ZoneOffset.UTC;
+ return (int) ldt.toEpochSecond(offset);
+ }
+ if (datetime instanceof OffsetDateTime) {
+ return (int) ((OffsetDateTime) datetime).toEpochSecond();
+ }
+ break;
+ case "QUARTER":
+ if (datetime instanceof LocalDate) {
+ int month = ((LocalDate) datetime).getMonthValue();
+ return (month - 1) / 3 + 1;
+ }
+ if (datetime instanceof LocalDateTime) {
+ int month = ((LocalDateTime) datetime).getMonthValue();
+ return (month - 1) / 3 + 1;
+ }
+ if (datetime instanceof OffsetDateTime) {
+ int month = ((OffsetDateTime) datetime).getMonthValue();
+ return (month - 1) / 3 + 1;
+ }
+ break;
+ case "WEEK":
+ if (datetime instanceof LocalDate) {
+ return datetime.get(WeekFields.ISO.weekOfYear());
+ }
+ if (datetime instanceof LocalDateTime) {
+ return datetime.get(WeekFields.ISO.weekOfYear());
+ }
+ if (datetime instanceof OffsetDateTime) {
+ return datetime.get(WeekFields.ISO.weekOfYear());
+ }
+ break;
+ case "CENTURY":
+ if (datetime instanceof LocalDate) {
+ int year = ((LocalDate) datetime).getYear();
+ return (year > 0) ? (year - 1) / 100 + 1 : year / 100;
+ }
+ if (datetime instanceof LocalDateTime) {
+ int year = ((LocalDateTime) datetime).getYear();
+ return (year > 0) ? (year - 1) / 100 + 1 : year / 100;
+ }
+ if (datetime instanceof OffsetDateTime) {
+ int year = ((OffsetDateTime) datetime).getYear();
+ return (year > 0) ? (year - 1) / 100 + 1 : year / 100;
+ }
+ break;
+ case "DECADE":
+ if (datetime instanceof LocalDate) {
+ return ((LocalDate) datetime).getYear() / 10;
+ }
+ if (datetime instanceof LocalDateTime) {
+ return ((LocalDateTime) datetime).getYear() / 10;
+ }
+ if (datetime instanceof OffsetDateTime) {
+ return ((OffsetDateTime) datetime).getYear() / 10;
+ }
+ break;
+ case "DOW":
+ if (datetime instanceof LocalDate) {
+ return ((LocalDate) datetime).getDayOfWeek().getValue() %
7;
+ }
+ if (datetime instanceof LocalDateTime) {
+ return ((LocalDateTime)
datetime).getDayOfWeek().getValue() % 7;
+ }
+ if (datetime instanceof OffsetDateTime) {
+ return ((OffsetDateTime)
datetime).getDayOfWeek().getValue() % 7;
+ }
+ break;
+ case "ISODOW":
+ if (datetime instanceof LocalDate) {
+ return ((LocalDate) datetime).getDayOfWeek().getValue();
+ }
+ if (datetime instanceof LocalDateTime) {
+ return ((LocalDateTime)
datetime).getDayOfWeek().getValue();
+ }
+ break;
+ case "DOY":
+ case "DAYOFYEAR":
+ if (datetime instanceof LocalDate) {
+ return ((LocalDate) datetime).getDayOfYear();
+ }
+ if (datetime instanceof LocalDateTime) {
+ return ((LocalDateTime) datetime).getDayOfYear();
+ }
+ if (datetime instanceof OffsetDateTime) {
+ return ((OffsetDateTime) datetime).getDayOfYear();
+ }
+ break;
+ case "ISOYEAR":
+ if (datetime instanceof LocalDate) {
+ LocalDate date = (LocalDate) datetime;
+ return date.get(WeekFields.ISO.weekBasedYear());
+ }
+ if (datetime instanceof LocalDateTime) {
+ LocalDate date = ((LocalDateTime) datetime).toLocalDate();
+ return date.get(WeekFields.ISO.weekBasedYear());
+ }
+ break;
+ case "MILLENNIUM":
Review Comment:
`OffsetDateTime` is not handled in the MILLENNIUM case. Add an `instanceof
OffsetDateTime` branch similar to other units so timestamptz values can return
the correct millennium.
--
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]