You are viewing a plain text version of this content. The canonical link for it is here.
Posted to commits@poi.apache.org by ki...@apache.org on 2015/09/02 01:10:44 UTC

svn commit: r1700686 - in /poi: site/src/documentation/content/xdocs/ trunk/src/java/org/apache/poi/ss/formula/functions/ trunk/src/java/org/apache/poi/ss/usermodel/ trunk/src/testcases/org/apache/poi/hssf/usermodel/ trunk/src/testcases/org/apache/poi/...

Author: kiwiwings
Date: Tue Sep  1 23:10:43 2015
New Revision: 1700686

URL: http://svn.apache.org/r1700686
Log:
Fix DAYS360 for US/EU handling
fix forbidden api calls
add TimeZone (user) override to DateUtil
fix a few left open resources in the junit tests

Modified:
    poi/site/src/documentation/content/xdocs/status.xml
    poi/trunk/src/java/org/apache/poi/ss/formula/functions/Days360.java
    poi/trunk/src/java/org/apache/poi/ss/usermodel/DateUtil.java
    poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestBugs.java
    poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFCell.java
    poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/AllFormulaEvalTests.java
    poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/TestFormulasFromSpreadsheet.java
    poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/AllIndividualFunctionEvaluationTests.java
    poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/TestDays360.java
    poi/trunk/src/testcases/org/apache/poi/ss/formula/ptg/AllFormulaTests.java
    poi/trunk/src/testcases/org/apache/poi/ss/usermodel/BaseTestCell.java

Modified: poi/site/src/documentation/content/xdocs/status.xml
URL: http://svn.apache.org/viewvc/poi/site/src/documentation/content/xdocs/status.xml?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/site/src/documentation/content/xdocs/status.xml (original)
+++ poi/site/src/documentation/content/xdocs/status.xml Tue Sep  1 23:10:43 2015
@@ -39,6 +39,7 @@
     </devs>
 
     <release version="3.13-beta2" date="2015-10-??">
+    	<action dev="PD" type="fix">Fix DAYS360 handling for US/EU method</action>
         <action dev="PD" type="fix" fixes-bug="58254">CellFormatResult.text should check for nulls as per the javadoc</action>
         <action dev="PD" type="fix" fixes-bug="58260">Fix checks for limit on number of styles in XSSF/SXSSF, fix more than 32k styles in SXSSF workbooks</action>
         <action dev="DN" type="fix" fixes-bug="58262">ReadOnlySharedStringsTable now handles workbooks with an empty SST part</action>

Modified: poi/trunk/src/java/org/apache/poi/ss/formula/functions/Days360.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/ss/formula/functions/Days360.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/ss/formula/functions/Days360.java (original)
+++ poi/trunk/src/java/org/apache/poi/ss/formula/functions/Days360.java Tue Sep  1 23:10:43 2015
@@ -17,7 +17,6 @@
 package org.apache.poi.ss.formula.functions;
 
 import java.util.Calendar;
-import java.util.GregorianCalendar;
 import java.util.Locale;
 import java.util.TimeZone;
 
@@ -28,10 +27,44 @@ import org.apache.poi.ss.formula.eval.Va
 import org.apache.poi.ss.usermodel.DateUtil;
 
 /**
- * Calculates the number of days between two dates based on a 360-day year
+ * <p>Calculates the number of days between two dates based on a 360-day year
  * (twelve 30-day months), which is used in some accounting calculations. Use
  * this function to help compute payments if your accounting system is based on
- * twelve 30-day months.
+ * twelve 30-day months.<p>
+ * 
+ * {@code DAYS360(start_date,end_date,[method])}
+ * 
+ * <ul>
+ * <li>Start_date, end_date (required):<br/>
+ * The two dates between which you want to know the number of days.<br/>
+ * If start_date occurs after end_date, the DAYS360 function returns a negative number.</li>
+ * 
+ * <li>Method (optional):<br/>
+ * A logical value that specifies whether to use the U.S. or European method in the calculation</li>
+ * 
+ * <li>Method set to false or omitted:<br/>
+ * the DAYS360 function uses the U.S. (NASD) method. If the starting date is the 31st of a month,
+ * it becomes equal to the 30th of the same month. If the ending date is the 31st of a month and
+ * the starting date is earlier than the 30th of a month, the ending date becomes equal to the
+ * 1st of the next month, otherwise the ending date becomes equal to the 30th of the same month.
+ * The month February and leap years are handled in the following way:<br/>
+ * On a non-leap year the function {@code =DAYS360("2/28/93", "3/1/93", FALSE)} returns 1 day
+ * because the DAYS360 function ignores the extra days added to February.<br/>
+ * On a leap year the function {@code =DAYS360("2/29/96","3/1/96", FALSE)} returns 1 day for
+ * the same reason.</li>
+ * 
+ * <li>Method Set to true:<br/>
+ * When you set the method parameter to TRUE, the DAYS360 function uses the European method.
+ * Starting dates or ending dates that occur on the 31st of a month become equal to the 30th of
+ * the same month. The month February and leap years are handled in the following way:<br/>
+ * On a non-leap year the function {@code =DAYS360("2/28/93", "3/1/93", TRUE)} returns
+ * 3 days because the DAYS360 function is counting the extra days added to February to give
+ * February 30 days.<br/>
+ * On a leap year the function {@code =DAYS360("2/29/96", "3/1/96", TRUE)} returns
+ * 2 days for the same reason.</li>
+ * </ul>
+ * 
+ * @see <a href="https://support.microsoft.com/en-us/kb/235575">DAYS360 Function Produces Different Values Depending on the Version of Excel</a>
  */
 public class Days360 extends Var2or3ArgFunction {
     /**
@@ -68,56 +101,57 @@ public class Days360 extends Var2or3ArgF
     }
 
     private static double evaluate(double d0, double d1, boolean method) {
-        Calendar startingDate = getStartingDate(d0);
-        Calendar endingDate = getEndingDateAccordingToStartingDate(d1, startingDate);
-        long startingDay = startingDate.get(Calendar.MONTH) * 30 + startingDate.get(Calendar.DAY_OF_MONTH);
-        long endingDay = (endingDate.get(Calendar.YEAR) - startingDate.get(Calendar.YEAR)) * 360
-                + endingDate.get(Calendar.MONTH) * 30 + endingDate.get(Calendar.DAY_OF_MONTH);
-        return endingDay - startingDay;
+        Calendar realStart = getDate(d0);
+        Calendar realEnd = getDate(d1);
+        int startingDate[] = getStartingDate(realStart, method);
+        int endingDate[] = getEndingDate(realEnd, realStart, method);
+        
+        return
+            (endingDate[0]*360+endingDate[1]*30+endingDate[2])-
+            (startingDate[0]*360+startingDate[1]*30+startingDate[2]);
     }
 
     private static Calendar getDate(double date) {
-        Calendar processedDate = new GregorianCalendar(DEFAULT_TIMEZONE, Locale.ROOT);
-        processedDate.setTime(DateUtil.getJavaDate(date, false));
+        Calendar processedDate = Calendar.getInstance(DEFAULT_TIMEZONE, Locale.ROOT);
+        processedDate.setTime(DateUtil.getJavaDate(date, false, DEFAULT_TIMEZONE));
         return processedDate;
     }
 
-    private static Calendar getStartingDate(double date) {
-        Calendar startingDate = getDate(date);
-        if (isLastDayOfMonth(startingDate)) {
-            startingDate.set(Calendar.DAY_OF_MONTH, 30);
-        }
-        return startingDate;
-    }
-
-    private static Calendar getEndingDateAccordingToStartingDate(double date, Calendar startingDate) {
-        Calendar endingDate = getDate(date);
-        endingDate.setTime(DateUtil.getJavaDate(date, false));
-        if (isLastDayOfMonth(endingDate)) {
-            if (startingDate.get(Calendar.DATE) < 30) {
-                endingDate = getFirstDayOfNextMonth(endingDate);
+    private static int[] getStartingDate(Calendar realStart, boolean method) {
+        Calendar d = realStart;
+        int yyyy = d.get(Calendar.YEAR);
+        int mm = d.get(Calendar.MONTH);
+        int dd = Math.min(30, d.get(Calendar.DAY_OF_MONTH));
+        
+        if (method == false && isLastDayOfMonth(d)) dd = 30;
+        
+        return new int[]{yyyy,mm,dd};
+    }
+
+    private static int[] getEndingDate(Calendar realEnd, Calendar realStart, boolean method) {
+        Calendar d = realEnd;
+        int yyyy = d.get(Calendar.YEAR);
+        int mm = d.get(Calendar.MONTH);
+        int dd = Math.min(30, d.get(Calendar.DAY_OF_MONTH));
+
+        if (method == false && realEnd.get(Calendar.DAY_OF_MONTH) == 31) {
+            if (realStart.get(Calendar.DAY_OF_MONTH) < 30) {
+                d.set(Calendar.DAY_OF_MONTH, 1);
+                d.add(Calendar.MONTH, 1);
+                yyyy = d.get(Calendar.YEAR);
+                mm = d.get(Calendar.MONTH);
+                dd = 1;
+            } else {
+                dd = 30;
             }
         }
-        return endingDate;
+        
+        return new int[]{yyyy,mm,dd};
     }
-
+    
     private static boolean isLastDayOfMonth(Calendar date) {
-        Calendar clone = (Calendar) date.clone();
-        clone.add(java.util.Calendar.MONTH, 1);
-        clone.add(java.util.Calendar.DAY_OF_MONTH, -1);
-        int lastDayOfMonth = clone.get(Calendar.DAY_OF_MONTH);
-        return date.get(Calendar.DAY_OF_MONTH) == lastDayOfMonth;
-    }
-
-    private static Calendar getFirstDayOfNextMonth(Calendar date) {
-        Calendar newDate = (Calendar) date.clone();
-        if (date.get(Calendar.MONTH) < Calendar.DECEMBER) {
-            newDate.set(Calendar.MONTH, date.get(Calendar.MONTH) + 1);
-        } else {
-            newDate.set(Calendar.MONTH, 1);
-            newDate.set(Calendar.YEAR, date.get(Calendar.YEAR) + 1);
-        }
-        newDate.set(Calendar.DATE, 1);
-        return newDate;
+        int dayOfMonth = date.get(Calendar.DAY_OF_MONTH);
+        int lastDayOfMonth = date.getActualMaximum(Calendar.DAY_OF_MONTH);
+        return (dayOfMonth == lastDayOfMonth);
     }
 }

Modified: poi/trunk/src/java/org/apache/poi/ss/usermodel/DateUtil.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/java/org/apache/poi/ss/usermodel/DateUtil.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/java/org/apache/poi/ss/usermodel/DateUtil.java (original)
+++ poi/trunk/src/java/org/apache/poi/ss/usermodel/DateUtil.java Tue Sep  1 23:10:43 2015
@@ -20,7 +20,6 @@ package org.apache.poi.ss.usermodel;
 
 import java.util.Calendar;
 import java.util.Date;
-import java.util.GregorianCalendar;
 import java.util.Locale;
 import java.util.TimeZone;
 import java.util.regex.Pattern;
@@ -79,7 +78,7 @@ public class DateUtil {
      * @param use1904windowing Should 1900 or 1904 date windowing be used?
      */
     public static double getExcelDate(Date date, boolean use1904windowing) {
-        Calendar calStart = new GregorianCalendar(TIMEZONE_UTC, Locale.ROOT);
+        Calendar calStart = Calendar.getInstance(getUserTimeZone(), Locale.ROOT);
         calStart.setTime(date);   // If date includes hours, minutes, and seconds, set them to 0
         return internalGetExcelDate(calStart, use1904windowing);
     }
@@ -315,9 +314,9 @@ public class DateUtil {
         int millisecondsInDay = (int)((date - wholeDays) * DAY_MILLISECONDS + 0.5);
         Calendar calendar;
         if (timeZone != null) {
-            calendar = new GregorianCalendar(timeZone, Locale.ROOT);
+            calendar = Calendar.getInstance(timeZone, Locale.ROOT);
         } else {
-            calendar = new GregorianCalendar(TIMEZONE_UTC, Locale.ROOT); // using default time-zone
+            calendar = Calendar.getInstance(getUserTimeZone(), Locale.ROOT); // using default time-zone
         }
         setCalendar(calendar, wholeDays, millisecondsInDay, use1904windowing, roundSeconds);
         return calendar;
@@ -334,6 +333,13 @@ public class DateUtil {
     };
     private static ThreadLocal<String> lastFormatString = new ThreadLocal<String>();
     private static ThreadLocal<Boolean> lastCachedResult = new ThreadLocal<Boolean>();
+    
+    private static ThreadLocal<TimeZone> userTimeZone = new ThreadLocal<TimeZone>() {
+        @Override
+        protected TimeZone initialValue() {
+            return TIMEZONE_UTC;
+        }
+    };
 
     private static boolean isCached(String formatString, int formatIndex) {
         String cachedFormatString = lastFormatString.get();
@@ -346,6 +352,23 @@ public class DateUtil {
         lastFormatString.set(formatString);
         lastCachedResult.set(Boolean.valueOf(cached));
     }
+
+    /**
+     * as timezone information is not stored in any format, it can be
+     * set before any date calculations take place
+     *
+     * @param timezone the timezone under which date calculations take place
+     */
+    public static void setUserTimeZone(TimeZone timezone) {
+        userTimeZone.set(timezone);
+    }
+    
+    /**
+     * @return the time zone which is used for date calculations
+     */
+    public static TimeZone getUserTimeZone() {
+        return userTimeZone.get();
+    }
     
     /**
      * Given a format ID and its format String, will check to see if the
@@ -661,7 +684,7 @@ public class DateUtil {
         int month = parseInt(monthStr, "month", 1, 12);
         int day = parseInt(dayStr, "day", 1, 31);
 
-        Calendar cal = new GregorianCalendar(TIMEZONE_UTC, Locale.ROOT);
+        Calendar cal = Calendar.getInstance(getUserTimeZone(), Locale.ROOT);
         cal.set(year, month-1, day, 0, 0, 0);
         cal.set(Calendar.MILLISECOND, 0);
         return cal.getTime();

Modified: poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestBugs.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestBugs.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestBugs.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestBugs.java Tue Sep  1 23:10:43 2015
@@ -39,6 +39,7 @@ import java.util.Calendar;
 import java.util.Date;
 import java.util.Iterator;
 import java.util.List;
+import java.util.TimeZone;
 
 import org.apache.poi.EncryptedDocumentException;
 import org.apache.poi.hssf.HSSFITestDataProvider;
@@ -68,6 +69,7 @@ import org.apache.poi.ss.usermodel.BaseT
 import org.apache.poi.ss.usermodel.Cell;
 import org.apache.poi.ss.usermodel.CellStyle;
 import org.apache.poi.ss.usermodel.DataFormatter;
+import org.apache.poi.ss.usermodel.DateUtil;
 import org.apache.poi.ss.usermodel.FormulaEvaluator;
 import org.apache.poi.ss.usermodel.Name;
 import org.apache.poi.ss.usermodel.Row;
@@ -1730,8 +1732,8 @@ public final class TestBugs extends Base
      */
     @Test
     public void bug46664() throws Exception {
-       HSSFWorkbook wb = new HSSFWorkbook();
-       HSSFSheet sheet = wb.createSheet("new_sheet");
+       HSSFWorkbook wb1 = new HSSFWorkbook();
+       HSSFSheet sheet = wb1.createSheet("new_sheet");
        HSSFRow row = sheet.createRow((short)0);
        row.createCell(0).setCellValue(new HSSFRichTextString("Column A"));
        row.createCell(1).setCellValue(new HSSFRichTextString("Column B"));
@@ -1741,7 +1743,7 @@ public final class TestBugs extends Base
        row.createCell(5).setCellValue(new HSSFRichTextString("Column F"));
 
        //set print area from column a to column c (on first row)
-       wb.setPrintArea(
+       wb1.setPrintArea(
                0, //sheet index
                0, //start column
                2, //end column
@@ -1749,11 +1751,12 @@ public final class TestBugs extends Base
                0  //end row
        );
 
-       wb = writeOutAndReadBack(wb);
+       HSSFWorkbook wb2 = writeOutAndReadBack(wb1);
+       wb1.close();
 
        // Ensure the tab index
        TabIdRecord tr = null;
-       for(Record r : wb.getWorkbook().getRecords()) {
+       for(Record r : wb2.getWorkbook().getRecords()) {
           if(r instanceof TabIdRecord) {
              tr = (TabIdRecord)r;
           }
@@ -1763,20 +1766,21 @@ public final class TestBugs extends Base
        assertEquals(0, tr._tabids[0]);
 
        // Ensure the print setup
-       assertEquals("new_sheet!$A$1:$C$1", wb.getPrintArea(0));
-       assertEquals("new_sheet!$A$1:$C$1", wb.getName("Print_Area").getRefersToFormula());
+       assertEquals("new_sheet!$A$1:$C$1", wb2.getPrintArea(0));
+       assertEquals("new_sheet!$A$1:$C$1", wb2.getName("Print_Area").getRefersToFormula());
 
        // Needs reference not value
-       NameRecord nr = wb.getWorkbook().getNameRecord(
-             wb.getNameIndex("Print_Area")
+       NameRecord nr = wb2.getWorkbook().getNameRecord(
+               wb2.getNameIndex("Print_Area")
        );
        assertEquals("Print_Area", nr.getNameText());
        assertEquals(1, nr.getNameDefinition().length);
        assertEquals(
              "new_sheet!$A$1:$C$1",
-             ((Area3DPtg)nr.getNameDefinition()[0]).toFormulaString(HSSFEvaluationWorkbook.create(wb))
+             ((Area3DPtg)nr.getNameDefinition()[0]).toFormulaString(HSSFEvaluationWorkbook.create(wb2))
        );
        assertEquals('R', nr.getNameDefinition()[0].getRVAType());
+       wb2.close();
     }
 
     /**
@@ -1932,14 +1936,14 @@ public final class TestBugs extends Base
      */
     @Test
     public void bug49689() throws Exception {
-       HSSFWorkbook wb = new HSSFWorkbook();
-       HSSFSheet s = wb.createSheet("Test");
+       HSSFWorkbook wb1 = new HSSFWorkbook();
+       HSSFSheet s = wb1.createSheet("Test");
        HSSFRow r = s.createRow(0);
        HSSFCell c = r.createCell(0);
 
-       HSSFCellStyle cs1 = wb.createCellStyle();
-       HSSFCellStyle cs2 = wb.createCellStyle();
-       HSSFCellStyle cs3 = wb.createCellStyle();
+       HSSFCellStyle cs1 = wb1.createCellStyle();
+       HSSFCellStyle cs2 = wb1.createCellStyle();
+       HSSFCellStyle cs3 = wb1.createCellStyle();
 
        assertEquals(21, cs1.getIndex());
        cs1.setUserStyleName("Testing");
@@ -1954,12 +1958,14 @@ public final class TestBugs extends Base
        c.setCellStyle(cs1);
 
        // Write out and read back
-       wb = writeOutAndReadBack(wb);
+       HSSFWorkbook wb2 = writeOutAndReadBack(wb1);
 
        // Re-check
-       assertEquals("Testing", wb.getCellStyleAt((short)21).getUserStyleName());
-       assertEquals("Testing 2", wb.getCellStyleAt((short)22).getUserStyleName());
-       assertEquals("Testing 3", wb.getCellStyleAt((short)23).getUserStyleName());
+       assertEquals("Testing", wb2.getCellStyleAt((short)21).getUserStyleName());
+       assertEquals("Testing 2", wb2.getCellStyleAt((short)22).getUserStyleName());
+       assertEquals("Testing 3", wb2.getCellStyleAt((short)23).getUserStyleName());
+       
+       wb2.close();
     }
 
     @Test
@@ -2187,51 +2193,59 @@ public final class TestBugs extends Base
 
     @Test
     public void bug48968() throws Exception {
-       HSSFWorkbook wb = openSample("48968.xls");
-       assertEquals(1, wb.getNumberOfSheets());
-
-       DataFormatter fmt = new DataFormatter();
-
-       // Check the dates
-       HSSFSheet s = wb.getSheetAt(0);
-       Cell cell_d20110325 = s.getRow(0).getCell(0);
-       Cell cell_d19000102 = s.getRow(11).getCell(0);
-       Cell cell_d19000100 = s.getRow(21).getCell(0);
-       assertEquals(s.getRow(0).getCell(3).getStringCellValue(), fmt.formatCellValue(cell_d20110325));
-       assertEquals(s.getRow(11).getCell(3).getStringCellValue(), fmt.formatCellValue(cell_d19000102));
-       // There is no such thing as 00/01/1900...
-       assertEquals("00/01/1900 06:14:24", s.getRow(21).getCell(3).getStringCellValue());
-       assertEquals("31/12/1899 06:14:24", fmt.formatCellValue(cell_d19000100));
-
-       // Check the cached values
-       assertEquals("HOUR(A1)",   s.getRow(5).getCell(0).getCellFormula());
-       assertEquals(11.0,         s.getRow(5).getCell(0).getNumericCellValue(), 0);
-       assertEquals("MINUTE(A1)", s.getRow(6).getCell(0).getCellFormula());
-       assertEquals(39.0,         s.getRow(6).getCell(0).getNumericCellValue(), 0);
-       assertEquals("SECOND(A1)", s.getRow(7).getCell(0).getCellFormula());
-       assertEquals(54.0,         s.getRow(7).getCell(0).getNumericCellValue(), 0);
-
-       // Re-evaulate and check
-       HSSFFormulaEvaluator.evaluateAllFormulaCells(wb);
-       assertEquals("HOUR(A1)",   s.getRow(5).getCell(0).getCellFormula());
-       assertEquals(11.0,         s.getRow(5).getCell(0).getNumericCellValue(), 0);
-       assertEquals("MINUTE(A1)", s.getRow(6).getCell(0).getCellFormula());
-       assertEquals(39.0,         s.getRow(6).getCell(0).getNumericCellValue(), 0);
-       assertEquals("SECOND(A1)", s.getRow(7).getCell(0).getCellFormula());
-       assertEquals(54.0,         s.getRow(7).getCell(0).getNumericCellValue(), 0);
-
-       // Push the time forward a bit and check
-       double date = s.getRow(0).getCell(0).getNumericCellValue();
-       s.getRow(0).getCell(0).setCellValue(date + 1.26);
-
-       HSSFFormulaEvaluator.evaluateAllFormulaCells(wb);
-       assertEquals("HOUR(A1)",   s.getRow(5).getCell(0).getCellFormula());
-       assertEquals(11.0+6.0,     s.getRow(5).getCell(0).getNumericCellValue(), 0);
-       assertEquals("MINUTE(A1)", s.getRow(6).getCell(0).getCellFormula());
-       assertEquals(39.0+14.0+1,  s.getRow(6).getCell(0).getNumericCellValue(), 0);
-       assertEquals("SECOND(A1)", s.getRow(7).getCell(0).getCellFormula());
-       assertEquals(54.0+24.0-60, s.getRow(7).getCell(0).getNumericCellValue(), 0);
+       TimeZone tz = DateUtil.getUserTimeZone();
+       try {
+           DateUtil.setUserTimeZone(TimeZone.getTimeZone("CET"));
+           
+           HSSFWorkbook wb = openSample("48968.xls");
+           assertEquals(1, wb.getNumberOfSheets());
+    
+           DataFormatter fmt = new DataFormatter();
+    
+           // Check the dates
+           HSSFSheet s = wb.getSheetAt(0);
+           Cell cell_d20110325 = s.getRow(0).getCell(0);
+           Cell cell_d19000102 = s.getRow(11).getCell(0);
+           Cell cell_d19000100 = s.getRow(21).getCell(0);
+           assertEquals(s.getRow(0).getCell(3).getStringCellValue(), fmt.formatCellValue(cell_d20110325));
+           assertEquals(s.getRow(11).getCell(3).getStringCellValue(), fmt.formatCellValue(cell_d19000102));
+           // There is no such thing as 00/01/1900...
+           assertEquals("00/01/1900 06:14:24", s.getRow(21).getCell(3).getStringCellValue());
+           assertEquals("31/12/1899 06:14:24", fmt.formatCellValue(cell_d19000100));
+    
+           // Check the cached values
+           assertEquals("HOUR(A1)",   s.getRow(5).getCell(0).getCellFormula());
+           assertEquals(11.0,         s.getRow(5).getCell(0).getNumericCellValue(), 0);
+           assertEquals("MINUTE(A1)", s.getRow(6).getCell(0).getCellFormula());
+           assertEquals(39.0,         s.getRow(6).getCell(0).getNumericCellValue(), 0);
+           assertEquals("SECOND(A1)", s.getRow(7).getCell(0).getCellFormula());
+           assertEquals(54.0,         s.getRow(7).getCell(0).getNumericCellValue(), 0);
+    
+           // Re-evaulate and check
+           HSSFFormulaEvaluator.evaluateAllFormulaCells(wb);
+           assertEquals("HOUR(A1)",   s.getRow(5).getCell(0).getCellFormula());
+           assertEquals(11.0,         s.getRow(5).getCell(0).getNumericCellValue(), 0);
+           assertEquals("MINUTE(A1)", s.getRow(6).getCell(0).getCellFormula());
+           assertEquals(39.0,         s.getRow(6).getCell(0).getNumericCellValue(), 0);
+           assertEquals("SECOND(A1)", s.getRow(7).getCell(0).getCellFormula());
+           assertEquals(54.0,         s.getRow(7).getCell(0).getNumericCellValue(), 0);
+    
+           // Push the time forward a bit and check
+           double date = s.getRow(0).getCell(0).getNumericCellValue();
+           s.getRow(0).getCell(0).setCellValue(date + 1.26);
+    
+           HSSFFormulaEvaluator.evaluateAllFormulaCells(wb);
+           assertEquals("HOUR(A1)",   s.getRow(5).getCell(0).getCellFormula());
+           assertEquals(11.0+6.0,     s.getRow(5).getCell(0).getNumericCellValue(), 0);
+           assertEquals("MINUTE(A1)", s.getRow(6).getCell(0).getCellFormula());
+           assertEquals(39.0+14.0+1,  s.getRow(6).getCell(0).getNumericCellValue(), 0);
+           assertEquals("SECOND(A1)", s.getRow(7).getCell(0).getCellFormula());
+           assertEquals(54.0+24.0-60, s.getRow(7).getCell(0).getNumericCellValue(), 0);
+       } finally {
+           DateUtil.setUserTimeZone(tz);
+       }
     }
+       
 
     /**
      * Mixture of Ascii and Unicode strings in a
@@ -2418,23 +2432,25 @@ public final class TestBugs extends Base
 
     @Test
     public void bug53432() throws IOException{
-        Workbook wb = new HSSFWorkbook(); //or new HSSFWorkbook();
-        wb.addPicture(new byte[]{123,22}, Workbook.PICTURE_TYPE_JPEG);
-        assertEquals(wb.getAllPictures().size(), 1);
-        wb.close();
-
-        wb.close();
-        wb = new HSSFWorkbook();
-
-        wb = writeOutAndReadBack((HSSFWorkbook) wb);
-        assertEquals(wb.getAllPictures().size(), 0);
-        wb.addPicture(new byte[]{123,22}, Workbook.PICTURE_TYPE_JPEG);
-        assertEquals(wb.getAllPictures().size(), 1);
-
-        wb = writeOutAndReadBack((HSSFWorkbook) wb);
-        assertEquals(wb.getAllPictures().size(), 1);
+        Workbook wb1 = new HSSFWorkbook(); //or new HSSFWorkbook();
+        wb1.addPicture(new byte[]{123,22}, Workbook.PICTURE_TYPE_JPEG);
+        assertEquals(wb1.getAllPictures().size(), 1);
+        wb1.close();
+
+        wb1.close();
+        wb1 = new HSSFWorkbook();
+
+        Workbook wb2 = writeOutAndReadBack((HSSFWorkbook) wb1);
+        wb1.close();
+        assertEquals(wb2.getAllPictures().size(), 0);
+        wb2.addPicture(new byte[]{123,22}, Workbook.PICTURE_TYPE_JPEG);
+        assertEquals(wb2.getAllPictures().size(), 1);
+
+        Workbook wb3 = writeOutAndReadBack((HSSFWorkbook) wb2);
+        wb2.close();
+        assertEquals(wb3.getAllPictures().size(), 1);
         
-        wb.close();
+        wb3.close();
     }
 
     @Test
@@ -2539,30 +2555,34 @@ public final class TestBugs extends Base
 
     @Test
     public void bug56325() throws IOException {
-        HSSFWorkbook wb;
+        HSSFWorkbook wb1;
 
         File file = HSSFTestDataSamples.getSampleFile("56325.xls");
         InputStream stream = new FileInputStream(file);
         try {
             POIFSFileSystem fs = new POIFSFileSystem(stream);
-            wb = new HSSFWorkbook(fs);
+            wb1 = new HSSFWorkbook(fs);
         } finally {
             stream.close();
         }
 
-        assertEquals(3, wb.getNumberOfSheets());
-        wb.removeSheetAt(0);
-        assertEquals(2, wb.getNumberOfSheets());
+        assertEquals(3, wb1.getNumberOfSheets());
+        wb1.removeSheetAt(0);
+        assertEquals(2, wb1.getNumberOfSheets());
+
+        HSSFWorkbook wb2 = HSSFTestDataSamples.writeOutAndReadBack(wb1);
+        wb1.close();
+        assertEquals(2, wb2.getNumberOfSheets());
+        wb2.removeSheetAt(0);
+        assertEquals(1, wb2.getNumberOfSheets());
+        wb2.removeSheetAt(0);
+        assertEquals(0, wb2.getNumberOfSheets());
 
-        wb = HSSFTestDataSamples.writeOutAndReadBack(wb);
-        assertEquals(2, wb.getNumberOfSheets());
-        wb.removeSheetAt(0);
-        assertEquals(1, wb.getNumberOfSheets());
-        wb.removeSheetAt(0);
-        assertEquals(0, wb.getNumberOfSheets());
-
-        wb = HSSFTestDataSamples.writeOutAndReadBack(wb);
-        assertEquals(0, wb.getNumberOfSheets());
+        HSSFWorkbook wb3 = HSSFTestDataSamples.writeOutAndReadBack(wb2);
+        wb2.close();
+        
+        assertEquals(0, wb3.getNumberOfSheets());
+        wb3.close();
     }
 
     @Test

Modified: poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFCell.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFCell.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFCell.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/hssf/usermodel/TestHSSFCell.java Tue Sep  1 23:10:43 2015
@@ -18,10 +18,11 @@
 package org.apache.poi.hssf.usermodel;
 
 import java.io.IOException;
+import java.util.Calendar;
 import java.util.Date;
 import java.util.GregorianCalendar;
-
-import junit.framework.AssertionFailedError;
+import java.util.Locale;
+import java.util.TimeZone;
 
 import org.apache.poi.hssf.HSSFITestDataProvider;
 import org.apache.poi.hssf.HSSFTestDataSamples;
@@ -38,6 +39,8 @@ import org.apache.poi.ss.usermodel.Row;
 import org.apache.poi.ss.usermodel.Sheet;
 import org.apache.poi.ss.usermodel.Workbook;
 
+import junit.framework.AssertionFailedError;
+
 /**
  * Tests various functionality having to do with {@link HSSFCell}.  For instance support for
  * particular datatypes, etc.
@@ -57,7 +60,9 @@ public final class TestHSSFCell extends
 	 *  but there's a separate unit test for that.
 	 */
 	public void testDateWindowingRead() {
-		GregorianCalendar cal = new GregorianCalendar(2000,0,1); // Jan. 1, 2000
+	    Calendar cal = Calendar.getInstance(TimeZone.getTimeZone("UTC"), Locale.ROOT);
+	    cal.set(2000, 0, 1, 0, 0, 0); // Jan. 1, 2000
+	    cal.clear(Calendar.MILLISECOND);
 		Date date = cal.getTime();
 
 		// first check a file with 1900 Date Windowing

Modified: poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/AllFormulaEvalTests.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/AllFormulaEvalTests.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/AllFormulaEvalTests.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/AllFormulaEvalTests.java Tue Sep  1 23:10:43 2015
@@ -17,30 +17,26 @@
 
 package org.apache.poi.ss.formula.eval;
 
-import junit.framework.Test;
-import junit.framework.TestSuite;
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
 
 /**
  * Collects all tests the package <tt>org.apache.poi.hssf.record.formula.eval</tt>.
- *
- * @author Josh Micich
  */
+@RunWith(Suite.class)
+@Suite.SuiteClasses({
+    TestAreaEval.class,
+    TestHSSFCircularReferences.class,
+    TestDivideEval.class,
+    TestEqualEval.class,
+    TestExternalFunction.class,
+    TestFormulaBugs.class,
+    TestFormulasFromSpreadsheet.class,
+    TestMinusZeroResult.class,
+    TestMissingArgEval.class,
+    TestPercentEval.class,
+    TestRangeEval.class,
+    TestUnaryPlusEval.class,
+})
 public class AllFormulaEvalTests {
-
-	public static Test suite() {
-		TestSuite result = new TestSuite(AllFormulaEvalTests.class.getName());
-		result.addTestSuite(TestAreaEval.class);
-		result.addTestSuite(TestHSSFCircularReferences.class);
-		result.addTestSuite(TestDivideEval.class);
-		result.addTestSuite(TestEqualEval.class);
-		result.addTestSuite(TestExternalFunction.class);
-		result.addTestSuite(TestFormulaBugs.class);
-		result.addTestSuite(TestFormulasFromSpreadsheet.class);
-		result.addTestSuite(TestMinusZeroResult.class);
-		result.addTestSuite(TestMissingArgEval.class);
-		result.addTestSuite(TestPercentEval.class);
-		result.addTestSuite(TestRangeEval.class);
-		result.addTestSuite(TestUnaryPlusEval.class);
-		return result;
-	}
 }

Modified: poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/TestFormulasFromSpreadsheet.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/TestFormulasFromSpreadsheet.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/TestFormulasFromSpreadsheet.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/ss/formula/eval/TestFormulasFromSpreadsheet.java Tue Sep  1 23:10:43 2015
@@ -17,24 +17,30 @@
 
 package org.apache.poi.ss.formula.eval;
 
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertNotNull;
+import static org.junit.Assert.fail;
+
 import java.io.PrintStream;
 import java.util.Collection;
 import java.util.Locale;
 
-import junit.framework.Assert;
-import junit.framework.AssertionFailedError;
-import junit.framework.TestCase;
-
 import org.apache.poi.hssf.HSSFTestDataSamples;
-import org.apache.poi.ss.formula.functions.TestMathX;
 import org.apache.poi.hssf.usermodel.HSSFFormulaEvaluator;
 import org.apache.poi.hssf.usermodel.HSSFWorkbook;
+import org.apache.poi.ss.formula.functions.TestMathX;
 import org.apache.poi.ss.usermodel.Cell;
 import org.apache.poi.ss.usermodel.CellValue;
 import org.apache.poi.ss.usermodel.Row;
 import org.apache.poi.ss.usermodel.Sheet;
 import org.apache.poi.util.POILogFactory;
 import org.apache.poi.util.POILogger;
+import org.junit.Assert;
+import org.junit.Before;
+import org.junit.Test;
+
+import junit.framework.AssertionFailedError;
+import junit.framework.TestCase;
 
 /**
  * Tests formulas and operators as loaded from a test data spreadsheet.<p/>
@@ -46,7 +52,7 @@ import org.apache.poi.util.POILogger;
  *
  * @author Amol S. Deshmukh &lt; amolweb at ya hoo dot com &gt;
  */
-public final class TestFormulasFromSpreadsheet extends TestCase {
+public final class TestFormulasFromSpreadsheet {
     private static final POILogger logger = POILogFactory.getLogger(TestFormulasFromSpreadsheet.class);
 
 	private static final class Result {
@@ -111,12 +117,8 @@ public final class TestFormulasFromSprea
 
 
 	private static void confirmExpectedResult(String msg, Cell expected, CellValue actual) {
-		if (expected == null) {
-			throw new AssertionFailedError(msg + " - Bad setup data expected value is null");
-		}
-		if(actual == null) {
-			throw new AssertionFailedError(msg + " - actual value was null");
-		}
+		assertNotNull(msg + " - Bad setup data expected value is null", expected);
+		assertNotNull(msg + " - actual value was null", actual);
 
 		switch (expected.getCellType()) {
 			case Cell.CELL_TYPE_BLANK:
@@ -131,7 +133,7 @@ public final class TestFormulasFromSprea
 				assertEquals(msg, ErrorEval.getText(expected.getErrorCellValue()), ErrorEval.getText(actual.getErrorValue()));
 				break;
 			case Cell.CELL_TYPE_FORMULA: // will never be used, since we will call method after formula evaluation
-				throw new AssertionFailedError("Cannot expect formula as result of formula evaluation: " + msg);
+				fail("Cannot expect formula as result of formula evaluation: " + msg);
 			case Cell.CELL_TYPE_NUMERIC:
 				assertEquals(msg, Cell.CELL_TYPE_NUMERIC, actual.getCellType());
 				TestMathX.assertEquals(msg, expected.getNumericCellValue(), actual.getNumberValue(), TestMathX.POS_ZERO, TestMathX.DIFF_TOLERANCE_FACTOR);
@@ -143,7 +145,7 @@ public final class TestFormulasFromSprea
 		}
 	}
 
-
+	@Before
 	protected void setUp() {
 		if (workbook == null) {
 			workbook = HSSFTestDataSamples.openSampleWorkbook(SS.FILENAME);
@@ -155,6 +157,7 @@ public final class TestFormulasFromSprea
 		_evaluationSuccessCount = 0;
 	}
 
+	@Test
 	public void testFunctionsFromTestSpreadsheet() {
 
 		processFunctionGroup(SS.START_OPERATORS_ROW_INDEX, null);
@@ -167,11 +170,9 @@ public final class TestFormulasFromSprea
 		String successMsg = "There were "
 				+ _evaluationSuccessCount + " successful evaluation(s) and "
 				+ _functionSuccessCount + " function(s) without error";
-		if(_functionFailureCount > 0) {
-			String msg = _functionFailureCount + " function(s) failed in "
-			+ _evaluationFailureCount + " evaluation(s).  " + successMsg;
-			throw new AssertionFailedError(msg);
-		}
+        String msg = _functionFailureCount + " function(s) failed in "
+                + _evaluationFailureCount + " evaluation(s).  " + successMsg;
+		assertEquals(msg, _functionFailureCount, 0);
         logger.log(POILogger.INFO, getClass().getName() + ": " + successMsg);
 	}
 
@@ -188,11 +189,9 @@ public final class TestFormulasFromSprea
 		while (true) {
 			Row r = sheet.getRow(rowIndex);
 			String targetFunctionName = getTargetFunctionName(r);
-			if(targetFunctionName == null) {
-				throw new AssertionFailedError("Test spreadsheet cell empty on row ("
-						+ (rowIndex+1) + "). Expected function name or '"
-						+ SS.FUNCTION_NAMES_END_SENTINEL + "'");
-			}
+			assertNotNull("Test spreadsheet cell empty on row ("
+                    + (rowIndex+1) + "). Expected function name or '"
+                    + SS.FUNCTION_NAMES_END_SENTINEL + "'", targetFunctionName);
 			if(targetFunctionName.equals(SS.FUNCTION_NAMES_END_SENTINEL)) {
 				// found end of functions list
 				break;
@@ -201,11 +200,9 @@ public final class TestFormulasFromSprea
 
 				// expected results are on the row below
 				Row expectedValuesRow = sheet.getRow(rowIndex + 1);
-				if(expectedValuesRow == null) {
-					int missingRowNum = rowIndex + 2; //+1 for 1-based, +1 for next row
-					throw new AssertionFailedError("Missing expected values row for function '"
-							+ targetFunctionName + " (row " + missingRowNum + ")");
-				}
+                int missingRowNum = rowIndex + 2; //+1 for 1-based, +1 for next row
+                assertNotNull("Missing expected values row for function '"
+                        + targetFunctionName + " (row " + missingRowNum + ")", expectedValuesRow);
 				switch(processFunctionRow(evaluator, targetFunctionName, r, expectedValuesRow)) {
 					case Result.ALL_EVALUATIONS_SUCCEEDED: _functionSuccessCount++; break;
 					case Result.SOME_EVALUATIONS_FAILED: _functionFailureCount++; break;

Modified: poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/AllIndividualFunctionEvaluationTests.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/AllIndividualFunctionEvaluationTests.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/AllIndividualFunctionEvaluationTests.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/AllIndividualFunctionEvaluationTests.java Tue Sep  1 23:10:43 2015
@@ -17,51 +17,47 @@
 
 package org.apache.poi.ss.formula.functions;
 
-import junit.framework.Test;
-import junit.framework.TestSuite;
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
 
 /**
  * Direct tests for all implementors of <code>Function</code>.
- *
- * @author Josh Micich
  */
-public final class AllIndividualFunctionEvaluationTests {
-
-	public static Test suite() {
-		TestSuite result = new TestSuite(AllIndividualFunctionEvaluationTests.class.getName());
-		result.addTestSuite(TestAverage.class);
-		result.addTestSuite(TestCountFuncs.class);
-		result.addTestSuite(TestDate.class);
-		result.addTestSuite(TestDays360.class);
-		result.addTestSuite(TestFinanceLib.class);
-		result.addTestSuite(TestFind.class);
-		result.addTestSuite(TestIndex.class);
-		result.addTestSuite(TestIndexFunctionFromSpreadsheet.class);
-		result.addTestSuite(TestIndirect.class);
-		result.addTestSuite(TestIsBlank.class);
-		result.addTestSuite(TestLen.class);
-		result.addTestSuite(TestLookupFunctionsFromSpreadsheet.class);
-		result.addTestSuite(TestMatch.class);
-		result.addTestSuite(TestMathX.class);
-		result.addTestSuite(TestMid.class);
-		result.addTestSuite(TestNper.class);
-		result.addTestSuite(TestOffset.class);
-		result.addTestSuite(TestPmt.class);
-		result.addTestSuite(TestRoundFuncs.class);
-		result.addTestSuite(TestRowCol.class);
-		result.addTestSuite(TestStatsLib.class);
-		result.addTestSuite(TestSubtotal.class);
-		result.addTestSuite(TestSumif.class);
-		result.addTestSuite(TestSumproduct.class);
-		result.addTestSuite(TestText.class);
-		result.addTestSuite(TestTFunc.class);
-		result.addTestSuite(TestTime.class);
-		result.addTestSuite(TestTrim.class);
-		result.addTestSuite(TestTrunc.class);
-		result.addTestSuite(TestValue.class);
-		result.addTestSuite(TestXYNumericFunction.class);
-		result.addTestSuite(TestAddress.class);
-		result.addTestSuite(TestClean.class);
-		return result;
-	}
+@RunWith(Suite.class)
+@Suite.SuiteClasses({
+    TestAverage.class,
+    TestCountFuncs.class,
+    TestDate.class,
+    TestDays360.class,
+    TestFinanceLib.class,
+    TestFind.class,
+    TestIndex.class,
+    TestIndexFunctionFromSpreadsheet.class,
+    TestIndirect.class,
+    TestIsBlank.class,
+    TestLen.class,
+    TestLookupFunctionsFromSpreadsheet.class,
+    TestMatch.class,
+    TestMathX.class,
+    TestMid.class,
+    TestNper.class,
+    TestOffset.class,
+    TestPmt.class,
+    TestRoundFuncs.class,
+    TestRowCol.class,
+    TestStatsLib.class,
+    TestSubtotal.class,
+    TestSumif.class,
+    TestSumproduct.class,
+    TestText.class,
+    TestTFunc.class,
+    TestTime.class,
+    TestTrim.class,
+    TestTrunc.class,
+    TestValue.class,
+    TestXYNumericFunction.class,
+    TestAddress.class,
+    TestClean.class
+})
+public class AllIndividualFunctionEvaluationTests {
 }

Modified: poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/TestDays360.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/TestDays360.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/TestDays360.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/ss/formula/functions/TestDays360.java Tue Sep  1 23:10:43 2015
@@ -17,52 +17,38 @@
 
 package org.apache.poi.ss.formula.functions;
 
+import static org.junit.Assert.assertEquals;
+import static org.junit.Assert.assertTrue;
+
 import java.util.Calendar;
 import java.util.Date;
-import java.util.GregorianCalendar;
 import java.util.Locale;
 
-import junit.framework.AssertionFailedError;
-import junit.framework.TestCase;
-
+import org.apache.poi.hssf.usermodel.HSSFDateUtil;
 import org.apache.poi.ss.formula.eval.BoolEval;
 import org.apache.poi.ss.formula.eval.NumberEval;
 import org.apache.poi.ss.formula.eval.ValueEval;
-import org.apache.poi.hssf.usermodel.HSSFDateUtil;
+import org.junit.Test;
 
-/**
- * @author Josh Micich
- */
-public final class TestDays360 extends TestCase {
+public final class TestDays360 {
 
 	/**
 	 * @param month 1-based
 	 */
 	private static Date makeDate(int year, int month, int day) {
-
-		Calendar cal = new GregorianCalendar(year, month-1, day, 0, 0, 0);
+		Calendar cal = Calendar.getInstance(Locale.ROOT);
+		cal.set(year, month-1, day, 0, 0, 0);
 		cal.set(Calendar.MILLISECOND, 0);
 		return cal.getTime();
 	}
+
 	private static Date decrementDay(Date d) {
-		Calendar c = new GregorianCalendar(Locale.ROOT);
-		c.setTimeInMillis(d.getTime());
+		Calendar c = (Calendar)d.clone();
 		c.add(Calendar.DAY_OF_MONTH, -1);
 		return c.getTime();
 	}
-	private static String fmt(Date d) {
-		Calendar c = new GregorianCalendar(Locale.ROOT);
-		c.setTimeInMillis(d.getTime());
-		StringBuilder sb = new StringBuilder();
-		sb.append(c.get(Calendar.YEAR));
-		sb.append("/");
-		sb.append(c.get(Calendar.MONTH)+1);
-		sb.append("/");
-		sb.append(c.get(Calendar.DAY_OF_MONTH));
-		return sb.toString();
-	}
-
 
+	@Test
 	public void testBasic() {
 		confirm(120, 2009, 1, 15, 2009, 5, 15);
 		confirm(158, 2009, 1, 26, 2009, 7, 4);
@@ -74,37 +60,47 @@ public final class TestDays360 extends T
 		// longer time spans
 		confirm(562, 2008, 8, 11, 2010, 3, 3);
 		confirm(916, 2007, 2, 23, 2009, 9, 9);
+		
+		// other tests
+		confirm(1, makeDate(1993, 2, 28), makeDate(1993, 3, 1), false);
+        confirm(1, makeDate(1996, 2, 29), makeDate(1996, 3, 1), false);
+        confirm(-2, makeDate(1993, 2, 28), makeDate(1993, 2, 28), false);
+        confirm(3, makeDate(1993, 2, 28), makeDate(1993, 3, 1), true);
+        confirm(2, makeDate(1996, 2, 29), makeDate(1996, 3, 1), true);
 	}
 
 	private static void confirm(int expResult, int y1, int m1, int d1, int y2, int m2, int d2) {
 		confirm(expResult, makeDate(y1, m1, d1), makeDate(y2, m2, d2), false);
 		confirm(-expResult, makeDate(y2, m2, d2), makeDate(y1, m1, d1), false);
-
 	}
+	
 	/**
 	 * The <tt>method</tt> parameter only makes a difference when the second parameter
 	 * is the last day of the month that does <em>not</em> have 30 days.
 	 */
-	public void DISABLED_testMonthBoundaries() {
+	@Test
+	public void testMonthBoundaries() {
 		// jan
-		confirmMonthBoundary(false, 1, 0, 0, 2, 3, 4);
-		confirmMonthBoundary(true,  1, 0, 0, 1, 3, 4);
+		confirmMonthBoundary(false, 2001, 1, 0, 0, 2, 3, 4);
+		confirmMonthBoundary(true,  2001, 1, 0, 0, 1, 2, 3);
 		// feb
-		confirmMonthBoundary(false, 2,-2, 1, 2, 3, 4);
-		confirmMonthBoundary(true,  2, 0, 1, 2, 3, 4);
+		confirmMonthBoundary(false, 2001, 2,-2, 1, 2, 3, 4);
+		confirmMonthBoundary(true,  2001, 2, 0, 1, 2, 3, 4);
 		// mar
-		confirmMonthBoundary(false, 3, 0, 0, 2, 3, 4);
-		confirmMonthBoundary(true,  3, 0, 0, 1, 3, 4);
+		confirmMonthBoundary(false, 2001, 3, 0, 0, 2, 3, 4);
+		confirmMonthBoundary(true,  2001, 3, 0, 0, 1, 2, 3);
 		// apr
-		confirmMonthBoundary(false, 4, 0, 1, 2, 3, 4);
-		confirmMonthBoundary(true,  4, 0, 1, 2, 3, 4);
+		confirmMonthBoundary(false, 2001, 4, 0, 1, 2, 3, 4);
+		confirmMonthBoundary(true,  2001, 4, 0, 1, 2, 3, 4);
 		// may
-		confirmMonthBoundary(false, 5, 0, 0, 2, 3, 4);
-		confirmMonthBoundary(true,  5, 0, 0, 1, 3, 4);
+		confirmMonthBoundary(false, 2001, 5, 0, 0, 2, 3, 4);
+		confirmMonthBoundary(true,  2001, 5, 0, 0, 1, 2, 3);
 		// jun
-		confirmMonthBoundary(false, 6, 0, 1, 2, 3, 4);
-		confirmMonthBoundary(true,  6, 0, 1, 2, 3, 4);
-		// etc...
+		confirmMonthBoundary(false, 2001, 6, 0, 1, 2, 3, 4);
+		confirmMonthBoundary(true,  2001, 6, 0, 1, 2, 3, 4);
+        // leap year
+        confirmMonthBoundary(false, 2012, 2, -1, 1, 2, 3, 4);
+        confirmMonthBoundary(true,  2012, 2, 0, 1, 2, 3, 4);
 	}
 
 
@@ -112,13 +108,12 @@ public final class TestDays360 extends T
 	 * @param monthNo 1-based
 	 * @param diffs
 	 */
-	private static void confirmMonthBoundary(boolean method, int monthNo, int...diffs) {
-		Date firstDayOfNextMonth = makeDate(2001, monthNo+1, 1);
+	private static void confirmMonthBoundary(boolean method, int year, int monthNo, int...diffs) {
+		Date firstDayOfNextMonth = makeDate(year, monthNo+1, 1);
 		Date secondArg = decrementDay(firstDayOfNextMonth);
 		Date firstArg = secondArg;
 
-		for (int i = 0; i < diffs.length; i++) {
-			int expResult = diffs[i];
+		for (int expResult : diffs) {
 			confirm(expResult, firstArg, secondArg, method);
 			firstArg = decrementDay(firstArg);
 		}
@@ -133,22 +128,17 @@ public final class TestDays360 extends T
 		} else {
 			ve = invokeDays360(convert(firstArg), convert(secondArg));
 		}
-		if (ve instanceof NumberEval) {
+		assertTrue("wrong return type (" + ve.getClass().getName() + ")", ve instanceof NumberEval);
 
-			NumberEval numberEval = (NumberEval) ve;
-			if (numberEval.getNumberValue() != expResult) {
-				throw new AssertionFailedError(fmt(firstArg) + " " + fmt(secondArg) + " " + method +
-						" wrong result got (" + numberEval.getNumberValue()
-						+ ") but expected (" + expResult + ")");
-			}
-			//	System.err.println(fmt(firstArg) + " " + fmt(secondArg) + " " + method + " success got (" + expResult + ")");
-			return;
-		}
-		throw new AssertionFailedError("wrong return type (" + ve.getClass().getName() + ")");
+		NumberEval numberEval = (NumberEval) ve;
+		String err = String.format(Locale.ROOT, "days360(%tF,%tF,%b) wrong result", firstArg, secondArg, method);
+		assertEquals(err, expResult, numberEval.getNumberValue(), 0);
 	}
+	
 	private static ValueEval invokeDays360(ValueEval...args) {
 		return new Days360().evaluate(args, -1, -1);
 	}
+	
 	private static NumberEval convert(Date d) {
 		return new NumberEval(HSSFDateUtil.getExcelDate(d));
 	}

Modified: poi/trunk/src/testcases/org/apache/poi/ss/formula/ptg/AllFormulaTests.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/ss/formula/ptg/AllFormulaTests.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/ss/formula/ptg/AllFormulaTests.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/ss/formula/ptg/AllFormulaTests.java Tue Sep  1 23:10:43 2015
@@ -22,40 +22,34 @@ import org.apache.poi.ss.formula.TestShe
 import org.apache.poi.ss.formula.eval.AllFormulaEvalTests;
 import org.apache.poi.ss.formula.function.AllFormulaFunctionTests;
 import org.apache.poi.ss.formula.functions.AllIndividualFunctionEvaluationTests;
-
-import junit.framework.Test;
-import junit.framework.TestSuite;
+import org.junit.runner.RunWith;
+import org.junit.runners.Suite;
 
 /**
  * Collects all tests for <tt>org.apache.poi.hssf.record.formula</tt>.
- * 
- * @author Josh Micich
  */
-public final class AllFormulaTests {
-	
-	public static Test suite() {
-		TestSuite result = new TestSuite(AllFormulaTests.class.getName());
-		result.addTest(AllFormulaEvalTests.suite());
-		result.addTest(AllFormulaFunctionTests.suite());
-		result.addTest(AllIndividualFunctionEvaluationTests.suite());
-
-		result.addTestSuite(TestArea3DPtg.class);
-		result.addTestSuite(TestAreaErrPtg.class);
-		result.addTestSuite(TestAreaPtg.class);
-		result.addTestSuite(TestArrayPtg.class);
-		result.addTestSuite(TestAttrPtg.class);
-		result.addTestSuite(TestErrPtg.class);
-		result.addTestSuite(TestExternalFunctionFormulas.class);
-		result.addTestSuite(TestFormulaShifter.class);
-		result.addTestSuite(TestFuncPtg.class);
-		result.addTestSuite(TestFuncVarPtg.class);
-		result.addTestSuite(TestIntersectionPtg.class);
-		result.addTestSuite(TestPercentPtg.class);
-		result.addTestSuite(TestRangePtg.class);
-		result.addTestSuite(TestRef3DPtg.class);
-		result.addTestSuite(TestReferencePtg.class);
-		result.addTestSuite(TestSheetNameFormatter.class);
-		result.addTestSuite(TestUnionPtg.class);
-		return result;
-	}
+@RunWith(Suite.class)
+@Suite.SuiteClasses({
+    AllFormulaEvalTests.class,
+    AllFormulaFunctionTests.class,
+    AllIndividualFunctionEvaluationTests.class,
+    TestArea3DPtg.class,
+    TestAreaErrPtg.class,
+    TestAreaPtg.class,
+    TestArrayPtg.class,
+    TestAttrPtg.class,
+    TestErrPtg.class,
+    TestExternalFunctionFormulas.class,
+    TestFormulaShifter.class,
+    TestFuncPtg.class,
+    TestFuncVarPtg.class,
+    TestIntersectionPtg.class,
+    TestPercentPtg.class,
+    TestRangePtg.class,
+    TestRef3DPtg.class,
+    TestReferencePtg.class,
+    TestSheetNameFormatter.class,
+    TestUnionPtg.class,    
+})
+public class AllFormulaTests {
 }

Modified: poi/trunk/src/testcases/org/apache/poi/ss/usermodel/BaseTestCell.java
URL: http://svn.apache.org/viewvc/poi/trunk/src/testcases/org/apache/poi/ss/usermodel/BaseTestCell.java?rev=1700686&r1=1700685&r2=1700686&view=diff
==============================================================================
--- poi/trunk/src/testcases/org/apache/poi/ss/usermodel/BaseTestCell.java (original)
+++ poi/trunk/src/testcases/org/apache/poi/ss/usermodel/BaseTestCell.java Tue Sep  1 23:10:43 2015
@@ -19,6 +19,8 @@ package org.apache.poi.ss.usermodel;
 
 import java.io.IOException;
 import java.util.Calendar;
+import java.util.Locale;
+import java.util.TimeZone;
 
 import junit.framework.AssertionFailedError;
 import junit.framework.TestCase;
@@ -78,7 +80,7 @@ public abstract class BaseTestCell exten
 		assertProhibitedValueAccess(cell, Cell.CELL_TYPE_NUMERIC, Cell.CELL_TYPE_BOOLEAN,
 				Cell.CELL_TYPE_FORMULA, Cell.CELL_TYPE_ERROR);
 
-		Calendar c = Calendar.getInstance();
+		Calendar c = Calendar.getInstance(TimeZone.getTimeZone("UTC"), Locale.ROOT);
 		c.setTimeInMillis(123456789);
 		cell.setCellValue(c.getTime());
 		assertEquals(c.getTime().getTime(), cell.getDateCellValue().getTime());



---------------------------------------------------------------------
To unsubscribe, e-mail: commits-unsubscribe@poi.apache.org
For additional commands, e-mail: commits-help@poi.apache.org