rewrote the ESNode management for users. ESUser is now used

*only* for active users (sessions), and each session has its own
ESUser wrapper, while the node within may be the same (if
both sessions are logged in as the same user.
This commit is contained in:
hns 2001-07-29 22:59:51 +00:00
parent cd6ee8ccbf
commit 33add5c06b
5 changed files with 55 additions and 36 deletions

View file

@ -444,7 +444,6 @@ public class Application extends UnicastRemoteObject implements IRemoteApp, IRep
if (pw != null && pw.equals (password)) { if (pw != null && pw.equals (password)) {
// give the user her piece of persistence // give the user her piece of persistence
u.setNode (unode); u.setNode (unode);
u.user.setNode (unode);
activeUsers.put (unode.getNameOrID (), u.user); activeUsers.put (unode.getNameOrID (), u.user);
return true; return true;
} }
@ -462,8 +461,7 @@ public class Application extends UnicastRemoteObject implements IRemoteApp, IRep
activeUsers.remove (uid); activeUsers.remove (uid);
// switch back to the non-persistent user node as cache // switch back to the non-persistent user node as cache
u.user.setNode (null); u.setNode (null);
u.setNode (u.user.getNode ());
} }
return true; return true;
} }
@ -495,7 +493,7 @@ public class Application extends UnicastRemoteObject implements IRemoteApp, IRep
String base = props.getProperty ("baseURI"); String base = props.getProperty ("baseURI");
String siteroot = props.getProperty ("rootPrototype"); String siteroot = props.getProperty ("rootPrototype");
setBaseURI (base); if (base != null) setBaseURI (base);
String href = n.getUrl (root, users, tmpname, siteroot); String href = n.getUrl (root, users, tmpname, siteroot);
return baseURI + href; return baseURI + href;

View file

@ -25,11 +25,9 @@ public class ESUser extends ESNode {
// if the user is online, this is his/her online session object // if the user is online, this is his/her online session object
public User user; public User user;
public ESUser (INode node, RequestEvaluator eval) { public ESUser (INode node, RequestEvaluator eval, User user) {
super (eval.esUserPrototype, eval.evaluator, node, eval); super (eval.esUserPrototype, eval.evaluator, node, eval);
user = (User) eval.app.activeUsers.get (node.getNameOrID ()); this.user = user;
if (user == null)
user = (User) eval.app.sessions.get (node.getNameOrID ());
if (user != null) { if (user != null) {
cache = user.cache; cache = user.cache;
cacheWrapper = new ESNode (cache, eval); cacheWrapper = new ESNode (cache, eval);
@ -56,25 +54,30 @@ public class ESUser extends ESNode {
} }
public void setUser (User user) { /**
if (this.user != user) { * The node for a user object changes at login and logout, so we don't use our
this.user = user; * own node, but just reach through to the session user object instead.
cache = user.cache; */
}
cacheWrapper = new ESNode (cache, eval);
}
public void setNode (INode node) { public void setNode (INode node) {
user.setNode (node);
if (node != null) { if (node != null) {
this.node = node; this.node = node;
nodeID = node.getID (); } else {
dbmap = node.getDbMapping (); // user.getNode will never return null. If the node is set to null (=user logged out)
eval.objectcache.put (node, this); // it will user the original transient cache node again.
// we don't take over the transient cache from the node, this.node = user.getNode ();
// because we always use the one from the user object.
} }
nodeID = this.node.getID ();
dbmap = this.node.getDbMapping ();
// we don't take over the transient cache from the node,
// because we always use the one from the user object.
} }
public void updateNode () {
node = user.getNode ();
nodeID = node.getID ();
dbmap = node.getDbMapping ();
}
public String toString () { public String toString () {
return ("UserObject "+node.getNameOrID ()); return ("UserObject "+node.getNameOrID ());

View file

@ -710,14 +710,16 @@ public class HopExtension {
Hashtable sessions = (Hashtable) app.sessions.clone (); Hashtable sessions = (Hashtable) app.sessions.clone ();
ESObject ap = this.evaluator.getArrayPrototype(); ESObject ap = this.evaluator.getArrayPrototype();
ArrayPrototype theArray = new ArrayPrototype (ap, this.evaluator); ArrayPrototype theArray = new ArrayPrototype (ap, this.evaluator);
theArray.setSize (sessions.size ());
int i=0; int i=0;
Hashtable visited = new Hashtable (); // Hashtable visited = new Hashtable ();
for (Enumeration e=sessions.elements(); e.hasMoreElements(); ) { for (Enumeration e=sessions.elements(); e.hasMoreElements(); ) {
User u = (User) e.nextElement (); User u = (User) e.nextElement ();
if (u.uid == null || !visited.containsKey (u.uid)) { // Note: we previously sorted out duplicate users - now we simply enumerate all active sessions.
theArray.setElementAt (reval.getNodeWrapper (u.getNode ()), i++); // if (u.uid == null || !visited.containsKey (u.uid)) {
if (u.uid != null) visited.put (u.uid, u); theArray.setElementAt (reval.getNodeWrapper (u), i++);
} // if (u.uid != null) visited.put (u.uid, u);
// }
} }
return theArray; return theArray;
} }

View file

@ -173,8 +173,8 @@ public class RequestEvaluator implements Runnable {
root = app.getDataRoot (); root = app.getDataRoot ();
ESUser esu = (ESUser) getNodeWrapper (user.getNode ()); ESUser esu = (ESUser) getNodeWrapper (user);
esu.setUser (user); // esu.setUser (user);
global.putHiddenProperty ("root", getNodeWrapper (root)); global.putHiddenProperty ("root", getNodeWrapper (root));
global.putHiddenProperty("user", esu); global.putHiddenProperty("user", esu);
global.putHiddenProperty ("req", new ESWrapper (req, evaluator)); global.putHiddenProperty ("req", new ESWrapper (req, evaluator));
@ -476,8 +476,8 @@ public class RequestEvaluator implements Runnable {
if (user == null) { if (user == null) {
current = global; current = global;
} else { } else {
ESUser esu = (ESUser) getNodeWrapper (user.getNode ()); ESUser esu = (ESUser) getNodeWrapper (user);
esu.setUser (user); // esu.setUser (user);
current = esu; current = esu;
} }
} }
@ -786,8 +786,8 @@ public class RequestEvaluator implements Runnable {
ESNode esn = (ESNode) objectcache.get (n); ESNode esn = (ESNode) objectcache.get (n);
if (esn == null || esn.getNode() != n) { if (esn == null || esn.getNode() != n) {
ObjectPrototype op = null;
String protoname = n.getPrototype (); String protoname = n.getPrototype ();
ObjectPrototype op = null;
// set the DbMapping of the node according to its prototype. // set the DbMapping of the node according to its prototype.
// this *should* be done on the objectmodel level, but isn't currently // this *should* be done on the objectmodel level, but isn't currently
@ -804,10 +804,7 @@ public class RequestEvaluator implements Runnable {
if (op == null) if (op == null)
op = esNodePrototype; // no prototype found for this node. op = esNodePrototype; // no prototype found for this node.
if ("user".equalsIgnoreCase (protoname)) esn = new ESNode (op, evaluator, n, this);
esn = new ESUser (n, this);
else
esn = new ESNode (op, evaluator, n, this);
objectcache.put (n, esn); objectcache.put (n, esn);
// app.logEvent ("Wrapper for "+n+" created"); // app.logEvent ("Wrapper for "+n+" created");
@ -816,6 +813,25 @@ public class RequestEvaluator implements Runnable {
return esn; return esn;
} }
public ESNode getNodeWrapper (User u) {
if (u == null)
return null;
ESUser esn = (ESUser) objectcache.get (u);
if (esn == null) {
esn = new ESUser (u.getNode(), this, u);
objectcache.put (u, esn);
} else {
// the user node may have changed (login/logout) while the ESUser was
// lingering in the cache.
esn.updateNode ();
}
return esn;
}
public ObjectPrototype getPrototype (String protoName) { public ObjectPrototype getPrototype (String protoName) {
return (ObjectPrototype) prototypes.get (protoName); return (ObjectPrototype) prototypes.get (protoName);
} }

View file

@ -29,7 +29,7 @@ public class User implements Serializable {
this.app = app; this.app = app;
setNode (null); setNode (null);
cache = new Node (sid); cache = new Node (sid);
cache.setPrototype ("user"); cache.setPrototype ("user");
sessionID = sid; sessionID = sid;
onSince = System.currentTimeMillis (); onSince = System.currentTimeMillis ();
lastTouched = onSince; lastTouched = onSince;