Uploaded image for project: 'JDK'
  1. JDK
  2. JDK-8190835

Subtraction with two javax.xml.datatype.Duration gives incorrect result

XMLWordPrintable

    • b01
    • x86_64
    • windows_10

      FULL PRODUCT VERSION :
      java version "1.8.0_152"
      Java(TM) SE Runtime Environment (build 1.8.0_152-b16)
      Java HotSpot(TM) 64-Bit Server VM (build 25.152-b16, mixed mode)

      ADDITIONAL OS VERSION INFORMATION :
      Edition: Windows 10 Pro
      Version: 1703
      OS Build: 15063.674
      System type: 64-bit operating system, x64-based processor

      A DESCRIPTION OF THE PROBLEM :
      Subtracting one javax.xml.datatype.Duration from another under certain conditions results in an incorrectly large number of minutes and seconds. The error occurs for time only operations which aren't outlier values so warnings in the JavaDoc about meaningless operations wouldn't be expected. The same calculation with java.time.Duration gives the correct result.

      Conditions
      * decimal seconds
      * non-zero minutes
      * second operand has a greater number of seconds than the first operand, i.e. the minutes are reduced.
       

      STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
      * Create an instance of javax.xml.datatype.DatatypeFactory.
      * Parse two duration strings with time components listed. e.g. "PT1M3.123S" to obtain two java.xml.datatype.Duration objects.
      * Use java.xml.datatype.Duration.subtract method to obtain result java.xml.datatype.Duration.

      EXPECTED VERSUS ACTUAL BEHAVIOR :
      EXPECTED -
      The subtraction should produce the calculable values as expected.

      2 minutes 3.123 seconds - 1 min 10.123 seconds = 53 seconds
      1 hour 4 minutes 3.123 seconds - 10.123 seconds = 1 hour 3 minutes 53 seconds
      ACTUAL -
      The values produced are incorrect, constant and appear to have an interrelation between different examples.

      2 minutes 3.123 seconds - 1 min 10.123 seconds = 883 minutes 0.020 seconds
      1 hour 4 minutes 3.123 seconds - 10.123 seconds = 1 hour 3883 minutes 0.020 seconds

      ERROR MESSAGES/STACK TRACES THAT OCCUR :
      There is no error, warning or crash log.

      REPRODUCIBILITY :
      This bug can be reproduced always.

      ---------- BEGIN SOURCE ----------
      Includes example of working cases using java.time.Duration.

      import java.time.Duration;
      import javax.xml.datatype.DatatypeConfigurationException;
      import javax.xml.datatype.DatatypeFactory;

      public class ExApp {

          public static void main(String[] args) throws DatatypeConfigurationException {

              //javax.xml.datatype.Duration - INCORRECT
              //Expected result: PT53S
              //Java result: PT1H883M0.020S
              DatatypeFactory factory = DatatypeFactory.newInstance();
              javax.xml.datatype.Duration dt1 = factory.newDuration("PT2M3.123S");
              javax.xml.datatype.Duration dt2 = factory.newDuration("PT1M10.123S");

              javax.xml.datatype.Duration res1 = dt1.subtract(dt2);
              System.out.println(dt1 + " - " + dt2 + " = " + res1);

              //java.time.Duration - CORRECT
              //Expected result: PT53S
              //Java result: PT53S
              Duration dur1 = Duration.parse("PT2M3.123S");
              Duration dur2 = Duration.parse("PT1M10.123S");
              Duration result = dur1.minus(dur2);
              System.out.println(dur1 + " - " + dur2 + " = " + result);

              //javax.xml.datatype.Duration - INCORRECT
              //Expected result:PT1H3M53S
              //Java result: PT1H3883M0.020S
              dt1 = factory.newDuration("PT1H4M3.123S");
              dt2 = factory.newDuration("PT10.123S");

              res1 = dt1.subtract(dt2);
              System.out.println(dt1 + " - " + dt2 + " = " + res1);

              //java.time.Duration - CORRECT
              //Expected result: PT1H3M53S
              //Java result: PT1H3M53S
              dur1 = Duration.parse("PT1H4M3.123S");
              dur2 = Duration.parse("PT10.123S");
              result = dur1.minus(dur2); //gives "PT53S" - correct
              System.out.println(dur1 + " - " + dur2 + " = " + result);

          }

      }
      ---------- END SOURCE ----------

      CUSTOMER SUBMITTED WORKAROUND :
      Workaround is to use java.time.Duration. However, the javax.xml.datatype.Duration is a legacy dependency in existing libraries and so beyond the control to workaround in this way.

            joehw Joe Wang
            webbuggrp Webbug Group
            Votes:
            0 Vote for this issue
            Watchers:
            2 Start watching this issue

              Created:
              Updated:
              Resolved: