it-swarm.com.de

Wo und wie werden Konfigurationsressourcendateien in servletbasierten Anwendungen abgelegt?

In meiner Webanwendung muss ich E-Mails an vordefinierte Benutzer wie [email protected] Senden. Daher möchte ich diese einer .properties - Datei hinzufügen und bei Bedarf darauf zugreifen. Ist dies ein korrekter Vorgang? Wenn ja, wo soll ich diese Datei ablegen? Ich verwende Netbeans IDE mit zwei separaten Ordnern für Quell- und JSP-Dateien.

209
sansknwoledge

Es ist deine Wahl. Grundsätzlich gibt es drei Möglichkeiten in einem Java Web Application Archive (WAR)):


1. Legen Sie es in Klassenpfad

Damit Sie es mit ClassLoader#getResourceAsStream() mit einem Klassenpfad-relativen Pfad laden können:

ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
InputStream input = classLoader.getResourceAsStream("foo.properties");
// ...
Properties properties = new Properties();
properties.load(input);

Hier soll foo.properties In einer der Wurzeln platziert werden, die durch den Standardklassenpfad einer Webanwendung abgedeckt sind, z. webapps /WEB-INF/lib und /WEB-INF/classes, server's /lib oder JDK/JRE's /lib. Wenn die Eigenschaftendatei webapp-spezifisch ist, platzieren Sie sie am besten in /WEB-INF/classes. Wenn Sie ein Standard-WAR-Projekt in einer IDE entwickeln, legen Sie es im Ordner src (dem Quellordner des Projekts) ab. Wenn Sie ein Maven-Projekt verwenden, legen Sie es im Ordner /main/resources Ab.

Sie können ihn alternativ auch außerhalb des Standardklassenpfads platzieren und seinen Pfad zum Klassenpfad des Anwendungsservers hinzufügen. In Tomcat können Sie es beispielsweise als shared.loader - Eigenschaft von Tomcat/conf/catalina.properties Konfigurieren.

Wenn Sie den foo.properties In eine Java= Paketstruktur wie com.example Eingefügt haben, müssen Sie ihn wie folgt laden

ClassLoader classLoader = Thread.currentThread().getContextClassLoader();
InputStream input = classLoader.getResourceAsStream("com/example/foo.properties");
// ...

Beachten Sie, dass dieser Pfad eines Kontextklassenladeprogramms nicht mit einem / Beginnen sollte. Nur wenn Sie ein "relatives" Klassenladeprogramm wie SomeClass.class.getClassLoader() verwenden, müssen Sie es tatsächlich mit einem / Starten.

ClassLoader classLoader = getClass().getClassLoader();
InputStream input = classLoader.getResourceAsStream("/com/example/foo.properties");
// ...

Die Sichtbarkeit der Eigenschaftendatei hängt dann jedoch vom jeweiligen Klassenladeprogramm ab. Es ist nur für denselben Klassenlader sichtbar, der die Klasse geladen hat. Wenn also die Klasse von z. Server Common Classloader anstelle von WebApp Classloader, und die Eigenschaftendatei befindet sich in WebApp selbst, dann ist es unsichtbar. Der Context Class Loader ist Ihre sicherste Methode, damit Sie die Eigenschaftendatei "überall" im Klassenpfad ablegen können und/oder beabsichtigen, eine von einem Server bereitgestellte Datei von der Webanwendung an zu überschreiben.


2. Stellen Sie es in den Webcontent

Damit Sie es mit ServletContext#getResourceAsStream() mit einem webcontent-relativen Pfad laden können:

InputStream input = getServletContext().getResourceAsStream("/WEB-INF/foo.properties");
// ...

Beachten Sie, dass ich demonstriert habe, dass die Datei im Ordner /WEB-INF Abgelegt werden soll, da sie sonst für jeden Webbrowser öffentlich zugänglich gewesen wäre. Beachten Sie auch, dass sich das ServletContext in jeder HttpServlet Klasse befindet, auf die nur die geerbten GenericServlet#getServletContext() und in Filter by - zugreifen können. FilterConfig#getServletContext() . Wenn Sie nicht in einer Servlet-Klasse sind, können Sie diese normalerweise nur mit @Inject Injizieren.


3. Legen Sie es im lokalen Dateisystem ab

Damit Sie es auf die übliche Weise Java.io Mit einem absoluten lokalen Dateisystempfad laden können:

InputStream input = new FileInputStream("/absolute/path/to/foo.properties");
// ...

Beachten Sie, wie wichtig es ist, einen absoluten Pfad zu verwenden. Relative lokale Dateisystempfade sind in einer Java EE-Webanwendung ein absolutes No-Go. Siehe auch den ersten Link "Siehe auch" weiter unten.


Welche soll ich wählen?

Wägen Sie die Vor- und Nachteile einfach in Ihrer eigenen Meinung zur Wartbarkeit ab.

Wenn die Eigenschaftendateien "statisch" sind und sich zur Laufzeit nicht ändern müssen, können Sie sie in der WAR-Datei belassen.

Wenn Sie die Eigenschaftendateien lieber von außerhalb der Webanwendung bearbeiten möchten, ohne die WAR-Datei jedes Mal neu erstellen und erneut bereitstellen zu müssen, fügen Sie sie in den Klassenpfad außerhalb des Projekts ein (fügen Sie ggf. das Verzeichnis zum Klassenpfad hinzu).

Wenn Sie es vorziehen, Eigenschaftendateien mithilfe der Properties#store() -Methode programmgesteuert aus der Webanwendung heraus zu bearbeiten, platzieren Sie sie außerhalb der Webanwendung. Da die Funktion Properties#store() ein Writer erfordert, können Sie keinen Pfad für das Festplattendateisystem verwenden. Dieser Pfad kann wiederum als VM Argument oder Systemeigenschaft an die Webanwendung übergeben werden. Vorsichtshalber never use getRealPath() . Alle Änderungen im Bereitstellungsordner gehen bei einer erneuten Bereitstellung verloren, aus dem einfachen Grund, dass die Änderungen nicht in der ursprünglichen WAR-Datei wiedergegeben werden.

Siehe auch:

451
BalusC

Warnung: Wenn Sie Konfigurationsdateien in Ihren WEB-INF/classes - Ordner legen und Ihre IDE, z. B. Eclipse, eine Bereinigung/Neuerstellung durchführt, werden Ihre Conf-Dateien beschädigt, es sei denn, sie befinden sich in Java Quellverzeichnis. Die großartige Antwort von BalusC spielt darauf in Option 1 an, aber ich wollte die Betonung hinzufügen.

Ich habe auf die harte Tour gelernt, dass beim "Kopieren" eines Webprojekts in Eclipse alle Quellordner bereinigt/neu erstellt werden. In meinem Fall hatte ich ein "verlinktes Quellverzeichnis" aus unserer POJO Java= Bibliothek hinzugefügt, das in den Ordner WEB-INF/classes Kompiliert wurde das Web-App-Projekt) verursachte das gleiche Problem.

Ich habe darüber nachgedacht, meine confs in den POJO src-Ordner zu legen, aber diese confs sind alle für Bibliotheken von Drittanbietern (wie Quartz oder URLRewrite), die sich im Ordner WEB-INF/lib Befinden. Das ergab also keinen Sinn. Ich habe vor, es im Ordner "src" des Webprojekts zu testen, wenn ich dazu komme, aber dieser Ordner ist derzeit leer und mit conf-Dateien scheint es unelegant.

Also stimme ich dafür, dass conf-Dateien in WEB-INF/commonConfFolder/filename.properties, next im Klassenordner abgelegt werden. Dies ist Balus Option 2.

8
Ed Pike

Beispiel: In der Datei web.xml das Tag

<context-param>
        <param-name>chatpropertyfile</param-name>
        <!--  Name of the chat properties file. It contains the name and description                   of rooms.-->     
        <param-value>chat.properties</param-value>
    </context-param>

Und chat.properties können Sie Ihre Eigenschaften wie folgt deklarieren

Zum Beispiel:

Jsp = Discussion about JSP can be made here.
Java = Talk about Java and related technologies like J2EE.
ASP = Discuss about Active Server Pages related technologies like VBScript and JScript etc.
Web_Designing = Any discussion related to HTML, JavaScript, DHTML etc.
StartUp = Startup chat room. Chatter is added to this after he logs in.
6

Es muss sich nur im Klassenpfad befinden (also sicherstellen, dass es als Teil des Builds unter/WEB-INF/classes in der .war endet).

5
Taylor Leese

Sie können dies mit Ihrem Quellordner tun, sodass diese Dateien bei jeder Erstellung automatisch in das Klassenverzeichnis kopiert werden.

Verwenden Sie anstelle der Eigenschaftendatei die XML-Datei.

Wenn die Daten zu klein sind, können Sie sogar mit web.xml auf die Eigenschaften zugreifen.

Beachten Sie, dass bei jedem dieser Ansätze ein Neustart des App-Servers erforderlich ist, damit die Änderungen übernommen werden.

3
Kalpak

Angenommen, Ihr Code sucht nach der Datei say app.properties. Kopieren Sie diese Datei in ein beliebiges Verzeichnis und fügen Sie dieses Verzeichnis dem Klassenpfad hinzu, indem Sie eine setenv.sh im bin-Verzeichnis von Tomcat erstellen.

In Ihrer Datei setenv.sh von Tomcat (wenn diese Datei nicht vorhanden ist, erstellen Sie eine, Tomcat lädt diese Datei setenv.sh. #!/bin/sh CLASSPATH="$CLASSPATH:/home/user/config_my_prod/"

Sie sollten Ihre Eigenschaftendateien nicht in ./webapps//WEB-INF/classes/app.properties haben

Der Tomcat-Klassenlader überschreibt den von WEB-INF/classes /

Eine gute Lektüre: https://Tomcat.Apache.org/Tomcat-8.0-doc/class-loader-howto.html

1
Thar