001 package coldfusion.cfc; 002 003 import java.io.File; 004 import java.io.IOException; 005 import java.io.OutputStream; 006 import java.io.Serializable; 007 import java.util.HashMap; 008 import java.util.Iterator; 009 import java.util.Map; 010 import java.util.Map.Entry; 011 012 import javax.servlet.http.HttpServletRequest; 013 import javax.servlet.http.HttpServletResponse; 014 015 import railo.loader.engine.CFMLEngine; 016 import railo.loader.engine.CFMLEngineFactory; 017 import railo.runtime.Component; 018 import railo.runtime.PageContext; 019 import railo.runtime.exp.PageException; 020 import railo.runtime.type.Collection.Key; 021 import railo.runtime.type.Struct; 022 import railo.runtime.util.Cast; 023 import railo.runtime.util.Creation; 024 025 026 public class CFCProxy { 027 028 private CFMLEngine engine; 029 private Cast caster; 030 private Creation creator; 031 032 private Component cfc=null; 033 private String path; 034 private Map thisData; 035 private boolean invokeDirectly=true; 036 private boolean autoFlush; 037 038 public CFCProxy(String path) throws Throwable { 039 this(path, null, true); 040 } 041 042 public CFCProxy(String path, boolean invokeDirectly) throws Throwable { 043 this(path, null, invokeDirectly); 044 } 045 046 public CFCProxy(String path, Map initialThis) throws Throwable { 047 this(path, initialThis, true); 048 } 049 050 public CFCProxy(String path, Map initialThis, boolean invokeDirectly) throws Throwable { 051 engine = CFMLEngineFactory.getInstance(); 052 caster = engine.getCastUtil(); 053 creator = engine.getCreationUtil(); 054 055 this.path=path; 056 this.invokeDirectly=invokeDirectly; 057 setThisScope(initialThis); 058 } 059 060 private void initCFC(PageContext pc) { 061 if(cfc==null && (invokeDirectly || pc!=null)) { 062 try { 063 if(pc==null)pc=engine.getThreadPageContext(); 064 cfc=engine.getCreationUtil().createComponentFromPath(pc, path); 065 } catch (PageException pe) {} 066 } 067 } 068 069 public void setThisScope(Map data) { 070 if(data!=null) { 071 if(thisData==null)this.thisData=new HashMap(); 072 073 Iterator<Entry> it = data.entrySet().iterator(); 074 Entry entry; 075 while(it.hasNext()){ 076 entry = it.next(); 077 thisData.put(entry.getKey(), entry.getValue()); 078 } 079 } 080 } 081 082 public Map getThisScope() { 083 initCFC(null); 084 if(cfc==null)return null; 085 086 Struct rtn=creator.createStruct(); 087 Iterator<Entry<Key, Object>> it = cfc.entryIterator(); 088 Entry<Key, Object> entry; 089 while(it.hasNext()){ 090 entry = it.next(); 091 rtn.setEL(entry.getKey(), entry.getValue()); 092 } 093 return rtn; 094 } 095 096 public final Object invoke(String methodName, Object args[]) throws Throwable { 097 if(invokeDirectly) return _invoke(methodName, args); 098 return _invoke(methodName, args, null, null, null); 099 } 100 101 public final Object invoke(String methodName, Object args[], HttpServletRequest request, HttpServletResponse response) throws Throwable { 102 if(invokeDirectly) return _invoke(methodName, args); 103 return _invoke(methodName, args, request, response, null); 104 } 105 106 public final Object invoke(String methodName, Object args[], HttpServletRequest request, HttpServletResponse response, OutputStream out) throws Throwable { 107 if(invokeDirectly) return _invoke(methodName, args); 108 return _invoke(methodName, args, request, response, out); 109 } 110 111 public static boolean inInvoke() { 112 return false; 113 } 114 115 private Object _invoke(String methodName, Object[] args) throws PageException { 116 CFMLEngine engine = CFMLEngineFactory.getInstance(); 117 PageContext pc = engine.getThreadPageContext(); 118 initCFC(pc); 119 return cfc.call(pc, methodName, args); 120 } 121 122 private Object _invoke(String methodName, Object[] args, HttpServletRequest req, HttpServletResponse rsp, OutputStream out) throws PageException { 123 CFMLEngine engine = CFMLEngineFactory.getInstance(); 124 Creation creator = engine.getCreationUtil(); 125 PageContext originalPC = engine.getThreadPageContext(); 126 127 // no OutputStream 128 if(out==null)out=DevNullOutputStream.DEV_NULL_OUTPUT_STREAM; 129 130 // no Request 131 if(req==null){ 132 // TODO new File 133 req=creator.createHttpServletRequest(new File("."), "Railo", "/", "", null, null, null, null, null); 134 } 135 // noRespone 136 if(rsp==null){ 137 rsp=creator.createHttpServletResponse(out); 138 } 139 140 141 PageContext pc = creator.createPageContext(req,rsp,out); 142 try{ 143 engine.registerThreadPageContext(pc); 144 initCFC(pc); 145 return cfc.call(pc, methodName, args); 146 } 147 finally{ 148 if(autoFlush) { 149 try { 150 pc.getRootWriter().flush(); 151 } catch (Throwable t) {} 152 } 153 engine.registerThreadPageContext(originalPC); 154 } 155 } 156 157 public void flush() throws IOException { 158 CFMLEngine engine = CFMLEngineFactory.getInstance(); 159 PageContext pc = engine.getThreadPageContext(); 160 pc.getRootWriter().flush(); 161 } 162 163 public void setAutoFlush(boolean autoFlush) { 164 this.autoFlush = autoFlush; 165 } 166 167 public void setApplicationExecution(boolean doApp) 168 { 169 //executeApplication = doApp; 170 } 171 172 } 173 174 final class DevNullOutputStream extends OutputStream implements Serializable { 175 176 public static final DevNullOutputStream DEV_NULL_OUTPUT_STREAM=new DevNullOutputStream(); 177 178 /** 179 * Constructor of the class 180 */ 181 private DevNullOutputStream() {} 182 183 /** 184 * @see java.io.OutputStream#close() 185 */ 186 public void close(){} 187 188 /** 189 * @see java.io.OutputStream#flush() 190 */ 191 public void flush() {} 192 193 /** 194 * @see java.io.OutputStream#write(byte[], int, int) 195 */ 196 public void write(byte[] b, int off, int len) {} 197 198 /** 199 * @see java.io.OutputStream#write(byte[]) 200 */ 201 public void write(byte[] b) {} 202 203 /** 204 * @see java.io.OutputStream#write(int) 205 */ 206 public void write(int b) {} 207 208 }