Repository: jmrozanec/cron-utils
Pull request #107 (2016-08-06 19:30:41)

Refactor joda to java8
Removed joda-time dependency. Added a joda-time exclusion from `htime`.

Replaced instances of Joda's `DateTime` with Java 8's `ZonedDateTime`.

All tests pass.


Patch:
diff --git a/pom.xml b/pom.xml
index 26f2f49..38dc3f4 100644
--- a/pom.xml
+++ b/pom.xml
@@ -62,7 +62,6 @@
         <slf4j.version>1.7.12</slf4j.version>
         <log4j.version>1.2.17</log4j.version>
         <commonsLang.version>3.4</commonsLang.version>
-        <jodatime.version>2.8.2</jodatime.version>
         <junit.version>4.12</junit.version>
         <mockito.version>1.10.19</mockito.version>
         <powermock.version>1.6.2</powermock.version>
@@ -84,16 +83,17 @@
             <artifactId>commons-lang3</artifactId>
             <version>${commonsLang.version}</version>
         </dependency>
-        <dependency>
-            <groupId>joda-time</groupId>
-            <artifactId>joda-time</artifactId>
-            <version>${jodatime.version}</version>
-        </dependency>
 
         <dependency>
             <groupId>com.cronutils</groupId>
             <artifactId>htime</artifactId>
             <version>${htime.version}</version>
+            <exclusions>
+                <exclusion>
+                    <groupId>joda-time</groupId>
+                    <artifactId>joda-time</artifactId>
+                </exclusion>
+            </exclusions>
         </dependency>
 
         <dependency>
diff --git a/src/main/java/com/cronutils/TimeConstants.java b/src/main/java/com/cronutils/TimeConstants.java
deleted file mode 100644
index 654c2f4..0000000
--- a/src/main/java/com/cronutils/TimeConstants.java
+++ /dev/null
@@ -1,17 +0,0 @@
-/*
- * Copyright 2014 jmrozanec
- * Licensed 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 com.cronutils;
-
-enum TimeConstants {
-    SECOND, MINUTE, HOUR, DAY;
-}
diff --git a/src/main/java/com/cronutils/descriptor/DescriptionStrategyFactory.java b/src/main/java/com/cronutils/descriptor/DescriptionStrategyFactory.java
index c70e162..46e6f6a 100644
--- a/src/main/java/com/cronutils/descriptor/DescriptionStrategyFactory.java
+++ b/src/main/java/com/cronutils/descriptor/DescriptionStrategyFactory.java
@@ -1,12 +1,14 @@
 package com.cronutils.descriptor;
 
-import com.cronutils.model.field.expression.FieldExpression;
-import com.cronutils.model.field.expression.On;
-import org.joda.time.DateTime;
-
+import java.time.DayOfWeek;
+import java.time.Month;
+import java.time.format.TextStyle;
 import java.util.ResourceBundle;
 import java.util.function.Function;
 
+import com.cronutils.model.field.expression.FieldExpression;
+import com.cronutils.model.field.expression.On;
+
 /*
 * Copyright 2014 jmrozanec
 * Licensed under the Apache License, Version 2.0 (the "License");
@@ -30,7 +32,7 @@ class DescriptionStrategyFactory {
      * @return - DescriptionStrategy instance, never null
      */
     public static DescriptionStrategy daysOfWeekInstance(final ResourceBundle bundle, final FieldExpression expression) {
-        final Function<Integer, String> nominal = integer -> new DateTime().withDayOfWeek(integer).dayOfWeek().getAsText(bundle.getLocale());
+        final Function<Integer, String> nominal = integer -> DayOfWeek.of(integer).getDisplayName(TextStyle.FULL, bundle.getLocale());
 
         NominalDescriptionStrategy dow = new NominalDescriptionStrategy(bundle, nominal, expression);
 
@@ -88,7 +90,7 @@ class DescriptionStrategyFactory {
     public static DescriptionStrategy monthsInstance(final ResourceBundle bundle, final FieldExpression expression) {
         return new NominalDescriptionStrategy(
                 bundle,
-                integer -> new DateTime().withMonthOfYear(integer).monthOfYear().getAsText(bundle.getLocale()),
+                integer -> Month.of(integer).getDisplayName(TextStyle.FULL, bundle.getLocale()),
                 expression
         );
     }
diff --git a/src/main/java/com/cronutils/mapper/ConstantsMapper.java b/src/main/java/com/cronutils/mapper/ConstantsMapper.java
index 651078d..f55053f 100644
--- a/src/main/java/com/cronutils/mapper/ConstantsMapper.java
+++ b/src/main/java/com/cronutils/mapper/ConstantsMapper.java
@@ -15,7 +15,7 @@ public class ConstantsMapper {
     private ConstantsMapper() {}
 
     public static final WeekDay QUARTZ_WEEK_DAY = new WeekDay(2, false);
-    public static final WeekDay JODATIME_WEEK_DAY = new WeekDay(1, false);
+    public static final WeekDay JAVA8 = new WeekDay(1, false);
     public static final WeekDay CRONTAB_WEEK_DAY = new WeekDay(1, true);
 
     /**
diff --git a/src/main/java/com/cronutils/model/time/ExecutionTime.java b/src/main/java/com/cronutils/model/time/ExecutionTime.java
index 951f4d5..528eb56 100644
--- a/src/main/java/com/cronutils/model/time/ExecutionTime.java
+++ b/src/main/java/com/cronutils/model/time/ExecutionTime.java
@@ -1,5 +1,24 @@
 package com.cronutils.model.time;
 
+import static com.cronutils.model.field.CronFieldName.DAY_OF_WEEK;
+import static com.cronutils.model.field.value.SpecialChar.QUESTION_MARK;
+import static com.cronutils.model.time.generator.FieldValueGeneratorFactory.createDayOfMonthValueGeneratorInstance;
+import static com.cronutils.model.time.generator.FieldValueGeneratorFactory.createDayOfWeekValueGeneratorInstance;
+import static java.time.temporal.TemporalAdjusters.lastDayOfMonth;
+
+import java.time.LocalDate;
+import java.time.LocalDateTime;
+import java.time.ZoneId;
+import java.time.ZonedDateTime;
+import java.util.Collections;
+import java.util.List;
+import java.util.Map;
+import java.util.Set;
+
+import org.apache.commons.lang3.Validate;
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
 import com.cronutils.mapper.WeekDay;
 import com.cronutils.model.Cron;
 import com.cronutils.model.definition.CronDefinition;
@@ -9,26 +28,10 @@ import com.cronutils.model.field.definition.DayOfWeekFieldDefinition;
 import com.cronutils.model.field.expression.Always;
 import com.cronutils.model.field.expression.QuestionMark;
 import com.cronutils.model.time.generator.FieldValueGenerator;
-import com.cronutils.model.time.generator.FieldValueGeneratorFactory;
 import com.cronutils.model.time.generator.NoSuchValueException;
 import com.google.common.annotations.VisibleForTesting;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
-import org.apache.commons.lang3.Validate;
-import org.joda.time.DateTime;
-import org.joda.time.DateTimeZone;
-import org.joda.time.Duration;
-import org.joda.time.Interval;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import java.util.Collections;
-import java.util.List;
-import java.util.Map;
-import java.util.Set;
-
-import static com.cronutils.model.field.CronFieldName.DAY_OF_WEEK;
-import static com.cronutils.model.field.value.SpecialChar.QUESTION_MARK;
 
 /*
  * Copyright 2014 jmrozanec
@@ -114,12 +117,12 @@ public class ExecutionTime {
     /**
      * Provide nearest date for next execution.
      * @param date - jodatime DateTime instance. If null, a NullPointerException will be raised.
-     * @return DateTime instance, never null. Next execution time.
+     * @return ZonedDateTime instance, never null. Next execution time.
      */
-    public DateTime nextExecution(DateTime date) {
+    public ZonedDateTime nextExecution(ZonedDateTime date) {
         Validate.notNull(date);
         try {
-            DateTime nextMatch = nextClosestMatch(date);
+            ZonedDateTime nextMatch = nextClosestMatch(date);
             if(nextMatch.equals(date)){
                 nextMatch = nextClosestMatch(date.plusSeconds(1));
             }
@@ -133,10 +136,10 @@ public class ExecutionTime {
      * If date is not match, will return next closest match.
      * If date is match, will return this date.
      * @param date - reference DateTime instance - never null;
-     * @return DateTime instance, never null. Value obeys logic specified above.
+     * @return ZonedDateTime instance, never null. Value obeys logic specified above.
      * @throws NoSuchValueException
      */
-    DateTime nextClosestMatch(DateTime date) throws NoSuchValueException {
+    ZonedDateTime nextClosestMatch(ZonedDateTime date) throws NoSuchValueException {
         List<Integer> year = yearsValueGenerator.generateCandidates(date.getYear(), date.getYear());
         TimeNode days = null;
         int lowestMonth = months.getValues().get(0);
@@ -145,80 +148,80 @@ public class ExecutionTime {
         int lowestSecond = seconds.getValues().get(0);
 
         NearestValue nearestValue;
-        DateTime newDate;
+        ZonedDateTime newDate;
         if(year.isEmpty()){
             int newYear = yearsValueGenerator.generateNextValue(date.getYear());
-            days = generateDays(cronDefinition, new DateTime(newYear, lowestMonth, 1, 0, 0));
+            days = generateDays(cronDefinition, ZonedDateTime.of(LocalDateTime.of(newYear, lowestMonth, 1, 0, 0), date.getZone()));
             return initDateTime(yearsValueGenerator.generateNextValue(date.getYear()), lowestMonth, days.getValues().get(0), lowestHour, lowestMinute, lowestSecond, date.getZone());
         }
-        if(!months.getValues().contains(date.getMonthOfYear())) {
-            nearestValue = months.getNextValue(date.getMonthOfYear(), 0);
+        if(!months.getValues().contains(date.getMonthValue())) {
+            nearestValue = months.getNextValue(date.getMonthValue(), 0);
             int nextMonths = nearestValue.getValue();
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), 1, 1, 0, 0, 0, date.getZone()).plusYears(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), 1, 1, 0, 0, 0), date.getZone()).plusYears(nearestValue.getShifts());
                 return nextClosestMatch(newDate);
             }
-            if (nearestValue.getValue() < date.getMonthOfYear()) {
+            if (nearestValue.getValue() < date.getMonthValue()) {
             	date = date.plusYears(1);
             }
-            days = generateDays(cronDefinition, new DateTime(date.getYear(), nextMonths, 1, 0, 0));
+            days = generateDays(cronDefinition, ZonedDateTime.of(LocalDateTime.of(date.getYear(), nextMonths, 1, 0, 0), date.getZone()));
             return initDateTime(date.getYear(), nextMonths, days.getValues().get(0), lowestHour, lowestMinute, lowestSecond, date.getZone());
         }
         days = generateDays(cronDefinition, date);
         if(!days.getValues().contains(date.getDayOfMonth())) {
             nearestValue = days.getNextValue(date.getDayOfMonth(), 0);
             if(nearestValue.getShifts()>0){
-                newDate = new DateTime(date.getYear(), date.getMonthOfYear(), 1, 0, 0, 0, date.getZone()).plusMonths(nearestValue.getShifts());
+                newDate = ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(), 1, 0, 0, 0), date.getZone()).plusMonths(nearestValue.getShifts());
                 return nextClosestMatch(newDate);
             }
             if (nearestValue.getValue() < date.getDayOfMonth()) {
             	date = date.plusMonths(1);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), nearestValue.getValue(), lowestHour, lowestMinute, lowestSecond, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), nearestValue.getValue(), lowestHour, lowestMinute, lowestSecond, date.getZone());
         }
-        if(!hours.getValues().contains(date.getHourOfDay())) {
-            nearestValue = hours.getNextValue(date.getHourOfDay(), 0);
+        if(!hours.getValues().contains(date.getHour())) {
+            nearestValue = hours.getNextValue(date.getHour(), 0);
             int nextHours = nearestValue.getValue();
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), date.getMonthOfYear(),
-                                date.getDayOfMonth(), 0, 0, 0, date.getZone()).plusDays(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(),
+                                date.getDayOfMonth(), 0, 0, 0), date.getZone()).plusDays(nearestValue.getShifts());
                 return nextClosestMatch(newDate);
             }
-            if (nearestValue.getValue() < date.getHourOfDay()) {
+            if (nearestValue.getValue() < date.getHour()) {
             	date = date.plusDays(1);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), date.getDayOfMonth(), nextHours, lowestMinute, lowestSecond, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), date.getDayOfMonth(), nextHours, lowestMinute, lowestSecond, date.getZone());
         }
-        if(!minutes.getValues().contains(date.getMinuteOfHour())) {
-            nearestValue = minutes.getNextValue(date.getMinuteOfHour(), 0);
+        if(!minutes.getValues().contains(date.getMinute())) {
+            nearestValue = minutes.getNextValue(date.getMinute(), 0);
             int nextMinutes = nearestValue.getValue();
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), date.getMonthOfYear(), date.getDayOfMonth(), date.getHourOfDay(),
-                                0, 0, date.getZone()).plusHours(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(), date.getDayOfMonth(), date.getHour(),
+                                0, 0), date.getZone()).plusHours(nearestValue.getShifts());
                 return nextClosestMatch(newDate);
             }
-            if (nearestValue.getValue() < date.getMinuteOfHour()) {
+            if (nearestValue.getValue() < date.getMinute()) {
             	date = date.plusHours(1);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), date.getDayOfMonth(), date.getHourOfDay(), nextMinutes, lowestSecond, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), date.getDayOfMonth(), date.getHour(), nextMinutes, lowestSecond, date.getZone());
         }
-        if(!seconds.getValues().contains(date.getSecondOfMinute())) {
-            nearestValue = seconds.getNextValue(date.getSecondOfMinute(), 0);
+        if(!seconds.getValues().contains(date.getSecond())) {
+            nearestValue = seconds.getNextValue(date.getSecond(), 0);
             int nextSeconds = nearestValue.getValue();
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), date.getMonthOfYear(),
-                                date.getDayOfMonth(), date.getHourOfDay(),
-                                date.getMinuteOfHour(),0, date.getZone()).plusMinutes(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(),
+                                date.getDayOfMonth(), date.getHour(),
+                                date.getMinute(),0), date.getZone()).plusMinutes(nearestValue.getShifts());
                 return nextClosestMatch(newDate);
             }
-            if (nearestValue.getValue() < date.getSecondOfMinute()) {
+            if (nearestValue.getValue() < date.getSecond()) {
             	date = date.plusMinutes(1);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), date.getDayOfMonth(), date.getHourOfDay(), date.getMinuteOfHour(), nextSeconds, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), date.getDayOfMonth(), date.getHour(), date.getMinute(), nextSeconds, date.getZone());
         }
         return date;
     }
@@ -226,11 +229,11 @@ public class ExecutionTime {
     /**
      * If date is not match, will return previous closest match.
      * If date is match, will return this date.
-     * @param date - reference DateTime instance - never null;
-     * @return DateTime instance, never null. Value obeys logic specified above.
+     * @param date - reference ZonedDateTime instance - never null;
+     * @return ZonedDateTime instance, never null. Value obeys logic specified above.
      * @throws NoSuchValueException
      */
-    DateTime previousClosestMatch(DateTime date) throws NoSuchValueException {
+    ZonedDateTime previousClosestMatch(ZonedDateTime date) throws NoSuchValueException {
         List<Integer> year = yearsValueGenerator.generateCandidates(date.getYear(), date.getYear());
         TimeNode days = generateDays(cronDefinition, date);
         int highestMonth = months.getValues().get(months.getValues().size()-1);
@@ -240,16 +243,16 @@ public class ExecutionTime {
         int highestSecond = seconds.getValues().get(seconds.getValues().size()-1);
 
         NearestValue nearestValue;
-        DateTime newDate;
+        ZonedDateTime newDate;
         if(year.isEmpty()){
             int previousYear = yearsValueGenerator.generatePreviousValue(date.getYear());
             if(highestDay>28){
-                int highestDayOfMonth = new DateTime(previousYear, highestMonth, 1,0,0).dayOfMonth().getMaximumValue();
+                int highestDayOfMonth = LocalDate.of(previousYear, highestMonth, 1).lengthOfMonth();
                 if(highestDay>highestDayOfMonth){
                     nearestValue = days.getPreviousValue(highestDay, 1);
                     if(nearestValue.getShifts()>0){
-                        newDate = new DateTime(previousYear, highestMonth, 1, 23, 59, 59, date.getZone())
-                                .minusMonths(nearestValue.getShifts()).dayOfMonth().withMaximumValue();
+                        newDate = ZonedDateTime.of(LocalDateTime.of(previousYear, highestMonth, 1, 23, 59, 59), ZoneId.systemDefault())
+                                .minusMonths(nearestValue.getShifts()).with(lastDayOfMonth());
                         return previousClosestMatch(newDate);
                     }else{
                         highestDay = nearestValue.getValue();
@@ -258,12 +261,12 @@ public class ExecutionTime {
             }
             return initDateTime(previousYear, highestMonth, highestDay, highestHour, highestMinute, highestSecond, date.getZone());
         }
-        if(!months.getValues().contains(date.getMonthOfYear())){
-            nearestValue = months.getPreviousValue(date.getMonthOfYear(), 0);
+        if(!months.getValues().contains(date.getMonthValue())){
+            nearestValue = months.getPreviousValue(date.getMonthValue(), 0);
             int previousMonths = nearestValue.getValue();
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), 12, 31, 23, 59, 59, date.getZone()).minusYears(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), 12, 31, 23, 59, 59), date.getZone()).minusYears(nearestValue.getShifts());
                 return previousClosestMatch(newDate);
             }
             return initDateTime(date.getYear(), previousMonths, highestDay, highestHour, highestMinute, highestSecond, date.getZone());
@@ -271,54 +274,54 @@ public class ExecutionTime {
         if(!days.getValues().contains(date.getDayOfMonth())){
             nearestValue = days.getPreviousValue(date.getDayOfMonth(), 0);
             if(nearestValue.getShifts()>0){
-                newDate = new DateTime(date.getYear(), date.getMonthOfYear(), 1, 23, 59, 59, date.getZone())
-                        .minusMonths(nearestValue.getShifts()).dayOfMonth().withMaximumValue();
+                newDate = ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(), 1, 23, 59, 59), date.getZone())
+                        .minusMonths(nearestValue.getShifts()).with(lastDayOfMonth());
                 return previousClosestMatch(newDate);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), nearestValue.getValue(), highestHour, highestMinute, highestSecond, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), nearestValue.getValue(), highestHour, highestMinute, highestSecond, date.getZone());
         }
-        if(!hours.getValues().contains(date.getHourOfDay())){
-            nearestValue = hours.getPreviousValue(date.getHourOfDay(), 0);
+        if(!hours.getValues().contains(date.getHour())){
+            nearestValue = hours.getPreviousValue(date.getHour(), 0);
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), date.getMonthOfYear(),
-                                date.getDayOfMonth(), 23, 59, 59, date.getZone()).minusDays(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(),
+                                date.getDayOfMonth(), 23, 59, 59), date.getZone()).minusDays(nearestValue.getShifts());
                 return previousClosestMatch(newDate);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), date.getDayOfMonth(), nearestValue.getValue(), highestMinute, highestSecond, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), date.getDayOfMonth(), nearestValue.getValue(), highestMinute, highestSecond, date.getZone());
         }
-        if(!minutes.getValues().contains(date.getMinuteOfHour())){
-            nearestValue = minutes.getPreviousValue(date.getMinuteOfHour(), 0);
+        if(!minutes.getValues().contains(date.getMinute())){
+            nearestValue = minutes.getPreviousValue(date.getMinute(), 0);
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), date.getMonthOfYear(),
-                                date.getDayOfMonth(), date.getHourOfDay(), 59, 59, date.getZone()).minusHours(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(),
+                                date.getDayOfMonth(), date.getHour(), 59, 59), date.getZone()).minusHours(nearestValue.getShifts());
                 return previousClosestMatch(newDate);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), date.getDayOfMonth(), date.getHourOfDay(), nearestValue.getValue(), highestSecond, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), date.getDayOfMonth(), date.getHour(), nearestValue.getValue(), highestSecond, date.getZone());
         }
-        if(!seconds.getValues().contains(date.getSecondOfMinute())){
-            nearestValue = seconds.getPreviousValue(date.getSecondOfMinute(), 0);
+        if(!seconds.getValues().contains(date.getSecond())){
+            nearestValue = seconds.getPreviousValue(date.getSecond(), 0);
             int previousSeconds = nearestValue.getValue();
             if(nearestValue.getShifts()>0){
                 newDate =
-                        new DateTime(date.getYear(), date.getMonthOfYear(),
-                                date.getDayOfMonth(), date.getHourOfDay(),
-                                date.getMinuteOfHour(), 59, date.getZone()).minusMinutes(nearestValue.getShifts());
+                        ZonedDateTime.of(LocalDateTime.of(date.getYear(), date.getMonthValue(),
+                                date.getDayOfMonth(), date.getHour(),
+                                date.getMinute(), 59), date.getZone()).minusMinutes(nearestValue.getShifts());
                 return previousClosestMatch(newDate);
             }
-            return initDateTime(date.getYear(), date.getMonthOfYear(), date.getDayOfMonth(), date.getHourOfDay(), date.getMinuteOfHour(), previousSeconds, date.getZone());
+            return initDateTime(date.getYear(), date.getMonthValue(), date.getDayOfMonth(), date.getHour(), date.getMinute(), previousSeconds, date.getZone());
         }
         return date;
     }
 
-    TimeNode generateDays(CronDefinition cronDefinition, DateTime date){
+    TimeNode generateDays(CronDefinition cronDefinition, ZonedDateTime date){
         boolean questionMarkSupported =
                 cronDefinition.getFieldDefinition(DAY_OF_WEEK).getConstraints().getSpecialChars().contains(QUESTION_MARK);
         if(questionMarkSupported){
             return new TimeNode(
                     generateDayCandidatesQuestionMarkSupported(
-                            date.getYear(), date.getMonthOfYear(),
+                            date.getYear(), date.getMonthValue(),
                             ((DayOfWeekFieldDefinition)
                                     cronDefinition.getFieldDefinition(DAY_OF_WEEK)
                             ).getMondayDoWValue()
@@ -327,7 +330,7 @@ public class ExecutionTime {
         }else{
             return new TimeNode(
                     generateDayCandidatesQuestionMarkNotSupported(
-                            date.getYear(), date.getMonthOfYear(),
+                            date.getYear(), date.getMonthValue(),
                             ((DayOfWeekFieldDefinition)
                                     cronDefinition.getFieldDefinition(DAY_OF_WEEK)
                             ).getMondayDoWValue()
@@ -341,19 +344,19 @@ public class ExecutionTime {
      * @param date - jodatime DateTime instance. If null, a NullPointerException will be raised.
      * @return jodatime Duration instance, never null. Time to next execution.
      */
-    public Duration timeToNextExecution(DateTime date){
-        return new Interval(date, nextExecution(date)).toDuration();
+    public java.time.Duration timeToNextExecution(ZonedDateTime date){
+        return java.time.Duration.between(date, nextExecution(date));
     }
 
     /**
      * Provide nearest date for last execution.
-     * @param date - jodatime DateTime instance. If null, a NullPointerException will be raised.
-     * @return DateTime instance, never null. Last execution time.
+     * @param date - ZonedDateTime instance. If null, a NullPointerException will be raised.
+     * @return ZonedDateTime instance, never null. Last execution time.
      */
-    public DateTime lastExecution(DateTime date){
+    public ZonedDateTime lastExecution(ZonedDateTime date){
         Validate.notNull(date);
         try {
-            DateTime previousMatch = previousClosestMatch(date);
+            ZonedDateTime previousMatch = previousClosestMatch(date);
             if(previousMatch.equals(date)){
                 previousMatch = previousClosestMatch(date.minusSeconds(1));
             }
@@ -368,73 +371,72 @@ public class ExecutionTime {
      * @param date - jodatime DateTime instance. If null, a NullPointerException will be raised.
      * @return jodatime Duration instance, never null. Time from last execution.
      */
-    public Duration timeFromLastExecution(DateTime date){
-        return new Interval(lastExecution(date), date).toDuration();
+    public java.time.Duration timeFromLastExecution(ZonedDateTime date){
+        return java.time.Duration.between(lastExecution(date), date);
     }
 
     /**
      * Provide feedback if a given date matches the cron expression.
-     * @param date - jodatime DateTime instance. If null, a NullPointerException will be raised.
+     * @param date - ZonedDateTime instance. If null, a NullPointerException will be raised.
      * @return true if date matches cron expression requirements, false otherwise.
      */
-    public boolean isMatch(DateTime date){
+    public boolean isMatch(ZonedDateTime date){
         return nextExecution(lastExecution(date)).equals(date);
     }
 
 	private List<Integer> generateDayCandidatesQuestionMarkNotSupported(int year, int month, WeekDay mondayDoWValue) {
-		DateTime date = new DateTime(year, month, 1, 1, 1);
-		Set<Integer> candidates = Sets.newHashSet();
-		if (daysOfMonthCronField.getExpression() instanceof Always && daysOfWeekCronField.getExpression() instanceof Always) {
-			candidates.addAll(FieldValueGeneratorFactory.createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month).generateCandidates(1,
-					date.dayOfMonth().getMaximumValue()));
-		} else {
-			if (daysOfMonthCronField.getExpression() instanceof Always) {
-				candidates.addAll(FieldValueGeneratorFactory.createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, year, month, mondayDoWValue)
-						.generateCandidates(1, date.dayOfMonth().getMaximumValue()));
-			} else {
-				if (daysOfWeekCronField.getExpression() instanceof Always) {
-					candidates.addAll(FieldValueGeneratorFactory.createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month).generateCandidates(
-							1, date.dayOfMonth().getMaximumValue()));
-				} else {
-					candidates.addAll(FieldValueGeneratorFactory.createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, year, month, mondayDoWValue)
-							.generateCandidates(1, date.dayOfMonth().getMaximumValue()));
-					candidates.addAll(FieldValueGeneratorFactory.createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month).generateCandidates(
-							1, date.dayOfMonth().getMaximumValue()));
-				}
-			}
-		}
-		List<Integer> candidatesList = Lists.newArrayList(candidates);
+        LocalDate date = LocalDate.of(year, month, 1);
+        int lengthOfMonth = date.lengthOfMonth();
+        Set<Integer> candidates = Sets.newHashSet();
+        if (daysOfMonthCronField.getExpression() instanceof Always && daysOfWeekCronField.getExpression() instanceof Always) {
+            candidates.addAll(createDayOfMonthValueGeneratorInstance(daysOfMonthCronField,
+                    year, month).generateCandidates(1, lengthOfMonth));
+        } else if (daysOfMonthCronField.getExpression() instanceof Always) {
+            candidates.addAll(createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, 
+                    year, month, mondayDoWValue).generateCandidates(1, lengthOfMonth));
+        } else if (daysOfWeekCronField.getExpression() instanceof Always) {
+            candidates.addAll(createDayOfMonthValueGeneratorInstance(daysOfMonthCronField,
+                    year, month).generateCandidates(1, lengthOfMonth));
+        } else {
+            candidates.addAll(createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, 
+                    year, month, mondayDoWValue).generateCandidates(1, lengthOfMonth));
+            candidates.addAll(createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month)
+                    .generateCandidates(1, lengthOfMonth));
+        }
+        List<Integer> candidatesList = Lists.newArrayList(candidates);
 		Collections.sort(candidatesList);
 		return candidatesList;
 	}
 
     private List<Integer> generateDayCandidatesQuestionMarkSupported(int year, int month, WeekDay mondayDoWValue){
-        DateTime date = new DateTime(year, month, 1,1,1);
+        LocalDate date = LocalDate.of(year, month, 1);
+        int lengthOfMonth = date.lengthOfMonth();
         Set<Integer> candidates = Sets.newHashSet();
-        if(daysOfMonthCronField.getExpression() instanceof Always && daysOfWeekCronField.getExpression() instanceof Always){
-            candidates.addAll(FieldValueGeneratorFactory.createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month).generateCandidates(1, date.dayOfMonth().getMaximumValue()));
+        if (daysOfMonthCronField.getExpression() instanceof Always && daysOfWeekCronField.getExpression() instanceof Always) {
+            candidates.addAll(createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month)
+                    .generateCandidates(1, lengthOfMonth));
+        } else if (daysOfMonthCronField.getExpression() instanceof QuestionMark) {
+            // the day of week calculator must get a -1 value to indicate its generating the first value of the month
+            candidates.addAll(createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, year, month, mondayDoWValue)
+                    .generateCandidates(-1, lengthOfMonth));
+        } else if (daysOfWeekCronField.getExpression() instanceof QuestionMark) {
+            candidates.addAll(createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month)
+                    .generateCandidates(1, lengthOfMonth));
         } else {
-            if(daysOfMonthCronField.getExpression() instanceof QuestionMark){
-            	// the day of week calculator must get a -1 value to indicate its generating the first value of the month
-                candidates.addAll(FieldValueGeneratorFactory.createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, year, month, mondayDoWValue).generateCandidates(-1, date.dayOfMonth().getMaximumValue()));
-            }else{
-                if(daysOfWeekCronField.getExpression() instanceof QuestionMark){
-                    candidates.addAll(FieldValueGeneratorFactory.createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month).generateCandidates(1, date.dayOfMonth().getMaximumValue()));
-                }else{
-                    candidates.addAll(FieldValueGeneratorFactory.createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, year, month, mondayDoWValue).generateCandidates(1, date.dayOfMonth().getMaximumValue()));
-                    candidates.addAll(FieldValueGeneratorFactory.createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month).generateCandidates(1, date.dayOfMonth().getMaximumValue()));
-                }
-            }
+            candidates.addAll(createDayOfWeekValueGeneratorInstance(daysOfWeekCronField, year, month, mondayDoWValue)
+                    .generateCandidates(1, lengthOfMonth));
+            candidates.addAll(createDayOfMonthValueGeneratorInstance(daysOfMonthCronField, year, month)
+                    .generateCandidates(1, lengthOfMonth));
         }
         List<Integer> candidatesList = Lists.newArrayList(candidates);
         Collections.sort(candidatesList);
         return candidatesList;
     }
 
-    private DateTime initDateTime(int years, int monthsOfYear, int dayOfMonth,
-                                  int hoursOfDay, int minutesOfHour, int secondsOfMinute, DateTimeZone timeZone) {
-        DateTime date =
-                new DateTime(0, 1, 1, 0, 0, 0, timeZone)
+    private ZonedDateTime initDateTime(int years, int monthsOfYear, int dayOfMonth,
+                                  int hoursOfDay, int minutesOfHour, int secondsOfMinute, ZoneId timeZone) {
+        ZonedDateTime date =
+                ZonedDateTime.of(LocalDateTime.of(0, 1, 1, 0, 0, 0), timeZone)
                         .plusYears(years)
                         .plusMonths(monthsOfYear - 1)
                         .plusDays(dayOfMonth - 1)
@@ -445,22 +447,22 @@ public class ExecutionTime {
                 hoursOfDay, minutesOfHour, secondsOfMinute, timeZone);
     }
 
-    private DateTime ensureSameDate(DateTime date, int years, int monthsOfYear, int dayOfMonth,
-                                    int hoursOfDay, int minutesOfHour, int secondsOfMinute, DateTimeZone timeZone){
-        if(date.getSecondOfMinute()!=secondsOfMinute){
-            date = date.plusSeconds(secondsOfMinute-date.getSecondOfMinute());
+    private ZonedDateTime ensureSameDate(ZonedDateTime date, int years, int monthsOfYear, int dayOfMonth,
+                                    int hoursOfDay, int minutesOfHour, int secondsOfMinute, ZoneId timeZone){
+        if(date.getSecond()!=secondsOfMinute){
+            date = date.plusSeconds(secondsOfMinute-date.getSecond());
         }
-        if(date.getMinuteOfHour()!=minutesOfHour){
-            date = date.plusMinutes(minutesOfHour-date.getMinuteOfHour());
+        if(date.getMinute()!=minutesOfHour){
+            date = date.plusMinutes(minutesOfHour-date.getMinute());
         }
-        if(date.getHourOfDay()!=hoursOfDay){
-            date = date.plusHours(hoursOfDay-date.getHourOfDay());
+        if(date.getHour()!=hoursOfDay){
+            date = date.plusHours(hoursOfDay-date.getHour());
         }
         if(date.getDayOfMonth()!=dayOfMonth){
             date = date.plusDays(dayOfMonth-date.getDayOfMonth());
         }
-        if(date.getMonthOfYear()!=monthsOfYear){
-            date = date.plusMonths(monthsOfYear-date.getMonthOfYear());
+        if(date.getMonthValue()!=monthsOfYear){
+            date = date.plusMonths(monthsOfYear-date.getMonthValue());
         }
         if(date.getYear()!=years){
             date = date.plusYears(years-date.getYear());
diff --git a/src/main/java/com/cronutils/model/time/generator/BetweenDayOfWeekValueGenerator.java b/src/main/java/com/cronutils/model/time/generator/BetweenDayOfWeekValueGenerator.java
index 4f10930..ca1dda0 100644
--- a/src/main/java/com/cronutils/model/time/generator/BetweenDayOfWeekValueGenerator.java
+++ b/src/main/java/com/cronutils/model/time/generator/BetweenDayOfWeekValueGenerator.java
@@ -1,5 +1,12 @@
 package com.cronutils.model.time.generator;
 
+import java.time.LocalDate;
+import java.util.Collections;
+import java.util.List;
+import java.util.Set;
+
+import org.apache.commons.lang3.Validate;
+
 import com.cronutils.mapper.WeekDay;
 import com.cronutils.model.field.CronField;
 import com.cronutils.model.field.CronFieldName;
@@ -9,12 +16,6 @@ import com.cronutils.model.field.expression.FieldExpression;
 import com.cronutils.parser.CronParserField;
 import com.google.common.collect.Lists;
 import com.google.common.collect.Sets;
-import org.apache.commons.lang3.Validate;
-import org.joda.time.DateTime;
-
-import java.util.Collections;
-import java.util.List;
-import java.util.Set;
 /*
  * Copyright 2015 jmrozanec
  * Licensed under the Apache License, Version 2.0 (the "License");
@@ -124,6 +125,6 @@ class BetweenDayOfWeekValueGenerator extends FieldValueGenerator {
 
 	@Override
 	public boolean isMatch(int value) {
-        return dowValidValues.contains(new DateTime(year, month, value, 0, 0).getDayOfWeek());
+        return dowValidValues.contains(LocalDate.of(year, month, value).getDayOfWeek().getValue());
 	}
 }
diff --git a/src/main/java/com/cronutils/model/time/generator/EveryFieldValueGenerator.java b/src/main/java/com/cronutils/model/time/generator/EveryFieldValueGenerator.java
index 6aaf48f..b6d02ff 100644
--- a/src/main/java/com/cronutils/model/time/generator/EveryFieldValueGenerator.java
+++ b/src/main/java/com/cronutils/model/time/generator/EveryFieldValueGenerator.java
@@ -1,15 +1,16 @@
 package com.cronutils.model.time.generator;
 
+import java.time.ZonedDateTime;
+import java.util.List;
+
+import org.slf4j.Logger;
+import org.slf4j.LoggerFactory;
+
 import com.cronutils.model.field.CronField;
 import com.cronutils.model.field.expression.Every;
 import com.cronutils.model.field.expression.FieldExpression;
 import com.google.common.annotations.VisibleForTesting;
 import com.google.common.collect.Lists;
-import org.joda.time.DateTime;
-import org.slf4j.Logger;
-import org.slf4j.LoggerFactory;
-
-import java.util.List;
 /*
  * Copyright 2015 jmrozanec
  * Licensed under the Apache License, Version 2.0 (the "License");
@@ -29,7 +30,7 @@ class EveryFieldValueGenerator extends FieldValueGenerator {
         super(cronField);
         log.trace(String.format(
                 "processing \"%s\" at %s",
-                cronField.getExpression().asString(), DateTime.now()
+                cronField.getExpression().asString(), ZonedDateTime.now()
         ));
     }
 
diff --git a/src/main/java/com/cronutils/model/time/generator/FieldValueGenerator.java b/src/main/java/com/cronutils/model/time/generator/FieldValueGenerator.java
index 01ad83f..25c6241 100644
--- a/src/main/java/com/cronutils/model/time/generator/FieldValueGenerator.java
+++ b/src/main/java/com/cronutils/model/time/generator/FieldValueGenerator.java
@@ -2,6 +2,11 @@ package com.cronutils.model.time.generator;
 
 import java.util.Collections;
 import java.util.List;
+
+import org.apache.commons.lang3.Validate;
+
+import com.cronutils.model.field.CronField;
+import com.cronutils.model.field.expression.FieldExpression;
 /*
  * Copyright 2015 jmrozanec
  * Licensed under the Apache License, Version 2.0 (the "License");
diff --git a/src/main/java/com/cronutils/model/time/generator/OnDayOfMonthValueGenerator.java b/src/main/java/com/cronutils/model/time/generator/OnDayOfMonthValueGenerator.java
index f2e85fa..92ba310 100644
--- a/src/main/java/com/cronutils/model/time/generator/OnDayOfMonthValueGenerator.java
+++ b/src/main/java/com/cronutils/model/time/generator/OnDayOfMonthValueGenerator.java
@@ -1,14 +1,17 @@
 package com.cronutils.model.time.generator;
 
+import java.time.DayOfWeek;
+import java.time.LocalDate;
+import java.util.List;
+
+import org.apache.commons.lang3.Validate;
+
 import com.cronutils.model.field.CronField;
 import com.cronutils.model.field.CronFieldName;
 import com.cronutils.model.field.expression.FieldExpression;
 import com.cronutils.model.field.expression.On;
 import com.google.common.collect.Lists;
-import org.apache.commons.lang3.Validate;
-import org.joda.time.DateTime;
 
-import java.util.List;
 /*
  * Copyright 2015 jmrozanec
  * Licensed under the Apache License, Version 2.0 (the "License");
@@ -24,19 +27,21 @@ import java.util.List;
 class OnDayOfMonthValueGenerator extends FieldValueGenerator {
     private int year;
     private int month;
+
     public OnDayOfMonthValueGenerator(CronField cronField, int year, int month) {
         super(cronField);
-        Validate.isTrue(CronFieldName.DAY_OF_MONTH.equals(cronField.getField()), "CronField does not belong to day of month");
+        Validate.isTrue(CronFieldName.DAY_OF_MONTH.equals(cronField.getField()), "CronField does not belong to day of" +
+                " month");
         this.year = year;
         this.month = month;
     }
 
     @Override
     public int generateNextValue(int reference) throws NoSuchValueException {
-        On on = ((On)cronField.getExpression());
+        On on = ((On) cronField.getExpression());
         int value = generateValue(on, year, month);
 
-        if(value<=reference){
+        if (value <= reference) {
             throw new NoSuchValueException();
         }
         return value;
@@ -44,9 +49,9 @@ class OnDayOfMonthValueGenerator extends FieldValueGenerator {
 
     @Override
     public int generatePreviousValue(int reference) throws NoSuchValueException {
-        On on = ((On)cronField.getExpression());
+        On on = ((On) cronField.getExpression());
         int value = generateValue(on, year, month);
-        if(value>=reference){
+        if (value >= reference) {
             throw new NoSuchValueException();
         }
         return value;
@@ -54,23 +59,25 @@ class OnDayOfMonthValueGenerator extends FieldValueGenerator {
 
     @Override
     protected List<Integer> generateCandidatesNotIncludingIntervalExtremes(int start, int end) {
-        List<Integer>values = Lists.newArrayList();
+        List<Integer> values = Lists.newArrayList();
         try {
             int reference = generateNextValue(start);
-            while(reference<end){
+            while (reference < end) {
                 values.add(reference);
-                reference=generateNextValue(reference);
+                reference = generateNextValue(reference);
             }
-        } catch (NoSuchValueException e) {}
+        } catch (NoSuchValueException e) {
+        }
         return values;
     }
 
     @Override
     public boolean isMatch(int value) {
-        On on = ((On)cronField.getExpression());
+        On on = ((On) cronField.getExpression());
         try {
             return value == generateValue(on, year, month);
-        } catch (NoSuchValueException ignored) {}//we just skip, since we generate values until we get the exception
+        } catch (NoSuchValueException ignored) {
+        }//we just skip, since we generate values until we get the exception
         return false;
     }
 
@@ -80,34 +87,32 @@ class OnDayOfMonthValueGenerator extends FieldValueGenerator {
     }
 
     private int generateValue(On on, int year, int month) throws NoSuchValueException {
-        int time = on.getTime().getValue();
-        switch (on.getSpecialChar().getValue()){
+        int dayOfMonth = on.getTime().getValue();
+        switch (on.getSpecialChar().getValue()) {
             case L:
-                return new DateTime(year, month, 1, 1, 1).dayOfMonth().getMaximumValue();
+                return LocalDate.of(year, month, 1).lengthOfMonth();
             case W: // First work day of the week
-                DateTime doM = new DateTime(year, month, time, 1, 1);
-                if(doM.getDayOfWeek()==6){//dayOfWeek is Saturday!
-                    if(time==1){//first day in month is Saturday! We execute on Monday
+                LocalDate doM = LocalDate.of(year, month, dayOfMonth);
+                if (doM.getDayOfWeek() == DayOfWeek.SATURDAY) {//dayOfWeek is Saturday!
+                    if (dayOfMonth == 1) {//first day in month is Saturday! We execute on Monday
                         return 3;
                     }
-                    return time-1;
+                    return dayOfMonth - 1;
                 }
-                if(doM.getDayOfWeek()==7){ // dayOfWeek is Sunday
-                    if((time+1)<=doM.dayOfMonth().getMaximumValue()){
-                        return time+1;
+                if (doM.getDayOfWeek() == DayOfWeek.SUNDAY) { // dayOfWeek is Sunday
+                    if ((dayOfMonth + 1) <= doM.lengthOfMonth()) {
+                        return dayOfMonth + 1;
                     }
                 }
-                return time;  // first day of week is a weekday            
+                return dayOfMonth;  // first day of week is a weekday            
             case LW:
-                DateTime lastDayOfMonth =
-                        new DateTime(year, month, new DateTime(year, month, 1, 1, 1)
-                                .dayOfMonth().getMaximumValue(), 1, 1);
-                int dow = lastDayOfMonth.getDayOfWeek();
+                LocalDate lastDayOfMonth = LocalDate.of(year, month, LocalDate.of(year, month, 1).lengthOfMonth());
+                int dow = lastDayOfMonth.getDayOfWeek().getValue();
                 int diff = dow - 5;
-                if(diff > 0){
-                    return lastDayOfMonth.minusDays(diff).dayOfMonth().get();
+                if (diff > 0) {
+                    return lastDayOfMonth.minusDays(diff).getDayOfMonth();
                 }
-                return lastDayOfMonth.dayOfMonth().get();
+                return lastDayOfMonth.getDayOfMonth();
         }
         throw new NoSuchValueException();
     }
diff --git a/src/main/java/com/cronutils/model/time/generator/OnDayOfWeekValueGenerator.java b/src/main/java/com/cronutils/model/time/generator/OnDayOfWeekValueGenerator.java
index 3798df9..eddad8b 100644
--- a/src/main/java/com/cronutils/model/time/generator/OnDayOfWeekValueGenerator.java
+++ b/src/main/java/com/cronutils/model/time/generator/OnDayOfWeekValueGenerator.java
@@ -1,5 +1,11 @@
 package com.cronutils.model.time.generator;
 
+import java.time.DayOfWeek;
+import java.time.LocalDate;
+import java.util.List;
+
+import org.apache.commons.lang3.Validate;
+
 import com.cronutils.mapper.ConstantsMapper;
 import com.cronutils.mapper.WeekDay;
 import com.cronutils.model.field.CronField;
@@ -7,10 +13,6 @@ import com.cronutils.model.field.CronFieldName;
 import com.cronutils.model.field.expression.FieldExpression;
 import com.cronutils.model.field.expression.On;
 import com.google.common.collect.Lists;
-import org.apache.commons.lang3.Validate;
-import org.joda.time.DateTime;
-
-import java.util.List;
 /*
  * Copyright 2015 jmrozanec
  * Licensed under the Apache License, Version 2.0 (the "License");
@@ -96,11 +98,11 @@ class OnDayOfWeekValueGenerator extends FieldValueGenerator {
     }
 
     private int generateHashValues(On on, int year, int month){
-        int dowForFirstDoM = new DateTime(year, month, 1, 1, 1).getDayOfWeek();//1-7
-        int requiredDoW = ConstantsMapper.weekDayMapping(mondayDoWValue, ConstantsMapper.JODATIME_WEEK_DAY, on.getTime().getValue());//to normalize to joda-time value
+        DayOfWeek dowForFirstDoM = LocalDate.of(year, month, 1).getDayOfWeek();//1-7
+        int requiredDoW = ConstantsMapper.weekDayMapping(mondayDoWValue, ConstantsMapper.JAVA8, on.getTime().getValue());//to normalize to joda-time value
         int requiredNth = on.getNth().getValue();
         int baseDay = 1;//day 1 from given month
-        int diff = dowForFirstDoM - requiredDoW;
+        int diff = dowForFirstDoM.getValue() - requiredDoW;
         if(diff == 0){
             //base day remains the same
         }
@@ -114,20 +116,20 @@ class OnDayOfWeekValueGenerator extends FieldValueGenerator {
     }
 
     private int generateLValues(On on, int year, int month) throws NoSuchValueException {
-        int lastDoM = new DateTime(year, month, 1, 1, 1).dayOfMonth().getMaximumValue();
-        DateTime lastDoMDateTime = new DateTime(year, month, lastDoM, 1, 1);
-        int dowForLastDoM = lastDoMDateTime.getDayOfWeek();//1-7
-        int requiredDoW = ConstantsMapper.weekDayMapping(mondayDoWValue, ConstantsMapper.JODATIME_WEEK_DAY, on.getTime().getValue());//to normalize to joda-time value
+        int lastDoM = LocalDate.of(year, month, 1).lengthOfMonth();
+        LocalDate lastDoMDateTime = LocalDate.of(year, month, lastDoM);
+        int dowForLastDoM = lastDoMDateTime.getDayOfWeek().getValue();//1-7
+        int requiredDoW = ConstantsMapper.weekDayMapping(mondayDoWValue, ConstantsMapper.JAVA8, on.getTime().getValue());//to normalize to joda-time value
         int dowDiff = dowForLastDoM - requiredDoW;
 
         if(dowDiff==0){
-            return lastDoMDateTime.dayOfMonth().get();
+            return lastDoMDateTime.getDayOfMonth();
         }
         if(dowDiff<0){
-            return lastDoMDateTime.minusDays(dowForLastDoM+(7-requiredDoW)).dayOfMonth().get();
+            return lastDoMDateTime.minusDays(dowForLastDoM+(7-requiredDoW)).getDayOfMonth();
         }
         if(dowDiff>0){
-            return lastDoMDateTime.minusDays(dowDiff).dayOfMonth().get();
+            return lastDoMDateTime.minusDays(dowDiff).getDayOfMonth();
         }
         throw new NoSuchValueException();
     }
@@ -145,9 +147,9 @@ class OnDayOfWeekValueGenerator extends FieldValueGenerator {
      */
 	private int generateNoneValues(On on, int year, int month, int reference) {
 		// the day of week the first of the month is on
-		int dowForFirstDoM = new DateTime(year, month, 1, 1, 1).getDayOfWeek();// 1-7
+		int dowForFirstDoM = LocalDate.of(year, month, 1).getDayOfWeek().getValue();// 1-7
 		// the day of week we need, normalize to jodatime
-		int requiredDoW = ConstantsMapper.weekDayMapping(mondayDoWValue, ConstantsMapper.JODATIME_WEEK_DAY, on.getTime().getValue());
+		int requiredDoW = ConstantsMapper.weekDayMapping(mondayDoWValue, ConstantsMapper.JAVA8, on.getTime().getValue());
 		// the first day of the month
 		int baseDay = 1;// day 1 from given month
 		// the difference between the days of week


Test patch:
diff --git a/src/test/java/com/cronutils/Issue55UnexpectedExecutionTimes.java b/src/test/java/com/cronutils/Issue55UnexpectedExecutionTimes.java
index 76c75ef..7181b32 100644
--- a/src/test/java/com/cronutils/Issue55UnexpectedExecutionTimes.java
+++ b/src/test/java/com/cronutils/Issue55UnexpectedExecutionTimes.java
@@ -1,5 +1,16 @@
 package com.cronutils;
 
+import static org.junit.Assert.assertEquals;
+
+import java.time.Instant;
+import java.time.ZoneOffset;
+import java.time.ZonedDateTime;
+import java.util.ArrayList;
+import java.util.List;
+
+import org.junit.Before;
+import org.junit.Test;
+
 import com.cronutils.model.Cron;
 import com.cronutils.model.definition.CronConstraint;
 import com.cronutils.model.definition.CronDefinition;
@@ -8,16 +19,6 @@ import com.cronutils.model.field.CronFieldName;
 import com.cronutils.model.field.expression.QuestionMark;
 import com.cronutils.model.time.ExecutionTime;
 import com.cronutils.parser.CronParser;
-import org.joda.time.DateTime;
-import org.joda.time.DateTimeZone;
-import org.joda.time.Instant;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.ArrayList;
-import java.util.List;
-
-import static org.junit.Assert.assertEquals;
 
 public class Issue55UnexpectedExecutionTimes {
     private CronDefinition cronDefinition;
@@ -56,8 +57,8 @@ public class Issue55UnexpectedExecutionTimes {
     public void testOnceEveryThreeDaysNoInstantsWithinTwoDays(){
         System.out.println();
         System.out.println("TEST1 - expecting 0 instants");
-        DateTime startTime = new DateTime(0, DateTimeZone.UTC);
-        final DateTime endTime = startTime.plusDays(2);
+        ZonedDateTime startTime = ZonedDateTime.of(0, 1, 1, 0, 0, 0, 0, ZoneOffset.UTC);
+        final ZonedDateTime endTime = startTime.plusDays(2);
         final CronParser parser = new CronParser(cronDefinition);
         final Cron cron = parser.parse("0 0 */3 * ?");
         final ExecutionTime executionTime = ExecutionTime.forCron(cron);
@@ -72,8 +73,8 @@ public class Issue55UnexpectedExecutionTimes {
     public void testOnceAMonthTwelveInstantsInYear(){
         System.out.println();
         System.out.println("TEST2 - expecting 12 instants");
-        DateTime startTime = new DateTime(0, DateTimeZone.UTC);
-        final DateTime endTime = startTime.plusDays(365);
+        ZonedDateTime startTime = ZonedDateTime.of(0, 1, 1, 0, 0, 0, 0, ZoneOffset.UTC);
+        final ZonedDateTime endTime = startTime.plusYears(1);
         final CronParser parser = new CronParser(cronDefinition);
         final Cron cron = parser.parse("0 12 L * ?");
         final ExecutionTime executionTime = ExecutionTime.forCron(cron);
@@ -83,10 +84,10 @@ public class Issue55UnexpectedExecutionTimes {
         assertEquals(12, instants.size());
     }
 
-    List<Instant> getInstants(ExecutionTime executionTime, DateTime startTime, DateTime endTime){
-        List<Instant> instantList = new ArrayList<Instant>();
-        DateTime next = executionTime.nextExecution(startTime);
-        while(next.isBefore(endTime.toDateTime())){
+    private List<Instant> getInstants(ExecutionTime executionTime, ZonedDateTime startTime, ZonedDateTime endTime){
+        List<Instant> instantList = new ArrayList<>();
+        ZonedDateTime next = executionTime.nextExecution(startTime);
+        while(next.isBefore(endTime)){
             instantList.add(next.toInstant());
             next = executionTime.nextExecution(next);
         }
diff --git a/src/test/java/com/cronutils/OpenIssuesTest.java b/src/test/java/com/cronutils/OpenIssuesTest.java
index 54c7984..df7ce4e 100644
--- a/src/test/java/com/cronutils/OpenIssuesTest.java
+++ b/src/test/java/com/cronutils/OpenIssuesTest.java
@@ -1,35 +1,25 @@
 package com.cronutils;
 
+import java.text.ParseException;
+import java.time.ZonedDateTime;
+import java.time.format.DateTimeFormatter;
+
+import org.junit.Test;
+
 import com.cronutils.model.Cron;
 import com.cronutils.model.CronType;
-import com.cronutils.model.definition.CronDefinition;
 import com.cronutils.model.definition.CronDefinitionBuilder;
 import com.cronutils.model.time.ExecutionTime;
 import com.cronutils.parser.CronParser;
-import org.joda.time.DateTime;
-import org.joda.time.DateTimeZone;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.text.DateFormat;
-import java.text.ParseException;
-import java.text.SimpleDateFormat;
-import java.util.Date;
-
-import static org.hamcrest.core.AnyOf.anyOf;
-import static org.hamcrest.core.Is.is;
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertThat;
 
 public class OpenIssuesTest {
-    DateFormat dfSimple = new SimpleDateFormat("hh:mm:ss MM/dd/yyyy a");
-    DateFormat df = new SimpleDateFormat("hh:mm:ss EEE, MMM dd yyyy a");
+    DateTimeFormatter dfSimple = DateTimeFormatter.ofPattern("hh:mm:ss MM/dd/yyyy a X");
+    DateTimeFormatter df = DateTimeFormatter.ofPattern("hh:mm:ss EEE, MMM dd yyyy a X");
 
     @Test
-    public void testBasicCron() throws ParseException
-    {
-        printDate("3:15:00 11/20/2015 PM");
-        printDate("3:15:00 11/27/2015 PM");
+    public void testBasicCron() throws ParseException {
+        printDate("03:15:00 11/20/2015 PM Z");
+        printDate("03:15:00 11/27/2015 PM Z");
 // printDate("3:15:00 11/29/2015 PM");
 // printDate("3:15:00 11/30/2015 PM");
 // printDate("3:15:00 12/01/2015 PM");
@@ -39,10 +29,9 @@ public class OpenIssuesTest {
 // printDate("3:15:00 12/31/2015 PM");
     }
 
-    private void printDate(String startDate) throws ParseException
-    {
-        Date now = dfSimple.parse(startDate);
-        System.out.println("Starting: "+ df.format(now));
+    private void printDate(String startDate) throws ParseException {
+        ZonedDateTime now = ZonedDateTime.parse(startDate, dfSimple);
+        System.out.println("Starting: " + df.format(now));
         printNextDate(now, "0 6 * * 0");//Sunday
         printNextDate(now, "0 6 * * 1");
         printNextDate(now, "0 6 * * 2");
@@ -52,23 +41,18 @@ public class OpenIssuesTest {
         printNextDate(now, "0 6 * * 6");
     }
 
-    private void printNextDate(Date now, String cronString)
-    {
-        Date date = nextSchedule(cronString, now);
+    private void printNextDate(ZonedDateTime now, String cronString) {
+        ZonedDateTime date = nextSchedule(cronString, now);
         System.out.println("Next time: " + df.format(date));
     }
 
-    public static Date nextSchedule(String cronString, Date lastExecution)
-    {
-        DateTime now = new DateTime(lastExecution);
-        CronParser cronParser =new CronParser(
-                CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX));
+    private static ZonedDateTime nextSchedule(String cronString, ZonedDateTime lastExecution) {
+        CronParser cronParser = new CronParser(CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX));
         Cron cron = cronParser.parse(cronString);
 
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime nextExecution = executionTime.nextExecution(now);
 
-        return nextExecution.toDate();
+        return executionTime.nextExecution(lastExecution);
     }
 }
 
diff --git a/src/test/java/com/cronutils/mapper/ConstantsMapperTest.java b/src/test/java/com/cronutils/mapper/ConstantsMapperTest.java
index 3e36408..e6795ec 100644
--- a/src/test/java/com/cronutils/mapper/ConstantsMapperTest.java
+++ b/src/test/java/com/cronutils/mapper/ConstantsMapperTest.java
@@ -20,7 +20,7 @@ public class ConstantsMapperTest {
     @Test
     public void testWeekDayMappingQuartzToJodatime() throws Exception {
         WeekDay quartz = ConstantsMapper.QUARTZ_WEEK_DAY;
-        WeekDay jodatime = ConstantsMapper.JODATIME_WEEK_DAY;
+        WeekDay jodatime = ConstantsMapper.JAVA8;
         for(int j=2; j<8; j++){
             assertEquals(j-1, ConstantsMapper.weekDayMapping(quartz, jodatime, j));
         }
@@ -30,7 +30,7 @@ public class ConstantsMapperTest {
     @Test
     public void testWeekDayMappingJodatimeToQuartz() throws Exception {
         WeekDay quartz = ConstantsMapper.QUARTZ_WEEK_DAY;
-        WeekDay jodatime = ConstantsMapper.JODATIME_WEEK_DAY;
+        WeekDay jodatime = ConstantsMapper.JAVA8;
         for(int j=1; j<7; j++){
             assertEquals(j+1, ConstantsMapper.weekDayMapping(jodatime, quartz, j));
         }
@@ -58,7 +58,7 @@ public class ConstantsMapperTest {
     @Test
     public void testWeekDayMappingCrontabToJodatime() throws Exception {
         WeekDay crontab = ConstantsMapper.CRONTAB_WEEK_DAY;
-        WeekDay jodatime = ConstantsMapper.JODATIME_WEEK_DAY;
+        WeekDay jodatime = ConstantsMapper.JAVA8;
         for(int j=1; j<7; j++){
             assertEquals(j, ConstantsMapper.weekDayMapping(crontab, jodatime, j));
         }
@@ -68,7 +68,7 @@ public class ConstantsMapperTest {
     @Test
     public void testWeekDayMappingJodatimeToCrontab() throws Exception {
         WeekDay crontab = ConstantsMapper.CRONTAB_WEEK_DAY;
-        WeekDay jodatime = ConstantsMapper.JODATIME_WEEK_DAY;
+        WeekDay jodatime = ConstantsMapper.JAVA8;
         for(int j=1; j<7; j++){
             assertEquals(j, ConstantsMapper.weekDayMapping(jodatime, crontab, j));
         }
diff --git a/src/test/java/com/cronutils/model/time/ExecutionTimeCron4jIntegrationTest.java b/src/test/java/com/cronutils/model/time/ExecutionTimeCron4jIntegrationTest.java
index 96487fc..bd0dff5 100644
--- a/src/test/java/com/cronutils/model/time/ExecutionTimeCron4jIntegrationTest.java
+++ b/src/test/java/com/cronutils/model/time/ExecutionTimeCron4jIntegrationTest.java
@@ -1,19 +1,19 @@
 package com.cronutils.model.time;
 
-import com.cronutils.model.CronType;
-import com.cronutils.model.definition.CronDefinitionBuilder;
-import com.cronutils.parser.CronParser;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotEquals;
+import static org.junit.Assert.assertTrue;
+
+import java.time.ZonedDateTime;
 
-import org.joda.time.DateTime;
 import org.junit.Before;
 import org.junit.Test;
 import org.slf4j.Logger;
 import org.slf4j.LoggerFactory;
 
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertNotEquals;
-import static org.junit.Assert.assertTrue;
-import static org.junit.Assert.fail;
+import com.cronutils.model.CronType;
+import com.cronutils.model.definition.CronDefinitionBuilder;
+import com.cronutils.parser.CronParser;
 
 /*
  * Copyright 2015 jmrozanec
@@ -50,14 +50,14 @@ public class ExecutionTimeCron4jIntegrationTest {
      */
     @Test
     public void testEveryWeekdayAt6() throws Exception {
-        DateTime lastRun = new DateTime();
+        ZonedDateTime lastRun = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(cron4jCronParser.parse(EVERY_WEEKDAY_AT_6));
         
         // iterate through the next 8 days so we roll over for a week
         // and make sure the next run time is always in the future from the prior run time
 		for (int i = 0; i < 8; i++) {
-			
-			DateTime nextRun = executionTime.nextExecution(lastRun);
+
+            ZonedDateTime nextRun = executionTime.nextExecution(lastRun);
 			log.debug("LastRun = [{}]", lastRun);
 			log.debug("NextRun = [{}]", nextRun);
 
@@ -73,18 +73,18 @@ public class ExecutionTimeCron4jIntegrationTest {
      */
     @Test
     public void testEvery2Hours() throws Exception {
-        DateTime lastRun = new DateTime();
+        ZonedDateTime lastRun = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(cron4jCronParser.parse(EVERY_2_HOURS));
         
         // iterate through the next 36 hours so we roll over the to the next day
         // and make sure the next run time is always in the future from the prior run time
 		for (int i = 0; i < 36; i++) {
-			
-			DateTime nextRun = executionTime.nextExecution(lastRun);
+
+            ZonedDateTime nextRun = executionTime.nextExecution(lastRun);
 			log.debug("LastRun = [{}]", lastRun);
 			log.debug("NextRun = [{}]", nextRun);
 
-			assertTrue(nextRun.getHourOfDay() % 2 == 0);
+			assertTrue(nextRun.getHour() % 2 == 0);
 			assertTrue(lastRun.isBefore(nextRun));
             lastRun = lastRun.plusHours(1);
 		}
@@ -95,18 +95,18 @@ public class ExecutionTimeCron4jIntegrationTest {
      */
     @Test
     public void testEvery15Minutes() throws Exception {
-        DateTime lastRun = new DateTime();
+        ZonedDateTime lastRun = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(cron4jCronParser.parse(EVERY_15_MINUTES));
         
         // iterate through the next 75 minutes so we roll over the top of the hour
         // and make sure the next run time is always in the future from the prior run time
 		for (int i = 0; i < 75; i++) {
-			
-			DateTime nextRun = executionTime.nextExecution(lastRun);
+
+            ZonedDateTime nextRun = executionTime.nextExecution(lastRun);
 			log.debug("LastRun = [{}]", lastRun);
 			log.debug("NextRun = [{}]", nextRun);
 
-			assertTrue(nextRun.getMinuteOfHour() % 15 == 0);
+			assertTrue(nextRun.getMinute() % 15 == 0);
 			assertTrue(lastRun.isBefore(nextRun));
             lastRun = lastRun.plusMinutes(1);
 		}
@@ -117,10 +117,10 @@ public class ExecutionTimeCron4jIntegrationTest {
      */
     @Test
     public void testDayOfWeekOverridesAlwaysAtDayOfMonth() throws Exception {
-        DateTime now = DateTime.now();
+        ZonedDateTime now = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(cron4jCronParser.parse(EVERY_MONDAY_AT_18));
-        DateTime next = executionTime.nextExecution(now);
-        assertEquals(1, next.getDayOfWeek());
+        ZonedDateTime next = executionTime.nextExecution(now);
+        assertEquals(1, next.getDayOfWeek().getValue());
         assertTrue(now.isBefore(next));
     }
 
@@ -129,9 +129,9 @@ public class ExecutionTimeCron4jIntegrationTest {
      */
     @Test
     public void testDayOfMonthOverridesAlwaysAtDayOfWeek() throws Exception {
-        DateTime now = DateTime.now();
+        ZonedDateTime now = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(cron4jCronParser.parse("0 18 1 * *"));
-        DateTime next = executionTime.nextExecution(now);
+        ZonedDateTime next = executionTime.nextExecution(now);
         assertEquals(1, next.getDayOfMonth());
         assertTrue(now.isBefore(next));
     }
@@ -141,10 +141,10 @@ public class ExecutionTimeCron4jIntegrationTest {
      */
     @Test
     public void testNextExecutionOverNextExecution() throws Exception {
-        DateTime now = DateTime.now();
+        ZonedDateTime now = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(cron4jCronParser.parse(EVERY_MONDAY_AT_18));
-        DateTime next = executionTime.nextExecution(now);
-        DateTime nextNext = executionTime.nextExecution(next);
+        ZonedDateTime next = executionTime.nextExecution(now);
+        ZonedDateTime nextNext = executionTime.nextExecution(next);
         assertTrue(now.isBefore(next));
         assertTrue(next.isBefore(nextNext));
     }
diff --git a/src/test/java/com/cronutils/model/time/ExecutionTimeCustomDefinitionIntegrationTest.java b/src/test/java/com/cronutils/model/time/ExecutionTimeCustomDefinitionIntegrationTest.java
index c820492..4f36a96 100644
--- a/src/test/java/com/cronutils/model/time/ExecutionTimeCustomDefinitionIntegrationTest.java
+++ b/src/test/java/com/cronutils/model/time/ExecutionTimeCustomDefinitionIntegrationTest.java
@@ -1,15 +1,17 @@
 package com.cronutils.model.time;
 
+import static java.time.ZoneOffset.UTC;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+import java.time.ZonedDateTime;
+
+import org.junit.Test;
+
 import com.cronutils.model.Cron;
 import com.cronutils.model.definition.CronDefinition;
 import com.cronutils.model.definition.CronDefinitionBuilder;
 import com.cronutils.parser.CronParser;
-import org.joda.time.DateTime;
-import org.joda.time.MutableDateTime;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
 
 public class ExecutionTimeCustomDefinitionIntegrationTest {
 
@@ -27,12 +29,12 @@ public class ExecutionTimeCustomDefinitionIntegrationTest {
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse("*/30 * * * * *");
 
-        DateTime startDateTime = new DateTime(2015, 8, 28, 12, 5, 44, 0);
-        DateTime expectedDateTime = new DateTime(2015, 8, 28, 12, 6, 0, 0);
+        ZonedDateTime startDateTime = ZonedDateTime.of(2015, 8, 28, 12, 5, 44, 0, UTC);
+        ZonedDateTime expectedDateTime = ZonedDateTime.of(2015, 8, 28, 12, 6, 0, 0, UTC);
 
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
 
-        DateTime nextExecutionDateTime = executionTime.nextExecution(startDateTime);
+        ZonedDateTime nextExecutionDateTime = executionTime.nextExecution(startDateTime);
         assertEquals(expectedDateTime, nextExecutionDateTime);
     }
 
@@ -51,19 +53,13 @@ public class ExecutionTimeCustomDefinitionIntegrationTest {
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse("0/30 * * * * *");
 
-        MutableDateTime mutableDateTime = new MutableDateTime();
-        mutableDateTime.setDateTime(2015, 8, 28, 12, 5, 14, 0);
-
-        DateTime startDateTime = mutableDateTime.toDateTime();
-
-        mutableDateTime = new MutableDateTime();
-        mutableDateTime.setDateTime(2015, 8, 28, 12, 5, 30, 0);
 
-        DateTime expectedDateTime = mutableDateTime.toDateTime();
+        ZonedDateTime startDateTime = ZonedDateTime.of(2015, 8, 28, 12, 5, 14, 0, UTC);
+        ZonedDateTime expectedDateTime = ZonedDateTime.of(2015, 8, 28, 12, 5, 30, 0, UTC);
 
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
 
-        DateTime nextExecutionDateTime = executionTime.nextExecution(startDateTime);
+        ZonedDateTime nextExecutionDateTime = executionTime.nextExecution(startDateTime);
         assertEquals(expectedDateTime, nextExecutionDateTime);
     }
 
@@ -86,9 +82,9 @@ public class ExecutionTimeCustomDefinitionIntegrationTest {
 
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse("0 0 */2 * * *");
-        DateTime startDateTime = DateTime.parse("2015-08-28T12:05:14.000-03:00");
+        ZonedDateTime startDateTime = ZonedDateTime.parse("2015-08-28T12:05:14.000-03:00");
 
-        assertTrue(DateTime.parse("2015-08-28T14:00:00.000-03:00").compareTo(ExecutionTime.forCron(cron).nextExecution(startDateTime)) == 0);
+        assertTrue(ZonedDateTime.parse("2015-08-28T14:00:00.000-03:00").compareTo(ExecutionTime.forCron(cron).nextExecution(startDateTime)) == 0);
     }
 
     /**
@@ -110,9 +106,9 @@ public class ExecutionTimeCustomDefinitionIntegrationTest {
 
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse("0 0 /2 * * *");
-        DateTime startDateTime = DateTime.parse("2015-08-28T12:05:14.000-03:00");
+        ZonedDateTime startDateTime = ZonedDateTime.parse("2015-08-28T12:05:14.000-03:00");
 
-        assertTrue(DateTime.parse("2015-08-28T14:00:00.000-03:00").compareTo(ExecutionTime.forCron(cron).nextExecution(startDateTime)) == 0);
+        assertTrue(ZonedDateTime.parse("2015-08-28T14:00:00.000-03:00").compareTo(ExecutionTime.forCron(cron).nextExecution(startDateTime)) == 0);
     }
 
     /**
@@ -140,9 +136,9 @@ public class ExecutionTimeCustomDefinitionIntegrationTest {
 
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse("30 3 * * MON-FRI");
-        DateTime sameDayBeforeEventStartDateTime = DateTime.parse("1970-01-01T00:00:00.000-03:00");
+        ZonedDateTime sameDayBeforeEventStartDateTime = ZonedDateTime.parse("1970-01-01T00:00:00.000-03:00");
         assertEquals(1, ExecutionTime.forCron(cron).nextExecution(sameDayBeforeEventStartDateTime).getDayOfMonth());
-        DateTime sameDayAfterEventStartDateTime = DateTime.parse("1970-01-01T12:00:00.000-03:00");
+        ZonedDateTime sameDayAfterEventStartDateTime = ZonedDateTime.parse("1970-01-01T12:00:00.000-03:00");
         assertEquals(2, ExecutionTime.forCron(cron).nextExecution(sameDayAfterEventStartDateTime).getDayOfMonth());
     }
 }
diff --git a/src/test/java/com/cronutils/model/time/ExecutionTimeQuartzIntegrationTest.java b/src/test/java/com/cronutils/model/time/ExecutionTimeQuartzIntegrationTest.java
index 0707bfc..05cde6d 100644
--- a/src/test/java/com/cronutils/model/time/ExecutionTimeQuartzIntegrationTest.java
+++ b/src/test/java/com/cronutils/model/time/ExecutionTimeQuartzIntegrationTest.java
@@ -1,23 +1,27 @@
 package com.cronutils.model.time;
 
-import com.cronutils.model.Cron;
-import com.cronutils.model.CronType;
-import com.cronutils.model.definition.CronDefinitionBuilder;
-import com.cronutils.parser.CronParser;
+import static java.time.ZoneOffset.UTC;
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.assertTrue;
+
+import java.time.DayOfWeek;
+import java.time.Duration;
+import java.time.LocalDate;
+import java.time.LocalTime;
+import java.time.ZoneId;
+import java.time.ZonedDateTime;
+import java.time.format.DateTimeFormatter;
+import java.time.temporal.ChronoUnit;
 
-import org.joda.time.DateTime;
-import org.joda.time.DateTimeConstants;
-import org.joda.time.DateTimeZone;
-import org.joda.time.Duration;
-import org.joda.time.Interval;
-import org.joda.time.format.DateTimeFormat;
-import org.joda.time.format.DateTimeFormatter;
 import org.junit.Before;
 import org.junit.Test;
 
-import java.text.SimpleDateFormat;
-
-import static org.junit.Assert.*;
+import com.cronutils.model.Cron;
+import com.cronutils.model.CronType;
+import com.cronutils.model.definition.CronDefinitionBuilder;
+import com.cronutils.parser.CronParser;
 
 /*
  * Copyright 2015 jmrozanec
@@ -47,34 +51,34 @@ public class ExecutionTimeQuartzIntegrationTest {
 
     @Test
     public void testNextExecutionEverySecond() throws Exception {
-        DateTime now = truncateToSeconds(DateTime.now());
-        DateTime expected = truncateToSeconds(now.plusSeconds(1));
+        ZonedDateTime now = truncateToSeconds(ZonedDateTime.now());
+        ZonedDateTime expected = truncateToSeconds(now.plusSeconds(1));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(EVERY_SECOND));
         assertEquals(expected, executionTime.nextExecution(now));
     }
 
     @Test
     public void testTimeToNextExecution() throws Exception {
-        DateTime now = truncateToSeconds(DateTime.now());
-        DateTime expected = truncateToSeconds(now.plusSeconds(1));
+        ZonedDateTime now = truncateToSeconds(ZonedDateTime.now());
+        ZonedDateTime expected = truncateToSeconds(now.plusSeconds(1));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(EVERY_SECOND));
-        assertEquals(new Interval(now, expected).toDuration(), executionTime.timeToNextExecution(now));
+        assertEquals(java.time.Duration.between(now, expected), executionTime.timeToNextExecution(now));
     }
 
     @Test
     public void testLastExecution() throws Exception {
-        DateTime now = truncateToSeconds(DateTime.now());
-        DateTime expected = truncateToSeconds(now.minusSeconds(1));
+        ZonedDateTime now = truncateToSeconds(ZonedDateTime.now());
+        ZonedDateTime expected = truncateToSeconds(now.minusSeconds(1));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(EVERY_SECOND));
         assertEquals(expected, executionTime.lastExecution(now));
     }
 
     @Test
     public void testTimeFromLastExecution() throws Exception {
-        DateTime now = truncateToSeconds(DateTime.now());
-        DateTime expected = truncateToSeconds(now.minusSeconds(1));
+        ZonedDateTime now = truncateToSeconds(ZonedDateTime.now());
+        ZonedDateTime expected = truncateToSeconds(now.minusSeconds(1));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(EVERY_SECOND));
-        assertEquals(new Interval(expected, now).toDuration(), executionTime.timeFromLastExecution(now));
+        assertEquals(java.time.Duration.between(expected, now), executionTime.timeToNextExecution(now));
     }
 
     /**
@@ -87,14 +91,14 @@ public class ExecutionTimeQuartzIntegrationTest {
     public void testDoesNotIgnoreMonthOrDayOfWeek(){
         //seconds, minutes, hours, dayOfMonth, month, dayOfWeek
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 11 11 11 11 ?"));
-        DateTime now = new DateTime(2015, 4, 15, 0, 0, 0);
-        DateTime whenToExecuteNext = executionTime.nextExecution(now);
+        ZonedDateTime now = ZonedDateTime.of(2015, 4, 15, 0, 0, 0, 0, UTC);
+        ZonedDateTime whenToExecuteNext = executionTime.nextExecution(now);
         assertEquals(2015, whenToExecuteNext.getYear());
-        assertEquals(11, whenToExecuteNext.getMonthOfYear());
+        assertEquals(11, whenToExecuteNext.getMonthValue());
         assertEquals(11, whenToExecuteNext.getDayOfMonth());
-        assertEquals(11, whenToExecuteNext.getHourOfDay());
-        assertEquals(11, whenToExecuteNext.getMinuteOfHour());
-        assertEquals(0, whenToExecuteNext.getSecondOfMinute());
+        assertEquals(11, whenToExecuteNext.getHour());
+        assertEquals(11, whenToExecuteNext.getMinute());
+        assertEquals(0, whenToExecuteNext.getSecond());
     }
 
     /**
@@ -103,12 +107,12 @@ public class ExecutionTimeQuartzIntegrationTest {
      */
     @Test
     public void testHourlyIntervalTimeFromLastExecution() throws Exception {
-        DateTime now = DateTime.now();
-        DateTime previousHour = now.minusHours(1);
-        String quartzCronExpression = String.format("0 0 %s * * ?", previousHour.getHourOfDay());
+        ZonedDateTime now = ZonedDateTime.now();
+        ZonedDateTime previousHour = now.minusHours(1);
+        String quartzCronExpression = String.format("0 0 %s * * ?", previousHour.getHour());
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(quartzCronExpression));
 
-        assertTrue(executionTime.timeFromLastExecution(now).getStandardMinutes() <= 120);
+        assertTrue(executionTime.timeFromLastExecution(now).toMinutes() <= 120);
     }
 
     /**
@@ -122,9 +126,9 @@ public class ExecutionTimeQuartzIntegrationTest {
         String expression = "0/1 * * 1/1 * ? *";  // every second every day
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(expression));
 
-        DateTime now = new DateTime().withTime(23, 59, 59, 0);
-        DateTime expected = now.plusSeconds(1);
-        DateTime nextExecution = executionTime.nextExecution(now);
+        ZonedDateTime now = ZonedDateTime.of(LocalDate.of(2016, 8, 5), LocalTime.of(23, 59, 59, 0), UTC);
+        ZonedDateTime expected = now.plusSeconds(1);
+        ZonedDateTime nextExecution = executionTime.nextExecution(now);
 
         assertEquals(expected, nextExecution);
     }
@@ -140,9 +144,9 @@ public class ExecutionTimeQuartzIntegrationTest {
         String expression = "0/1 * * 1/1 * ? *";  // every second every day
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(expression));
 
-        DateTime now = new DateTime(2015, 1, 31, 23, 59, 59, 0);
-        DateTime expected = now.plusSeconds(1);
-        DateTime nextExecution = executionTime.nextExecution(now);
+        ZonedDateTime now = ZonedDateTime.of(2015, 1, 31, 23, 59, 59, 0, UTC);
+        ZonedDateTime expected = now.plusSeconds(1);
+        ZonedDateTime nextExecution = executionTime.nextExecution(now);
 
         assertEquals(expected, nextExecution);
     }
@@ -153,9 +157,9 @@ public class ExecutionTimeQuartzIntegrationTest {
     @Test
     public void testTimeShiftingProperlyDone() throws Exception {
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 0/10 22 ? * *"));
-        DateTime nextExecution = executionTime.nextExecution(DateTime.now().withHourOfDay(15).withMinuteOfHour(27));
-        assertEquals(22, nextExecution.getHourOfDay());
-        assertEquals(0, nextExecution.getMinuteOfHour());
+        ZonedDateTime nextExecution = executionTime.nextExecution(ZonedDateTime.now().withHour(15).withMinute(27));
+        assertEquals(22, nextExecution.getHour());
+        assertEquals(0, nextExecution.getMinute());
     }
 
     /**
@@ -171,10 +175,10 @@ public class ExecutionTimeQuartzIntegrationTest {
      */
     @Test
     public void testSaturdayExecutionTime(){
-        DateTime now = DateTime.now();
+        ZonedDateTime now = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 0 3 ? * 6"));
-        DateTime last = executionTime.lastExecution(now);
-        DateTime next = executionTime.nextExecution(now);
+        ZonedDateTime last = executionTime.lastExecution(now);
+        ZonedDateTime next = executionTime.nextExecution(now);
         assertNotEquals(last, next);
     }
 
@@ -183,10 +187,10 @@ public class ExecutionTimeQuartzIntegrationTest {
      */
     @Test
     public void testWeekdayExecutionTime(){
-        DateTime now = DateTime.now();
+        ZonedDateTime now = ZonedDateTime.now();
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 0 3 ? * *"));
-        DateTime last = executionTime.lastExecution(now);
-        DateTime next = executionTime.nextExecution(now);
+        ZonedDateTime last = executionTime.lastExecution(now);
+        ZonedDateTime next = executionTime.nextExecution(now);
         assertNotEquals(last, next);
     }
 
@@ -196,10 +200,10 @@ public class ExecutionTimeQuartzIntegrationTest {
     @Test
     public void testExecutionTimeForRanges(){
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("* 10-20 * * * ? 2099"));
-        DateTime scanTime = DateTime.parse("2016-02-29T11:00:00.000-06:00");
-        DateTime nextTime = executionTime.nextExecution(scanTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-02-29T11:00:00.000-06:00");
+        ZonedDateTime nextTime = executionTime.nextExecution(scanTime);
         assertNotNull(nextTime);
-        assertEquals(10, nextTime.getMinuteOfHour());
+        assertEquals(10, nextTime.getMinute());
     }
 
     /**
@@ -208,10 +212,10 @@ public class ExecutionTimeQuartzIntegrationTest {
     @Test
     public void testLastExecutionTimeForFixedMonth(){
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 30 12 1 9 ? 2010"));
-        DateTime scanTime = DateTime.parse("2016-01-08T11:00:00.000-06:00");
-        DateTime lastTime = executionTime.lastExecution(scanTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-01-08T11:00:00.000-06:00");
+        ZonedDateTime lastTime = executionTime.lastExecution(scanTime);
         assertNotNull(lastTime);
-        assertEquals(9, lastTime.getMonthOfYear());
+        assertEquals(9, lastTime.getMonthValue());
     }
 
     /**
@@ -221,10 +225,10 @@ public class ExecutionTimeQuartzIntegrationTest {
     public void testNextExecutionRightDoWForFixedMonth(){
         //cron format: s,m,H,DoM,M,DoW,Y
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 * * ? 5 1 *"));
-        DateTime scanTime = DateTime.parse("2016-03-06T20:17:28.000-03:00");
-        DateTime nextTime = executionTime.nextExecution(scanTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-03-06T20:17:28.000-03:00");
+        ZonedDateTime nextTime = executionTime.nextExecution(scanTime);
         assertNotNull(nextTime);
-        assertEquals(DateTimeConstants.SUNDAY, nextTime.getDayOfWeek());
+        assertEquals(DayOfWeek.SUNDAY, nextTime.getDayOfWeek());
     }
 
     /**
@@ -234,10 +238,10 @@ public class ExecutionTimeQuartzIntegrationTest {
     public void testNextExecutionRightDoWForFixedYear(){
         //cron format: s,m,H,DoM,M,DoW,Y
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 * * ? * 1 2099"));
-        DateTime scanTime = DateTime.parse("2016-03-06T20:17:28.000-03:00");
-        DateTime nextTime = executionTime.nextExecution(scanTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-03-06T20:17:28.000-03:00");
+        ZonedDateTime nextTime = executionTime.nextExecution(scanTime);
         assertNotNull(nextTime);
-        assertEquals(DateTimeConstants.SUNDAY, nextTime.getDayOfWeek());
+        assertEquals(DayOfWeek.SUNDAY, nextTime.getDayOfWeek());
     }
 
     /**
@@ -268,13 +272,13 @@ public class ExecutionTimeQuartzIntegrationTest {
         String cronText = "0 0 18 ? * MON";
         Cron cron = parser.parse(cronText);
         final ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime now = DateTime.parse("2016-03-18T19:02:51.424+09:00");
-        DateTime next = executionTime.nextExecution(now);
-        DateTime nextNext = executionTime.nextExecution(next);
-        assertEquals(DateTimeConstants.MONDAY, next.getDayOfWeek());
-        assertEquals(DateTimeConstants.MONDAY, nextNext.getDayOfWeek());
-        assertEquals(18, next.getHourOfDay());
-        assertEquals(18, nextNext.getHourOfDay());
+        ZonedDateTime now = ZonedDateTime.parse("2016-03-18T19:02:51.424+09:00");
+        ZonedDateTime next = executionTime.nextExecution(now);
+        ZonedDateTime nextNext = executionTime.nextExecution(next);
+        assertEquals(DayOfWeek.MONDAY, next.getDayOfWeek());
+        assertEquals(DayOfWeek.MONDAY, nextNext.getDayOfWeek());
+        assertEquals(18, next.getHour());
+        assertEquals(18, nextNext.getHour());
     }
 
     /**
@@ -285,14 +289,14 @@ public class ExecutionTimeQuartzIntegrationTest {
      * @throws Exception
      */
     @Test
-    public void testMultipleMinuteIntervalTimeFromLastExecution() throws Exception {
+    public void testMultipleMinuteIntervalTimeFromLastExecution() {
         String expression = "* 8-10,23-25,38-40,53-55 * * * ? *"; // every second for intervals of minutes
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(expression));
 
-        assertEquals(301, executionTime.timeFromLastExecution(new DateTime().withTime(3, 1, 0, 0)).getStandardSeconds());
-        assertEquals(1, executionTime.timeFromLastExecution(new DateTime().withTime(13, 8, 4, 0)).getStandardSeconds());
-        assertEquals(1, executionTime.timeFromLastExecution(new DateTime().withTime(13, 11, 0, 0)).getStandardSeconds());
-        assertEquals(63, executionTime.timeFromLastExecution(new DateTime().withTime(13, 12, 2, 0)).getStandardSeconds());
+        assertEquals(301, executionTime.timeFromLastExecution(ZonedDateTime.of(LocalDate.now(), LocalTime.of(3, 1, 0, 0), UTC)).getSeconds());
+        assertEquals(1, executionTime.timeFromLastExecution(ZonedDateTime.of(LocalDate.now(), LocalTime.of(13, 8, 4, 0), UTC)).getSeconds());
+        assertEquals(1, executionTime.timeFromLastExecution(ZonedDateTime.of(LocalDate.now(), LocalTime.of(13, 11, 0, 0), UTC)).getSeconds());
+        assertEquals(63, executionTime.timeFromLastExecution(ZonedDateTime.of(LocalDate.now(), LocalTime.of(13, 12, 2, 0), UTC)).getSeconds());
     }
 
     /**
@@ -303,46 +307,42 @@ public class ExecutionTimeQuartzIntegrationTest {
      * @throws Exception
      */
     @Test
-    public void testMultipleMinuteIntervalMatch() throws Exception {
-        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(new DateTime(2014, 9, 20, 20, 0, 0)), false);
-        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(new DateTime(2014, 9, 20, 21, 0, 0)), true);
-        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(new DateTime(2014, 9, 20, 0, 0, 0)), true);
-        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(new DateTime(2014, 9, 20, 4, 0, 0)), true);
-        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(new DateTime(2014, 9, 20, 5, 0, 0)), false);
+    public void testMultipleMinuteIntervalMatch() {
+        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(ZonedDateTime.of(2014, 9, 20, 20, 0, 0, 0, UTC)), false);
+        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(ZonedDateTime.of(2014, 9, 20, 21, 0, 0, 0, UTC)), true);
+        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(ZonedDateTime.of(2014, 9, 20, 0, 0, 0, 0, UTC)), true);
+        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(ZonedDateTime.of(2014, 9, 20, 4, 0, 0, 0, UTC)), true);
+        assertEquals(ExecutionTime.forCron(parser.parse("* * 21-23,0-4 * * ?")).isMatch(ZonedDateTime.of(2014, 9, 20, 5, 0, 0, 0, UTC)), false);
     }
 
     @Test
     public void testDayLightSavingsSwitch() {
-        try {
-            // every 2 minutes
-            String expression = "* 0/2 * * * ?";
-            Cron cron = parser.parse(expression);
-
-            // SIMULATE SCHEDULE JUST PRIOR TO DST
-            DateTimeFormatter formatter = DateTimeFormat.forPattern("yyyy MM dd HH:mm:ss").withZone(DateTimeZone.forID("America/Denver"));
-            DateTime prevRun = new DateTime(formatter.parseDateTime("2016 03 13 01:59:59"));
-
-            ExecutionTime executionTime = ExecutionTime.forCron(cron);
-            DateTime nextRun = executionTime.nextExecution(prevRun);
-            // Assert we got 3:00am
-            assertEquals("Incorrect Hour", 3, nextRun.getHourOfDay());
-            assertEquals("Incorrect Minute", 0, nextRun.getMinuteOfHour());
-
-            // SIMULATE SCHEDULE POST DST - simulate a schedule after DST 3:01 with the same cron, expect 3:02
-            nextRun = nextRun.plusMinutes(1);
-            nextRun = executionTime.nextExecution(nextRun);
-            assertEquals("Incorrect Hour", 3, nextRun.getHourOfDay());
-            assertEquals("Incorrect Minute", 2, nextRun.getMinuteOfHour());
-
-            // SIMULATE SCHEDULE NEXT DAY DST - verify after midnight on DST switch things still work as expected
-            prevRun = new DateTime(new SimpleDateFormat("yyyy MM dd HH:mm:ss").parseObject("2016 03 14 00:00:59"));
-            nextRun = executionTime.nextExecution(prevRun);
-            assertEquals("incorrect hour", nextRun.getHourOfDay(), 0);
-            assertEquals("incorrect minute", nextRun.getMinuteOfHour(), 2);
-        }
-        catch(Exception e) {
-            fail("Exception Received: " +e.getMessage());
-        }
+        // every 2 minutes
+        String expression = "* 0/2 * * * ?";
+        Cron cron = parser.parse(expression);
+
+        // SIMULATE SCHEDULE JUST PRIOR TO DST
+        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy MM dd HH:mm:ss")
+                .withZone(ZoneId.of("America/Denver"));
+        ZonedDateTime prevRun = ZonedDateTime.parse("2016 03 13 01:59:59", formatter);
+
+        ExecutionTime executionTime = ExecutionTime.forCron(cron);
+        ZonedDateTime nextRun = executionTime.nextExecution(prevRun);
+        // Assert we got 3:00am
+        assertEquals("Incorrect Hour", 3, nextRun.getHour());
+        assertEquals("Incorrect Minute", 0, nextRun.getMinute());
+
+        // SIMULATE SCHEDULE POST DST - simulate a schedule after DST 3:01 with the same cron, expect 3:02
+        nextRun = nextRun.plusMinutes(1);
+        nextRun = executionTime.nextExecution(nextRun);
+        assertEquals("Incorrect Hour", 3, nextRun.getHour());
+        assertEquals("Incorrect Minute", 2, nextRun.getMinute());
+
+        // SIMULATE SCHEDULE NEXT DAY DST - verify after midnight on DST switch things still work as expected
+        prevRun = ZonedDateTime.parse("2016-03-14T00:00:59Z");
+        nextRun = executionTime.nextExecution(prevRun);
+        assertEquals("incorrect hour", nextRun.getHour(), 0);
+        assertEquals("incorrect minute", nextRun.getMinute(), 2);
     }
 
     /**
@@ -350,18 +350,13 @@ public class ExecutionTimeQuartzIntegrationTest {
      */
     @Test
     public void testCronWithFirstWorkDayOfWeek() {
-        try {
-            String cronText = "0 0 12 1W * ? *";
-            Cron cron = parser.parse(cronText);
-            DateTime dt = new DateTime(new SimpleDateFormat("yyyy MM dd HH:mm:ss").parseObject("2016 03 29 00:00:59"));
-
-            ExecutionTime executionTime = ExecutionTime.forCron(cron);
-            DateTime nextRun = executionTime.nextExecution(dt);
-            assertEquals("incorrect Day", nextRun.getDayOfMonth(), 1); // should be April 1st (Friday)
-        }
-        catch(Exception e) {
-            fail("Exception Received: "+e.getMessage());
-        }
+        String cronText = "0 0 12 1W * ? *";
+        Cron cron = parser.parse(cronText);
+        ZonedDateTime dt = ZonedDateTime.parse("2016-03-29T00:00:59Z");
+
+        ExecutionTime executionTime = ExecutionTime.forCron(cron);
+        ZonedDateTime nextRun = executionTime.nextExecution(dt);
+        assertEquals("incorrect Day", nextRun.getDayOfMonth(), 1); // should be April 1st (Friday)
     }
 
     /**
@@ -370,7 +365,7 @@ public class ExecutionTimeQuartzIntegrationTest {
      */
     @Test
     public void testDayOfWeekMapping() {
-        DateTime fridayMorning = new DateTime(2016, 4, 22, 0, 0, 0, DateTimeZone.UTC);
+        ZonedDateTime fridayMorning = ZonedDateTime.of(2016, 4, 22, 0, 0, 0, 0, UTC);
         ExecutionTime numberExec = ExecutionTime.forCron(parser.parse("0 0 12 ? * 2,3,4,5,6 *"));
         ExecutionTime nameExec = ExecutionTime.forCron(parser.parse("0 0 12 ? * MON,TUE,WED,THU,FRI *"));
         assertEquals("same generated dates", numberExec.nextExecution(fridayMorning),
@@ -382,32 +377,32 @@ public class ExecutionTimeQuartzIntegrationTest {
      */
     @Test
     public void testMinimumInterval() {
-        Duration s1 = Duration.standardSeconds(1);
+        Duration s1 = Duration.ofSeconds(1);
         assertEquals(getMinimumInterval("* * * * * ?"), s1);
         assertEquals("Should ignore whitespace", getMinimumInterval("*   *    *  *       * ?"), s1);
         assertEquals(getMinimumInterval("0/1 * * * * ?"), s1);
         assertEquals(getMinimumInterval("*/1 * * * * ?"), s1);
 
-        Duration s60 = Duration.standardSeconds(60);
+        Duration s60 = Duration.ofSeconds(60);
         assertEquals(getMinimumInterval("0 * * * * ?"), s60);
         assertEquals(getMinimumInterval("0 */1 * * * ?"), s60);
 
-        assertEquals(getMinimumInterval("0 */5 * * * ?"), Duration.standardSeconds(300));
-        assertEquals(getMinimumInterval("0 0 * * * ?"), Duration.standardSeconds(3600));
-        assertEquals(getMinimumInterval("0 0 */3 * * ?"), Duration.standardSeconds(10800));
-        assertEquals(getMinimumInterval("0 0 0 * * ?"), Duration.standardSeconds(86400));
+        assertEquals(getMinimumInterval("0 */5 * * * ?"), Duration.ofSeconds(300));
+        assertEquals(getMinimumInterval("0 0 * * * ?"), Duration.ofSeconds(3600));
+        assertEquals(getMinimumInterval("0 0 */3 * * ?"), Duration.ofSeconds(10800));
+        assertEquals(getMinimumInterval("0 0 0 * * ?"), Duration.ofSeconds(86400));
     }
 
     private Duration getMinimumInterval(String quartzPattern) {
         ExecutionTime et = ExecutionTime.forCron(parser.parse(quartzPattern));
-        DateTime coolDay = new DateTime(2016, 1, 1, 0, 0, 0);
+        ZonedDateTime coolDay = ZonedDateTime.of(2016, 1, 1, 0, 0, 0, 0, UTC);
         // Find next execution time #1
-        DateTime t1 = et.nextExecution(coolDay);
+        ZonedDateTime t1 = et.nextExecution(coolDay);
         // Find next execution time #2 right after #1, the interval between them is minimum
         return et.timeToNextExecution(t1);
     }
 
-    private DateTime truncateToSeconds(DateTime dateTime){
-        return dateTime.secondOfMinute().roundFloorCopy();
+    private ZonedDateTime truncateToSeconds(ZonedDateTime dateTime){
+        return dateTime.truncatedTo(ChronoUnit.SECONDS);
     }
 }
\ No newline at end of file
diff --git a/src/test/java/com/cronutils/model/time/generator/ExecutionTimeUnixIntegrationTest.java b/src/test/java/com/cronutils/model/time/generator/ExecutionTimeUnixIntegrationTest.java
index e774dd4..e760f45 100644
--- a/src/test/java/com/cronutils/model/time/generator/ExecutionTimeUnixIntegrationTest.java
+++ b/src/test/java/com/cronutils/model/time/generator/ExecutionTimeUnixIntegrationTest.java
@@ -1,17 +1,20 @@
 package com.cronutils.model.time.generator;
 
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
+import java.time.Duration;
+import java.time.ZoneId;
+import java.time.ZonedDateTime;
+
+import org.junit.Test;
+
 import com.cronutils.model.Cron;
 import com.cronutils.model.CronType;
 import com.cronutils.model.definition.CronDefinition;
 import com.cronutils.model.definition.CronDefinitionBuilder;
 import com.cronutils.model.time.ExecutionTime;
 import com.cronutils.parser.CronParser;
-import org.joda.time.DateTime;
-import org.joda.time.DateTimeZone;
-import org.junit.Test;
-
-import static org.junit.Assert.assertEquals;
-import static org.junit.Assert.assertTrue;
 
 public class ExecutionTimeUnixIntegrationTest {
 
@@ -21,7 +24,7 @@ public class ExecutionTimeUnixIntegrationTest {
         String crontab = "* * * * *";//m,h,dom,M,dow
         Cron cron = parser.parse(crontab);
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime scanTime = DateTime.parse("2016-02-29T11:00:00.000-06:00");
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-02-29T11:00:00.000-06:00");
         assertTrue(executionTime.isMatch(scanTime));
     }
 
@@ -31,7 +34,7 @@ public class ExecutionTimeUnixIntegrationTest {
         String crontab = "0 * * * 1-5";//m,h,dom,M,dow
         Cron cron = parser.parse(crontab);
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime scanTime = DateTime.parse("2016-03-04T11:00:00.000-06:00");
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-03-04T11:00:00.000-06:00");
         assertTrue(executionTime.isMatch(scanTime));
     }
 
@@ -42,8 +45,8 @@ public class ExecutionTimeUnixIntegrationTest {
     public void testEveryTenMinutesNextExecution(){
         CronParser parser = new CronParser(CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("*/10 * * * *"));
-        DateTime time = DateTime.parse("2015-09-05T13:43:00.000-07:00");
-        assertEquals(DateTime.parse("2015-09-05T13:50:00.000-07:00"), executionTime.nextExecution(time));
+        ZonedDateTime time = ZonedDateTime.parse("2015-09-05T13:43:00.000-07:00");
+        assertEquals(ZonedDateTime.parse("2015-09-05T13:50:00.000-07:00"), executionTime.nextExecution(time));
     }
 
     /**
@@ -54,9 +57,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         Cron cron = new CronParser(cronDefinition).parse("*/2 * * * *");
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime time = DateTime.parse("2015-09-05T13:56:00.000-07:00");
-        DateTime next = executionTime.nextExecution(time);
-        DateTime shouldBeInNextHour = executionTime.nextExecution(next);
+        ZonedDateTime time = ZonedDateTime.parse("2015-09-05T13:56:00.000-07:00");
+        ZonedDateTime next = executionTime.nextExecution(time);
+        ZonedDateTime shouldBeInNextHour = executionTime.nextExecution(next);
         assertEquals(next.plusMinutes(2), shouldBeInNextHour);
     }
 
@@ -68,8 +71,8 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron myCron = parser.parse("0 3 * * 3");
-        DateTime time = DateTime.parse("2015-09-17T00:00:00.000-07:00");
-        assertEquals(DateTime.parse("2015-09-23T03:00:00.000-07:00"), ExecutionTime.forCron(myCron).nextExecution(time));
+        ZonedDateTime time = ZonedDateTime.parse("2015-09-17T00:00:00.000-07:00");
+        assertEquals(ZonedDateTime.parse("2015-09-23T03:00:00.000-07:00"), ExecutionTime.forCron(myCron).nextExecution(time));
     }
 
     /**
@@ -80,8 +83,8 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron myCron = parser.parse("0 3 * * 3");
-        DateTime time = DateTime.parse("2015-09-17T00:00:00.000-07:00");
-        assertEquals(DateTime.parse("2015-09-16T03:00:00.000-07:00"), ExecutionTime.forCron(myCron).lastExecution(time));
+        ZonedDateTime time = ZonedDateTime.parse("2015-09-17T00:00:00.000-07:00");
+        assertEquals(ZonedDateTime.parse("2015-09-16T03:00:00.000-07:00"), ExecutionTime.forCron(myCron).lastExecution(time));
     }
 
     /**
@@ -93,9 +96,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse(crontab);
-        DateTime date = DateTime.parse("2015-10-13T17:26:54.468-07:00");
+        ZonedDateTime date = ZonedDateTime.parse("2015-10-13T17:26:54.468-07:00");
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        assertEquals(DateTime.parse("2015-10-12T23:59:00.000-07:00"), executionTime.lastExecution(date));
+        assertEquals(ZonedDateTime.parse("2015-10-12T23:59:00.000-07:00"), executionTime.lastExecution(date));
     }
 
     /**
@@ -107,9 +110,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse(crontab);
-        DateTime date = DateTime.parse("2015-10-13T17:26:54.468-07:00");
+        ZonedDateTime date = ZonedDateTime.parse("2015-10-13T17:26:54.468-07:00");
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        assertEquals(DateTime.parse("2015-10-19T00:00:00.000-07:00"), executionTime.nextExecution(date));
+        assertEquals(ZonedDateTime.parse("2015-10-19T00:00:00.000-07:00"), executionTime.nextExecution(date));
     }
 
     /**
@@ -121,9 +124,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse(crontab);
-        DateTime date = DateTime.parse("2015-11-02T00:10:00.000");
+        ZonedDateTime date = ZonedDateTime.parse("2015-11-02T00:10:00Z");
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        assertEquals(DateTime.parse("2015-10-26T11:00:00.000"), executionTime.lastExecution(date));
+        assertEquals(ZonedDateTime.parse("2015-10-26T11:00:00Z"), executionTime.lastExecution(date));
     }
 
     /**
@@ -136,9 +139,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse(crontab);
-        DateTime date = DateTime.parse("2015-11-10T17:01:00Z");
+        ZonedDateTime date = ZonedDateTime.parse("2015-11-10T17:01:00Z");
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        assertEquals(DateTime.parse("2015-11-10T17:00:00Z"), executionTime.lastExecution(date));
+        assertEquals(ZonedDateTime.parse("2015-11-10T17:00:00Z"), executionTime.lastExecution(date));
     }
 
     /**
@@ -151,9 +154,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse(crontab);
-        DateTime date = DateTime.parse("2015-11-10T17:01:00Z");
+        ZonedDateTime date = ZonedDateTime.parse("2015-11-10T17:01:00Z");
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        assertEquals(DateTime.parse("2015-11-10T17:00:00Z"), executionTime.lastExecution(date));
+        assertEquals(ZonedDateTime.parse("2015-11-10T17:00:00Z"), executionTime.lastExecution(date));
     }
 
     /**
@@ -167,12 +170,12 @@ public class ExecutionTimeUnixIntegrationTest {
         String crontab = "* * */3 */4 */5";//m,h,dom,M,dow
         Cron cron = parser.parse(crontab);
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime scanTime = DateTime.parse("2015-12-10T16:32:56.586-08:00");
-        DateTime nextExecutionTime = executionTime.nextExecution(scanTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2015-12-10T16:32:56.586-08:00");
+        ZonedDateTime nextExecutionTime = executionTime.nextExecution(scanTime);
         //DoW: 0-6 -> 0, 5 (sunday, friday)
         //DoM: 1-31 -> 1, 4, 7, 10, 13, 16, 19, 22, 25, 28, 31
         //M: 1-12 -> 1, 5, 9
-        assertEquals(DateTime.parse("2016-01-01T00:00:00.000-08:00"), nextExecutionTime);
+        assertEquals(ZonedDateTime.parse("2016-01-01T00:00:00.000-08:00"), nextExecutionTime);
     }
 
     /**
@@ -186,9 +189,9 @@ public class ExecutionTimeUnixIntegrationTest {
         String crontab = "* * */4 * *";//m,h,dom,M,dow
         Cron cron = parser.parse(crontab);
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime scanTime = DateTime.parse("2015-12-10T16:32:56.586-08:00");
-        DateTime nextExecutionTime = executionTime.nextExecution(scanTime);
-        assertEquals(DateTime.parse("2015-12-13T00:00:00.000-08:00"), nextExecutionTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2015-12-10T16:32:56.586-08:00");
+        ZonedDateTime nextExecutionTime = executionTime.nextExecution(scanTime);
+        assertEquals(ZonedDateTime.parse("2015-12-13T00:00:00.000-08:00"), nextExecutionTime);
     }
 
     /**
@@ -203,9 +206,9 @@ public class ExecutionTimeUnixIntegrationTest {
         //DoW: 0-6 -> 0, 4 (sunday, thursday)
         Cron cron = parser.parse(crontab);
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        DateTime scanTime = DateTime.parse("2016-01-28T16:32:56.586-08:00");
-        DateTime nextExecutionTime = executionTime.nextExecution(scanTime);
-        assertEquals(DateTime.parse("2016-02-04T00:00:00.000-08:00"), nextExecutionTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-01-28T16:32:56.586-08:00");
+        ZonedDateTime nextExecutionTime = executionTime.nextExecution(scanTime);
+        assertEquals(ZonedDateTime.parse("2016-02-04T00:00:00.000-08:00"), nextExecutionTime);
     }
 
     /**
@@ -217,9 +220,9 @@ public class ExecutionTimeUnixIntegrationTest {
         String crontab = "0 * * * 1-5";//m,h,dom,M,dow
         //DoW: 0-6 -> 1, 2, 3, 4, 5 -> in this year:
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse(crontab));
-        DateTime scanTime = DateTime.parse("2016-02-29T11:00:00.000-06:00");
-        DateTime nextExecutionTime = executionTime.nextExecution(scanTime);
-        assertEquals(DateTime.parse("2016-02-29T12:00:00.000-06:00"), nextExecutionTime);
+        ZonedDateTime scanTime = ZonedDateTime.parse("2016-02-29T11:00:00.000-06:00");
+        ZonedDateTime nextExecutionTime = executionTime.nextExecution(scanTime);
+        assertEquals(ZonedDateTime.parse("2016-02-29T12:00:00.000-06:00"), nextExecutionTime);
     }
 
     /**
@@ -230,9 +233,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronParser parser = new CronParser(CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 17 * * *"));// daily at 17:00
         // Daylight savings for New York 2016 is Mar 13 at 2am
-        DateTime last = new DateTime(2016, 3, 12, 17, 0, DateTimeZone.forID("America/New_York"));
-        DateTime next = executionTime.nextExecution(last);
-        long millis = next.getMillis() - last.getMillis();
+        ZonedDateTime last = ZonedDateTime.of(2016, 3, 12, 17, 0, 0, 0, ZoneId.of("America/New_York"));
+        ZonedDateTime next = executionTime.nextExecution(last);
+        long millis = Duration.between(last, next).toMillis();
         assertEquals(23, (millis / 3600000));
         assertEquals(last.getZone(), next.getZone());
     }
@@ -245,9 +248,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronParser parser = new CronParser(CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 17 * * *"));// daily at 17:00
         // Daylight savings for New York 2016 is Mar 13 at 2am
-        DateTime now = new DateTime(2016, 3, 12, 17, 0, DateTimeZone.forID("America/Phoenix"));
-        DateTime last = executionTime.lastExecution(now);
-        long millis = now.getMillis() - last.getMillis();
+        ZonedDateTime now = ZonedDateTime.of(2016, 3, 12, 17, 0, 0, 0, ZoneId.of("America/Phoenix"));
+        ZonedDateTime last = executionTime.lastExecution(now);
+        long millis = Duration.between(last, now).toMillis();
         assertEquals(24, (millis / 3600000));
         assertEquals(now.getZone(), last.getZone());
     }
@@ -261,9 +264,9 @@ public class ExecutionTimeUnixIntegrationTest {
         CronDefinition cronDefinition = CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX);
         CronParser parser = new CronParser(cronDefinition);
         Cron cron = parser.parse(crontab);
-        DateTime date = DateTime.parse("2014-11-30T00:00:00Z");
+        ZonedDateTime date = ZonedDateTime.parse("2014-11-30T00:00:00Z");
         ExecutionTime executionTime = ExecutionTime.forCron(cron);
-        assertEquals(DateTime.parse("2014-12-01T08:00:00Z"), executionTime.nextExecution(date));
+        assertEquals(ZonedDateTime.parse("2014-12-01T08:00:00Z"), executionTime.nextExecution(date));
     }
 
     /**
@@ -273,7 +276,7 @@ public class ExecutionTimeUnixIntegrationTest {
     public void testNextExecution2016() {
         CronParser parser = new CronParser(CronDefinitionBuilder.instanceDefinitionFor(CronType.UNIX));
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("1 0 * * tue"));
-        DateTime date = DateTime.parse("2016-05-24T01:02:50Z");
-        assertEquals(DateTime.parse("2016-05-31T00:01:00Z"), executionTime.nextExecution(date));
+        ZonedDateTime date = ZonedDateTime.parse("2016-05-24T01:02:50Z");
+        assertEquals(ZonedDateTime.parse("2016-05-31T00:01:00Z"), executionTime.nextExecution(date));
     }
 }
diff --git a/src/test/java/com/cronutils/model/time/generator/OnDayOfMonthValueGeneratorLTest.java b/src/test/java/com/cronutils/model/time/generator/OnDayOfMonthValueGeneratorLTest.java
index 7284391..d4d90b3 100644
--- a/src/test/java/com/cronutils/model/time/generator/OnDayOfMonthValueGeneratorLTest.java
+++ b/src/test/java/com/cronutils/model/time/generator/OnDayOfMonthValueGeneratorLTest.java
@@ -1,5 +1,15 @@
 package com.cronutils.model.time.generator;
 
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertFalse;
+import static org.junit.Assert.assertTrue;
+
+import java.time.LocalDate;
+import java.util.List;
+
+import org.junit.Before;
+import org.junit.Test;
+
 import com.cronutils.model.field.CronField;
 import com.cronutils.model.field.CronFieldName;
 import com.cronutils.model.field.constraint.FieldConstraints;
@@ -7,13 +17,6 @@ import com.cronutils.model.field.constraint.FieldConstraintsBuilder;
 import com.cronutils.model.field.expression.On;
 import com.cronutils.model.field.value.SpecialChar;
 import com.cronutils.model.field.value.SpecialCharFieldValue;
-import org.joda.time.DateTime;
-import org.junit.Before;
-import org.junit.Test;
-
-import java.util.List;
-
-import static org.junit.Assert.*;
 /*
  * Copyright 2015 jmrozanec
  * Licensed under the Apache License, Version 2.0 (the "License");
@@ -30,7 +33,7 @@ public class OnDayOfMonthValueGeneratorLTest {
     private OnDayOfMonthValueGenerator fieldValueGenerator;
     private int year = 2015;
     private int month = 2;
-    private int lastDayInMonth = new DateTime(2015, 2, 1, 1, 1).dayOfMonth().getMaximumValue();
+    private int lastDayInMonth = LocalDate.of(2015, 2, 1).lengthOfMonth();
 
     @Before
     public void setUp(){
diff --git a/src/test/java/com/cronutils/parser/CronParserQuartzIntegrationTest.java b/src/test/java/com/cronutils/parser/CronParserQuartzIntegrationTest.java
index 77b6d85..6aa9aa0 100644
--- a/src/test/java/com/cronutils/parser/CronParserQuartzIntegrationTest.java
+++ b/src/test/java/com/cronutils/parser/CronParserQuartzIntegrationTest.java
@@ -1,22 +1,21 @@
 package com.cronutils.parser;
 
-import com.cronutils.descriptor.CronDescriptor;
-import com.cronutils.model.Cron;
-import com.cronutils.model.CronType;
-import com.cronutils.model.definition.CronDefinition;
-import com.cronutils.model.definition.CronDefinitionBuilder;
-import com.cronutils.model.time.ExecutionTime;
+import static org.junit.Assert.assertEquals;
+
+import java.time.ZonedDateTime;
+import java.util.Locale;
 
-import org.joda.time.DateTime;
-import org.joda.time.format.DateTimeFormat;
-import org.joda.time.format.DateTimeFormatter;
-import org.junit.Assert;
 import org.junit.Before;
 import org.junit.Rule;
 import org.junit.Test;
 import org.junit.rules.ExpectedException;
 
-import java.util.Locale;
+import com.cronutils.descriptor.CronDescriptor;
+import com.cronutils.model.Cron;
+import com.cronutils.model.CronType;
+import com.cronutils.model.definition.CronDefinition;
+import com.cronutils.model.definition.CronDefinitionBuilder;
+import com.cronutils.model.time.ExecutionTime;
 
 /*
  * Copyright 2015 jmrozanec
@@ -31,9 +30,7 @@ import java.util.Locale;
  * limitations under the License.
  */
 public class CronParserQuartzIntegrationTest {
-
-    private final static DateTimeFormatter formatter = DateTimeFormat.forPattern("YYYY-MM-DD HH:mm:ss");
-
+    
     private CronParser parser;
 
     @Rule
@@ -195,10 +192,10 @@ public class CronParserQuartzIntegrationTest {
     @Test
     public void testIntervalSeconds() {
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0/20 * * * * ?"));
-        DateTime now = DateTime.parse("2005-08-09 18:32:42", formatter);
-        DateTime lastExecution = executionTime.lastExecution(now);
-        DateTime assertDate = DateTime.parse("2005-01-09 18:32:40", formatter);
-        Assert.assertEquals(assertDate, lastExecution);
+        ZonedDateTime now = ZonedDateTime.parse("2005-08-09T18:32:42Z");
+        ZonedDateTime lastExecution = executionTime.lastExecution(now);
+        ZonedDateTime assertDate = ZonedDateTime.parse("2005-08-09T18:32:40Z");
+        assertEquals(assertDate, lastExecution);
     }
 
     /**
@@ -207,10 +204,10 @@ public class CronParserQuartzIntegrationTest {
     @Test
     public void testIntervalMinutes() {
         ExecutionTime executionTime = ExecutionTime.forCron(parser.parse("0 0/7 * * * ?"));
-        DateTime now = DateTime.parse("2005-08-09 18:32:42", formatter);
-        DateTime lastExecution = executionTime.lastExecution(now);
-        DateTime assertDate = DateTime.parse("2005-01-09 18:28:00", formatter);
-        Assert.assertEquals(assertDate, lastExecution);
+        ZonedDateTime now = ZonedDateTime.parse("2005-08-09T18:32:42Z");
+        ZonedDateTime lastExecution = executionTime.lastExecution(now);
+        ZonedDateTime assertDate = ZonedDateTime.parse("2005-08-09T18:28:00Z");
+        assertEquals(assertDate, lastExecution);
     }
 
     /**
diff --git a/src/test/java/com/cronutils/validator/CronValidatorQuartzIntegrationTest.java b/src/test/java/com/cronutils/validator/CronValidatorQuartzIntegrationTest.java
index 5983b38..36e04cf 100644
--- a/src/test/java/com/cronutils/validator/CronValidatorQuartzIntegrationTest.java
+++ b/src/test/java/com/cronutils/validator/CronValidatorQuartzIntegrationTest.java
@@ -1,15 +1,15 @@
 package com.cronutils.validator;
 
-import com.cronutils.model.CronType;
-import com.cronutils.model.definition.CronDefinitionBuilder;
-import com.cronutils.parser.CronParser;
-import org.joda.time.DateTime;
+import java.time.LocalDate;
+import java.time.format.DateTimeFormatter;
+import java.util.Locale;
+
 import org.junit.Before;
 import org.junit.Test;
 
-import java.util.Locale;
-
-import static org.junit.Assert.assertTrue;
+import com.cronutils.model.CronType;
+import com.cronutils.model.definition.CronDefinitionBuilder;
+import com.cronutils.parser.CronParser;
 
 /*
  * Copyright 2015 jmrozanec
@@ -43,9 +43,9 @@ public class CronValidatorQuartzIntegrationTest {
      */
     @Test
     public void testSingleMonthMappingIsValid(){
-        DateTime date = new DateTime(2015, 1, 1, 1, 1);
+        LocalDate date = LocalDate.of(2015, 1, 1);
         for(int j=0;j<12;j++){
-            String expression = String.format("0 0 0 * %s ? *", date.plusMonths(j).toString("MMM", Locale.US).toUpperCase());
+            String expression = String.format("0 0 0 * %s ? *", date.plusMonths(j).format(DateTimeFormatter.ofPattern("MMM", Locale.US)).toUpperCase());
             parser.parse(expression);
         }
     }