2008-09-25 348 views
11

我尝试使用下面的代码复制文件:哪些java.io.IOException的可能原因:“文件名,目录名或卷标语法不正确”

File targetFile = new File(targetPath + File.separator + filename); 
... 
targetFile.createNewFile(); 
fileInputStream = new FileInputStream(fileToCopy); 
fileOutputStream = new FileOutputStream(targetFile); 
byte[] buffer = new byte[64*1024]; 
int i = 0; 
while((i = fileInputStream.read(buffer)) != -1) { 
    fileOutputStream.write(buffer, 0, i); 
} 

对于一些用户在targetFile.createNewFile导致此异常:

java.io.IOException: The filename, directory name, or volume label syntax is incorrect 
    at java.io.WinNTFileSystem.createFileExclusively(Native Method) 
    at java.io.File.createNewFile(File.java:850) 

文件名和目录名似乎是正确的。在执行复制代码之前的目录targetPath甚至检查是否存在以及文件名看起来像这样:AB_timestamp.xml

用户有写权限targetPath,可以复制该文件,而无需使用操作系统的问题。

由于我没有访问此机还发生在,不能重现我为你们的提示在此例外的原因,我自己的机器上的问题。

回答

5

试试这个,因为它需要在TARGETPATH和文件名之间的路径调整目录分隔符的更多的关怀:

File targetFile = new File(targetPath, filename); 
0

你检查TARGETPATH是一个目录,或者存在同名只是些什么呢? (我知道你说用户可以从操作系统复制它,但也许他们正在输入其他东西)。

targetPath是否已经以File.separator结束?

(这将有助于如果您可以登录并告诉我们TARGETPATH和文件名的值是一个失败的情况下)

0

也许问题是,它是复制在网络上的文件,在共享驱动器?我认为在使用NFS编写文件时,如果路径是\ mypc \ myshared文件夹,Java可能会出现问题。

这个问题发生的路径是什么?

0

尝试添加一些记录,看看到底什么是文件试图创建,以确保父母是很好的目录名称和路径。

此外,您还可以看看电视,而不是使用循环。 ;-)

0

你说“对于一些用户” - 所以它适用于其他人?这里有什么区别,用户是在不同的机器上运行不同的实例,还是服务于并发用户的服务器?

如果是后者,我会说这是一种并发错误莫名其妙 - 两个线程检查尝试创建与WinNTFileSystem.createFileExclusively(本机方法)同时放文件。

当我看在OpenJDK源无论createNewFile或createFileExclusively是同步的,所以你可能要同步这个块自己。

1

尝试在不同目录中创建文件 - 例如, “C:\”在你确认你有写入权限之后。如果可行,文件的路径名称是错误的。

看看在异常的注释,并尝试以改变文件的路径名的所有元素。实验。得出结论。

0

也许文件已经存在。如果您的时间戳分辨率不够好,可能会出现这种情况。由于它是一个IOException,因此您可能不会遇到权限问题(在这种情况下,您将得到一个SecurityException)。

在尝试创建文件并尝试记录发生的事情之前,我会首先检查文件是否存在。

查看public boolean createNewFile()了解更多关于您正在使用的方法的信息。

+0

API实际上表示,如果文件已经存在但不会抛出IOException,但在此情况下仅返回false。 – Turismo 2008-09-25 09:51:15

0

由于我无法重现我自己的机器上的错误或拿到手的代码失败的用户的机器我一直等到现在宣布一个被接受的答案。 我改变了代码如下:

File parentFolder = new File(targetPath); 
... do some checks on parentFolder here ... 
File targetFile = new File(parentFolder, filename); 
targetFile.createNewFile(); 
fileInputStream = new FileInputStream(fileToCopy); 
fileOutputStream = new FileOutputStream(targetFile); 
byte[] buffer = new byte[64*1024]; 
int i = 0; 
while((i = fileInputStream.read(buffer)) != -1) { 
    fileOutputStream.write(buffer, 0, i); 
} 

它的工作对用户报告问题之后。

所以看起来Alexanders的答案有诀窍 - 尽管我实际上使用的构造函数与他给出的略有不同,但沿着相同的路线。

我还没有通过再次运行旧版本并检查它是否仍然失败来帮助我验证代码更改是否解决了错误(而不是他以不同的方式做)。

BTW。记录已到位,记录的路径似乎确定 - 抱歉没有提到这一点。我认为这是理所当然的,并发现它不必要地复杂问题中的代码。

感谢您的有用答案。

3

我刚刚遇到同样的问题。我认为它必须与写访问权限有关。我在尝试写入c:\时遇到了错误,但在更改为D:\时,一切正常。 显然Java的没有写权限我的系统驱动器(运行Windows 7安装在C :)

+0

同意。当引用C:\ Users \ user \ Desktop中的文件时,我遇到了同样的错误...但是当将文件移动到C:\ temp时,问题已解决,因此肯定可能是与权限相关的问题。 – Imre 2017-10-10 09:57:30

3

下面是测试程序我用

import java.io.File; 
public class TestWrite { 

    public static void main(String[] args) { 
     if (args.length!=1) { 
      throw new IllegalArgumentException("Expected 1 argument: dir for tmp file"); 
     } 
     try { 
      File.createTempFile("bla",".tmp",new File(args[0])); 
     } catch (Exception e) { 
      System.out.println("exception:"+e); 
      e.printStackTrace(); 
     } 
    } 
} 
+0

如果通过解决此问题的答案不能帮助您,则应该为您的问题开一个新问题。如果您将问题作为对此问题的答案发布,则不太可能得到答案。 – Turismo 2011-02-08 08:54:01

1

仅供参考,当我的文件名有冒号的时间戳时,例如myfile_HH:mm:ss.csv删除冒号解决了问题。

相关问题