JDK-8189862 : java.io.File constructor File(File, String) creates wrong path on Windows JDK9
  • Type: Bug
  • Component: core-libs
  • Sub-Component: java.io
  • Affected Version: 9
  • Priority: P3
  • Status: Closed
  • Resolution: Not an Issue
  • OS: windows
  • CPU: x86_64
  • Submitted: 2017-10-17
  • Updated: 2017-11-13
  • Resolved: 2017-10-25
Related Reports
Relates :  
Description
FULL PRODUCT VERSION :
java version "9"
Java(TM) SE Runtime Environment (build 9+181)
Java HotSpot(TM) 64-Bit Server VM (build 9+181, mixed mode)

ADDITIONAL OS VERSION INFORMATION :
Microsoft Windows [Version 10.0.15063]

A DESCRIPTION OF THE PROBLEM :
when the parent File object has only drive name (such as 'c:'),
the sub folder constructor File(File, String) creates wrong path on JDK9.
JDK8 works fine.

STEPS TO FOLLOW TO REPRODUCE THE PROBLEM :
see the test code.

EXPECTED VERSUS ACTUAL BEHAVIOR :
EXPECTED -
see the test code.
ACTUAL -
see the stack trace.

ERROR MESSAGES/STACK TRACES THAT OCCUR :
java.lang.AssertionError: 
Expected: is "C:\a"
     but: was "C:a"
	at org.hamcrest.MatcherAssert.assertThat(MatcherAssert.java:20)
	at org.junit.Assert.assertThat(Assert.java:956)
	at org.junit.Assert.assertThat(Assert.java:923)
	at FileConstructorTest.test(FileConstructorTest.java:13)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke0(Native Method)
	at java.base/jdk.internal.reflect.NativeMethodAccessorImpl.invoke(NativeMethodAccessorImpl.java:62)
	at java.base/jdk.internal.reflect.DelegatingMethodAccessorImpl.invoke(DelegatingMethodAccessorImpl.java:43)
	at java.base/java.lang.reflect.Method.invoke(Method.java:564)
	at org.junit.runners.model.FrameworkMethod$1.runReflectiveCall(FrameworkMethod.java:50)
	at org.junit.internal.runners.model.ReflectiveCallable.run(ReflectiveCallable.java:12)
	at org.junit.runners.model.FrameworkMethod.invokeExplosively(FrameworkMethod.java:47)
	at org.junit.internal.runners.statements.InvokeMethod.evaluate(InvokeMethod.java:17)
	at org.junit.runners.ParentRunner.runLeaf(ParentRunner.java:325)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:78)
	at org.junit.runners.BlockJUnit4ClassRunner.runChild(BlockJUnit4ClassRunner.java:57)
	at org.junit.runners.ParentRunner$3.run(ParentRunner.java:290)
	at org.junit.runners.ParentRunner$1.schedule(ParentRunner.java:71)
	at org.junit.runners.ParentRunner.runChildren(ParentRunner.java:288)
	at org.junit.runners.ParentRunner.access$000(ParentRunner.java:58)
	at org.junit.runners.ParentRunner$2.evaluate(ParentRunner.java:268)
	at org.junit.runners.ParentRunner.run(ParentRunner.java:363)
	at org.eclipse.jdt.internal.junit4.runner.JUnit4TestReference.run(JUnit4TestReference.java:86)
	at org.eclipse.jdt.internal.junit.runner.TestExecution.run(TestExecution.java:38)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:539)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.runTests(RemoteTestRunner.java:761)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.run(RemoteTestRunner.java:461)
	at org.eclipse.jdt.internal.junit.runner.RemoteTestRunner.main(RemoteTestRunner.java:207)



REPRODUCIBILITY :
This bug can be reproduced always.

---------- BEGIN SOURCE ----------
import static org.hamcrest.Matchers.*;
import static org.junit.Assert.*;

import java.io.File;

import org.junit.Test;

public class FileConstructorTest {
    
    @Test
    public void test() {
        File parent = new File("C:");
        assertThat(new File(parent, "a").toString(), is("C:\\a"));
    }

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


Comments
Closing as not an issue as per the comment above.
25-10-2017

The correct result is "C:a", not "C:\a". So I think we can close this bug.
24-10-2017

The documentation at https://docs.oracle.com/javase/9/docs/api/java/io/File.html mentions that : For Microsoft Windows platforms, the prefix of a pathname that contains a drive specifier consists of the drive letter followed by ":" and *****possibly***** followed by "\\" if the pathname is absolute. But in JDK 9, the test case passes only when "\\" is appended to C: , whereas in JDK 8, it passes both with or without "\\" appended to C: Attached is the test case to reproduce this: JDK 8u151- Pass JDK 9+181 - Fail
24-10-2017