18

我正在尝试使用以下代码复制文件:

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并且可以使用操作系统复制文件而不会出现问题。

由于我无法访问机器,这还发生在我自己的机器上,并且无法在我自己的机器上重现该问题,所以我向您寻求有关此异常原因的提示。

4

13 回答 13

18

当文件名的时间戳带有冒号时,可能会发生这种情况,例如。myfile_HH:mm:ss.csv 删除冒号解决了这个问题。

于 2016-02-16T23:20:51.073 回答
7

试试这个,因为它更注意调整 targetPath 和文件名之间的路径中的目录分隔符:

File targetFile = new File(targetPath, filename);
于 2008-09-25T15:01:04.857 回答
7

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

于 2010-04-25T09:56:31.627 回答
2

这是我使用的测试程序

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();
        }
    }
}
于 2011-02-07T12:53:47.527 回答
1

尝试在不同的目录中创建文件 - 例如“C:\”,然后确保您具有对该目录的写入权限。如果可行,则文件的路径名错误。

查看 Exception 中的注释并尝试更改文件路径名中的所有元素。实验。得出结论。

于 2008-09-25T07:45:53.483 回答
1

删除完整路径中文件/文件夹名称中的任何特殊字符。

于 2019-06-26T10:43:52.093 回答
0

您是否检查 targetPath 是一个目录,或者是否存在具有该名称的东西?(我知道您说用户可以从操作系统复制它,但也许他们正在输入其他内容)。

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

(如果您可以记录并告诉我们在失败案例中 targetPath 和 filename 的值是什么,这会有所帮助)

于 2008-09-25T07:28:52.337 回答
0

也许问题在于它正在通过网络将文件复制到共享驱动器?我认为当路径类似于 \mypc\myshared 文件夹时,使用 NFS 写入文件时 java 可能会出现问题。

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

于 2008-09-25T07:29:51.633 回答
0

尝试添加一些日志以查看文件试图创建的名称和路径,以确保父目录是一个目录。

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

于 2008-09-25T07:30:20.227 回答
0

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

如果是后者,我会说这是一个并发错误 - 两个线程检查尝试同时使用 WinNTFileSystem.createFileExclusively(Native Method) 创建文件。

当我查看 OpenJDK 源代码时,createNewFile 和 createFileExclusively 都没有同步,因此您可能必须自己同步这个块。

于 2008-09-25T07:39:07.790 回答
0

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

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

查看public boolean createNewFile()以获取有关您正在使用的方法的更多信息。

于 2008-09-25T09:29:00.333 回答
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 的回答似乎起到了作用——尽管我实际上使用的构造函数与他给出的构造函数略有不同,但思路相同。

我还必须说服该用户通过再次运行旧版本并检查它是否仍然失败来帮助我验证代码更改是否修复了错误(而不是他做不同的事情)。

顺便提一句。日志记录已经到位,并且记录的路径似乎没问题 - 抱歉没有提到这一点。我认为这是理所当然的,并发现它不必要地使问题中的代码复杂化。

感谢您提供有用的答案。

于 2008-10-15T09:22:21.170 回答
0

当 TOMCAT 主页设置有训练反斜杠时,在 Eclipse 中为我生成了一个非常相似的错误:“... java.io.IOException:文件名、目录名或卷标语法不正确”。

建议的小修改:- http://www.coderanch.com/t/556633/Tomcat/java-io-IOException-filename-directory 为我修复了它。

于 2012-11-30T10:50:05.597 回答