it-swarm.com.de

Spring kann die Bean-XML-Konfigurationsdatei nicht finden, wenn sie existiert

Ich versuche, meine erste Bean in Spring zu erstellen, bekam jedoch ein Problem mit dem Laden eines Kontexts . Ich habe eine Konfigurations-XML-Datei der Bean in src/main/resources.

Ich erhalte folgende IOException:

Ausnahme im Thread "main" org.springframework.beans.factory.BeanDefinitionStoreException: IOException analysiert das XML-Dokument aus der Klassenpfadressource [src/main/resources/beans.xml]; geschachtelte Ausnahme ist 

Java.io.FileNotFoundException: Klassenpfadressource [src/main/resources/beans.xml] kann nicht geöffnet werden, weil es nicht existiert

aber ich verstehe es nicht, da ich den folgenden Code teste:

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

was gibt mir wahr! resources befindet sich im Klassenpfad. Was ist falsch?

64
dawrutowicz

Danke, aber das war nicht die Lösung. Ich habe herausgefunden, warum es für mich nicht funktionierte.

Da hatte ich eine Erklärung abgegeben: 

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

Ich dachte, ich würde auf das Wurzelverzeichnis des Projekts verweisen, wenn die Datei beans.xml vorhanden war ..__ Dann legte ich die Konfigurationsdatei auf src/main/resources und änderte die Initialisierung in: 

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

es war immer noch eine IO Ausnahme.

Dann wurde die Datei in src/main/resources/belassen, aber ich habe die Deklaration folgendermaßen geändert:

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

und es hat das Problem gelöst - vielleicht ist es für jemanden hilfreich.

danke und Prost!

Bearbeiten:

Da ich viele Leute für die Lösung begeistern und vor einigen Jahren mit Spring als Student erste Erfahrung gemacht habe, möchte ich kurz erklären, warum es funktioniert.

Wenn das Projekt kompiliert und gepackt wird, werden alle Dateien und Unterverzeichnisse von 'src/main/Java' im Projekt in das Stammverzeichnis des gepackten jar (das Artefakt, das wir erstellen möchten) gespeichert. Die gleiche Regel gilt für 'src/main/resources'. 

Dies ist eine Konvention, die von vielen Tools wie maven oder sbt beim Erstellen eines Projekts beachtet wird (Hinweis: als Standardkonfiguration!). Wenn der Code (aus dem Posting) im laufenden Modus war, konnte er nichts wie "src/main/resources/beans.xml" finden, weil sich die beans.xml im Stammverzeichnis von jar befand (kopiert nach/beans) .xml in erstelltem Glas/Ohr/Krieg). 

Bei der Verwendung von ClassPathXmlApplicationContext lautete die korrekte Standortdeklaration für die XML-Definitionen von Beans "/beans.xml", da dies der Pfad ist, zu dem sie in jar und später in classpath gehört.

Es kann überprüft werden, indem ein Glas mit einem Archivierer (d. H. Rar) ausgepackt wird und der Inhalt der Verzeichnisstruktur angezeigt wird. 

Ich würde empfehlen, Artikel über classpath als Ergänzung zu lesen.

128
dawrutowicz

Versuche dies:

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

datei: Präfixpunkt auf Dateisystemressourcen, nicht auf Klassenpfad.

dateipfad kann relativ oder systembezogen sein (/ home/user/Work/src ...)

46

Ich hatte auch ein ähnliches Problem, aber wegen einer etwas anderen Ursache, also teile es hier, falls es irgendjemandem helfen kann.

Mein Dateispeicherort

beans.xml file

wie ich es benutzt habe

ClassPathXmlApplicationContext("beans.xml");

Es gibt zwei Lösungen

  1. Nehmen Sie die beans.xml aus dem Paket und legen Sie sie in das Standardpaket ein.
  2. Geben Sie den Paketnamen an, während Sie es verwenden, nämlich.

ClassPathXmlApplicationContext("com/mypackage/beans.xml");

19
Kalher

src/main/resources ist ein Quellverzeichnis, Sie sollten nicht direkt darauf verweisen. Wenn Sie das Projekt erstellen/verpacken, wird der Inhalt an die richtige Stelle für Ihren Klassenpfad kopiert. Sie sollten es dann so laden

new ClassPathXmlApplicationContext("beans.xml")

Oder so

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

benutze es ApplicationContext context = new FileSystemXmlApplicationContext("Beans.xml");

4
Deep Shah

Sie haben sich das SRC-Verzeichnis angesehen. Die XML-Datei existiert tatsächlich dort. Schauen Sie sich jedoch die Klasse oder das Verzeichnis bin/build an, in dem alle Ausgabeklassen festgelegt sind. Ich vermute, dass Sie nur den Ressourcen-/beans.xml-Pfad benötigen.

3
Michael Z

Ich vermute, Sie bauen eine .war/.jar-Datei und sind daher keine Datei mehr, sondern eine Ressource innerhalb dieses Pakets. Versuchen Sie stattdessen ClassLoader.getResourceAsStream (String-Pfad) .

3
Brian Agnew

Dies liegt daran, dass applicationContect.xml oder any_filename.XML nicht unter dem richtigen Pfad abgelegt wird.

Fehlersuche Schritte

1: Fügen Sie die XML-Datei unter dem Ressourcenordner hinzu.

2: Wenn Sie keinen Ressourcenordner haben. Erstellen Sie einen Ordner, indem Sie mit "Neu" navigieren. Klicken Sie mit der rechten Maustaste auf das Projekt "Neu"> "Quellordner", geben Sie ihm den Namen " resource " und platzieren Sie Ihre XML-Datei darunter.

2
Gani

Im Frühling befinden sich alle Quelldateien in src/main/Java. Ebenso werden die Ressourcen im Allgemeinen in src/main/resources gespeichert. Behalten Sie also Ihre Spring-Konfigurationsdatei im Ressourcenordner.

Stellen Sie sicher, dass Sie den ClassPath-Eintrag für Ihre Dateien auch in src/main/resources haben.

Überprüfen Sie in .classpath die folgenden zwei Zeilen. Wenn sie fehlen, fügen Sie sie hinzu.

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

Wenn Sie also alles haben, sollte der unten stehende Code funktionieren.

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

1
Shashesh

Beachten Sie, dass der erste applicationContext als Teil von web.xml geladen wird. was mit dem unten genannten erwähnt wird.

<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>

Wo wie unter Code wird auch versucht, einen weiteren applicationContext zu erstellen.

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

Siehe Unterschied zwischen beans.xml und applicationContext.xml

Und wenn appliationContext.xml unter <META-INF/spring/> mit <import resource="beans.xml"/> deklariert wurde, lädt dieser appliationContext.xml den beans.xml an derselben Stelle META-INF/spring von appliationContext.xml.

Wohingegen; im Code; wenn es wie unten erklärt wird

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

Hier wird in der beans.xml nach WEB-INF/classes OR in Eclipse src/main/resources gesucht.

[Wenn Sie beans.xml bei src/main/resources hinzugefügt haben, wird es möglicherweise beim Erstellen des WARs unter WEB-INF/classes platziert.]

Insgesamt werden also ZWEI -Dateien nachgeschlagen.

Ich habe dieses Problem behoben, indem ich beim Importieren von applicationContext.xml wie folgt Klassenpfadsuche hinzugefügt habe

<import resource="classpath*:beans.xml" />

und entfernte die Zeile ClassPathXmlApplicationContext("beans.xml") im Java-Code, so dass nur ein ApplicationContext geladen wird.

1

Ich habe das Gegenteil von den meisten gemacht. Ich verwende Force IDE Luna Java EE und platzierte meine Beans.xml-Datei innerhalb des Pakets. Ich habe jedoch der Zeichenfolge Beans.xml - für das Argument ClassPathXMLApplicationContext - den relativen Pfad vorangestellt. In meiner Hauptanwendung - derjenigen, die auf die Datei Beans.xml zugreift - habe ich also: 

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

Ich bemerkte auch, dass sobald ich die Datei Beans.xml aus dem Ordner src in das Paket verschoben hatte, sich ein Bean-Image unten links neben dem XML-Dateisymbol befand, das nicht vorhanden war, als sich diese XML-Datei außerhalb des Pakets befand. Dies ist ein guter Indikator, wenn ich wissen möchte, dass ClassPathXMLAppllicationsContext jetzt auf die Beans-XML-Datei zugreifen kann.

0
user1548875

Gradle : v4.10.3

IDE: IntelliJ

Ich war mit diesem Problem konfrontiert, als ich gradle zum Ausführen meines Builds und Tests verwendete. Das Kopieren der applicationContext.xml überall hat nicht geholfen. Sogar die Angabe des vollständigen Pfades wie unten hat nicht geholfen!

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

Die Lösung (zumindest für gradle) liegt in der Art und Weise, wie gradle Ressourcen verarbeitet. Für mein Gradle-Projekt hatte ich den Arbeitsbereich wie unter https://docs.gradle.org/current/userguide/Java_plugin.html#sec:Java_project_layout definiert angelegt.

Bei der Ausführung eines Tests mit Standard-Gradle-Tasks wird der Schritt "processTestResources" ausgeführt, in dem nach Testressourcen unter C:\.....\src\test\resources gesucht wird (Gradle stellt den vollständigen Pfad hilfreich zur Verfügung ).

Ihre .properties-Datei und applicationContext.xml müssen sich in diesem Verzeichnis befinden. Wenn das Ressourcenverzeichnis nicht vorhanden ist (wie in meinem Fall), müssen Sie es erstellen und die Datei (en) dort kopieren. Danach hat die Angabe des Dateinamens problemlos funktioniert.

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

Ich habe dieses Problem erlebt und es hat mich verrückt gemacht; Letztendlich habe ich in meiner POM.xml folgende Lüge gefunden, die die Ursache des Problems war:

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

Ich war mir nicht sicher, ob ich es schreiben sollte, aber vielleicht hat jemand ein paar Stunden gespart:

mvn clean

kann den Job machen, wenn Ihre gesamte Konfiguration bereits perfekt ist!

0
İsmail Yavuz

Wenn dieses Problem Sie immer noch durchdringt und Sie mit Eclipse entwickeln, werfen Sie einen Blick auf diesen Eclipse-Fehler: resources-Dateien aus "src/main/resources" werden nicht korrekt in classpath eingeschlossen.

Die Lösung scheint die Eigenschaften des Projekts, des Java-Erstellungspfads und der Quellordner zu betrachten. Löschen Sie das /src/main/resources-Verzeichnis und fügen Sie es erneut hinzu. Dies bewirkt, dass Eclipse daran erinnert wird, dass diese Dateien in den Klassenpfad kopiert werden müssen.

Dieser Fehler hat mich betroffen, als ich die Eclipse-Version "Neon" verwendete. (Und war sehr frustrierend, bis ich die eben beschriebene einfache Lösung erkannte)

0
Geeb

Das hat bei mir funktioniert:

  new ClassPathXmlApplicationContext("classpath:beans.xml");
0
Sushrut Rathi