2012-04-03 3 views
1

Zuerst, Entschuldigung für die Wiederholung einer Variation einer oft gestellten Frage. Ich kämpfe jedoch, um den besten Ansatz hier zu verstehen. Ich habe eine Anwendung, die Hibernate und Glassfish 3 verwendet. Wie andere möchte ich Hibernate-Eigenschaften von außerhalb der WAR-Datei laden können. Die einzige Lösung, die ich zur Arbeit gebracht habe, ist die folgende. Es lädt die Eigenschaften aus dem Ordner domains/domain1/config.Lesen Sie Hibernate-Eigenschaften von außerhalb Krieg mit ServletContext

private Properties getLocalHibernateProperties() { 
    Properties properties = new Properties(); 
    try { 
    File pf = new File(System.getProperty("user.dir"), PROPERTIES_FILE_NAME); 
    InputStream inStream = new FileInputStream(pf); 
    properties.load(inStream); 
    } 
    catch (Exception e) { 
    e.printStackTrace(); 
    }  
    return properties; 
} 

Allerdings habe ich auch und Beispiel How to read properties file placed outside war? gefunden, die die ServletContext verwendet. die verschiedenen Teile der Kombination:

in web.xml <listener-class>foo.bar.startup.HibernatePropertiesLoader</listener-class> 

public class HibernatePropertiesLoader implements ServletContextListener { 
    public void contextInitialized(ServletContextEvent event){ 
     ServletContext context = event.getServletContext(); 
     context.setAttribute("settings", new HibernatePropertiesReader(context)); 
    } 
    public void contextDestroyed(ServletContextEvent event){} 
} 

public class HibernatePropertiesReader { 
    ServletContext ctx = null; 

    public HibernatePropertiesReader(ServletContext ctx) { 
    this.ctx = ctx; 
    } 

    public Properties getLocalHibernateProperties() { 
    Properties properties = new Properties(); 
    try { 
     InputStream inStream = ctx.getResourceAsStream(PROPERTIES_FILE); 
     properties.load(inStream); 
    } 
    catch (Exception e) { 
     e.printStackTrace(); 
     }  
    return properties; 
    } 
} 

ich, dass die zweite Lösung der CLASSPATH des Servlets sucht verstehen - (ist das richtig?) und ist damit flexibler als meine ursprüngliche Lösung. Ich verstehe jedoch nicht, wie ich die Eigenschaften meiner HibernateUtils-Klasse verwenden (auf sie zugreifen) kann. Ich denke, dass dies bedeutet, dass es etwas von grundlegender Bedeutung ist in meinem Verständnis von ServletContext fehlt ....

Hilfe, Beratung, bessere Lösungen geschätzt ...

Antwort

2

Die ServletContext.getResourceAsStream typischerweise eine Datei zu laden, wird verwendet, von der Web-App selbst. Zum Beispiel, wenn Sie Ihre Eigenschaften legen Dateien wie:

<CONTAINER_ROOT>/webapps/<CONTEXT>/WEB-INF/conf/hibernate.properties 

Dann können Sie die Datei laden

ctx.getResourceAsStream("/WEB-INF/conf/hibernate.properties"); 

Das Verfahren unter Verwendung kann auch verwendet werden, um „Ressourcen“ von JAR-Dateien zu laden, aber die erste Methode ist wahrscheinlich besser für eine Konfigurationsdatei. Die JavaDocs sind in diesem Fall ziemlich hilfreich.

== == UPDATE

Ich sehe dein Problem ist jetzt, wie Sie die Eigenschaften aus dem Servlet-Kontext und in der Hibernate-Konfiguration erhalten widersprechen. Dies hängt davon ab, wie Ihr Anwendungslayout aussieht. Benutzt du Frühling?

Sie sind, wäre eine schnelle und schmutzige Lösung Angenommen, den ServletContextAware Schnittstelle (unter der Annahme HibernateUtil von Spring aufgebaut ist) zu haben HibernateUitl implementieren und hat Code wie die folgenden

public class HibernateUtil implements ServletContextAware { 

private ServletContext servletContext; 

... 

public void setServletContext(ServletContext servletContext) { 
    this.servletContext = servletContext; 
} 

private Properties getProperties() { 
    return servletContext.getAttribute("settings").getLocalHibernateProperties(); 
} 

... 

} 

Paare Dieser HibernateUtil auf den Servlet-API obwohl das unerwünscht sein kann. Eine etwas sauberere Lösung könnte darin bestehen, eine HibernatePropertiesSource-Schnittstelle zu erstellen und dann eine ServletContextHibernatePropertiesSource-Implementierung zu verwenden, die die obigen Methoden aufweist und diese in HibernateUtil einfügt.

Auch dies ist alles unter der Annahme, dass Sie Spring verwenden.

+0

also, der ServletContext ist nicht wirklich geeignet, um 'installationsspezifische' Eigenschaften von außerhalb der Anwendung zu laden? Es fiel mir auf, dass die erste Lösung vielleicht nicht so flexibel war - vielleicht liege ich hier falsch. – skyman

+0

Was ist mit der Installation spezifischer Eigenschaften im Kontextstammsatz? Haben Sie vorgeschlagen, sie in das Home-Verzeichnis des Benutzers zu legen? Ein einzelner Benutzer könnte mehrere Instanzen derselben Anwendung auf verschiedenen Ports ausführen. – Pace

+0

Ich vermute, dass ich versuche, ein Problem zu lösen, wo ich die WAR für eine Website aktualisieren muss, ohne die lokalen Konfigurationsdaten zu ersetzen. Habe ich Recht, wenn ich sage, dass sich der Kontextstamm tatsächlich in der unverpackten WAR befindet? – skyman

Verwandte Themen