327

我的项目具有以下结构:

/src/main/java/
/src/main/resources/
/src/test/java/
/src/test/resources/

我有一个文件/src/test/resources/test.csv,我想从单元测试中加载文件/src/test/java/MyTest.java

我有这段代码不起作用。它抱怨“没有这样的文件或目录”。

BufferedReader br = new BufferedReader (new FileReader(test.csv))

我也试过这个

InputStream is = (InputStream) MyTest.class.getResourcesAsStream(test.csv))

这也行不通。它返回null。我正在使用 Maven 来构建我的项目。

4

20 回答 20

314

尝试下一个:

ClassLoader classloader = Thread.currentThread().getContextClassLoader();
InputStream is = classloader.getResourceAsStream("test.csv");

如果上述方法不起作用,则各种项目已添加以下类:1此处为代码)。2ClassLoaderUtil

以下是如何使用该类的一些示例:

src\main\java\com\company\test\YourCallingClass.java
src\main\java\com\opensymphony\xwork2\util\ClassLoaderUtil.java
src\main\resources\test.csv
// java.net.URL
URL url = ClassLoaderUtil.getResource("test.csv", YourCallingClass.class);
Path path = Paths.get(url.toURI());
List<String> lines = Files.readAllLines(path, StandardCharsets.UTF_8);
// java.io.InputStream
InputStream inputStream = ClassLoaderUtil.getResourceAsStream("test.csv", YourCallingClass.class);
InputStreamReader streamReader = new InputStreamReader(inputStream, StandardCharsets.UTF_8);
BufferedReader reader = new BufferedReader(streamReader);
for (String line; (line = reader.readLine()) != null;) {
    // Process line
}

笔记

  1. The Wayback Machine中看到它
  2. 也在GitHub中。
于 2013-04-01T18:29:13.977 回答
90

尝试:

InputStream is = MyTest.class.getResourceAsStream("/test.csv");

IIRCgetResourceAsStream()默认情况下是相对于类的包的。

正如@Terran 所说,不要忘记/在文件名的开头添加

于 2013-04-01T18:27:53.910 回答
51

在 Spring 项目中尝试以下代码

ClassPathResource resource = new ClassPathResource("fileName");
InputStream inputStream = resource.getInputStream();

或非春季项目

 ClassLoader classLoader = getClass().getClassLoader();
 File file = new File(classLoader.getResource("fileName").getFile());
 InputStream inputStream = new FileInputStream(file);
于 2017-04-14T16:35:54.053 回答
39

这是使用Guava的一种快速解决方案:

import com.google.common.base.Charsets;
import com.google.common.io.Resources;

public String readResource(final String fileName, Charset charset) throws IOException {
        return Resources.toString(Resources.getResource(fileName), charset);
}

用法:

String fixture = this.readResource("filename.txt", Charsets.UTF_8)
于 2016-03-04T19:53:35.700 回答
16

非春季项目:

String filePath = Objects.requireNonNull(getClass().getClassLoader().getResource("any.json")).getPath();

Stream<String> lines = Files.lines(Paths.get(filePath));

或者

String filePath = Objects.requireNonNull(getClass().getClassLoader().getResource("any.json")).getPath();

InputStream in = new FileInputStream(filePath);

对于spring项目,也可以使用一行代码获取resources文件夹下的任意文件:

File file = ResourceUtils.getFile(ResourceUtils.CLASSPATH_URL_PREFIX + "any.json");

String content = new String(Files.readAllBytes(file.toPath()));
于 2019-12-09T21:13:08.500 回答
9

对于1.7 之后的 java

 List<String> lines = Files.readAllLines(Paths.get(getClass().getResource("test.csv").toURI()));

或者,如果您在 Spring echosystem 中,您可以使用 Spring utils

final val file = ResourceUtils.getFile("classpath:json/abcd.json");

要了解更多幕后情况,请查看以下博客

https://todzhang.com/blogs/tech/en/save_resources_to_files

于 2019-10-04T05:36:15.037 回答
7

我面临同样的问题

类加载器未找到该文件,这意味着它未打包到工件(jar)中。您需要构建项目。例如,使用 Maven:

mvn clean package

因此,您添加到资源文件夹的文件将进入 Maven 构建并可供应用程序使用。

我想保留我的答案:它没有解释如何读取文件(其他答案确实解释了这一点),它回答了为什么 InputStreamresourcenull。类似的答案在这里

于 2019-03-29T02:16:43.377 回答
5
ClassLoader loader = Thread.currentThread().getContextClassLoader();
InputStream is = loader.getResourceAsStream("test.csv");

如果您使用上下文 ClassLoader 来查找资源,那么肯定会降低应用程序性能。

于 2014-11-30T01:18:59.510 回答
5

现在我正在说明从 maven 创建的资源目录中读取字体的源代码,

scr/main/resources/calibril.ttf

在此处输入图像描述

Font getCalibriLightFont(int fontSize){
    Font font = null;
    try{
        URL fontURL = OneMethod.class.getResource("/calibril.ttf");
        InputStream fontStream = fontURL.openStream();
        font = new Font(Font.createFont(Font.TRUETYPE_FONT, fontStream).getFamily(), Font.PLAIN, fontSize);
        fontStream.close();
    }catch(IOException | FontFormatException ief){
        font = new Font("Arial", Font.PLAIN, fontSize);
        ief.printStackTrace();
    }   
    return font;
}

它对我有用,希望整个源代码也能帮助你,享受吧!

于 2017-09-27T15:45:43.050 回答
3

导入以下内容:

import java.io.IOException;
import java.io.FileNotFoundException;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.InputStream;
import java.util.ArrayList;

以下方法在字符串的 ArrayList 中返回一个文件:

public ArrayList<String> loadFile(String filename){

  ArrayList<String> lines = new ArrayList<String>();

  try{

    ClassLoader classloader = Thread.currentThread().getContextClassLoader();
    InputStream inputStream = classloader.getResourceAsStream(filename);
    InputStreamReader streamReader = new InputStreamReader(inputStream, StandardCharsets.UTF_8);
    BufferedReader reader = new BufferedReader(streamReader);
    for (String line; (line = reader.readLine()) != null;) {
      lines.add(line);
    }

  }catch(FileNotFoundException fnfe){
    // process errors
  }catch(IOException ioe){
    // process errors
  }
  return lines;
}
于 2018-11-02T19:26:01.977 回答
1

getResource()src/main/resources仅适用于放置的资源文件。要获取位于路径中的文件,而不是src/main/resourcessrc/test/java您需要显式创建它。

以下示例可能对您有所帮助

import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.net.URISyntaxException;
import java.net.URL;

public class Main {
    public static void main(String[] args) throws URISyntaxException, IOException {
        URL location = Main.class.getProtectionDomain().getCodeSource().getLocation();
        BufferedReader br = new BufferedReader(new FileReader(location.getPath().toString().replace("/target/classes/", "/src/test/java/youfilename.txt")));
    }
}
于 2017-02-20T08:35:06.603 回答
1

您可以使用 com.google.common.io.Resources.getResource 读取文件的 url,然后使用 java.nio.file.Files 读取文件的内容来获取文件内容。

URL urlPath = Resources.getResource("src/main/resource");
List<String> multilineContent= Files.readAllLines(Paths.get(urlPath.toURI()));
于 2020-04-05T18:04:08.600 回答
1

如果您以静态方法加载文件,那么 ClassLoader classLoader = getClass().getClassLoader(); 这可能会给您一个错误。

你可以试试这个你想从资源加载的文件是资源>>图像>>Test.gif

import org.springframework.core.io.ClassPathResource;
import org.springframework.core.io.Resource;

Resource resource = new ClassPathResource("Images/Test.gif");

    File file = resource.getFile();
于 2020-09-23T05:43:33.500 回答
1

要从 src/resources 文件夹中读取文件,请尝试以下操作:

DataSource fds = new FileDataSource(getFileHandle("images/sample.jpeg"));

public static File getFileHandle(String fileName){
       return new File(YourClassName.class.getClassLoader().getResource(fileName).getFile());
}

在非静态引用的情况下:

return new File(getClass().getClassLoader().getResource(fileName).getFile());
于 2021-02-03T07:09:20.057 回答
0

代码在不运行 Maven-build jar 时是否有效,例如从您的 IDE 运行时?如果是这样,请确保该文件实际上包含在 jar 中。资源文件夹应该包含在 pom 文件中,在<build><resources>.

于 2013-04-01T18:35:40.043 回答
0

以下类可用于从 加载 aresourceclasspath在给定的 出现问题时接收合适的错误消息filePath

import java.io.InputStream;
import java.nio.file.NoSuchFileException;

public class ResourceLoader
{
    private String filePath;

    public ResourceLoader(String filePath)
    {
        this.filePath = filePath;

        if(filePath.startsWith("/"))
        {
            throw new IllegalArgumentException("Relative paths may not have a leading slash!");
        }
    }

    public InputStream getResource() throws NoSuchFileException
    {
        ClassLoader classLoader = this.getClass().getClassLoader();

        InputStream inputStream = classLoader.getResourceAsStream(filePath);

        if(inputStream == null)
        {
            throw new NoSuchFileException("Resource file not found. Note that the current directory is the source folder!");
        }

        return inputStream;
    }
}
于 2015-02-02T18:08:40.003 回答
0

我通过写为

InputStream schemaStream = 
      ProductUtil.class.getClassLoader().getResourceAsStream(jsonSchemaPath);
byte[] buffer = new byte[schemaStream.available()];
schemaStream.read(buffer);

File tempFile = File.createTempFile("com/package/schema/testSchema", "json");
tempFile.deleteOnExit();
FileOutputStream out = new FileOutputStream(tempFile);
out.write(buffer);
于 2019-01-22T13:40:34.987 回答
0
this.getClass().getClassLoader().getResource("filename").getPath()
于 2019-10-23T07:05:06.947 回答
0

即使我遵循了答案,也找不到我在测试文件夹中的文件。它通过重建项目得到解决。似乎 IntelliJ 没有自动识别新文件。很讨厌发现。

于 2020-10-15T09:57:56.147 回答
-2

我让它在没有任何参考“类”或“类加载器”的情况下工作。

假设我们有三个场景,文件'example.file'的位置和你的工作目录(你的应用程序执行的地方)是home/mydocuments/program/projects/myapp:

a) 工作目录的子文件夹:myapp/res/files/example.file

b) 不属于工作目录的子文件夹:projects/files/example.file

b2)另一个不属于工作目录的子文件夹:program/files/example.file

c) 根文件夹:home/mydocuments/files/example.file(Linux;在 Windows 中将 home/ 替换为 C:)

1)获得正确的路径:a)String path = "res/files/example.file"; b)String path = "../projects/files/example.file" b2)String path = "../../program/files/example.file" c)String path = "/home/mydocuments/files/example.file"

基本上,如果它是根文件夹,则路径名以斜杠开头。如果是子文件夹,路径名前不能有斜杠。如果子文件夹不是工作目录的后代,则必须使用“../” cd 到它。这告诉系统上一个文件夹。

2)通过传递正确的路径创建一个文件对象:

File file = new File(path);

3) 你现在可以开始了:

BufferedReader br = new BufferedReader(new FileReader(file));
于 2016-08-06T02:25:50.270 回答