diff --git a/src/helma/framework/ResponseTrans.java b/src/helma/framework/ResponseTrans.java index 8afa3403..203caeaf 100644 --- a/src/helma/framework/ResponseTrans.java +++ b/src/helma/framework/ResponseTrans.java @@ -5,6 +5,7 @@ package helma.framework; import java.io.*; import java.util.*; +import helma.framework.core.Skin; import helma.objectmodel.*; import helma.util.*; @@ -13,7 +14,7 @@ import helma.util.*; * class are directly exposed to JavaScript as global property res. */ -public class ResponseTrans implements Externalizable { +public final class ResponseTrans implements Externalizable { /** * Set the MIME content type of the response. @@ -64,6 +65,8 @@ public class ResponseTrans implements Externalizable { private transient Object skinpath = null; // the processed skinpath as array of Nodes or directory names private transient Object[] translatedSkinpath = null; + // hashmap for skin caching + private transient HashMap skincache; static final long serialVersionUID = -8627370766119740844L; @@ -327,8 +330,9 @@ public class ResponseTrans implements Externalizable { } public void setSkinpath (Object obj) { - this.skinpath = obj; - this.translatedSkinpath = null; + skinpath = obj; + translatedSkinpath = null; + skincache = null; } public Object getSkinpath () { @@ -343,6 +347,18 @@ public class ResponseTrans implements Externalizable { return translatedSkinpath; } + public Skin getCachedSkin (String id) { + if (skincache == null) + return null; + return (Skin) skincache.get (id); + } + + public void cacheSkin (String id, Skin skin) { + if (skincache == null) + skincache = new HashMap (); + skincache.put (id, skin); + } + public synchronized void setCookie (String key, String value) { setCookie (key, value, -1); } diff --git a/src/helma/scripting/fesi/HopExtension.java b/src/helma/scripting/fesi/HopExtension.java index 45460134..fc747dd1 100644 --- a/src/helma/scripting/fesi/HopExtension.java +++ b/src/helma/scripting/fesi/HopExtension.java @@ -23,7 +23,7 @@ import org.xml.sax.InputSource; * (Node objects), the global prototype, the session object etc. */ -public class HopExtension { +public final class HopExtension { protected Application app; protected FesiEvaluator fesi; @@ -436,11 +436,7 @@ public class HopExtension { if (arguments.length != 1 || ESNull.theNull.equals (arguments[0])) throw new EcmaScriptException ("createSkin must be called with one String argument"); String str = arguments[0].toString (); - Skin skin = (Skin) app.skincache.get (str); - if (skin == null) { - skin = new Skin (str, app); - app.skincache.put (str, skin); - } + Skin skin = new Skin (str, app); return new ESWrapper (skin, evaluator); } } @@ -502,8 +498,14 @@ public class HopExtension { // ready... retrieve the skin and render it. Object javaObject = thisObject == null ? null : thisObject.toJavaObject (); - if (skin == null) - skin = app.getSkin (javaObject, arguments[0].toString (), skinpath); + if (skin == null) { + String skinid = app.getPrototypeName(javaObject)+"/"+arguments[0].toString (); + skin = res.getCachedSkin (skinid); + if (skin == null) { + skin = app.getSkin (javaObject, arguments[0].toString (), skinpath); + res.cacheSkin (skinid, skin); + } + } if (asString) res.pushStringBuffer (); if (skin != null)