当Spring xml配置文件存在时,它找不到它

时间:2012-10-15 10:32:32

标签: spring configuration javabeans applicationcontext

我正在尝试在Spring中创建我的第一个bean但是在加载上下文时遇到了问题。 我在src / main / resources中有一个bean的配置XML文件。

我收到以下IOException:

  

线程“main”中的异常org.springframework.beans.factory.BeanDefinitionStoreException:从类路径资源[src / main / resources / beans.xml]解析XML文档的IOException;嵌套异常是

     

java.io.FileNotFoundException:类路径资源[src / main / resources / beans.xml]不能       因为它不存在而被打开

但是我没理解,因为我做了以下代码测试:

File f = new File("src/main/resources/beans.xml");
System.out.println("Exist test: " + f.exists());

这给了我真实的! resources位于类路径中。怎么了?

18 个答案:

答案 0 :(得分:134)

谢谢,但那不是解决方案。我发现它为什么不适合我。

因为我做了一个声明:

ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");

我认为当beans.xml文件存在时我会引用项目的根目录。 然后我将配置文件放到src / main / resources并将初始化更改为:

ApplicationContext context = new ClassPathXmlApplicationContext("src/main/resources/beans.xml");

它仍然是IO例外。

然后该文件保留在src / main / resources /中,但我将声明更改为:

ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml");

它解决了问题 - 也许对某人有帮助。

谢谢和欢呼!

编辑:

由于我让很多人赞成这个解决方案并且几年前曾作为学生初次体验过Spring,我觉得很想解释它为什么会起作用。

在编译和打包项目时,项目中'src / main / java'的所有文件和子目录都会进入打包jar的根目录(我们要创建的工件)。同样的规则适用于'src / main / resources'。

这是一个在构建项目过程中受到maven或sbt等许多工具所尊重的约定(注意:作为默认配置!)。当代码(来自帖子)处于运行模式时,它找不到像“src / main / resources / beans.xml”那样的东西,因为beans.xml位于jar的根目录中(复制到/ beans) .xml在创建的jar / ear / war中)。

使用ClassPathXmlApplicationContext时,bean xml定义的正确位置声明(在本例中为“/beans.xml”),因为这是它在jar中所属的路径,稍后在类路径中。

可以通过使用归档程序(即rar)解压缩jar来验证它,并使用目录结构查看其内容。

我建议阅读有关classpath的文章作为补充。

答案 1 :(得分:46)

试试这个:

new ClassPathXmlApplicationContext("file:src/main/resources/beans.xml");

file:预先指向文件系统资源,而不是类路径。

文件路径可以是相对的或系统的(/ home / user / Work / src ...)

答案 2 :(得分:18)

我也遇到了类似的问题,但因为有点不同,所以如果它可以帮助任何人,请分享到这里。

我的档案位置

beans.xml file

我的使用方式

ClassPathXmlApplicationContext("beans.xml");

有两种解决方案

  1. 将beans.xml从包中取出并放入默认包中。
  2. 使用时指定包名称即
  3. ClassPathXmlApplicationContext("com/mypackage/beans.xml");

答案 3 :(得分:6)

src/main/resources是一个源目录,您不应该直接引用它。在构建/打包项目时,内容将被复制到类路径的正确位置。然后你应该像这样加载它

new ClassPathXmlApplicationContext("beans.xml")

或者像这样

new GenericXmlApplicationContext("classpath:beans.xml");

答案 4 :(得分:4)

使用它 ApplicationContext context = new FileSystemXmlApplicationContext("Beans.xml");

答案 5 :(得分:3)

你看过src目录。那里确实存在xml文件。但请查看设置所有输出类的class或bin / build目录。我怀疑你只需要使用resources / beans.xml路径。

答案 6 :(得分:3)

我怀疑你正在构建.war / .jar,因此它不再是文件,而是该软件包中的资源。请改为ClassLoader.getResourceAsStream(String path)

答案 7 :(得分:2)

在Spring中,所有源文件都在src / main / java中。同样,资源通常保存在src / main / resources中。因此,请将spring配置文件保存在资源文件夹中。

确保您在src / main / resources中的文件也有ClassPath条目。

在.classpath中检查以下2行。如果他们丢失了,请添加它们。

<classpathentry path="src/main/java" kind="src"/>
<classpathentry path="src/main/resources" kind="src" />

所以,如果你有一切就绪,下面的代码应该有用。

ApplicationContext ctx = new ClassPathXmlApplicationContext(“Spring-Module.xml”);

答案 8 :(得分:2)

这是因为applicationContect.xml或any_filename.XML没有放置在正确的路径下。

故障排除步骤

1:将XML文件添加到资源文件夹下。

2:如果没有资源文件夹。通过右键单击新建new> Source Folder来导航新文件,将其命名为 resource ,然后将XML文件放在其下。

答案 9 :(得分:1)

请注意,第一个applicationContext作为web.xml的一部分加载;以下提到。

<context-param>
    <param-name>contextConfigLocation</param-name>
    <param-value>META-INF/spring/applicationContext.xml</param-value>
</context-param>

<servlet>
    <servlet-name>myOwn-controller</servlet-name>
    <servlet-class>org.springframework.web.servlet.DispatcherServlet</servlet-class>
    <init-param>
        <param-name>contextConfigLocation</param-name>
        <param-value>META-INF/spring/applicationContext.xml</param-value>
    </init-param>
    <load-on-startup>1</load-on-startup>
</servlet>

以下代码也将尝试再创建一个applicationContext。

private static final ApplicationContext context = 
               new ClassPathXmlApplicationContext("beans.xml");

请参阅beans.xmlapplicationContext.xml

之间的difference

如果appliationContext.xml下的<META-INF/spring/>已声明<import resource="beans.xml"/>,则此appliationContext.xml正在加载beans.xml META-INF/spring { {1}}。

在哪里;在代码中;如果声明如下

appliationContext.xml

这是在ApplicationContext context = new ClassPathXmlApplicationContext("beans.xml"); 或者在eclipse WEB-INF/classes中查看beans.xml。

[如果您在src/main/resources添加了beans.xml,则可能会在创建WAR时将其置于src/main/resources。]

查找完全两个文件。

我通过在WEB-INF/classes导入时添加类路径查找来解决此问题,如下所示

applicationContext.xml

并删除了java代码中的行<import resource="classpath*:beans.xml" /> ,因此只会加载一个ApplicationContext。

答案 10 :(得分:0)

如果这个问题仍然让您感到困惑,并且您正在使用Eclipse进行开发,请查看此Eclipse错误:Resources files from "src/main/resources" are not correctly included in classpath

解决方案似乎是查看项目属性,Java构建路径,源文件夹。删除/src/main/resources目录并重新添加。这会导致提醒Eclipse需要将这些文件复制到类路径中。

使用&#34; Neon&#34;这个错误影响了我。发布Eclipse。 (在我意识到刚刚描述的简单修复之前,我感到非常沮丧)

答案 11 :(得分:0)

我做了与大多数人相反的事情。我正在使用Force IDE Luna Java EE,并将我的Beans.xml文件放在包中;但是,我在Beans.xml字符串之前 - 对于ClassPathXMLApplicationContext参数 - 使用相对路径。所以在我的主应用程序中 - 访问Beans.xml文件的那个 - 我有:

    ApplicationContext context = 
         new ClassPathXmlApplicationContext("com/tutorialspoin/Beans.xml");

我还注意到,只要我将Beans.xml文件从src文件夹移到包中,就会在XML文件图标的左下方有一个Bean图像,当该xml文件在外面时,该图像不存在包裹。这是一个很好的指示,让我知道现在可以通过ClassPathXMLAppllicationsContext访问beans xml文件。

答案 12 :(得分:0)

我遇到了这个问题,这让我发疯了;我最终在我的POM.xml中找到了以下内容,这就是问题的原因:

<resources>
    <resource>
        <directory>src/main/resources</directory>
        <filtering>true</filtering>
        <includes>
            <include>**/*.properties</include>
        </includes>
    </resource>
</resources>

答案 13 :(得分:0)

我不确定要写什么,但也许有人可以节省几个小时:

mvn clean

如果您的整个配置已经很完美,则可以完成工作!

答案 14 :(得分:0)

成绩:v4.10.3

IDE :IntelliJ

使用gradle运行我的构建和测试时,我遇到了这个问题。到处复制applicationContext.xml并没有帮助。即使按如下所示指定完整路径也无济于事!

context = new ClassPathXmlApplicationContext("C:\\...\\applicationContext.xml");

解决方案(至少适用于gradle)在于gradle处理资源的方式。对于我的gradle项目,我已经按照https://docs.gradle.org/current/userguide/java_plugin.html#sec:java_project_layout

的定义布置了工作区

使用默认gradle任务运行测试时,包括“ processTestResources”步骤,该步骤在 C:\ ..... \ src \ test \ resources 中查找测试资源(有帮助的分级提供完整的路径)。

您的.properties文件和applicationContext.xml必须在此目录中。如果资源目录不存在(如本例所示),则需要创建该目录,然后在其中复制文件。之后,只需指定文件名就可以了。

context = new ClassPathXmlApplicationContext("applicationContext.xml");

答案 15 :(得分:0)

我已经在这个问题上停留了一段时间,并提出了以下解决方案

  1. 创建 ApplicationContextAware 类(这是实现 ApplicationContextAware 的类)
  2. ApplicationContextAware 中,我们只能实现一种方法

    公共无效setApplicationContext(ApplicationContext上下文)引发BeansException

  3. 告诉这个新bean的spring上下文(我称之为SpringContext)

    bean id="springContext" class="packe.of.SpringContext" />
    

这是代码段

import org.springframework.beans.BeansException;
import org.springframework.context.ApplicationContext;
import org.springframework.context.ApplicationContextAware;

public class SpringContext implements ApplicationContextAware {
  private static ApplicationContext context;

  @Override
  public void setApplicationContext(ApplicationContext context) throws BeansException {
    this.context = context;
  }
  public static ApplicationContext getApplicationContext() {
    return context;
  }
}
  1. 然后,您可以调用spring上下文之外的任何应用程序上下文方法,例如

    
    SomeServiceClassOrComponent utilityService SpringContext.getApplicationContext().getBean(SomeServiceClassOrComponent .class);
    

我希望这可以解决许多用户的问题

答案 16 :(得分:0)

Beans.xml或file.XML没有放置在正确的路径下。如果您有Maven项目,则应将XML文件添加到资源文件夹下。 src-> main-> java-> resources

答案 17 :(得分:0)

我在 IntelliJ 上遇到了同样的问题。以下是我解决它的方法:

1. 在 Spring 应用程序类中添加了如下资源导入以及其他导入:@ImportResource("applicationContext.xml")

2. 看到 IDE 显示:Cannot resolve file 'applicationContext.xml' 并建议其期望文件的路径(这不是文件 applicationContext.xml 最初保存的资源)

3. 在预期位置复制文件,异常得到解决。

下面的屏幕截图以方便参考: enter image description here

但是如果您想将其保留在资源中,请按照下面的这个很好的答案链接并添加资源路径,以便对其进行搜索。有了这个设置异常解决没有@ImportResource 在上面的步骤中描述:

https://stackoverflow.com/a/24843914/5916535