Du verwendest einen veralteten Browser. Es ist möglich, dass diese oder andere Websites nicht korrekt angezeigt werden. Du solltest ein Upgrade durchführen oder ein alternativer Browser verwenden.
kann mir jemand sagen, wann der konstruktor und wann die init()-funktion eines servlets aufgerufen wird?
ist es möglicherweise so, dass wenn eine hohe anzahl von requests auf das servlet gemacht wird, sich verschiedene instanzen des HttpServlet bilden, welche in unterschiedlichen threads laufen?
(also der konstruktor pro servlet möglicherweise > 1 mal aufgerufen wird)
wie sieht es mit der init-funktion aus? in der api-dok lese ich folgendes:
"A convenience method which can be overridden so that there's no need to call super.init(config)."
nein, ein konkr. problem habe ich soweit nicht, frage mich nur jedes mal was ich wo reinschreiben soll? (trotzdem hat's soweit immer funktioniert, fragt sich nur auf welche weise...?)
wenn diese aussage von mir nicht stimmt: "(also der konstruktor pro servlet möglicherweise > 1 mal aufgerufen wird)"
dann stimmt wohl diese auch nicht?
-> "ist es möglicherweise so, dass wenn eine hohe anzahl von requests auf das servlet gemacht wird, sich verschiedene instanzen des HttpServlet bilden, welche in unterschiedlichen threads laufen?"
es ist also immer nur 1 instanz davon im speicher? wie sieht es mit dem threads auf bei einer hohen anzahl requests, weisst du das evtl.?
Denke da gab es ein Missverständniss..
Pro Instanz kein der Konstruktor nur einmal aufgerufen werden, nämlich um eine Instanz zu erzeugen
Kann sein dass ich mich irre, aber ServeltPooling sollte es nicht (mehr) geben, d.h. pro ServletContainer & ServletMapping eine Instanz des Servlets, durch das alle Requests/Threads geschleust werden, ist auch kein Problem, denn Sevlets müssen von Haus aus Multithreadingfähing sein, das SingleThreadedModel ist Deprecated.
In der init() Methode kann man initialisierungen von Ressourcen durchführen und die servlet-init Paramter aus der web.xml einlesen.
"Pro Instanz kein der Konstruktor nur einmal aufgerufen werden, nämlich um eine Instanz zu erzeugen"
ja, da gab es offensichtlich ein missverständnis... natürlich klar! ;-)
konkret geht es darum, properties-files (name/value) zu laden, in das erfolgt per singleton (man muss dann halt den server neu starten, ist aber resourcenschonender...)
die singleton-methode getInstance(...) kann eine IOException werfen, dort fängt das problem an. wenn das nicht der fall wäre, könnte ich bereits im klassenrumpf folgendes schreiben:
private static final Properties myprop = ResourceLoader.getInstance();
stattdessen gibt es nun halt andere möglichkeiten:
1:
Java:
public class MyServlet extends HttpServlet
{
// static, final & nicht definiert, muss also im static-konstruktor geladen werden...
// könnte auch NICHT "final" sein...
private static final Properties myprop;
static
{
try
{
myprop = ResourceLoader.getInstance();
}
catch (final IOException e)
{
throw new RuntimeException("Problem while loading properties file: " + e);
}
}
}
-> hier habe ich die sicherheit, dass der static-block 100%ig garantiert nur 1x ausgeführt wird! (unabhängig von servlet api, im ggs. zur init-funktion...)
2:
Java:
public class MyServlet extends HttpServlet
{
// final & nicht definiert, muss also im konstruktor geladen werden...
// könnte auch NICHT "final", möglicherweise aber "static"...
private final Properties myprop;
public MyServlet()
{
try
{
myprop = ResourceLoader.getInstance();
}
catch (final IOException e)
{
throw new RuntimeException("Problem while loading properties file: " + e);
}
}
}
-> wenn WIRKLICH nur 1 exemplar instanziert wird, auch kein problem...
3:
Java:
public class MyServlet extends HttpServlet
{
// könnte auch "static" sein !!!
private Properties myprop = null;
@Override
public void init(final ServletConfig config) throws ServletException
{
try
{
myprop = ResourceLoader.getInstance();
}
catch (final IOException e)
{
throw new RuntimeException("Problem while loading properties file: " + e);
}
}
}
4: die andere möglichkeit wäre, die IOException in der singleton-klasse zu catchen, und an eine RuntimeException weiterzugeben. so dass getInstance() direkt im klassenrumpf ausgeführt werden könnte...
fall 4 ist natürlich ein wenig ein anderes thema... da kann man keine exceptions mehr catchen.
angenommen man hat die zahl zwischen 1-3, was ist am sinnvollsten? was würdest zu sagen?
"Pro Instanz kein der Konstruktor nur einmal aufgerufen werden, nämlich um eine Instanz zu erzeugen"
ja, da gab es offensichtlich ein missverständnis... natürlich klar! ;-)
konkret geht es darum, properties-files (name/value) zu laden, in das erfolgt per singleton (man muss dann halt den server neu starten, ist aber resourcenschonender...)
die singleton-methode getInstance(...) kann eine IOException werfen, dort fängt das problem an. wenn das nicht der fall wäre, könnte ich bereits im klassenrumpf folgendes schreiben:
private static final Properties myprop = ResourceLoader.getInstance();
stattdessen gibt es nun halt andere möglichkeiten:
1:
Java:
public class MyServlet extends HttpServlet
{
// static, final & nicht definiert, muss also im static-konstruktor geladen werden...
// könnte auch NICHT "final" sein...
private static final Properties myprop;
static
{
try
{
myprop = ResourceLoader.getInstance();
}
catch (final IOException e)
{
throw new RuntimeException("Problem while loading properties file: " + e);
}
}
}
-> hier habe ich die sicherheit, dass der static-block 100%ig garantiert nur 1x ausgeführt wird! (unabhängig von servlet api, im ggs. zur init-funktion...) hier bräuchte es kein singleton, doch ich kann ResourceLoader.getInstance(); auch an einem komplett anderen "ort" (als im servlet) verwenden!
2:
Java:
public class MyServlet extends HttpServlet
{
// final & nicht definiert, muss also im konstruktor geladen werden...
// könnte auch NICHT "final", möglicherweise aber "static"...
private final Properties myprop;
public MyServlet()
{
try
{
myprop = ResourceLoader.getInstance();
}
catch (final IOException e)
{
throw new RuntimeException("Problem while loading properties file: " + e);
}
}
}
-> wenn WIRKLICH nur 1 exemplar des servlets instanziert wird, auch kein problem... trotz singleton will ich die getInstance nicht unnötig aufrufen!!
3:
Java:
public class MyServlet extends HttpServlet
{
// könnte auch "static" sein !!!
private Properties myprop = null;
@Override
public void init(final ServletConfig config) throws ServletException
{
try
{
myprop = ResourceLoader.getInstance();
}
catch (final IOException e)
{
throw new RuntimeException("Problem while loading properties file: " + e);
}
}
}
wo liegt der vorteil?
anderer ansatz: eine andere möglichkeit wäre, die IOException in der singleton-klasse zu catchen, und an eine RuntimeException weiterzugeben. so dass getInstance() direkt im klassenrumpf ausgeführt werden könnte...
fall 4 ist natürlich ein wenig ein anderes thema... da kann man keine exceptions mehr catchen.
angenommen man hat die zahl zwischen 1-3, was ist am sinnvollsten? was würdest du zu sagen?
(viele wege führen nach rom, aber einer davon ist der beste...)
habe da immer wieder ein durcheinander mit diesem RuntimeException's
"Sehe keine Notwendigkeit für ein Singleton, dafür kann man auch sehr gut den ApplicationScope nutzen, oder besser gleich Serlvet Init Parameter."
ja, dann hat man das objekt für sämtliche webapplikationen verfügbar, unabhängig von request, session, einzelner webapplikation etc... nur: man sollte doch dafür sorgen, dass die instanz, die man der ApplicationScope.setAttribute(str, obj) mitgibt, sich nicht bei jedem request neu kreiert wird?
den application scope hätte man innerhalt der init(...)-funktion verfügbar, richtig? (nicht aber innerhalb des konstruktor, schon gar nicht innerhalb des static-konstruktors!)
also innerhalb der init-funktion ("local scope") die properties instanzieren, und dem application scope setzen? wäre das sauber?
servlet-init parameter geht nicht, das liest ja die web.xml aus... nicht geeignet in meinem fall...
gruss, jan
p.s.: habe meine codes nachträglich kommentiert, so gut es geht begründet...
Verstehe nicht was du damit sagen willst, unchecked Exceptions kann man genauso catchen wie checked Exceptions.
Bei einer IOException während dem auslesen der Conig parameter sollte es allerdings egal sein ob du catched oder nicht, heisst erstmal die App kann nciht hochgefahren werden.
Wenn es ein durcheinander gibt liegt das nciht daran ob checked oder unchecked Exceptions verwendet werden, wobei checked Excetpions schaffen mehr durcheinander.
ja, dann hat man das objekt für sämtliche webapplikationen verfügbar, unabhängig von request, session, einzelner webapplikation etc...
nur: man sollte doch dafür sorgen, dass die instanz, die man der ApplicationScope.setAttribute(str, ojb) mitgibt, sich nicht bei jedem request neu kreiert wird?
public class SoWieSo
{
// getInstance1 throws RuntimeException
private static final Object o1 = Singleton.getInstance1();
// -> geht im klassenrumpf, da try/catch bei RuntimeException NICHT ZWANGSLÄUFIG notwendig, aber möglich...
// getInstance2 throws IOException
private static final Object o2 = Singleton.getInstance2();
// -> geht NICHT im klassenrumpf, da try/catch bei IOException ZWANGSLÄUFIG notwendig...
}
2.was ist denn der application scope, PRO SERVLET (nicht für das ganze deployment) IMMER verfügbar, request- und session-unabhängig?
3. möglichweise?
4. keine members in spiel bringen: da die init-funktion nur 1x aufgerufen wird, kann die ganze Properties-geschichte dort LOKAL instanziert, und dem applications scope mitgegeben werden...