first implementation of system lever skin support
This commit is contained in:
parent
9922ea3fd8
commit
bf0ecdd923
7 changed files with 187 additions and 17 deletions
|
@ -52,7 +52,7 @@ public class Application extends UnicastRemoteObject implements IRemoteApp, Runn
|
||||||
long requestTimeout = 60000; // 60 seconds for request timeout.
|
long requestTimeout = 60000; // 60 seconds for request timeout.
|
||||||
ThreadGroup threadgroup;
|
ThreadGroup threadgroup;
|
||||||
|
|
||||||
protected String templateExtension, scriptExtension, actionExtension;
|
protected String templateExtension, scriptExtension, actionExtension, skinExtension;
|
||||||
|
|
||||||
// A transient node that is shared among all evaluators
|
// A transient node that is shared among all evaluators
|
||||||
protected INode appnode;
|
protected INode appnode;
|
||||||
|
@ -95,6 +95,7 @@ public class Application extends UnicastRemoteObject implements IRemoteApp, Runn
|
||||||
templateExtension = props.getProperty ("templateExtension", ".hsp");
|
templateExtension = props.getProperty ("templateExtension", ".hsp");
|
||||||
scriptExtension = props.getProperty ("scriptExtension", ".js");
|
scriptExtension = props.getProperty ("scriptExtension", ".js");
|
||||||
actionExtension = props.getProperty ("actionExtension", ".hac");
|
actionExtension = props.getProperty ("actionExtension", ".hac");
|
||||||
|
skinExtension = ".skin";
|
||||||
|
|
||||||
sessions = new Hashtable ();
|
sessions = new Hashtable ();
|
||||||
activeUsers = new Hashtable ();
|
activeUsers = new Hashtable ();
|
||||||
|
|
|
@ -602,18 +602,30 @@ public class HopExtension {
|
||||||
this.asString = asString;
|
this.asString = asString;
|
||||||
}
|
}
|
||||||
public ESValue callFunction (ESObject thisObject, ESValue[] arguments) throws EcmaScriptException {
|
public ESValue callFunction (ESObject thisObject, ESValue[] arguments) throws EcmaScriptException {
|
||||||
if (arguments.length != 1 || !(arguments[0] instanceof ESWrapper))
|
if (arguments.length < 1 || arguments.length > 2 || arguments[0] ==null || arguments[0] == ESNull.theNull)
|
||||||
throw new EcmaScriptException ("renderSkin must be called with one Skin argument!");
|
throw new EcmaScriptException ("renderSkin must be called with one Skin argument and an optional parameter argument");
|
||||||
try {
|
try {
|
||||||
Skin skin = (Skin) ((ESWrapper) arguments[0]).toJavaObject ();
|
Skin skin = null;
|
||||||
ESNode handlerNode = global ? null : (ESNode) thisObject;
|
ESNode handlerNode = global ? null : (ESNode) thisObject;
|
||||||
|
// first, see if the first argument already is a skin object. If not, it's the name of the skin to be called
|
||||||
|
if (arguments[0] instanceof ESWrapper) {
|
||||||
|
Object obj = ((ESWrapper) arguments[0]).toJavaObject ();
|
||||||
|
if (obj instanceof Skin)
|
||||||
|
skin = (Skin) obj;
|
||||||
|
}
|
||||||
|
if (skin == null)
|
||||||
|
skin = reval.getSkin (handlerNode, arguments[0].toString ());
|
||||||
if (asString)
|
if (asString)
|
||||||
reval.res.pushStringBuffer ();
|
reval.res.pushStringBuffer ();
|
||||||
skin.render (reval, handlerNode);
|
try {
|
||||||
|
skin.render (reval, handlerNode);
|
||||||
|
} catch (NullPointerException npx) {
|
||||||
|
reval.res.write ("[Skin not found: "+arguments[0]+"]");
|
||||||
|
}
|
||||||
if (asString)
|
if (asString)
|
||||||
return new ESString (reval.res.popStringBuffer ());
|
return new ESString (reval.res.popStringBuffer ());
|
||||||
} catch (ClassCastException x) {
|
} catch (Exception x) {
|
||||||
throw new EcmaScriptException ("renderSkin must be called with one Skin argument!");
|
throw new EcmaScriptException ("renderSkin: "+x);
|
||||||
}
|
}
|
||||||
return ESNull.theNull;
|
return ESNull.theNull;
|
||||||
}
|
}
|
||||||
|
|
|
@ -24,7 +24,7 @@ public class Prototype {
|
||||||
String id;
|
String id;
|
||||||
String name;
|
String name;
|
||||||
Application app;
|
Application app;
|
||||||
Hashtable templates, functions, actions;
|
Hashtable templates, functions, actions, skins;
|
||||||
File codeDir;
|
File codeDir;
|
||||||
long lastUpdate;
|
long lastUpdate;
|
||||||
|
|
||||||
|
@ -86,6 +86,18 @@ public class Prototype {
|
||||||
return (Action) actions.get (afname);
|
return (Action) actions.get (afname);
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public SkinFile getSkinFile (String sfname) {
|
||||||
|
return (SkinFile) skins.get (sfname);
|
||||||
|
}
|
||||||
|
|
||||||
|
public Skin getSkin (String sfname) {
|
||||||
|
SkinFile sf = (SkinFile) skins.get (sfname);
|
||||||
|
if (sf != null)
|
||||||
|
return sf.getSkin ();
|
||||||
|
else
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
public File getCodeDir () {
|
public File getCodeDir () {
|
||||||
return codeDir;
|
return codeDir;
|
||||||
}
|
}
|
||||||
|
|
|
@ -653,6 +653,17 @@ public class RequestEvaluator implements Runnable {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
public Skin getSkin (ESObject thisObject, String skinname) {
|
||||||
|
INode n = null;
|
||||||
|
if (thisObject != null && thisObject instanceof ESNode)
|
||||||
|
n = ((ESNode) thisObject).getNode ();
|
||||||
|
Prototype proto = app.getPrototype (n);
|
||||||
|
if (proto != null)
|
||||||
|
return proto.getSkin (skinname);
|
||||||
|
else
|
||||||
|
return null;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
/**
|
/**
|
||||||
* Returns a node wrapper only if it already exists in the cache table. This is used
|
* Returns a node wrapper only if it already exists in the cache table. This is used
|
||||||
|
|
|
@ -55,12 +55,12 @@ public class Skin {
|
||||||
parts = partBuffer.toArray ();
|
parts = partBuffer.toArray ();
|
||||||
}
|
}
|
||||||
|
|
||||||
public void render (RequestEvaluator reval, ESNode handlerNode) {
|
public void render (RequestEvaluator reval, ESNode thisNode) {
|
||||||
if (parts == null)
|
if (parts == null)
|
||||||
return;
|
return;
|
||||||
for (int i=0; i<parts.length; i++) {
|
for (int i=0; i<parts.length; i++) {
|
||||||
if (parts[i] instanceof Macro)
|
if (parts[i] instanceof Macro)
|
||||||
((Macro) parts[i]).render (reval, handlerNode);
|
((Macro) parts[i]).render (reval, thisNode);
|
||||||
else
|
else
|
||||||
reval.res.write (parts[i]);
|
reval.res.write (parts[i]);
|
||||||
}
|
}
|
||||||
|
@ -165,7 +165,7 @@ public class Skin {
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
public void render (RequestEvaluator reval, ESNode handlerNode) {
|
public void render (RequestEvaluator reval, ESNode thisNode) {
|
||||||
|
|
||||||
if ("response".equalsIgnoreCase (handler)) {
|
if ("response".equalsIgnoreCase (handler)) {
|
||||||
renderFromResponse (reval);
|
renderFromResponse (reval);
|
||||||
|
@ -182,12 +182,13 @@ public class Skin {
|
||||||
arguments[0] = par;
|
arguments[0] = par;
|
||||||
|
|
||||||
if (handler != null) {
|
if (handler != null) {
|
||||||
// not a macro handled by global - need to find handler object
|
// not a global macro - need to find handler object
|
||||||
if (handlerNode != null) {
|
if (thisNode != null) {
|
||||||
// was called with this object - check it or its parents for matching prototype
|
// was called with this object - check it or its parents for matching prototype
|
||||||
if (!handler.equalsIgnoreCase ("this") && !handler.equalsIgnoreCase (handlerNode.getPrototypeName ())) {
|
if (!handler.equalsIgnoreCase ("this") && !handler.equalsIgnoreCase (thisNode.getPrototypeName ())) {
|
||||||
// the handler object is not what we want
|
// the handler object is not what we want
|
||||||
INode n = handlerNode.getNode();
|
INode n = thisNode.getNode();
|
||||||
|
// walk down parent chain to find handler object
|
||||||
while (n != null) {
|
while (n != null) {
|
||||||
if (handler.equalsIgnoreCase (n.getPrototype())) {
|
if (handler.equalsIgnoreCase (n.getPrototype())) {
|
||||||
handlerObject = reval.getNodeWrapper (n);
|
handlerObject = reval.getNodeWrapper (n);
|
||||||
|
@ -197,12 +198,12 @@ public class Skin {
|
||||||
}
|
}
|
||||||
} else {
|
} else {
|
||||||
// we already have the right handler object
|
// we already have the right handler object
|
||||||
handlerObject = handlerNode;
|
handlerObject = thisNode;
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if (handlerObject == null) {
|
if (handlerObject == null) {
|
||||||
// eiter because handlerNode == null or the right object wasn't found in the targetNode path
|
// eiter because thisNode == null or the right object wasn't found in the targetNode path
|
||||||
// go check request path for an object with matching prototype
|
// go check request path for an object with matching prototype
|
||||||
int l = reval.reqPath.size();
|
int l = reval.reqPath.size();
|
||||||
for (int i=l-1; i>=0; i--) {
|
for (int i=l-1; i>=0; i--) {
|
||||||
|
|
106
src/helma/framework/core/SkinFile.java
Normal file
106
src/helma/framework/core/SkinFile.java
Normal file
|
@ -0,0 +1,106 @@
|
||||||
|
// SkinFile.java
|
||||||
|
// Copyright (c) Hannes Wallnöfer 2001
|
||||||
|
|
||||||
|
package helma.framework.core;
|
||||||
|
|
||||||
|
import java.util.*;
|
||||||
|
import java.io.*;
|
||||||
|
import helma.objectmodel.IServer;
|
||||||
|
|
||||||
|
|
||||||
|
/**
|
||||||
|
* This represents a File containing a Hop skin
|
||||||
|
*/
|
||||||
|
|
||||||
|
|
||||||
|
public class SkinFile {
|
||||||
|
|
||||||
|
String name;
|
||||||
|
Prototype prototype;
|
||||||
|
Application app;
|
||||||
|
File file;
|
||||||
|
Skin skin;
|
||||||
|
long lastmod;
|
||||||
|
|
||||||
|
public SkinFile (File file, String name, Prototype proto) {
|
||||||
|
this.prototype = proto;
|
||||||
|
this.app = proto.app;
|
||||||
|
this.name = name;
|
||||||
|
this.file = file;
|
||||||
|
this.skin = null;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
public void update (File f) {
|
||||||
|
|
||||||
|
this.file = f;
|
||||||
|
|
||||||
|
long fmod = file.lastModified ();
|
||||||
|
// we only update this if we already have read the skin
|
||||||
|
if (skin == null || lastmod == fmod)
|
||||||
|
return;
|
||||||
|
|
||||||
|
read ();
|
||||||
|
}
|
||||||
|
|
||||||
|
private void read () {
|
||||||
|
try {
|
||||||
|
FileReader reader = new FileReader (file);
|
||||||
|
char c[] = new char[(int) file.length()];
|
||||||
|
reader.read (c);
|
||||||
|
reader.close();
|
||||||
|
skin = new Skin (new String (c));
|
||||||
|
} catch (IOException x) {
|
||||||
|
IServer.getLogger().log ("Error reading Skin "+file+": "+x);
|
||||||
|
}
|
||||||
|
|
||||||
|
lastmod = file.lastModified ();
|
||||||
|
}
|
||||||
|
|
||||||
|
public Skin getSkin () {
|
||||||
|
if (skin == null)
|
||||||
|
read ();
|
||||||
|
return skin;
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
|
@ -157,6 +157,7 @@ public class TypeManager implements Runnable {
|
||||||
Hashtable ntemp = new Hashtable ();
|
Hashtable ntemp = new Hashtable ();
|
||||||
Hashtable nfunc = new Hashtable ();
|
Hashtable nfunc = new Hashtable ();
|
||||||
Hashtable nact = new Hashtable ();
|
Hashtable nact = new Hashtable ();
|
||||||
|
Hashtable nskins = new Hashtable ();
|
||||||
|
|
||||||
for (int i=0; i<list.length; i++) {
|
for (int i=0; i<list.length; i++) {
|
||||||
File tmpfile = new File (dir, list[i]);
|
File tmpfile = new File (dir, list[i]);
|
||||||
|
@ -182,6 +183,7 @@ public class TypeManager implements Runnable {
|
||||||
} catch (Throwable x) {
|
} catch (Throwable x) {
|
||||||
IServer.getLogger().log ("Error creating prototype: "+x);
|
IServer.getLogger().log ("Error creating prototype: "+x);
|
||||||
}
|
}
|
||||||
|
|
||||||
} else if (list[i].endsWith (app.actionExtension) && tmpfile.length () > 0) {
|
} else if (list[i].endsWith (app.actionExtension) && tmpfile.length () > 0) {
|
||||||
try {
|
try {
|
||||||
Action af = new Action (tmpfile, tmpname, proto);
|
Action af = new Action (tmpfile, tmpname, proto);
|
||||||
|
@ -189,11 +191,19 @@ public class TypeManager implements Runnable {
|
||||||
} catch (Throwable x) {
|
} catch (Throwable x) {
|
||||||
IServer.getLogger().log ("Error creating prototype: "+x);
|
IServer.getLogger().log ("Error creating prototype: "+x);
|
||||||
}
|
}
|
||||||
|
} else if (list[i].endsWith (app.skinExtension)) {
|
||||||
|
try {
|
||||||
|
SkinFile sf = new SkinFile (tmpfile, tmpname, proto);
|
||||||
|
nskins.put (tmpname, sf);
|
||||||
|
} catch (Throwable x) {
|
||||||
|
IServer.getLogger().log ("Error creating prototype: "+x);
|
||||||
|
}
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
proto.templates = ntemp;
|
proto.templates = ntemp;
|
||||||
proto.functions = nfunc;
|
proto.functions = nfunc;
|
||||||
proto.actions = nact;
|
proto.actions = nact;
|
||||||
|
proto.skins = nskins;
|
||||||
|
|
||||||
// init prototype on evaluators that are already initialized.
|
// init prototype on evaluators that are already initialized.
|
||||||
Iterator evals = getRegisteredRequestEvaluators ();
|
Iterator evals = getRegisteredRequestEvaluators ();
|
||||||
|
@ -212,6 +222,7 @@ public class TypeManager implements Runnable {
|
||||||
Hashtable ntemp = new Hashtable ();
|
Hashtable ntemp = new Hashtable ();
|
||||||
Hashtable nfunc = new Hashtable ();
|
Hashtable nfunc = new Hashtable ();
|
||||||
Hashtable nact = new Hashtable ();
|
Hashtable nact = new Hashtable ();
|
||||||
|
Hashtable nskins = new Hashtable ();
|
||||||
|
|
||||||
for (int i=0; i<list.length; i++) {
|
for (int i=0; i<list.length; i++) {
|
||||||
File tmpfile = new File (dir, list[i]);
|
File tmpfile = new File (dir, list[i]);
|
||||||
|
@ -266,6 +277,21 @@ public class TypeManager implements Runnable {
|
||||||
}
|
}
|
||||||
nact.put (tmpname, af);
|
nact.put (tmpname, af);
|
||||||
|
|
||||||
|
} else if (list[i].endsWith (app.skinExtension)) {
|
||||||
|
SkinFile sf = proto.getSkinFile (tmpname);
|
||||||
|
try {
|
||||||
|
if (sf == null) {
|
||||||
|
sf = new SkinFile (tmpfile, tmpname, proto);
|
||||||
|
idleSeconds = 0;
|
||||||
|
} else if (sf.lastmod != tmpfile.lastModified ()) {
|
||||||
|
sf.update (tmpfile);
|
||||||
|
idleSeconds = 0;
|
||||||
|
}
|
||||||
|
} catch (Throwable x) {
|
||||||
|
IServer.getLogger().log ("Error updating prototype: "+x);
|
||||||
|
}
|
||||||
|
nskins.put (tmpname, sf);
|
||||||
|
|
||||||
} else if ("type.properties".equalsIgnoreCase (list[i])) {
|
} else if ("type.properties".equalsIgnoreCase (list[i])) {
|
||||||
try {
|
try {
|
||||||
if (proto.dbmap.read ()) {
|
if (proto.dbmap.read ()) {
|
||||||
|
@ -280,6 +306,7 @@ public class TypeManager implements Runnable {
|
||||||
proto.templates = ntemp;
|
proto.templates = ntemp;
|
||||||
proto.functions = nfunc;
|
proto.functions = nfunc;
|
||||||
proto.actions = nact;
|
proto.actions = nact;
|
||||||
|
proto.skins = nskins;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Add table
Reference in a new issue