Als aufsteigender Stern kann JSP eine bestimmte Position in der Serverprogrammierumgebung einnehmen, was eng mit der guten Unterstützung einer Reihe von Industriestandards zusammenhängt. Session ist eine der von ihr bereitgestellten Infrastrukturen. Als Programmierer können Sie eine einfache sitzungsbasierte Benutzerverwaltung problemlos implementieren, ohne sich Gedanken darüber machen zu müssen, wie diese auf dem Client implementiert wird. Heutzutage gibt es verschiedene Möglichkeiten, mit Online-Benutzern umzugehen.
Zum einen wird die Seitenaktualisierung vom Benutzer gesteuert und der Server steuert eine Zeitüberschreitung von beispielsweise 30 Minuten. Nach Ablauf der Zeit wird der Benutzer rausgeschmissen, wenn keine Aktion erfolgt. Der Vorteil dieser Methode besteht darin, dass, wenn der Benutzer vergisst, sich abzumelden, andere vor böswilligen Vorgängen geschützt werden können. Der Nachteil besteht darin, dass Sie sich beim Absenden möglicherweise erneut anmelden müssen, wenn Sie etwas tun, das viel Zeit in Anspruch nimmt und dieses Zeitlimit überschreitet. Wenn die ursprüngliche Blattoberfläche erneut versagen muss, kann es sein, dass Sie Ihre geleistete Arbeit verlieren. Aus Implementierungssicht ist dies die einfachste, und die Serverseite implementiert diesen Modus standardmäßig.
Eine andere Möglichkeit besteht darin, dass die Site eine Frame-Struktur annimmt und es einen Frame oder einen versteckten Iframe gibt, der ständig aktualisiert wird, sodass Sie nie rausgeschmissen werden. Um jedoch festzustellen, ob Sie online sind, muss der Server einen festlegen Wenn Sie diese Benommenheitszeit überschreiten, wird davon ausgegangen, dass Sie nicht mehr online sind, wenn Sie außer dieser automatisch aktualisierten Seite keine anderen Seiten aktualisieren. Ein typisches Beispiel für diesen Ansatz ist xici.net. Sein Vorteil besteht darin, dass kontinuierliche Aktualisierungen verwendet werden können, um einige Server-Push-ähnliche Funktionen zu implementieren, z. B. das Senden von Nachrichten zwischen Internetnutzern.
Unabhängig davon, welcher Modus verwendet wird, müssen einige zusätzliche Arbeiten durchgeführt werden, um alle derzeit Online-Benutzer zu durchsuchen. Es gibt keine API zum Abrufen der Sitzungsliste in der Servlet-API.
Was verwendet werden kann, ist Listener. Die Spezifikationen von Servlet 2.2 und 2.3 unterscheiden sich hier geringfügig. HttpSessionBindingListener in 2.2 kann eine Klasse implementieren, die Sie benachrichtigt, wenn sich das Attribut in einer HTTPSession ändert. HttpSessionAttributeListener wurde ebenfalls in 2.3 eingeführt. Da die Umgebung, die ich verwende, Visual Age für Java 4 und JRun Server 3.1 ist, wird die Servlet 2.3-Programmierung nicht direkt unterstützt. Dazu
gehört die Erstellung einer neuen Klasse Implementieren Sie die HttpSessionBindingListener-Schnittstelle. Diese Schnittstelle verfügt über zwei Methoden:
public void valueBound(HttpSessionBindingEvent event)
public void valueUnbound(HttpSessionBindingEvent event)
Wenn Sie Session.addAttribute(String,Object) ausführen und eine Klasse hinzugefügt haben, die die HttpSessionBindingListener-Schnittstelle als Attribut implementiert, benachrichtigt Session Ihre Klasse und rufen Sie Ihre valueBound-Methode auf. Im Gegenteil, die Session.removeAttribute-Methode entspricht der valueUndound-Methode.
Die öffentliche Klasse HttpSessionBinding implementiert javax.servlet.http.HttpSessionBindingListener
.
{
ServletContext application = null;
public HttpSessionBinding(ServletContext application)
{
super
()
;
.application = application;
}
public void valueBound(javax.servlet.http.HttpSessionBindingEvent e)
{
Vector activeSessions = (Vector) application.getAttribute("activeSessions");
if (activeSessions == null)
{
activeSessions = new Vector();
}
JDBCUser sessionUser = (JDBCUser)e.getSession().getAttribute("user");
if (sessionUser != null)
{
activeSessions.add(e.getSession());
}
application.setAttribute("activeSessions",activeSessions) ;
}
public void valueUnbound(javax.servlet.http.HttpSessionBindingEvent e)
{
JDBCUser sessionUser = (JDBCUser)e.getSession().getAttribute("user");
if (sessionUser == null)
{
Vector activeSessions = (Vector) application .getAttribute("activeSessions");
if (activeSessions != null)
{
activeSessions.remove(e.getSession().getId());
application.setAttribute
(
"
activeSessions
",activeSessions)
;
Klasse ist eine beliebige Benutzerklasse. Fügen Sie bei der Benutzeranmeldung sowohl die User-Klasse als auch die HttpSessionBinding-Klasse zur Sitzung hinzu.
Auf diese Weise wird jedes Mal, wenn sich ein Benutzer anmeldet, ein Datensatz zum Attributvektor „activeSessions“ in der Anwendung hinzugefügt. Immer wenn die Sitzung abläuft, wird valueUnbound ausgelöst und die Sitzung, bei der das Zeitlimit überschritten wird, wird aus diesem Vektor gelöscht.
public void login()
throws ACLException,SQLException,IOException
{
/* get JDBC User Class */
if (user != null )
{
logout ();
}
{
// wenn die Sitzung abgelaufen ist oder sich der Benutzer nicht angemeldet hat, speichern Sie die Ziel-URL vorübergehend.
uf = new JDBCUserFactory();
if ( (this.request.getParameter("userID")= =null) ||. (this.request.getParameter("password")==null) )
{
throw new ACLException("Bitte geben Sie einen gültigen Benutzernamen und ein gültiges Passwort ein."
}
JDBCUser user = (JDBCUser) uf.UserLogin(
this .request.getParameter("userID"),
this.request.getParameter
("
password") )
; ,new HttpSessionBinding (application));
}
}
Fügen Sie beim Anmelden den Benutzer und die BindingNotofy-Zweckklasse zur Sitzung hinzu. Beim Abmelden müssen Sie die Sitzung im ActiveSessions-Vektor aktiv löschen.
public void logout()
throws SQLException,ACLException
{
if (this.user == null && this.session.getAttribute("user")==null)
{
return ;
}
Vector activeSessions = (Vector) this.application.getAttribute("activeSessions");
if (activeSessions != null)
{
activeSessions.remove(this.session)
;
}
java. util.Enumeration e = this.session.getAttribute();
while (e.hasMoreElements())
{
String
s = (String)e.nextElement
(s)
this.user );
this.user = null;
}
Diese beiden Funktionen befinden sich in einer HttpSessionManager-Klasse. Diese Klasse verweist auf das globale Anwendungsobjekt. Der andere Code dieser Klasse hat nichts mit diesem Artikel zu tun und ist ziemlich lang, daher werde ich ihn nicht veröffentlichen.
Schauen wir uns an, wie man es in JSP verwendet.
Angenommen, ein Anmeldeformular wird an doLogin.jsp gesendet und das Formular enthält die Felder „Benutzername“ und „Kennwort“. Auszug:
<%
HttpSessionManager hsm = new HttpSessionManager(application,request,response);
try
{
hsm.login();
}
Catch (UserNotFoundException e)
{
Response.sendRedirect("InsufficientPrivilege.jsp?detail=User%20does%20not %20exist .");
return;
}
Catch (InvalidPasswordException e2)
{
Response.sendRedirect("InsufficientPrivilege.jsp?detail=Invalid%20Password");
Return;
}
Catch (Exception e3)
{
%> Error:<%=e3. toString( ) %><br>
Drücken Sie<a href="login.jsp">
Hier</a>, um sich erneut anzumelden.
}
Response.sendRedirect
("index.jsp")
;
Jetzt haben So erhalten Sie eine Liste der derzeit online befindlichen Benutzer.
<body bgcolor="#FFFFFF">
<table cellespacing="0" cellpadding="0" width="100%">
<tr >
<td style="width:24px">SessionId
</td>
<td style= "width:80px" >Benutzer
</td>
<td style="width:80px" >Anmeldezeit
</td>
<td style="width:80px" >Letzte Zugriffszeit
</td>
</tr>
<%
Vector activeSessions = (Vector) application.getAttribute("activeSessions");
if (activeSessions == null)
{
activeSessions = new Vector(
"activeSessions",activeSessions
}
Iterator it = activeSessions.iterator(); ;
while (it.hasNext())
{
HttpSession sess = (HttpSession)it.next();
JDBCUser sessionUser = (JDBCUser)sess.getAttribute("user");
String userId = (sessionUser!=null)?sessionUser.getUserID ():"None";
%>
<tr>
<td nowrap=''><%= sess.getId() %></td>
<td nowrap=''><%= userId %></td>
<td nowrap=''>
<%= BeaconDate.getInstance( new Java.util.Date(sess.getCreationTime())).getDateTimeString()%></td>
<td class="<%= stl %>3 " nowrap=''>
<%= BeaconDate.getInstance( new java.util.Date(sess.getLastAccessedTime())).getDateTimeString()%></td>
</tr>
<%
}
%>
</table>
</body>
Der obige Code ruft activeSessions aus der Anwendung ab und zeigt die spezifische Zeit an. Es wird davon ausgegangen, dass es sich bei der BeaconDate-Klasse um eine formatierte Zeitklasse handelt.
Auf diese Weise erhalten wir einen Rahmen zum Anzeigen der Liste der Online-Benutzer. Das Paging von Online-Benutzerlisten und andere Funktionen sind für diesen Artikel irrelevant und werden nicht besprochen.
Dies ist ein Beispiel für ein Nicht-Aktualisierungsmodell, das auf dem Sitzungs-Timeout-Mechanismus basiert. Mein Kollege Sonymusic wies darauf hin, dass dies aufgrund der unterschiedlichen Vorstellungen der einzelnen Hersteller oft nicht zuverlässig sei. Unter Berücksichtigung dieser Anforderung muss ermittelt werden, ob die Zeit seit der letzten Verwendung durch den aktuellen Benutzer einen vorgegebenen Zeitwert überschreitet, wenn jede Blattoberfläche aktualisiert wird. Dies bedeutet im Wesentlichen, dass Sie das Sitzungs-Timeout selbst implementieren. Wenn Sie ein Aktualisierungsmodell implementieren müssen, müssen Sie diese Methode zur Beurteilung der Aktualisierung für jede Blattoberfläche verwenden.