spezielles Auto-Start-Servlet beim Start und Aktienanwendungsdaten zu initialisieren
-
28-09-2019 - |
Frage
Ich brauche eine Konfiguration zu erhalten und zu externen Ressourcen / Objekte / Systeme irgendwo und speichern sie in Anwendungsbereich verbinden.
Ich kann meine Anwendung zwei Möglichkeiten zur Einrichtung finden Sie unter:
- Überschreiben der
init()
in den bestehenden Servlets und erforderlichen Code dort und alle konstruierten Objekte innerhalb derselben Servlet zu halten. - eine Art von einer Initialisierung Servlet hat und mit seiner
init()
der Arbeit zu tun. Dann erstellen Objekte inServletContext
speichert es mit meinen anderen Servlets zu teilen.
Welche von oben ist besser Ansatz? Gibt es eine bessere Art und Weise zu teilen Objekte zwischen Servlets? Aufruf direkt voneinander oder so ...?
Lösung
Keiner von beiden ist der bessere Ansatz. Servlets sollen auf HTTP-Ereignisse (HTTP-Requests), nicht auf Auslösungen (Start / Stop).
hören CDI / JSF / EJB nicht verfügbar? Verwenden Sie ServletContextListener
@WebListener
public class Config implements ServletContextListener {
public void contextInitialized(ServletContextEvent event) {
// Do stuff during webapp's startup.
}
public void contextDestroyed(ServletContextEvent event) {
// Do stuff during webapp's shutdown.
}
}
Wenn Sie nicht auf Servlet 3.0 sind noch nicht und können nicht aktualisiert werden und somit nicht @WebListener
Anmerkung verwenden kann, dann müssen Sie es manuell registrieren in /WEB-INF/web.xml
wie unten:
<listener>
<listener-class>com.example.Config</listener-class>
</listener>
Zum Speichern und erhalten Objekte in den Anwendungsbereich (so dass alle Servlets auf sie zugreifen kann), verwenden ServletContext#setAttribute()
und #getAttribute()
.
Hier ist ein Beispiel, das den Hörer Laden selbst in dem Anwendungsbereich kann:
public void contextInitialized(ServletContextEvent event) {
event.getServletContext().setAttribute("config", this);
// ...
}
und erhalten dann in einem Servlet:
protected void doGet(HttpServletRequest request, HttpServletResponse response) {
Config config = (Config) getServletContext().getAttribute("config");
// ...
}
Es ist auch in JSP EL von ${config}
verfügbar. So können Sie es eine einfache Bohne auch machen könnte.
CDI verfügbar? Verwenden Sie @Observes
auf ApplicationScoped.class
import javax.enterprise.context.ApplicationScoped;
@ApplicationScoped
public class Config {
public void init(@Observes @Initialized(ApplicationScoped.class) ServletContext context) {
// Do stuff during webapp's startup.
}
public void destroy(@Observes @Destroyed(ApplicationScoped.class) ServletContext context) {
// Do stuff during webapp's shutdown.
}
}
Dies ist in einem Servlet über @Inject
zur Verfügung. Machen Sie es bei Bedarf auch @Named
, so dass es über #{config}
in EL auch verfügbar ist.
Noted sollte sein, dass diese seit CDI 1.1 neu ist. Wenn Sie immer noch auf CDI 1.0 sind und nicht aktualisieren können, dann einen anderen Ansatz wählen.
JSF zur Verfügung? Verwenden Sie @ManagedBean(eager=true)
import javax.faces.bean.ManagedBean
import javax.faces.bean.ApplicationScoped;
@ManagedBean(eager=true)
@ApplicationScoped
public class Config {
@PostConstruct
public void init() {
// Do stuff during webapp's startup.
}
@PreDestroy
public void destroy() {
// Do stuff during webapp's shutdown.
}
}
Dies ist über #{config}
in EL ebenfalls zur Verfügung.
EJB zur Verfügung? Betrachten Sie @Startup
@Singleton
@Startup
@Singleton
public class Config {
@PostConstruct
public void init() {
// Do stuff during webapp's startup.
}
@PreDestroy
public void destroy() {
// Do stuff during webapp's shutdown.
}
}
Dies ist in einem Servlet über @EJB
zur Verfügung. Ich sage „betrachten“, weil Sie nicht einen EJB im Interesse eines Starthaken missbrauchen sollten. Darüber hinaus ist ein @Singleton
ist standardmäßig Lese- / Schreib gesperrt und in erster Linie für die Transaktions Sachen wie Terminplanung Hintergrundjobs intented.