2. 使用 Resource
在 Spring 中,我们可以通过 Resource
接口来定位并读取资源文件。Spring 提供了资源加载机制,通过 ResourceLoader
来决定使用哪种 Resource
实现类,具体取决于我们提供的路径。
Resource
接口本身并不直接代表资源内容,而是访问资源内容的一种方式。我们可以通过多种方式获取 Resource
实例。
2.1. 使用 ResourceLoader
如果我们希望延迟加载资源,可以使用 ResourceLoader
:
ResourceLoader resourceLoader = new DefaultResourceLoader();
Resource resource = resourceLoader.getResource("classpath:resource.txt");
我们也可以通过 @Autowired
注入 ResourceLoader
:
@Autowired
private ResourceLoader resourceLoader;
2.2. 使用 @Value
更简洁的方式是直接通过 @Value
注解注入 Resource
:
@Value("classpath:resource.txt")
private Resource resource;
3. 将 Resource
转换为 String
获取到 Resource
后,我们需要将其内容读取为字符串。我们可以创建一个 ResourceReader
工具类,提供静态方法 asString
来完成这个任务。
首先,获取输入流:
InputStream inputStream = resource.getInputStream();
接着,使用 Spring 提供的 FileCopyUtils.copyToString
方法将其转换为字符串:
public class ResourceReader {
public static String asString(Resource resource) {
try (Reader reader = new InputStreamReader(resource.getInputStream(), UTF_8)) {
return FileCopyUtils.copyToString(reader);
} catch (IOException e) {
throw new UncheckedIOException(e);
}
}
// 其他工具方法
}
除了 FileCopyUtils
,我们也可以使用 StreamUtils.copyToString
等方式完成转换。
我们还可以再提供一个方法 readFileToString
,用于根据路径加载资源并转换为字符串:
public static String readFileToString(String path) {
ResourceLoader resourceLoader = new DefaultResourceLoader();
Resource resource = resourceLoader.getResource(path);
return asString(resource);
}
4. 添加 @Configuration
类
如果每个 Bean 都单独加载资源内容,不仅会造成代码重复,还可能占用更多内存。一个更优雅的做法是,在应用上下文初始化时统一加载资源内容,并通过 Spring Bean 管理其生命周期。
我们可以创建一个配置类:
@Configuration
public class LoadResourceConfig {
// Bean 定义
}
4.1. 使用 Bean 保存资源内容
在配置类中定义 Bean,用于保存资源内容:
@Bean
public String resourceString() {
return ResourceReader.readFileToString("classpath:resource.txt");
}
然后在需要使用的类中通过 @Autowire
注入:
public class LoadResourceAsStringIntegrationTest {
private static final String EXPECTED_RESOURCE_VALUE = "..."; // 文件内容
@Autowired
@Qualifier("resourceString")
private String resourceString;
@Test
public void givenUsingResourceStringBean_whenConvertingAResourceToAString_thenCorrect() {
assertEquals(EXPECTED_RESOURCE_VALUE, resourceString);
}
}
⚠️注意:我们使用了 @Qualifier
,因为 String
是一个通用类型,多个 Bean 可能存在类型冲突。Bean 名称默认来源于配置类中方法的名称。
5. 使用 SpEL 表达式注入资源内容
最后,我们也可以使用 Spring Expression Language (SpEL) 来实现资源内容的直接注入。
使用 @Value
注解将资源内容注入到字段中:
public class LoadResourceAsStringIntegrationTest {
private static final String EXPECTED_RESOURCE_VALUE = "..."; // 文件内容
@Value("#{T(com.baeldung.loadresourceasstring.ResourceReader).readFileToString('classpath:resource.txt')}")
private String resourceStringUsingSpel;
@Test
public void givenUsingSpel_whenConvertingAResourceToAString_thenCorrect() {
assertEquals(EXPECTED_RESOURCE_VALUE, resourceStringUsingSpel);
}
}
我们在 ResourceReader
中添加了一个辅助方法,使用 Apache Commons 的 FileUtils
来读取资源:
public class ResourceReader {
public static String readFileToString(String path) throws IOException {
return FileUtils.readFileToString(ResourceUtils.getFile(path), StandardCharsets.UTF_8);
}
}
✅优点:SpEL 写法紧凑,适合简单场景。
❌缺点:表达式过长或复杂时,可读性下降,建议封装成工具方法。
6. 总结
本篇文章我们介绍了几种在 Spring 中将资源文件内容加载为字符串的方式:
- ✅ 通过
ResourceLoader
或@Value
获取Resource
实例 - ✅ 使用
FileCopyUtils
或StreamUtils
将Resource
转换为String
- ✅ 通过
@Configuration
集中管理资源加载逻辑,避免重复代码 - ✅ 使用 SpEL 直接注入资源内容,适用于简单场景
这些方法各有优劣,根据项目复杂度和需求选择合适的方式即可。对于资源内容复用较多的场景,推荐使用配置类 + Bean 注入的方式,结构清晰、易于维护。
完整示例代码已托管在 GitHub:Load Resource as String 示例代码