001    package railo.runtime;
002    
003    
004    import java.io.IOException;
005    import java.io.OutputStream;
006    import java.util.Date;
007    import java.util.Enumeration;
008    import java.util.HashMap;
009    import java.util.HashSet;
010    import java.util.LinkedList;
011    import java.util.List;
012    import java.util.Locale;
013    import java.util.Map;
014    import java.util.Map.Entry;
015    import java.util.Set;
016    import java.util.Stack;
017    import java.util.TimeZone;
018    
019    import javax.servlet.Servlet;
020    import javax.servlet.ServletConfig;
021    import javax.servlet.ServletContext;
022    import javax.servlet.ServletException;
023    import javax.servlet.ServletRequest;
024    import javax.servlet.ServletResponse;
025    import javax.servlet.http.HttpServlet;
026    import javax.servlet.http.HttpServletRequest;
027    import javax.servlet.http.HttpServletResponse;
028    import javax.servlet.http.HttpSession;
029    import javax.servlet.jsp.JspException;
030    import javax.servlet.jsp.JspWriter;
031    import javax.servlet.jsp.tagext.BodyContent;
032    import javax.servlet.jsp.tagext.BodyTag;
033    import javax.servlet.jsp.tagext.Tag;
034    import javax.servlet.jsp.tagext.TryCatchFinally;
035    
036    import org.apache.oro.text.regex.MalformedPatternException;
037    import org.apache.oro.text.regex.Pattern;
038    import org.apache.oro.text.regex.PatternMatcherInput;
039    import org.apache.oro.text.regex.Perl5Compiler;
040    import org.apache.oro.text.regex.Perl5Matcher;
041    
042    import railo.print;
043    import railo.commons.io.BodyContentStack;
044    import railo.commons.io.IOUtil;
045    import railo.commons.io.res.Resource;
046    import railo.commons.io.res.util.ResourceClassLoader;
047    import railo.commons.io.res.util.ResourceUtil;
048    import railo.commons.lang.PhysicalClassLoader;
049    import railo.commons.lang.SizeOf;
050    import railo.commons.lang.StringUtil;
051    import railo.commons.lang.SystemOut;
052    import railo.commons.lang.mimetype.MimeType;
053    import railo.commons.lang.types.RefBoolean;
054    import railo.commons.lang.types.RefBooleanImpl;
055    import railo.commons.lock.KeyLock;
056    import railo.commons.lock.Lock;
057    import railo.commons.net.HTTPUtil;
058    import railo.intergral.fusiondebug.server.FDSignal;
059    import railo.runtime.component.ComponentLoader;
060    import railo.runtime.config.Config;
061    import railo.runtime.config.ConfigImpl;
062    import railo.runtime.config.ConfigWeb;
063    import railo.runtime.config.ConfigWebImpl;
064    import railo.runtime.config.ConfigWebUtil;
065    import railo.runtime.config.Constants;
066    import railo.runtime.config.NullSupportHelper;
067    import railo.runtime.db.DataSource;
068    import railo.runtime.db.DataSourceManager;
069    import railo.runtime.db.DatasourceConnection;
070    import railo.runtime.db.DatasourceConnectionPool;
071    import railo.runtime.db.DatasourceManagerImpl;
072    import railo.runtime.debug.ActiveLock;
073    import railo.runtime.debug.ActiveQuery;
074    import railo.runtime.debug.DebugCFMLWriter;
075    import railo.runtime.debug.DebugEntryTemplate;
076    import railo.runtime.debug.Debugger;
077    import railo.runtime.debug.DebuggerImpl;
078    import railo.runtime.dump.DumpUtil;
079    import railo.runtime.dump.DumpWriter;
080    import railo.runtime.engine.ExecutionLog;
081    import railo.runtime.engine.ThreadLocalPageContext;
082    import railo.runtime.err.ErrorPage;
083    import railo.runtime.err.ErrorPageImpl;
084    import railo.runtime.err.ErrorPagePool;
085    import railo.runtime.exp.Abort;
086    import railo.runtime.exp.ApplicationException;
087    import railo.runtime.exp.CasterException;
088    import railo.runtime.exp.ExceptionHandler;
089    import railo.runtime.exp.ExpressionException;
090    import railo.runtime.exp.MissingIncludeException;
091    import railo.runtime.exp.PageException;
092    import railo.runtime.exp.PageExceptionBox;
093    import railo.runtime.exp.PageServletException;
094    import railo.runtime.functions.dynamicEvaluation.Serialize;
095    import railo.runtime.interpreter.CFMLExpressionInterpreter;
096    import railo.runtime.interpreter.VariableInterpreter;
097    import railo.runtime.listener.AppListenerSupport;
098    import railo.runtime.listener.ApplicationContext;
099    import railo.runtime.listener.ApplicationContextPro;
100    import railo.runtime.listener.ApplicationListener;
101    import railo.runtime.listener.ClassicApplicationContext;
102    import railo.runtime.listener.JavaSettings;
103    import railo.runtime.listener.JavaSettingsImpl;
104    import railo.runtime.listener.ModernAppListener;
105    import railo.runtime.listener.ModernAppListenerException;
106    import railo.runtime.listener.NoneAppListener;
107    import railo.runtime.monitor.RequestMonitor;
108    import railo.runtime.net.ftp.FTPPool;
109    import railo.runtime.net.ftp.FTPPoolImpl;
110    import railo.runtime.net.http.HTTPServletRequestWrap;
111    import railo.runtime.net.http.ReqRspUtil;
112    import railo.runtime.op.Caster;
113    import railo.runtime.op.Decision;
114    import railo.runtime.orm.ORMConfiguration;
115    import railo.runtime.orm.ORMEngine;
116    import railo.runtime.orm.ORMSession;
117    import railo.runtime.query.QueryCache;
118    import railo.runtime.rest.RestRequestListener;
119    import railo.runtime.rest.RestUtil;
120    import railo.runtime.security.Credential;
121    import railo.runtime.security.CredentialImpl;
122    import railo.runtime.tag.Login;
123    import railo.runtime.tag.TagHandlerPool;
124    import railo.runtime.type.Array;
125    import railo.runtime.type.Collection;
126    import railo.runtime.type.Collection.Key;
127    import railo.runtime.type.Iterator;
128    import railo.runtime.type.KeyImpl;
129    import railo.runtime.type.Query;
130    import railo.runtime.type.SVArray;
131    import railo.runtime.type.Sizeable;
132    import railo.runtime.type.Struct;
133    import railo.runtime.type.StructImpl;
134    import railo.runtime.type.UDF;
135    import railo.runtime.type.it.ItAsEnum;
136    import railo.runtime.type.ref.Reference;
137    import railo.runtime.type.ref.VariableReference;
138    import railo.runtime.type.scope.Application;
139    import railo.runtime.type.scope.Argument;
140    import railo.runtime.type.scope.ArgumentImpl;
141    import railo.runtime.type.scope.CGI;
142    import railo.runtime.type.scope.CGIImpl;
143    import railo.runtime.type.scope.Client;
144    import railo.runtime.type.scope.Cluster;
145    import railo.runtime.type.scope.Cookie;
146    import railo.runtime.type.scope.CookieImpl;
147    import railo.runtime.type.scope.Form;
148    import railo.runtime.type.scope.FormImpl;
149    import railo.runtime.type.scope.Local;
150    import railo.runtime.type.scope.LocalNotSupportedScope;
151    import railo.runtime.type.scope.Request;
152    import railo.runtime.type.scope.RequestImpl;
153    import railo.runtime.type.scope.Scope;
154    import railo.runtime.type.scope.ScopeContext;
155    import railo.runtime.type.scope.ScopeFactory;
156    import railo.runtime.type.scope.ScopeSupport;
157    import railo.runtime.type.scope.Server;
158    import railo.runtime.type.scope.Session;
159    import railo.runtime.type.scope.Threads;
160    import railo.runtime.type.scope.URL;
161    import railo.runtime.type.scope.URLForm;
162    import railo.runtime.type.scope.URLImpl;
163    import railo.runtime.type.scope.Undefined;
164    import railo.runtime.type.scope.UndefinedImpl;
165    import railo.runtime.type.scope.UrlFormImpl;
166    import railo.runtime.type.scope.Variables;
167    import railo.runtime.type.scope.VariablesImpl;
168    import railo.runtime.type.util.CollectionUtil;
169    import railo.runtime.type.util.KeyConstants;
170    import railo.runtime.util.VariableUtil;
171    import railo.runtime.util.VariableUtilImpl;
172    import railo.runtime.writer.CFMLWriter;
173    import railo.runtime.writer.DevNullBodyContent;
174    
175    /**
176     * page context for every page object. 
177     * the PageContext is a jsp page context expanded by CFML functionality.
178     * for example you have the method getSession to get jsp combatible session object (HTTPSession)
179     *  and with sessionScope() you get CFML combatible session object (Struct,Scope).
180     */
181    public final class PageContextImpl extends PageContext implements Sizeable {
182            
183            private static final RefBoolean DUMMY_BOOL = new RefBooleanImpl(false);
184            
185            private static int counter=0;
186            
187            /** 
188             * Field <code>pathList</code>
189             */
190        private LinkedList<UDF> udfs=new LinkedList<UDF>();
191        private LinkedList<PageSource> pathList=new LinkedList<PageSource>();
192        private LinkedList<PageSource> includePathList=new LinkedList<PageSource>();
193        private Set<PageSource> includeOnce=new HashSet<PageSource>();
194            
195            /**
196             * Field <code>executionTime</code>
197             */
198            protected int executionTime=0;
199            
200            private HTTPServletRequestWrap req;
201            private HttpServletResponse rsp;
202            private HttpServlet servlet;
203            
204            private JspWriter writer;
205        private JspWriter forceWriter;
206        private BodyContentStack bodyContentStack;
207        private DevNullBodyContent devNull;
208        
209            private ConfigWebImpl config;
210            //private DataSourceManager manager;
211            //private CFMLCompilerImpl compiler;
212            
213            // Scopes
214            private ScopeContext scopeContext;
215        private Variables variablesRoot=new VariablesImpl();//ScopeSupport(false,"variables",Scope.SCOPE_VARIABLES);
216        private Variables variables=variablesRoot;//new ScopeSupport("variables",Scope.SCOPE_VARIABLES);
217        private Undefined undefined;
218            
219        private URLImpl _url=new URLImpl();
220            private FormImpl _form=new FormImpl();
221            
222            private URLForm urlForm=new UrlFormImpl(_form,_url);
223            private URL url;
224            private Form form;
225            
226            
227            private RequestImpl request=new RequestImpl();
228            private CGIImpl cgi=new CGIImpl();      
229            private Argument argument=new ArgumentImpl();
230        private static LocalNotSupportedScope localUnsupportedScope=LocalNotSupportedScope.getInstance();
231            private Local local=localUnsupportedScope;
232            private Session session;
233            private Server server;
234            private Cluster cluster;
235            private CookieImpl cookie=new CookieImpl();
236            private Client client;
237            private Application application;
238    
239        private DebuggerImpl debugger=new DebuggerImpl();
240            private long requestTimeout=-1;
241            private short enablecfoutputonly=0;
242            private int outputState;
243            private String cfid;
244            private String cftoken;
245    
246            private int id;
247            private int requestId;
248            
249            
250            private boolean psq;
251            private Locale locale;
252            private TimeZone timeZone;
253            
254        // Pools
255        private ErrorPagePool errorPagePool=new ErrorPagePool();
256            private TagHandlerPool tagHandlerPool;
257            private FTPPool ftpPool=new FTPPoolImpl();
258            private final QueryCache queryCache;
259    
260            private Component activeComponent;
261            private UDF activeUDF;
262        //private ComponentScope componentScope=new ComponentScope(this);
263            
264            private Credential remoteUser;
265        
266        protected VariableUtilImpl variableUtil=new VariableUtilImpl();
267    
268        private PageException exception;
269        private PageSource base;
270    
271        ApplicationContext applicationContext;
272        ApplicationContext defaultApplicationContext;
273    
274        private ScopeFactory scopeFactory=new ScopeFactory();
275    
276        private Tag parentTag=null;
277        private Tag currentTag=null;
278        private Thread thread;
279        private long startTime;
280            private boolean isCFCRequest;
281            
282            private DatasourceManagerImpl manager;
283            private Struct threads;
284            private boolean hasFamily=false;
285            //private CFMLFactoryImpl factory;
286            private PageContextImpl parent;
287            private Map<String,DatasourceConnection> conns=new HashMap<String,DatasourceConnection>();
288            private boolean fdEnabled;
289            private ExecutionLog execLog;
290            private boolean useSpecialMappings;
291            
292    
293            private ORMSession ormSession;
294            private boolean isChild;
295            private boolean gatewayContext;
296            private String serverPassword;
297    
298            private PageException pe;
299    
300            public long sizeOf() {
301                    
302                    return 
303                    SizeOf.size(pathList)+
304                    SizeOf.size(includePathList)+
305                    SizeOf.size(executionTime)+
306                    SizeOf.size(writer)+
307                    SizeOf.size(forceWriter)+
308                    SizeOf.size(bodyContentStack)+
309                    SizeOf.size(variables)+
310                    SizeOf.size(url)+
311                    SizeOf.size(form)+
312                    SizeOf.size(_url)+
313                    SizeOf.size(_form)+
314                    SizeOf.size(request)+
315    
316                    SizeOf.size(argument)+
317                    SizeOf.size(local)+
318                    SizeOf.size(cookie)+
319                    SizeOf.size(debugger)+
320                    SizeOf.size(requestTimeout)+
321                    SizeOf.size(enablecfoutputonly)+
322                    SizeOf.size(outputState)+
323                    SizeOf.size(cfid)+
324                    SizeOf.size(cftoken)+
325                    SizeOf.size(id)+
326                    SizeOf.size(psq)+
327                    SizeOf.size(locale)+
328                    SizeOf.size(errorPagePool)+
329                    SizeOf.size(tagHandlerPool)+
330                    SizeOf.size(ftpPool)+
331                    SizeOf.size(activeComponent)+
332                    SizeOf.size(activeUDF)+
333                    SizeOf.size(remoteUser)+
334                    SizeOf.size(exception)+
335                    SizeOf.size(base)+
336                    SizeOf.size(applicationContext)+
337                    SizeOf.size(defaultApplicationContext)+
338                    SizeOf.size(parentTag)+
339                    SizeOf.size(currentTag)+
340                    SizeOf.size(startTime)+
341                    SizeOf.size(isCFCRequest)+
342                    SizeOf.size(conns)+
343                    SizeOf.size(serverPassword)+
344                    SizeOf.size(ormSession);
345            }
346            
347            
348    
349            /** 
350             * default Constructor
351             * @param factoryImpl 
352             * @param scopeContext
353             * @param config Configuration of the CFML Container
354             * @param compiler CFML Compiler
355             * @param queryCache Query Cache Object
356             * @param id identity of the pageContext
357             */
358            public PageContextImpl(ScopeContext scopeContext, ConfigWebImpl config, QueryCache queryCache,int id,HttpServlet servlet) {
359                    // must be first because is used after
360                    tagHandlerPool=config.getTagHandlerPool();
361            this.servlet=servlet;
362                    this.id=id;
363                    //this.factory=factory;
364                    
365            bodyContentStack=new BodyContentStack();
366            devNull=bodyContentStack.getDevNullBodyContent();
367            
368            this.config=config;
369            manager=new DatasourceManagerImpl(config);
370            
371                this.scopeContext=scopeContext;
372            undefined=
373                    new UndefinedImpl(this,config.getScopeCascadingType());
374            
375            
376                    //this.compiler=compiler;
377            //tagHandlerPool=config.getTagHandlerPool();
378                    this.queryCache=queryCache;
379                    server=ScopeContext.getServerScope(this);
380                    
381                    defaultApplicationContext=new ClassicApplicationContext(config,"",true,null);
382                    
383            }
384    
385            @Override
386            public void initialize(
387                            Servlet servlet, 
388                            ServletRequest req, 
389                            ServletResponse rsp, 
390                            String errorPageURL, 
391                            boolean needsSession, 
392                            int bufferSize, 
393                            boolean autoFlush) throws IOException, IllegalStateException, IllegalArgumentException {
394               initialize(
395                               (HttpServlet)servlet,
396                               (HttpServletRequest)req,
397                               (HttpServletResponse)rsp,
398                               errorPageURL,
399                               needsSession,
400                               bufferSize,
401                               autoFlush,false);
402            }
403            
404            /**
405             * initialize a existing page context
406             * @param servlet
407             * @param req
408             * @param rsp
409             * @param errorPageURL
410             * @param needsSession
411             * @param bufferSize
412             * @param autoFlush
413             */
414            public PageContextImpl initialize(
415                             HttpServlet servlet, 
416                             HttpServletRequest req, 
417                             HttpServletResponse rsp, 
418                             String errorPageURL, 
419                             boolean needsSession, 
420                             int bufferSize, 
421                             boolean autoFlush,
422                             boolean isChild) {
423                    requestId=counter++;
424                    rsp.setContentType("text/html; charset=UTF-8");
425                    this.isChild=isChild;
426                    
427            //rsp.setHeader("Connection", "close");
428            applicationContext=defaultApplicationContext;
429            
430            startTime=System.currentTimeMillis();
431            thread=Thread.currentThread();
432            
433            isCFCRequest = StringUtil.endsWithIgnoreCase(req.getServletPath(),"."+config.getCFCExtension());
434            
435            this.req=new HTTPServletRequestWrap(req);
436            this.rsp=rsp;
437            this.servlet=servlet;
438    
439             // Writers
440            if(config.debugLogOutput()) {
441                    CFMLWriter w = config.getCFMLWriter(req,rsp);
442                    w.setAllowCompression(false);
443                    DebugCFMLWriter dcw = new DebugCFMLWriter(w);
444                    bodyContentStack.init(dcw);
445                    debugger.setOutputLog(dcw);
446            }
447            else {
448                    bodyContentStack.init(config.getCFMLWriter(req,rsp));
449            }
450            
451                    
452            writer=bodyContentStack.getWriter();
453            forceWriter=writer;
454             
455                     // Scopes
456             server=ScopeContext.getServerScope(this);
457             if(hasFamily) {
458                     variablesRoot=new VariablesImpl();
459                     variables=variablesRoot;
460                     request=new RequestImpl();
461                     _url=new URLImpl();
462                     _form=new FormImpl();
463                     urlForm=new UrlFormImpl(_form,_url);
464                     undefined=
465                    new UndefinedImpl(this,config.getScopeCascadingType());
466                     
467                     hasFamily=false;
468             }
469             else if(variables==null) {
470                     variablesRoot=new VariablesImpl();
471                     variables=variablesRoot;
472             }
473             request.initialize(this);
474             
475                     if(config.mergeFormAndURL()) {
476                             url=urlForm;
477                             form=urlForm;
478                     }
479                     else {
480                             url=_url;
481                             form=_form;
482                     }
483             //url.initialize(this);
484                     //form.initialize(this);
485                     //undefined.initialize(this);
486                     
487             
488            psq=config.getPSQL();
489                    
490                    fdEnabled=!config.allowRequestTimeout();
491                    
492                    if(config.getExecutionLogEnabled())
493                            this.execLog=config.getExecutionLogFactory().getInstance(this);
494                    if(config.debug())
495                            debugger.init(config);
496                            
497            return this;
498             }
499            
500            @Override
501            public void release() {
502            if(config.getExecutionLogEnabled()){
503                    execLog.release();
504                            execLog=null;
505            }
506                    
507                    if(config.debug()) {
508                    if(!gatewayContext)config.getDebuggerPool().store(this, debugger);
509                    debugger.reset();
510            }
511            
512                    this.serverPassword=null;
513    
514                    boolean isChild=parent!=null;
515                    parent=null;
516                    // Attention have to be before close
517                    if(client!=null){
518                    client.touchAfterRequest(this);
519                    client=null;
520            }
521                    if(session!=null){
522                    session.touchAfterRequest(this);
523                    session=null;
524            }
525                    
526                    // ORM
527            if(ormSession!=null){
528                    // flush orm session
529                    try {
530                                    ORMEngine engine=ormSession.getEngine();
531                            ORMConfiguration config=engine.getConfiguration(this);
532                            if(config==null || (config.flushAtRequestEnd() && config.autoManageSession())){
533                                            ormSession.flush(this);
534                                            //ormSession.close(this);
535                                            //print.err("2orm flush:"+Thread.currentThread().getId());
536                                    }
537                                    ormSession.close(this);
538                            } 
539                    catch (Throwable t) {
540                            //print.printST(t);
541                    }
542                    
543                            
544                    // release connection
545                            DatasourceConnectionPool pool = this.config.getDatasourceConnectionPool();
546                            DatasourceConnection dc=ormSession.getDatasourceConnection();
547                            if(dc!=null)pool.releaseDatasourceConnection(dc);
548                   
549                    ormSession=null;
550            }
551            
552                    
553                    close();
554            thread=null;
555            base=null;
556            //RequestImpl r = request;
557            
558            // Scopes
559            if(hasFamily) {
560                    if(!isChild){
561                            req.disconnect();
562                    }
563                    
564                    request=null;
565                    _url=null;
566                    _form=null;
567                urlForm=null;
568                undefined=null;
569                variables=null;
570                variablesRoot=null;
571                if(threads!=null && threads.size()>0) threads.clear();
572                
573            }
574            else {
575                if(variables.isBind()) {
576                    variables=null;
577                    variablesRoot=null;
578                }
579                else {
580                    variables=variablesRoot;
581                    variables.release(this);
582                }
583                undefined.release(this);
584                urlForm.release(this);
585                    request.release();
586            }
587            cgi.release();
588            argument.release(this);
589            local=localUnsupportedScope;
590            
591            cookie.release();
592                    //if(cluster!=null)cluster.release();
593            
594            //client=null;
595            //session=null;
596            
597                    
598            
599            
600                    application=null;// not needed at the moment -> application.releaseAfterRequest();
601                    applicationContext=null;
602                    
603                    // Properties
604            requestTimeout=-1;
605            outputState=0;
606            cfid=null;
607            cftoken=null;
608            locale=null;
609            timeZone=null;
610            url=null;
611            form=null;
612            
613            
614            // Pools
615            errorPagePool.clear();
616    
617            // transaction connection
618            if(!conns.isEmpty()){
619                    java.util.Iterator<Entry<String, DatasourceConnection>> it = conns.entrySet().iterator();
620                    DatasourceConnectionPool pool = config.getDatasourceConnectionPool();
621                    while(it.hasNext())     {
622                            pool.releaseDatasourceConnection((it.next().getValue()));
623                    }
624                    conns.clear();
625            }
626            
627            
628            
629            pathList.clear();
630            includePathList.clear();
631                    executionTime=0;
632                    
633                    bodyContentStack.release();
634                    
635    
636            
637                    //activeComponent=null;
638                    remoteUser=null;
639                    exception=null;
640                    ftpPool.clear();
641            parentTag=null;
642            currentTag=null;
643            
644            // Req/Rsp
645            //if(req!=null)
646                    req.clear();
647            req=null;
648            rsp=null;
649            servlet=null;
650    
651            // Writer
652            writer=null;
653            forceWriter=null;
654            if(pagesUsed.size()>0)pagesUsed.clear();
655            
656            activeComponent=null;
657            activeUDF=null;
658            
659    
660            gatewayContext=false;
661            
662            manager.release();
663            includeOnce.clear();
664            pe=null;
665    
666            }
667    
668        @Override
669        public void write(String str) throws IOException {
670            writer.write(str);
671            }
672    
673        @Override
674        public void forceWrite(String str) throws IOException {
675            forceWriter.write(str);
676        }
677            
678        @Override
679        public void writePSQ(Object o) throws IOException, PageException {
680            if(o instanceof Date || Decision.isDate(o, false)) {
681                            writer.write(Caster.toString(o));
682                    }
683                    else {
684                writer.write(psq?Caster.toString(o):StringUtil.replace(Caster.toString(o),"'","''",false));
685                    }
686            } 
687            
688        @Override
689        public void flush() {
690                    try {
691                            getOut().flush();
692                    } catch (IOException e) {}
693            }
694            
695        @Override
696        public void close() {
697                    IOUtil.closeEL(getOut());
698            }
699            
700        public PageSource getRelativePageSource(String realPath) {
701            SystemOut.print(config.getOutWriter(),"method getRelativePageSource is deprecated");
702            if(StringUtil.startsWith(realPath,'/')) return PageSourceImpl.best(getPageSources(realPath));
703            if(pathList.size()==0) return null;
704                    return pathList.getLast().getRealPage(realPath);
705            }
706        
707        public PageSource getRelativePageSourceExisting(String realPath) {
708            if(StringUtil.startsWith(realPath,'/')) return getPageSourceExisting(realPath);
709            if(pathList.size()==0) return null;
710                    PageSource ps = pathList.getLast().getRealPage(realPath);
711                    if(PageSourceImpl.pageExist(ps)) return ps;
712                    return null;
713            }
714        
715        public PageSource[] getRelativePageSources(String realPath) {
716            if(StringUtil.startsWith(realPath,'/')) return getPageSources(realPath);
717            if(pathList.size()==0) return null;
718                    return new PageSource[]{ pathList.getLast().getRealPage(realPath)};
719            }
720        
721        public PageSource getPageSource(String realPath) {
722            SystemOut.print(config.getOutWriter(),"method getPageSource is deprecated");
723            return PageSourceImpl.best(config.getPageSources(this,applicationContext.getMappings(),realPath,false,useSpecialMappings,true));
724            }
725        
726        public PageSource[] getPageSources(String realPath) {
727            return config.getPageSources(this,applicationContext.getMappings(),realPath,false,useSpecialMappings,true);
728            }
729        
730        public PageSource getPageSourceExisting(String realPath) {
731            return config.getPageSourceExisting(this,applicationContext.getMappings(),realPath,false,useSpecialMappings,true,false);
732            }
733    
734        public boolean useSpecialMappings(boolean useTagMappings) {
735                    boolean b=this.useSpecialMappings;
736                    this.useSpecialMappings=useTagMappings;
737                    return b;
738            }
739        public boolean useSpecialMappings() {
740                    return useSpecialMappings;
741            }
742        
743    
744        public Resource getPhysical(String realPath, boolean alsoDefaultMapping){
745            return config.getPhysical(applicationContext.getMappings(),realPath, alsoDefaultMapping);
746        }
747        
748    
749            public PageSource toPageSource(Resource res, PageSource defaultValue){
750                    return config.toPageSource(applicationContext.getMappings(),res, defaultValue);
751            }
752    
753            @Override
754            public void doInclude(String realPath) throws PageException {
755                    doInclude(getRelativePageSources(realPath),false);
756            }
757            
758            @Override
759            public void doInclude(String realPath, boolean runOnce) throws PageException {
760                    doInclude(getRelativePageSources(realPath),runOnce);
761            }
762    
763            @Override
764            public void doInclude(PageSource source) throws PageException {
765                    doInclude(new PageSource[]{source},false);
766            }
767    
768            @Override
769            public void doInclude(PageSource[] sources, boolean runOnce) throws PageException {
770            // debug
771                    if(!gatewayContext && config.debug()) {
772                            int currTime=executionTime;
773                long exeTime=0;
774                long time=System.nanoTime();
775                
776                Page currentPage = PageSourceImpl.loadPage(this, sources);
777                            if(runOnce && includeOnce.contains(currentPage.getPageSource())) return;
778                DebugEntryTemplate debugEntry=debugger.getEntry(this,currentPage.getPageSource());
779                try {
780                    addPageSource(currentPage.getPageSource(),true);
781                    debugEntry.updateFileLoadTime((int)(System.nanoTime()-time));
782                    exeTime=System.nanoTime();
783    
784                    currentPage.call(this);
785                            }
786                            catch(Throwable t){
787                                    PageException pe = Caster.toPageException(t);
788                                    if(Abort.isAbort(pe)) {
789                        if(Abort.isAbort(pe,Abort.SCOPE_REQUEST))throw pe;
790                    }
791                    else {
792                            if(fdEnabled){
793                                    FDSignal.signal(pe, false);
794                            }
795                            pe.addContext(currentPage.getPageSource(),-187,-187, null);// TODO was soll das 187
796                            throw pe;
797                    }
798                            }
799                            finally {
800                                    includeOnce.add(currentPage.getPageSource());
801                                    int diff= ((int)(System.nanoTime()-exeTime)-(executionTime-currTime));
802                                executionTime+=(int)(System.nanoTime()-time);
803                                    debugEntry.updateExeTime(diff);
804                                    removeLastPageSource(true);
805                            }       
806                    }
807            // no debug
808                    else {
809                            Page currentPage = PageSourceImpl.loadPage(this, sources);
810                            if(runOnce && includeOnce.contains(currentPage.getPageSource())) return;
811                    try {
812                                    addPageSource(currentPage.getPageSource(),true);
813                    currentPage.call(this);
814                            }
815                            catch(Throwable t){
816                                    PageException pe = Caster.toPageException(t);
817                                    if(Abort.isAbort(pe)) {
818                                            if(Abort.isAbort(pe,Abort.SCOPE_REQUEST))throw pe;
819                    }
820                    else    {
821                            pe.addContext(currentPage.getPageSource(),-187,-187, null);
822                            throw pe;
823                    }
824                            }
825                            finally {
826                                    includeOnce.add(currentPage.getPageSource());
827                                    removeLastPageSource(true);
828                            }       
829                    }
830            }
831    
832            @Override
833        public Array getTemplatePath() throws PageException {
834            int len=includePathList.size();
835            SVArray sva = new SVArray();
836            PageSource ps;
837            for(int i=0;i<len;i++) {
838                    ps=includePathList.get(i);
839                    if(i==0) {
840                            if(!ps.equals(getBasePageSource()))
841                                    sva.append(ResourceUtil.getResource(this,getBasePageSource()).getAbsolutePath());
842                    }
843                    sva.append(ResourceUtil.getResource(this, ps).getAbsolutePath());
844            }
845            //sva.setPosition(sva.size());
846            return sva;
847        }
848      
849        public List<PageSource> getPageSourceList() {
850            return (List<PageSource>) pathList.clone();
851        }
852        
853        
854        
855        protected PageSource getPageSource(int index) {
856            return includePathList.get(index-1);
857        }
858        public synchronized void copyStateTo(PageContextImpl other) {
859            
860            
861            
862            
863            // private Debugger debugger=new DebuggerImpl();
864            other.requestTimeout=requestTimeout;
865            other.locale=locale;
866            other.timeZone=timeZone;
867            other.fdEnabled=fdEnabled;
868            other.useSpecialMappings=useSpecialMappings;
869            other.serverPassword=serverPassword;
870            
871            
872            hasFamily=true;
873            other.hasFamily=true;
874            other.parent=this;
875                    other.applicationContext=applicationContext;
876                    other.thread=Thread.currentThread();
877                    other.startTime=System.currentTimeMillis();
878                    other.isCFCRequest = isCFCRequest;
879            
880            
881            
882            // path
883            other.base=base;
884            java.util.Iterator<PageSource> it = includePathList.iterator();
885            while(it.hasNext()) {
886                    other.includePathList.add(it.next());
887            }
888            it = pathList.iterator();
889            while(it.hasNext()) {
890                    other.pathList.add(it.next());
891            }
892            
893            
894            // scopes
895            //other.req.setAttributes(request);
896            /*HttpServletRequest org = other.req.getOriginalRequest();
897            if(org instanceof HttpServletRequestDummy) {
898                    ((HttpServletRequestDummy)org).setAttributes(request);
899            }*/
900            other.req=req;
901            other.request=request;
902            other.form=form;
903            other.url=url;
904            other.urlForm=urlForm;
905            other._url=_url;
906            other._form=_form;
907            other.variables=variables;
908            other.undefined=new UndefinedImpl(other,(short)other.undefined.getType());
909            
910            // writers
911            other.bodyContentStack.init(config.getCFMLWriter(other.req,other.rsp));
912            //other.bodyContentStack.init(other.req,other.rsp,other.config.isSuppressWhitespace(),other.config.closeConnection(), other.config.isShowVersion(),config.contentLength(),config.allowCompression());
913            other.writer=other.bodyContentStack.getWriter();
914            other.forceWriter=other.writer;
915            
916            other.psq=psq;
917            other.gatewayContext=gatewayContext;
918            
919            // thread
920            if(threads!=null){
921                    synchronized (threads) {
922                                    
923                            java.util.Iterator<Entry<Key, Object>> it2 = threads.entryIterator();
924                            Entry<Key, Object> entry;
925                            while(it2.hasNext()) {
926                                    entry = it2.next();
927                                    other.setThreadScope(entry.getKey(), (Threads)entry.getValue());
928                            }
929                            }
930            }
931            
932            
933        }
934        
935        /*public static void setState(PageContextImpl other,ApplicationContext applicationContext, boolean isCFCRequest) {
936    
937            other.hasFamily=true;
938            
939                    other.applicationContext=applicationContext;
940                    other.thread=Thread.currentThread();
941                    other.startTime=System.currentTimeMillis();
942            other.isCFCRequest = isCFCRequest;
943            
944            // path
945            other.base=base;
946            java.util.Iterator it = includePathList.iterator();
947            while(it.hasNext()) {
948                    other.includePathList.add(it.next());
949            }
950            
951            // scopes
952            other.request=request;
953            other.form=form;
954            other.url=url;
955            other.urlForm=urlForm;
956            other._url=_url;
957            other._form=_form;
958            other.variables=variables;
959            other.undefined=new UndefinedImpl(other,(short)other.undefined.getType());
960            
961            // writers
962            other.bodyContentStack.init(other.rsp,other.config.isSuppressWhitespace(),other.config.closeConnection(),other.config.isShowVersion());
963            other.writer=other.bodyContentStack.getWriter();
964            other.forceWriter=other.writer;
965            
966            other.psq=psq;
967            }*/
968        
969        public int getCurrentLevel() {
970            return includePathList.size()+1;
971        }
972        
973        /**
974         * @return the current template SourceFile
975         */
976        public PageSource getCurrentPageSource() {
977            return pathList.getLast();
978        }
979        
980        /**
981         * @return the current template SourceFile
982         */
983        public PageSource getCurrentTemplatePageSource() {
984            return includePathList.getLast();
985        }
986            
987        /**
988         * @return base template file
989         */
990        public PageSource getBasePageSource() {
991                    return base;
992            }
993            
994        @Override
995        public Resource getRootTemplateDirectory() {
996                    return config.getResource(ReqRspUtil.getRootPath(servlet.getServletContext()));
997            }
998    
999        @Override
1000        public Scope scope(int type) throws PageException {
1001            switch(type) {
1002                case Scope.SCOPE_UNDEFINED:     return undefinedScope();
1003                case Scope.SCOPE_URL:           return urlScope();
1004                case Scope.SCOPE_FORM:          return formScope();
1005                case Scope.SCOPE_VARIABLES:     return variablesScope();
1006                case Scope.SCOPE_REQUEST:       return requestScope();
1007                case Scope.SCOPE_CGI:           return cgiScope();
1008                case Scope.SCOPE_APPLICATION:   return applicationScope();
1009                case Scope.SCOPE_ARGUMENTS:     return argumentsScope();
1010                case Scope.SCOPE_SESSION:       return sessionScope();
1011                case Scope.SCOPE_SERVER:        return serverScope();
1012                case Scope.SCOPE_COOKIE:        return cookieScope();
1013                case Scope.SCOPE_CLIENT:        return clientScope();
1014                case Scope.SCOPE_LOCAL:         
1015                case ScopeSupport.SCOPE_VAR:                return localScope();
1016                case Scope.SCOPE_CLUSTER:return clusterScope();
1017            }
1018            return variables;
1019        }
1020        
1021        public Scope scope(String strScope,Scope defaultValue) throws PageException {
1022            if(strScope==null)return defaultValue;
1023            strScope=strScope.toLowerCase().trim(); 
1024            if("variables".equals(strScope))        return variablesScope(); 
1025            if("url".equals(strScope))                      return urlScope();
1026            if("form".equals(strScope))                     return formScope();
1027            if("request".equals(strScope))          return requestScope();
1028            if("cgi".equals(strScope))                      return cgiScope();
1029            if("application".equals(strScope))      return applicationScope();
1030            if("arguments".equals(strScope))        return argumentsScope();
1031            if("session".equals(strScope))          return sessionScope();
1032            if("server".equals(strScope))           return serverScope();
1033            if("cookie".equals(strScope))           return cookieScope();
1034            if("client".equals(strScope))           return clientScope();
1035            if("local".equals(strScope))            return localScope();
1036            if("cluster".equals(strScope))          return clusterScope();
1037            
1038                return defaultValue;
1039        }
1040        
1041        @Override
1042        public Undefined undefinedScope() {
1043            if(!undefined.isInitalized()) undefined.initialize(this);
1044            return undefined;
1045        }
1046        
1047        /**
1048         * @return undefined scope, undefined scope is a placeholder for the scopecascading
1049         */
1050        public Undefined us() {
1051            if(!undefined.isInitalized()) undefined.initialize(this);
1052            return undefined;
1053        }
1054        
1055        @Override
1056        public Variables variablesScope() { return variables; }
1057            
1058        @Override
1059        public URL urlScope() { 
1060            if(!url.isInitalized())url.initialize(this);
1061                    return url;
1062        }
1063            
1064        @Override
1065        public Form formScope() {
1066            if(!form.isInitalized())form.initialize(this);
1067                    return form;
1068        }
1069            
1070        @Override
1071        public URLForm urlFormScope() {
1072            if(!urlForm.isInitalized())urlForm.initialize(this);
1073                    return urlForm;
1074        }
1075    
1076        @Override
1077        public Request requestScope() { return request; }
1078            
1079        @Override
1080        public CGI cgiScope() {
1081                    if(!cgi.isInitalized())cgi.initialize(this);
1082                    return cgi;
1083            }
1084            
1085        @Override
1086        public Application applicationScope() throws PageException {
1087                    if(application==null) {
1088                            if(!applicationContext.hasName())
1089                                    throw new ExpressionException("there is no application context defined for this application","you can define a application context with the tag "+railo.runtime.config.Constants.CFAPP_NAME+"/"+railo.runtime.config.Constants.APP_CFC);
1090                            application=scopeContext.getApplicationScope(this,DUMMY_BOOL);
1091                    }
1092                    return application; 
1093            }
1094    
1095        @Override
1096        public Argument argumentsScope() { return argument; }
1097    
1098        
1099        @Override
1100        public Argument argumentsScope(boolean bind) { 
1101                //Argument a=argumentsScope(); 
1102                if(bind)argument.setBind(true); 
1103                return argument; 
1104        } 
1105        
1106        @Override
1107        public Local localScope() { 
1108            //if(local==localUnsupportedScope) 
1109            //      throw new PageRuntimeException(new ExpressionException("Unsupported Context for Local Scope"));
1110            return local;
1111        }
1112        
1113        @Override
1114        public Local localScope(boolean bind) { 
1115            if(bind)local.setBind(true); 
1116            //if(local==localUnsupportedScope) 
1117            //      throw new PageRuntimeException(new ExpressionException("Unsupported Context for Local Scope"));
1118            return local; 
1119        }
1120    
1121        
1122        public Object localGet() throws PageException { 
1123            return localGet(false);
1124        }
1125        
1126        public Object localGet(boolean bind) throws PageException { 
1127            // inside a local supported block
1128            if(undefined.getCheckArguments()){
1129                    return localScope(bind);
1130            }
1131            return undefinedScope().get(KeyConstants._local);
1132        }
1133    
1134        public Object localTouch() throws PageException { 
1135            return localTouch(false);
1136        }
1137        
1138        public Object localTouch(boolean bind) throws PageException { 
1139            // inside a local supported block
1140            if(undefined.getCheckArguments()){
1141                    return localScope(bind);
1142            }
1143            return touch(undefinedScope(), KeyConstants._local);
1144            //return undefinedScope().get(LOCAL);
1145        }
1146        
1147        public Object thisGet() throws PageException { 
1148            return thisTouch();
1149        }
1150    
1151        public Object thisTouch() throws PageException {
1152            // inside a component
1153            if(undefined.variablesScope() instanceof ComponentScope){
1154                    return ((ComponentScope)undefined.variablesScope()).getComponent();
1155            }
1156            return undefinedScope().get(KeyConstants._THIS);
1157        }
1158        
1159            
1160        /**
1161         * @param local sets the current local scope
1162         * @param argument sets the current argument scope
1163         */
1164        public void setFunctionScopes(Local local,Argument argument) {
1165            this.argument=argument;
1166                    this.local=local;
1167                    undefined.setFunctionScopes(local,argument);
1168            }
1169            
1170        @Override
1171        public Session sessionScope() throws PageException {
1172                    return sessionScope(true);
1173            }
1174        public Session sessionScope(boolean checkExpires) throws PageException {
1175                    if(session==null)       {
1176                            checkSessionContext();
1177                            session=scopeContext.getSessionScope(this,DUMMY_BOOL);
1178                    }
1179                    return session;
1180            }
1181    
1182    
1183            public void invalidateUserScopes(boolean migrateSessionData,boolean migrateClientData) throws PageException {
1184                    checkSessionContext();
1185                    scopeContext.invalidateUserScope(this, migrateSessionData, migrateClientData);
1186            }
1187        
1188        private void checkSessionContext() throws ExpressionException {
1189            if(!applicationContext.hasName())
1190                            throw new ExpressionException("there is no session context defined for this application","you can define a session context with the tag "+Constants.CFAPP_NAME+"/"+Constants.APP_CFC);
1191                    if(!applicationContext.isSetSessionManagement())
1192                            throw new ExpressionException("session scope is not enabled","you can enable session scope with tag "+Constants.CFAPP_NAME+"/"+Constants.APP_CFC);
1193            }
1194    
1195        @Override
1196        public Server serverScope() { 
1197                    //if(!server.isInitalized()) server.initialize(this);
1198                    return server;
1199            }
1200            
1201        public void reset() {
1202            server=ScopeContext.getServerScope(this);
1203            }
1204        
1205            @Override
1206        public Cluster clusterScope() throws PageException {
1207            return clusterScope(true);
1208            }
1209        
1210        public Cluster clusterScope(boolean create) throws PageException { 
1211            if(cluster==null && create) {
1212                    cluster=ScopeContext.getClusterScope(config,create);
1213                    //cluster.initialize(this);
1214            }
1215            //else if(!cluster.isInitalized()) cluster.initialize(this);
1216                    return cluster;
1217            }
1218    
1219        @Override
1220        public Cookie cookieScope() { 
1221            if(!cookie.isInitalized()) cookie.initialize(this);
1222            return cookie;
1223        }
1224            
1225        @Override
1226        public Client clientScope() throws PageException { 
1227                    if(client==null) {
1228                            if(!applicationContext.hasName())
1229                                    throw new ExpressionException("there is no client context defined for this application",
1230                                                    "you can define a client context with the tag "+Constants.CFAPP_NAME+"/"+Constants.APP_CFC);
1231                            if(!applicationContext.isSetClientManagement())
1232                                    throw new ExpressionException("client scope is not enabled",
1233                                                    "you can enable client scope with tag "+Constants.CFAPP_NAME+"/"+Constants.APP_CFC);
1234                            
1235                            client= scopeContext.getClientScope(this);
1236                    }
1237                    return client;
1238            }
1239        
1240        public Client clientScopeEL() { 
1241                    if(client==null) {
1242                            if(applicationContext==null || !applicationContext.hasName())                           return null;
1243                            if(!applicationContext.isSetClientManagement()) return null;
1244                            client= scopeContext.getClientScopeEL(this);
1245                    }
1246                    return client;
1247            }
1248            
1249        @Override
1250        public Object set(Object coll, String key, Object value) throws PageException {
1251                return variableUtil.set(this,coll,key,value);
1252            }
1253    
1254            public Object set(Object coll, Collection.Key key, Object value) throws PageException {
1255                    return variableUtil.set(this,coll,key,value);
1256            }
1257            
1258        @Override
1259        public Object touch(Object coll, String key) throws PageException {
1260                Object o=getCollection(coll,key,null);
1261                if(o!=null) return o;
1262                return set(coll,key,new StructImpl());
1263            } 
1264    
1265            @Override
1266            public Object touch(Object coll, Collection.Key key) throws PageException {
1267                    Object o=getCollection(coll,key,null);
1268                if(o!=null) return o;
1269                return set(coll,key,new StructImpl());
1270            }
1271        
1272        /*private Object _touch(Scope scope, String key) throws PageException {
1273                Object o=scope.get(key,null);
1274                if(o!=null) return o;
1275                return scope.set(key, new StructImpl());
1276            }*/     
1277        
1278    
1279        
1280        
1281    
1282        @Override
1283        public Object getCollection(Object coll, String key) throws PageException {
1284            return variableUtil.getCollection(this,coll,key);
1285            }
1286    
1287            @Override
1288            public Object getCollection(Object coll, Collection.Key key) throws PageException {
1289                    return variableUtil.getCollection(this,coll,key);
1290            }
1291            
1292        @Override
1293        public Object getCollection(Object coll, String key, Object defaultValue) {
1294                    return variableUtil.getCollection(this,coll,key,defaultValue);
1295            }
1296    
1297            @Override
1298            public Object getCollection(Object coll, Collection.Key key, Object defaultValue) {
1299                    return variableUtil.getCollection(this,coll,key,defaultValue);
1300            }
1301            
1302        @Override
1303        public Object get(Object coll, String key) throws PageException {
1304                    return variableUtil.get(this,coll,key);
1305            }
1306    
1307            @Override
1308            public Object get(Object coll, Collection.Key key) throws PageException {
1309                    return variableUtil.get(this,coll,key);
1310            }
1311            
1312        @Override
1313        public Reference getReference(Object coll, String key) throws PageException {
1314                    return new VariableReference(coll,key);
1315            }
1316    
1317            public Reference getReference(Object coll, Collection.Key key) throws PageException {
1318                    return new VariableReference(coll,key);
1319            }
1320    
1321        @Override
1322        public Object get(Object coll, String key, Object defaultValue) {
1323            return variableUtil.get(this,coll,key, defaultValue);
1324        }
1325    
1326            @Override
1327            public Object get(Object coll, Collection.Key key, Object defaultValue) {
1328                    return variableUtil.get(this,coll,key, defaultValue);
1329            }
1330            
1331        @Override
1332        public Object setVariable(String var, Object value) throws PageException {
1333                //return new CFMLExprInterpreter().interpretReference(this,new ParserString(var)).set(value);
1334                return VariableInterpreter.setVariable(this,var,value);
1335            }
1336        
1337        @Override
1338        public Object getVariable(String var) throws PageException {
1339                    return VariableInterpreter.getVariable(this,var);
1340            }
1341        
1342    
1343        public void param(String type, String name, Object defaultValue,String regex) throws PageException {
1344            param(type, name, defaultValue,Double.NaN,Double.NaN,regex,-1);
1345        }
1346            public void param(String type, String name, Object defaultValue,double min, double max) throws PageException {
1347            param(type, name, defaultValue,min,max,null,-1);
1348        }
1349    
1350        public void param(String type, String name, Object defaultValue,int maxLength) throws PageException {
1351            param(type, name, defaultValue,Double.NaN,Double.NaN,null,maxLength);
1352        }
1353    
1354        public void param(String type, String name, Object defaultValue) throws PageException {
1355            param(type, name, defaultValue,Double.NaN,Double.NaN,null,-1);
1356        }
1357            
1358        private void param(String type, String name, Object defaultValue, double min,double max, String strPattern, int maxLength) throws PageException {
1359                    
1360            
1361            // check attributes type
1362            if(type==null)type="any";
1363                    else type=type.trim().toLowerCase();
1364    
1365            // check attributes name
1366            if(StringUtil.isEmpty(name))
1367                            throw new ExpressionException("The attribute name is required");
1368            
1369            Object value=null;
1370                    boolean isNew=false;
1371                    
1372                    // get value
1373                    value=VariableInterpreter.getVariableEL(this,name,NullSupportHelper.NULL());
1374                    if(NullSupportHelper.NULL()==value) {
1375                            if(defaultValue==null)
1376                                    throw new ExpressionException("The required parameter ["+name+"] was not provided.");
1377                            value=defaultValue;
1378                            isNew=true;
1379                    }
1380                    
1381                    // cast and set value
1382                    if(!"any".equals(type)) {
1383                            // range
1384                            if("range".equals(type)) {
1385                                    double number = Caster.toDoubleValue(value);
1386                                    if(!Decision.isValid(min)) throw new ExpressionException("Missing attribute [min]");
1387                                    if(!Decision.isValid(max)) throw new ExpressionException("Missing attribute [max]");
1388                                    if(number<min || number>max)
1389                                            throw new ExpressionException("The number ["+Caster.toString(number)+"] is out of range [min:"+Caster.toString(min)+";max:"+Caster.toString(max)+"]");
1390                                    setVariable(name,Caster.toDouble(number));
1391                            }
1392                            // regex
1393                            else if("regex".equals(type) || "regular_expression".equals(type)) {
1394                                    String str=Caster.toString(value);
1395                                    
1396                                    if(strPattern==null) throw new ExpressionException("Missing attribute [pattern]");
1397                                    
1398                                    try {
1399                                            Pattern pattern = new Perl5Compiler().compile(strPattern, Perl5Compiler.DEFAULT_MASK);
1400                                    PatternMatcherInput input = new PatternMatcherInput(str);
1401                                    if( !new Perl5Matcher().matches(input, pattern))
1402                                            throw new ExpressionException("The value ["+str+"] doesn't match the provided pattern ["+strPattern+"]");
1403                                    
1404                                    } catch (MalformedPatternException e) {
1405                                            throw new ExpressionException("The provided pattern ["+strPattern+"] is invalid",e.getMessage());
1406                                    }
1407                                    setVariable(name,str);
1408                            }
1409                            else {
1410                                    if(!Decision.isCastableTo(type,value,true,true,maxLength)) {
1411                                            if(maxLength>-1 && ("email".equalsIgnoreCase(type) || "url".equalsIgnoreCase(type) || "string".equalsIgnoreCase(type))) {
1412                                                    StringBuilder msg=new StringBuilder(CasterException.createMessage(value, type));
1413                                                    msg.append(" with a maximum length of "+maxLength+" characters");
1414                                                    throw new CasterException(msg.toString());      
1415                                            }
1416                                            throw new CasterException(value,type);  
1417                                    }
1418                                    
1419                                    
1420                                    
1421                                    setVariable(name,value);
1422                                    //REALCAST setVariable(name,Caster.castTo(this,type,value,true));
1423                            }
1424                    }
1425                else if(isNew) setVariable(name,value);
1426            }
1427        
1428        
1429        
1430        
1431            
1432        @Override
1433        public Object removeVariable(String var) throws PageException {
1434                    return VariableInterpreter.removeVariable(this,var);
1435            }
1436    
1437        /**
1438         * 
1439         * a variable reference, references to variable, to modifed it, with global effect.
1440         * @param var variable name to get
1441         * @return return a variable reference by string syntax ("scopename.key.key" -> "url.name")
1442         * @throws PageException
1443         */
1444        public VariableReference getVariableReference(String var) throws PageException { 
1445                return VariableInterpreter.getVariableReference(this,var);
1446            } 
1447            
1448        @Override
1449        public Object getFunction(Object coll, String key, Object[] args) throws PageException {
1450            return variableUtil.callFunctionWithoutNamedValues(this,coll,key,args);
1451            }
1452    
1453            @Override
1454            public Object getFunction(Object coll, Key key, Object[] args) throws PageException {
1455                    return variableUtil.callFunctionWithoutNamedValues(this,coll,key,args);
1456            }
1457            
1458        @Override
1459        public Object getFunctionWithNamedValues(Object coll, String key, Object[] args) throws PageException {
1460                    return variableUtil.callFunctionWithNamedValues(this,coll,key,args);
1461            }
1462    
1463            @Override
1464            public Object getFunctionWithNamedValues(Object coll, Key key, Object[] args) throws PageException {
1465                    return variableUtil.callFunctionWithNamedValues(this,coll,key,args);
1466            }
1467    
1468        @Override
1469        public ConfigWeb getConfig() {
1470            return config;
1471        }
1472        
1473        @Override
1474        public Iterator getIterator(String key) throws PageException {
1475                    Object o=VariableInterpreter.getVariable(this,key);
1476                    if(o instanceof Iterator) return (Iterator) o;
1477                    throw new ExpressionException("["+key+"] is not a iterator object");
1478            }
1479    
1480        @Override
1481        public Query getQuery(String key) throws PageException {
1482                    Object value=VariableInterpreter.getVariable(this,key);
1483                    if(Decision.isQuery(value)) return Caster.toQuery(value);
1484            throw new CasterException(value,Query.class);///("["+key+"] is not a query object, object is from type ");
1485            }
1486        
1487        @Override
1488        public Query getQuery(Object value) throws PageException {
1489            if(Decision.isQuery(value)) return Caster.toQuery(value);
1490            value=VariableInterpreter.getVariable(this,Caster.toString(value));
1491            if(Decision.isQuery(value)) return Caster.toQuery(value);
1492            throw new CasterException(value,Query.class);
1493            }
1494    
1495            @Override
1496            public void setAttribute(String name, Object value) {
1497                try {
1498                if(value==null)removeVariable(name);
1499                else setVariable(name,value);
1500            } catch (PageException e) {}
1501            }
1502    
1503            @Override
1504            public void setAttribute(String name, Object value, int scope) {
1505                    switch(scope){
1506                    case javax.servlet.jsp.PageContext.APPLICATION_SCOPE:
1507                            if(value==null) getServletContext().removeAttribute(name);
1508                            else getServletContext().setAttribute(name, value);
1509                    break;
1510                    case javax.servlet.jsp.PageContext.PAGE_SCOPE:
1511                            setAttribute(name, value);
1512                    break;
1513                    case javax.servlet.jsp.PageContext.REQUEST_SCOPE:
1514                            if(value==null) req.removeAttribute(name);
1515                            else setAttribute(name, value);
1516                    break;
1517                    case javax.servlet.jsp.PageContext.SESSION_SCOPE:
1518                            HttpSession s = req.getSession(true);
1519                            if(value==null)s.removeAttribute(name);
1520                            else s.setAttribute(name, value);
1521                    break;
1522                    }       
1523            }
1524    
1525            @Override
1526            public Object getAttribute(String name) {
1527                    try {
1528                            return getVariable(name);
1529                    } catch (PageException e) {
1530                            return null;
1531                    }
1532            }
1533    
1534            @Override
1535            public Object getAttribute(String name, int scope) {
1536                    switch(scope){
1537                    case javax.servlet.jsp.PageContext.APPLICATION_SCOPE:
1538                            return getServletContext().getAttribute(name);
1539                    case javax.servlet.jsp.PageContext.PAGE_SCOPE:
1540                            return getAttribute(name);
1541                    case javax.servlet.jsp.PageContext.REQUEST_SCOPE:
1542                            return req.getAttribute(name);
1543                    case javax.servlet.jsp.PageContext.SESSION_SCOPE:
1544                            HttpSession s = req.getSession();
1545                            if(s!=null)return s.getAttribute(name);
1546                    break;
1547                    }       
1548                    return null;
1549            }
1550    
1551            @Override
1552            public Object findAttribute(String name) {
1553                    // page
1554                    Object value=getAttribute(name);
1555                    if(value!=null) return value;
1556                    // request
1557                    value=req.getAttribute(name);
1558                    if(value!=null) return value;
1559                    // session
1560                    HttpSession s = req.getSession();
1561                    value=s!=null?s.getAttribute(name):null;
1562                    if(value!=null) return value;
1563                    // application
1564                    value=getServletContext().getAttribute(name);
1565                    if(value!=null) return value;
1566                    
1567                    
1568                    return null;
1569            }
1570    
1571            @Override
1572            public void removeAttribute(String name) {
1573                    setAttribute(name, null);
1574            }
1575    
1576            @Override
1577            public void removeAttribute(String name, int scope) {
1578                    setAttribute(name, null,scope);
1579            }
1580    
1581            @Override
1582            public int getAttributesScope(String name) {
1583                    // page
1584                    if(getAttribute(name)!=null) return PageContext.PAGE_SCOPE;
1585            // request
1586            if(req.getAttribute(name) != null) return PageContext.REQUEST_SCOPE;
1587            // session
1588            HttpSession s = req.getSession();
1589            if(s!=null && s.getAttribute(name) != null) return PageContext.SESSION_SCOPE;
1590            // application
1591            if(getServletContext().getAttribute(name)!=null) return PageContext.APPLICATION_SCOPE;
1592            
1593                    return 0;
1594            }
1595    
1596            @Override
1597            public Enumeration getAttributeNamesInScope(int scope) {
1598                    
1599            switch(scope){
1600                    case javax.servlet.jsp.PageContext.APPLICATION_SCOPE:
1601                            return getServletContext().getAttributeNames();
1602                    case javax.servlet.jsp.PageContext.PAGE_SCOPE:
1603                            return ItAsEnum.toStringEnumeration(variablesScope().keyIterator());
1604                    case javax.servlet.jsp.PageContext.REQUEST_SCOPE:
1605                            return req.getAttributeNames();
1606                    case javax.servlet.jsp.PageContext.SESSION_SCOPE:
1607                            return req.getSession(true).getAttributeNames();
1608                    }
1609                    return null;
1610            }
1611    
1612            @Override
1613            public JspWriter getOut() {
1614                    return forceWriter;
1615            }
1616    
1617            @Override
1618            public HttpSession getSession() {
1619                    return getHttpServletRequest().getSession();
1620            }
1621    
1622            @Override
1623            public Object getPage() {
1624                    return variablesScope();
1625            }
1626    
1627            @Override
1628            public ServletRequest getRequest() {
1629                    return getHttpServletRequest();
1630            }
1631            
1632        @Override
1633        public HttpServletRequest getHttpServletRequest() {
1634                    return req;
1635            }
1636    
1637            @Override
1638            public ServletResponse getResponse() {
1639                    return rsp;
1640            }
1641    
1642        @Override
1643        public HttpServletResponse getHttpServletResponse() {
1644                    return rsp;
1645            }
1646        
1647        public OutputStream getResponseStream() throws IOException {
1648            return getRootOut().getResponseStream();
1649            }
1650    
1651            @Override
1652            public Exception getException() {
1653                    // TODO impl
1654                    return exception;
1655            }
1656    
1657            @Override
1658            public ServletConfig getServletConfig() {
1659                    return config;
1660            }
1661    
1662            @Override
1663            public ServletContext getServletContext() {
1664                    return servlet.getServletContext();
1665            }
1666    
1667            /*public static void main(String[] args) {
1668                    repl(" susi #error.susi# sorglos","susi", "Susanne");
1669                    repl(" susi #error.Susi# sorglos","susi", "Susanne");
1670            }*/
1671            private static String repl(String haystack, String needle, String replacement) {
1672                    //print.o("------------");
1673                    //print.o(haystack);
1674                    //print.o(needle);
1675                    StringBuilder regex=new StringBuilder("#[\\s]*error[\\s]*\\.[\\s]*");
1676                    
1677                    char[] carr = needle.toCharArray();
1678                    for(int i=0;i<carr.length;i++){
1679                            regex.append("[");
1680                            regex.append(Character.toLowerCase(carr[i]));
1681                            regex.append(Character.toUpperCase(carr[i]));
1682                            regex.append("]");
1683                    }
1684                    
1685                    
1686                    regex.append("[\\s]*#");
1687                    //print.o(regex);
1688                    
1689                    
1690                    haystack=haystack.replaceAll(regex.toString(), replacement);
1691                    //print.o(haystack);
1692                    return haystack;
1693            }
1694            
1695            
1696            @Override
1697            public void handlePageException(PageException pe) {
1698                    if(!Abort.isSilentAbort(pe)) {
1699                            
1700                            String charEnc = rsp.getCharacterEncoding();
1701                    if(StringUtil.isEmpty(charEnc,true)) {
1702                                    rsp.setContentType("text/html");
1703                    }
1704                    else {
1705                            rsp.setContentType("text/html; charset=" + charEnc);
1706                    }
1707                            
1708                            int statusCode=getStatusCode(pe);
1709                            
1710                            if(getConfig().getErrorStatusCode())rsp.setStatus(statusCode);
1711                            
1712                            ErrorPage ep=errorPagePool.getErrorPage(pe,ErrorPageImpl.TYPE_EXCEPTION);
1713                            
1714                            ExceptionHandler.printStackTrace(this,pe);
1715                            ExceptionHandler.log(getConfig(),pe);
1716                            // error page exception
1717                            if(ep!=null) {
1718                                    try {
1719                                            Struct sct=pe.getErrorBlock(this,ep);
1720                                            variablesScope().setEL(KeyConstants._error,sct);
1721                                            variablesScope().setEL(KeyConstants._cferror,sct);
1722                                            
1723                                            doInclude(ep.getTemplate());
1724                                            return;
1725                                    } catch (Throwable t) {
1726                                            if(Abort.isSilentAbort(t)) return;
1727                                            pe=Caster.toPageException(t);
1728                                    }
1729                                    
1730                            }
1731                            
1732                            // error page request
1733                            
1734                            ep=errorPagePool.getErrorPage(pe,ErrorPageImpl.TYPE_REQUEST);
1735                            if(ep!=null) {
1736                                    PageSource ps = ep.getTemplate();
1737                                    if(ps.physcalExists()){
1738                                            Resource res = ps.getResource();
1739                                            try {
1740                                                    String content = IOUtil.toString(res, getConfig().getTemplateCharset());
1741                                                    Struct sct=pe.getErrorBlock(this,ep);
1742                                                    java.util.Iterator<Entry<Key, Object>> it = sct.entryIterator();
1743                                                    Entry<Key, Object> e;
1744                                                    String v;
1745                                                    while(it.hasNext()){
1746                                                            e = it.next();
1747                                                            v=Caster.toString(e.getValue(),null);
1748                                                            if(v!=null)content=repl(content, e.getKey().getString(), v);
1749                                                    }
1750                                                    
1751                                                    write(content);
1752                                                    return;
1753                                            } catch (Throwable t) {
1754                                                    pe=Caster.toPageException(t);
1755                                                    
1756                                            }
1757                                            
1758                                    }
1759                                    else pe=new ApplicationException("The error page template for type request only works if the actual source file also exists . If the exception file is in an Railo archive (.rc/.rcs), you need to use type exception instead.");
1760                            }
1761                            
1762                            
1763                            try {
1764                                    if(statusCode!=404)
1765                                            forceWrite("<!-- Railo ["+Info.getVersionAsString()+"] Error -->");
1766                                    
1767                                    String template=getConfig().getErrorTemplate(statusCode);
1768                                    if(!StringUtil.isEmpty(template)) {
1769                                            try {
1770                                                    Struct catchBlock=pe.getCatchBlock(getConfig());
1771                                                    variablesScope().setEL(KeyConstants._cfcatch,catchBlock);
1772                                                    variablesScope().setEL(KeyConstants._catch,catchBlock);
1773                                                    doInclude(template);
1774                                                return;
1775                                    } 
1776                                            catch (PageException e) {
1777                                                    pe=e;
1778                                            }
1779                                    }
1780                                    if(!Abort.isSilentAbort(pe))forceWrite(getConfig().getDefaultDumpWriter(DumpWriter.DEFAULT_RICH).toString(this,pe.toDumpData(this, 9999,DumpUtil.toDumpProperties()),true));
1781                            } 
1782                            catch (Exception e) { 
1783                            }
1784                    }
1785            }
1786    
1787            private int getStatusCode(PageException pe) {
1788                    int statusCode=500;
1789                    int maxDeepFor404=0;
1790                    if(pe instanceof ModernAppListenerException){
1791                            pe=((ModernAppListenerException)pe).getPageException();
1792                            maxDeepFor404=1;
1793                    }
1794                    else if(pe instanceof PageExceptionBox)
1795                            pe=((PageExceptionBox)pe).getPageException();
1796                    
1797                    if(pe instanceof MissingIncludeException) {
1798                            MissingIncludeException mie=(MissingIncludeException) pe;
1799                            if(mie.getPageDeep()<=maxDeepFor404) statusCode=404;
1800                    }
1801                    
1802                    // TODO Auto-generated method stub
1803                    return statusCode;
1804            }
1805    
1806    
1807            @Override
1808            public void handlePageException(Exception e) {
1809                    handlePageException(Caster.toPageException(e));         
1810            }
1811    
1812            @Override
1813            public void handlePageException(Throwable t) {
1814            handlePageException(Caster.toPageException(t));
1815            }
1816    
1817        @Override
1818        public void setHeader(String name, String value) {
1819                    rsp.setHeader(name,value);
1820            }
1821    
1822            @Override
1823            public BodyContent pushBody() {
1824            forceWriter=bodyContentStack.push();
1825            if(enablecfoutputonly>0 && outputState==0) {
1826                writer=devNull;
1827            }
1828            else writer=forceWriter;
1829            return (BodyContent)forceWriter;
1830            }
1831    
1832            @Override
1833            public JspWriter popBody() {
1834            forceWriter=bodyContentStack.pop();
1835            if(enablecfoutputonly>0 && outputState==0) {
1836                writer=devNull;
1837            }
1838            else writer=forceWriter;
1839            return forceWriter;
1840            }
1841    
1842        @Override
1843        public void outputStart() {
1844                    outputState++;
1845            if(enablecfoutputonly>0 && outputState==1)writer=forceWriter;
1846                    //if(enablecfoutputonly && outputState>0) unsetDevNull();
1847            }
1848    
1849        @Override
1850        public void outputEnd() {
1851                    outputState--;
1852                    if(enablecfoutputonly>0 && outputState==0)writer=devNull;
1853            }
1854    
1855        @Override
1856        public void setCFOutputOnly(boolean boolEnablecfoutputonly) {
1857            if(boolEnablecfoutputonly)this.enablecfoutputonly++;
1858            else if(this.enablecfoutputonly>0)this.enablecfoutputonly--;
1859            setCFOutputOnly(enablecfoutputonly);
1860            //if(!boolEnablecfoutputonly)setCFOutputOnly(enablecfoutputonly=0);
1861        }
1862    
1863        @Override
1864        public void setCFOutputOnly(short enablecfoutputonly) {
1865            this.enablecfoutputonly=enablecfoutputonly;
1866            if(enablecfoutputonly>0) {
1867                if(outputState==0) writer=devNull;
1868            }
1869            else {
1870                writer=forceWriter;
1871            }
1872        }
1873    
1874        @Override
1875        public boolean setSilent() {
1876            boolean before=bodyContentStack.getDevNull();
1877                    bodyContentStack.setDevNull(true);
1878                    
1879            forceWriter = bodyContentStack.getWriter();
1880            writer=forceWriter;
1881            return before;
1882            }
1883            
1884        @Override
1885        public boolean unsetSilent() {
1886            boolean before=bodyContentStack.getDevNull();
1887            bodyContentStack.setDevNull(false);
1888            
1889            forceWriter = bodyContentStack.getWriter();
1890            if(enablecfoutputonly>0 && outputState==0) {
1891                writer=devNull;
1892            }
1893            else writer=forceWriter;
1894            return before;
1895            }
1896        
1897    
1898        @Override
1899        public Debugger getDebugger() {
1900                    return debugger;
1901            }
1902        
1903        @Override
1904        public void executeRest(String realPath, boolean throwExcpetion) throws PageException  {
1905            ApplicationListener listener=null;//config.get ApplicationListener();
1906                try{
1907            String pathInfo = req.getPathInfo();
1908            
1909            // charset
1910            try{
1911                    String charset=HTTPUtil.splitMimeTypeAndCharset(req.getContentType(),new String[]{"",""})[1];
1912            if(StringUtil.isEmpty(charset))charset=ThreadLocalPageContext.getConfig().getWebCharset();
1913                    java.net.URL reqURL = new java.net.URL(req.getRequestURL().toString());
1914                    String path=ReqRspUtil.decode(reqURL.getPath(),charset,true);
1915                    String srvPath=req.getServletPath();
1916                    if(path.startsWith(srvPath)) {
1917                            pathInfo=path.substring(srvPath.length());
1918                    }
1919            }
1920            catch (Exception e){}
1921            
1922            
1923            // Service mapping
1924            if(StringUtil.isEmpty(pathInfo) || pathInfo.equals("/")) {// ToDo
1925                    // list available services (if enabled in admin)
1926                    if(config.getRestList()) {
1927                            try {
1928                                            HttpServletRequest _req = getHttpServletRequest();
1929                                    write("Available sevice mappings are:<ul>");
1930                                            railo.runtime.rest.Mapping[] mappings = config.getRestMappings();
1931                                            String path;
1932                                            for(int i=0;i<mappings.length;i++){
1933                                                    path=_req.getContextPath()+ReqRspUtil.getScriptName(_req)+mappings[i].getVirtual();
1934                                                    write("<li>"+path+"</li>");
1935                                                    
1936                                                    
1937                                            }
1938                                            write("</ul>");
1939                                            
1940                                    } catch (IOException e) {
1941                                            throw Caster.toPageException(e);
1942                                    }
1943                    }
1944                    else 
1945                            RestUtil.setStatus(this, 404, null);
1946                            return;
1947            }       
1948            
1949            // check for matrix
1950            int index;
1951            String entry;
1952            Struct matrix=new StructImpl();
1953            while((index=pathInfo.lastIndexOf(';'))!=-1){
1954                    entry=pathInfo.substring(index+1);
1955                    pathInfo=pathInfo.substring(0,index);
1956                    if(StringUtil.isEmpty(entry,true)) continue;
1957                    
1958                    index=entry.indexOf('=');
1959                    if(index!=-1)matrix.setEL(entry.substring(0,index).trim(), entry.substring(index+1).trim());
1960                    else matrix.setEL(entry.trim(), "");
1961            }
1962            
1963            // get accept
1964            List<MimeType> accept = ReqRspUtil.getAccept(this);
1965            MimeType contentType = ReqRspUtil.getContentType(this);
1966            
1967            // check for format extension
1968            //int format = getApplicationContext().getRestSettings().getReturnFormat();
1969            int format;
1970            boolean hasFormatExtension=false;
1971            if(StringUtil.endsWithIgnoreCase(pathInfo, ".json")) {
1972                    pathInfo=pathInfo.substring(0,pathInfo.length()-5);
1973                    format = UDF.RETURN_FORMAT_JSON;
1974                    accept.clear();
1975                    accept.add(MimeType.APPLICATION_JSON);
1976                    hasFormatExtension=true;
1977            }
1978            else if(StringUtil.endsWithIgnoreCase(pathInfo, ".wddx")) {
1979                    pathInfo=pathInfo.substring(0,pathInfo.length()-5);
1980                    format = UDF.RETURN_FORMAT_WDDX;
1981                    accept.clear();
1982                    accept.add(MimeType.APPLICATION_WDDX);
1983                    hasFormatExtension=true;
1984            }
1985            else if(StringUtil.endsWithIgnoreCase(pathInfo, ".cfml")) {
1986                    pathInfo=pathInfo.substring(0,pathInfo.length()-5);
1987                    format = UDF.RETURN_FORMAT_SERIALIZE;
1988                    accept.clear();
1989                    accept.add(MimeType.APPLICATION_CFML);
1990                    hasFormatExtension=true;
1991            }
1992            else if(StringUtil.endsWithIgnoreCase(pathInfo, ".serialize")) {
1993                    pathInfo=pathInfo.substring(0,pathInfo.length()-10);
1994                    format = UDF.RETURN_FORMAT_SERIALIZE;
1995                    accept.clear();
1996                    accept.add(MimeType.APPLICATION_CFML);
1997                    hasFormatExtension=true;
1998            }
1999            else if(StringUtil.endsWithIgnoreCase(pathInfo, ".xml")) {
2000                    pathInfo=pathInfo.substring(0,pathInfo.length()-4);
2001                    format = UDF.RETURN_FORMAT_XML;
2002                    accept.clear();
2003                    accept.add(MimeType.APPLICATION_XML);
2004                    hasFormatExtension=true;
2005            }
2006            else {
2007                    format = getApplicationContext().getRestSettings().getReturnFormat();
2008                    //MimeType mt=MimeType.toMimetype(format);
2009                    //if(mt!=null)accept.add(mt);
2010            }
2011            
2012            if(accept.size()==0) accept.add(MimeType.ALL);
2013            
2014            // loop all mappings
2015            //railo.runtime.rest.Result result = null;//config.getRestSource(pathInfo, null);
2016            RestRequestListener rl=null;
2017            railo.runtime.rest.Mapping[] restMappings = config.getRestMappings();
2018            railo.runtime.rest.Mapping m,mapping=null,defaultMapping=null;
2019            //String callerPath=null;
2020            if(restMappings!=null)for(int i=0;i<restMappings.length;i++) {
2021                m = restMappings[i];
2022                if(m.isDefault())defaultMapping=m;
2023                if(pathInfo.startsWith(m.getVirtualWithSlash(),0) && m.getPhysical()!=null) {
2024                    mapping=m;
2025                    //result = m.getResult(this,callerPath=pathInfo.substring(m.getVirtual().length()),format,matrix,null);
2026                    rl=new RestRequestListener(m,pathInfo.substring(m.getVirtual().length()),matrix,format,hasFormatExtension,accept,contentType,null);
2027                    break;
2028                }
2029            }
2030            
2031            // default mapping
2032            if(mapping==null && defaultMapping!=null && defaultMapping.getPhysical()!=null) {
2033                    mapping=defaultMapping;
2034                //result = mapping.getResult(this,callerPath=pathInfo,format,matrix,null);
2035                    rl=new RestRequestListener(mapping,pathInfo,matrix,format,hasFormatExtension,accept,contentType,null);
2036            }
2037            
2038            
2039            //base = PageSourceImpl.best(config.getPageSources(this,null,realPath,true,false,true));
2040            
2041            
2042            if(mapping==null || mapping.getPhysical()==null){
2043                    RestUtil.setStatus(this,404,"no rest service for ["+pathInfo+"] found");
2044            }
2045            else {
2046                    base=config.toPageSource(null, mapping.getPhysical(), null);
2047                    listener=((MappingImpl)base.getMapping()).getApplicationListener();
2048                listener.onRequest(this, base,rl);
2049            }
2050            
2051            
2052            
2053            }
2054                catch(Throwable t) {
2055                    PageException pe = Caster.toPageException(t);
2056                    if(!Abort.isSilentAbort(pe)){
2057                            log(true);
2058                            if(fdEnabled){
2059                                    FDSignal.signal(pe, false);
2060                            }
2061                            if(listener==null) {
2062                                    if(base==null)listener=config.getApplicationListener();
2063                                    else listener=((MappingImpl)base.getMapping()).getApplicationListener();
2064                            }
2065                            listener.onError(this,pe);      
2066                    }
2067                    else log(false);
2068    
2069                    if(throwExcpetion) throw pe;
2070                }
2071                finally {
2072                    if(enablecfoutputonly>0){
2073                    setCFOutputOnly((short)0);
2074                }
2075                base=null;
2076                }
2077        }
2078    
2079            @Override
2080        public void execute(String realPath, boolean throwExcpetion) throws PageException  {
2081            execute(realPath, throwExcpetion, true);
2082        }
2083        public void execute(String realPath, boolean throwExcpetion, boolean onlyTopLevel) throws PageException  {
2084            //SystemOut.printDate(config.getOutWriter(),"Call:"+realPath+" (id:"+getId()+";running-requests:"+config.getThreadQueue().size()+";)");
2085                if(realPath.startsWith("/mapping-")){
2086                    base=null;
2087                    int index = realPath.indexOf('/',9);
2088                    if(index>-1){
2089                            String type = realPath.substring(9,index);
2090                            if(type.equalsIgnoreCase("tag")){
2091                                    base=getPageSource(
2092                                                    new Mapping[]{config.getTagMapping(),config.getServerTagMapping()},
2093                                                    realPath.substring(index)
2094                                                    );
2095                            }
2096                            else if(type.equalsIgnoreCase("customtag")){
2097                                    base=getPageSource(
2098                                                    config.getCustomTagMappings(),
2099                                                    realPath.substring(index)
2100                                                    );
2101                            }
2102                            /*else if(type.equalsIgnoreCase("gateway")){
2103                                    base=config.getGatewayEngine().getMapping().getPageSource(realPath.substring(index));
2104                                    if(!base.exists())base=getPageSource(realPath.substring(index));
2105                            }*/
2106                    }
2107                    if(base==null) base=PageSourceImpl.best(config.getPageSources(this,null,realPath,onlyTopLevel,false,true));
2108                }
2109                else base=PageSourceImpl.best(config.getPageSources(this,null,realPath,onlyTopLevel,false,true));
2110                ApplicationListener listener=gatewayContext?new NoneAppListener():((MappingImpl)base.getMapping()).getApplicationListener();
2111                
2112                try {
2113                    listener.onRequest(this,base,null);
2114                    log(false);
2115                }
2116                catch(Throwable t) {
2117                    PageException pe = Caster.toPageException(t);
2118                    if(!Abort.isSilentAbort(pe)){
2119                            this.pe=pe;
2120                            log(true);
2121                            if(fdEnabled){
2122                                    FDSignal.signal(pe, false);
2123                            }
2124                            listener.onError(this,pe);      
2125                    }
2126                    else log(false);
2127    
2128                    if(throwExcpetion) throw pe;
2129                }
2130                finally {
2131                    
2132                    
2133                if(enablecfoutputonly>0){
2134                    setCFOutputOnly((short)0);
2135                }
2136                if(!gatewayContext && getConfig().debug()) {
2137                    try {
2138                                            listener.onDebug(this);
2139                                    } 
2140                    catch (PageException pe) {
2141                            if(!Abort.isSilentAbort(pe))listener.onError(this,pe);
2142                                    }
2143                }
2144                base=null;
2145                }
2146            }
2147    
2148            private void log(boolean error) {
2149                    if(!isGatewayContext() && config.isMonitoringEnabled()) {
2150                RequestMonitor[] monitors = config.getRequestMonitors();
2151                if(monitors!=null)for(int i=0;i<monitors.length;i++){
2152                    if(monitors[i].isLogEnabled()){
2153                            try {
2154                                    monitors[i].log(this,error);
2155                                    } 
2156                                    catch (Throwable e) {}
2157                        }
2158                }
2159                    }
2160            }
2161    
2162            private PageSource getPageSource(Mapping[] mappings, String realPath) {
2163                    PageSource ps;
2164                    //print.err(mappings.length);
2165            for(int i=0;i<mappings.length;i++) {
2166                ps = mappings[i].getPageSource(realPath);
2167                //print.err(ps.getDisplayPath());
2168                if(ps.exists()) return ps;
2169                
2170            }
2171                    return null;
2172            }
2173    
2174    
2175    
2176            @Override
2177            public void include(String realPath) throws ServletException,IOException  {
2178                    HTTPUtil.include(this, realPath);
2179            }
2180            
2181    
2182            @Override
2183            public void forward(String realPath) throws ServletException, IOException {
2184                    HTTPUtil.forward(this, realPath);
2185            }
2186    
2187            public void include(PageSource ps) throws ServletException  {
2188                    try {
2189                            doInclude(ps);
2190                    } catch (PageException pe) {
2191                            throw new PageServletException(pe);
2192                    }
2193            }
2194    
2195        @Override
2196        public void clear() {
2197                    try {
2198                            //print.o(getOut().getClass().getName());
2199                            getOut().clear();
2200                    } catch (IOException e) {}
2201            }
2202            
2203        @Override
2204        public long getRequestTimeout() {
2205                    if(requestTimeout==-1)
2206                            requestTimeout=config.getRequestTimeout().getMillis();
2207                    return requestTimeout;
2208            }
2209            
2210        @Override
2211        public void setRequestTimeout(long requestTimeout) {
2212                    this.requestTimeout = requestTimeout;
2213            }
2214    
2215        @Override
2216        public String getCFID() {
2217                    if(cfid==null) initIdAndToken();
2218                    return cfid;
2219            }
2220    
2221        @Override
2222        public String getCFToken() {
2223                    if(cftoken==null) initIdAndToken();
2224                    return cftoken;
2225            }
2226    
2227        @Override
2228        public String getURLToken() {
2229                if(getConfig().getSessionType()==Config.SESSION_TYPE_J2EE) {
2230                    HttpSession s = getSession();
2231                        return "CFID="+getCFID()+"&CFTOKEN="+getCFToken()+"&jsessionid="+(s!=null?getSession().getId():"");
2232                    }
2233                    return "CFID="+getCFID()+"&CFTOKEN="+getCFToken();
2234            }
2235        
2236        @Override
2237        public String getJSessionId() {
2238                if(getConfig().getSessionType()==Config.SESSION_TYPE_J2EE) {
2239                        return getSession().getId();
2240                    }
2241                    return null;
2242            }
2243    
2244        /**
2245         * initialize the cfid and the cftoken
2246         */
2247        private void initIdAndToken() {
2248            boolean setCookie=true;
2249            // From URL
2250            Object oCfid = urlScope().get(KeyConstants._cfid,null);
2251            Object oCftoken = urlScope().get(KeyConstants._cftoken,null);
2252            // Cookie
2253            if((oCfid==null || !Decision.isGUIdSimple(oCfid)) || oCftoken==null) {
2254                setCookie=false;
2255                oCfid = cookieScope().get(KeyConstants._cfid,null);
2256                oCftoken = cookieScope().get(KeyConstants._cftoken,null);
2257            }
2258            if(oCfid!=null && !Decision.isGUIdSimple(oCfid) ) {
2259                    oCfid=null;
2260            }
2261            // New One
2262            if(oCfid==null || oCftoken==null) {
2263                setCookie=true;
2264                cfid=ScopeContext.getNewCFId();
2265                cftoken=ScopeContext.getNewCFToken();
2266            }
2267            else {
2268                cfid=Caster.toString(oCfid,null);
2269                cftoken=Caster.toString(oCftoken,null);
2270            }
2271            
2272            if(setCookie && applicationContext.isSetClientCookies()) {
2273                cookieScope().setCookieEL(KeyConstants._cfid,cfid,CookieImpl.NEVER,false,"/",applicationContext.isSetDomainCookies()?(String) cgiScope().get(KeyConstants._server_name,null):null);
2274                cookieScope().setCookieEL(KeyConstants._cftoken,cftoken,CookieImpl.NEVER,false,"/",applicationContext.isSetDomainCookies()?(String) cgiScope().get(KeyConstants._server_name,null):null);
2275            }
2276        }
2277        
2278    
2279        public void resetIdAndToken() {
2280            cfid=ScopeContext.getNewCFId();
2281            cftoken=ScopeContext.getNewCFToken();
2282            if(applicationContext.isSetClientCookies()) {
2283                cookieScope().setCookieEL(KeyConstants._cfid,cfid,CookieImpl.NEVER,false,"/",applicationContext.isSetDomainCookies()?(String) cgiScope().get(KeyConstants._server_name,null):null);
2284                cookieScope().setCookieEL(KeyConstants._cftoken,cftoken,CookieImpl.NEVER,false,"/",applicationContext.isSetDomainCookies()?(String) cgiScope().get(KeyConstants._server_name,null):null);
2285            }
2286        }
2287        
2288    
2289        @Override
2290        public int getId() {
2291                    return id;
2292            }
2293    
2294        /**
2295         * @return returns the root JSP Writer
2296         * 
2297         */
2298        public CFMLWriter getRootOut() {
2299                    return bodyContentStack.getBase();
2300            }
2301        public JspWriter getRootWriter() {
2302                    return bodyContentStack.getBase();
2303            }
2304    
2305        @Override
2306        public Locale getLocale() {
2307                    if(locale==null) locale=config.getLocale();
2308                    return locale;
2309            }
2310    
2311        @Override
2312        public void setPsq(boolean psq) {
2313                    this.psq=psq;
2314            }
2315            
2316        @Override
2317        public boolean getPsq() {
2318                    return psq;
2319            }
2320            
2321        @Override
2322        public void setLocale(Locale locale) {
2323                    
2324                    //String old=GetLocale.call(pc);
2325                    this.locale=locale;
2326            HttpServletResponse rsp = getHttpServletResponse();
2327            
2328            String charEnc = rsp.getCharacterEncoding();
2329            rsp.setLocale(locale);
2330            if(charEnc.equalsIgnoreCase("UTF-8")) {
2331                    rsp.setContentType("text/html; charset=UTF-8");
2332            }
2333            else if(!charEnc.equalsIgnoreCase(rsp.getCharacterEncoding())) {
2334                    rsp.setContentType("text/html; charset=" + charEnc);
2335            }
2336            }
2337        
2338    
2339        @Override
2340        public void setLocale(String strLocale) throws ExpressionException {
2341                    setLocale(Caster.toLocale(strLocale));
2342            }
2343    
2344        @Override
2345        public void setErrorPage(ErrorPage ep) {
2346                    errorPagePool.setErrorPage(ep);
2347            }
2348            
2349        @Override
2350        public Tag use(String tagClassName) throws PageException {
2351    
2352            parentTag=currentTag;
2353                    currentTag= tagHandlerPool.use(tagClassName);
2354            if(currentTag==parentTag) throw new ApplicationException("");
2355            currentTag.setPageContext(this);
2356            currentTag.setParent(parentTag);
2357            return currentTag;
2358            }
2359        
2360        @Override
2361        public Tag use(Class clazz) throws PageException {
2362            return use(clazz.getName());
2363            }
2364            
2365        @Override
2366        public void reuse(Tag tag) throws PageException {
2367            currentTag=tag.getParent();
2368            tagHandlerPool.reuse(tag);
2369            }
2370    
2371        @Override
2372        public QueryCache getQueryCache() {
2373            return queryCache;
2374        }
2375        
2376        @Override
2377        public void initBody(BodyTag bodyTag, int state) throws JspException {
2378            if (state != Tag.EVAL_BODY_INCLUDE) {
2379                bodyTag.setBodyContent(pushBody());
2380                bodyTag.doInitBody();
2381            }
2382        }
2383        
2384        @Override
2385        public void releaseBody(BodyTag bodyTag, int state) {
2386            if(bodyTag instanceof TryCatchFinally) {
2387                ((TryCatchFinally)bodyTag).doFinally();
2388            }
2389            if (state != Tag.EVAL_BODY_INCLUDE)popBody();
2390        }
2391        
2392        /* *
2393         * @return returns the cfml compiler 
2394         * /
2395        public CFMLCompiler getCompiler() {
2396            return compiler;
2397        }*/
2398        
2399        @Override
2400        public void setVariablesScope(Variables variables) {
2401            this.variables=variables;
2402            undefinedScope().setVariableScope(variables);
2403            
2404            if(variables instanceof ComponentScope) {
2405                    activeComponent=((ComponentScope)variables).getComponent();
2406                /*if(activeComponent.getAbsName().equals("jm.pixeltex.supersuperApp")){
2407                    print.dumpStack();
2408                }*/
2409            }
2410            else {
2411                activeComponent=null;
2412            }
2413        }
2414    
2415        @Override
2416        public Component getActiveComponent() {
2417            return activeComponent;
2418        }
2419        
2420        @Override
2421        public Credential getRemoteUser() throws PageException {
2422            if(remoteUser==null) {
2423                    Key name = KeyImpl.init(Login.getApplicationName(applicationContext));
2424                        Resource roles = config.getConfigDir().getRealResource("roles");
2425                        
2426                    if(applicationContext.getLoginStorage()==Scope.SCOPE_SESSION) {
2427                    Object auth = sessionScope().get(name,null);
2428                    if(auth!=null) {
2429                        remoteUser=CredentialImpl.decode(auth,roles);
2430                    }
2431                }
2432                else if(applicationContext.getLoginStorage()==Scope.SCOPE_COOKIE) {
2433                    Object auth = cookieScope().get(name,null);
2434                    if(auth!=null) {
2435                        remoteUser=CredentialImpl.decode(auth,roles);
2436                    }
2437                }
2438            }
2439            return remoteUser;
2440        }
2441        
2442        @Override
2443        public void clearRemoteUser() {
2444            if(remoteUser!=null)remoteUser=null;
2445            String name=Login.getApplicationName(applicationContext);
2446                
2447            cookieScope().removeEL(KeyImpl.init(name));
2448            try {
2449                            sessionScope().removeEL(KeyImpl.init(name));
2450                    } catch (PageException e) {}
2451            
2452        }
2453        
2454        @Override
2455        public void setRemoteUser(Credential remoteUser) {
2456            this.remoteUser = remoteUser;
2457        }
2458        
2459        @Override
2460        public VariableUtil getVariableUtil() {
2461            return variableUtil;
2462        }
2463    
2464        @Override
2465        public void throwCatch() throws PageException {
2466            if(exception!=null) throw exception;
2467            throw new ApplicationException("invalid context for tag/script expression rethow");
2468        }
2469    
2470        @Override
2471        public PageException setCatch(Throwable t) {
2472            if(t==null) {
2473                    exception=null;
2474                    undefinedScope().removeEL(KeyConstants._cfcatch);
2475            }
2476            else {
2477                    exception = Caster.toPageException(t);
2478                    undefinedScope().setEL(KeyConstants._cfcatch,exception.getCatchBlock(config));
2479                    if(!gatewayContext && config.debug() && config.hasDebugOptions(ConfigImpl.DEBUG_EXCEPTION)) debugger.addException(config,exception);
2480            }
2481            return exception;
2482        }
2483        
2484        public void setCatch(PageException pe) {
2485            exception = pe;
2486            if(pe==null) {
2487                    undefinedScope().removeEL(KeyConstants._cfcatch);
2488            }
2489            else {
2490                    undefinedScope().setEL(KeyConstants._cfcatch,pe.getCatchBlock(config));
2491                    if(!gatewayContext && config.debug() && config.hasDebugOptions(ConfigImpl.DEBUG_EXCEPTION)) debugger.addException(config,exception);
2492            }
2493        }
2494        
2495        public void setCatch(PageException pe,boolean caught, boolean store) {
2496                    if(fdEnabled){
2497                    FDSignal.signal(pe, caught);
2498            }
2499            exception = pe;
2500            if(store){
2501                    if(pe==null) {
2502                            undefinedScope().removeEL(KeyConstants._cfcatch);
2503                    }
2504                    else {
2505                            undefinedScope().setEL(KeyConstants._cfcatch,pe.getCatchBlock(config));
2506                            if(!gatewayContext && config.debug() && config.hasDebugOptions(ConfigImpl.DEBUG_EXCEPTION)) debugger.addException(config,exception);
2507                    }
2508            }
2509        }
2510        
2511        /**
2512         * @return return current catch
2513         */
2514        public PageException getCatch() {
2515            return exception;
2516        }
2517        
2518        @Override
2519        public void clearCatch() {
2520            exception = null;
2521            undefinedScope().removeEL(KeyConstants._cfcatch);
2522        }
2523    
2524        @Override
2525        public void addPageSource(PageSource ps, boolean alsoInclude) {
2526            pathList.add(ps);
2527            if(alsoInclude) 
2528                includePathList.add(ps);
2529        }
2530        
2531    
2532        public void addPageSource(PageSource ps, PageSource psInc) {
2533            pathList.add(ps);
2534            if(psInc!=null) 
2535                includePathList.add(psInc);
2536        }
2537    
2538        @Override
2539        public void removeLastPageSource(boolean alsoInclude) {
2540            if(!pathList.isEmpty())pathList.removeLast();
2541            if(alsoInclude && !includePathList.isEmpty()) 
2542                includePathList.removeLast();
2543        }
2544    
2545    
2546        public UDF[] getUDFs() {
2547            return udfs.toArray(new UDF[udfs.size()]);
2548        }
2549        
2550        public void addUDF(UDF udf) {
2551            udfs.add(udf);
2552        }
2553    
2554        public void removeUDF() {
2555            if(!udfs.isEmpty())udfs.pop();
2556        }
2557    
2558        @Override
2559        public FTPPool getFTPPool() {
2560            return ftpPool;
2561        }
2562    
2563        /* *
2564         * @return Returns the manager.
2565         * /
2566        public DataSourceManager getManager() {
2567            return manager;
2568        }*/
2569        
2570        @Override
2571        public ApplicationContext getApplicationContext() {
2572            return applicationContext;
2573        }
2574        
2575        @Override
2576        public void setApplicationContext(ApplicationContext applicationContext) {
2577            
2578            session=null;
2579            application=null;
2580            client=null;
2581            this.applicationContext = applicationContext;
2582            
2583            int scriptProtect = applicationContext.getScriptProtect();
2584            
2585            // ScriptProtecting
2586            if(config.mergeFormAndURL()) {
2587                    form.setScriptProtecting(applicationContext,
2588                                    (scriptProtect&ApplicationContext.SCRIPT_PROTECT_FORM)>0 
2589                                    || 
2590                                    (scriptProtect&ApplicationContext.SCRIPT_PROTECT_URL)>0);
2591            }
2592            else {
2593                form.setScriptProtecting(applicationContext,(scriptProtect&ApplicationContext.SCRIPT_PROTECT_FORM)>0);
2594                url.setScriptProtecting(applicationContext,(scriptProtect&ApplicationContext.SCRIPT_PROTECT_URL)>0);
2595            }
2596            cookie.setScriptProtecting(applicationContext,(scriptProtect&ApplicationContext.SCRIPT_PROTECT_COOKIE)>0);
2597            cgi.setScriptProtecting(applicationContext,(scriptProtect&ApplicationContext.SCRIPT_PROTECT_CGI)>0);
2598            undefined.reinitialize(this);
2599        }
2600        
2601        /**
2602         * @return return  value of method "onApplicationStart" or true
2603         * @throws PageException 
2604         */
2605        public boolean initApplicationContext(ApplicationListener listener) throws PageException {
2606            boolean initSession=false;
2607            //AppListenerSupport listener = (AppListenerSupport) config.get ApplicationListener();
2608            KeyLock<String> lock = config.getContextLock();
2609            String name=StringUtil.emptyIfNull(applicationContext.getName());
2610            String token=name+":"+getCFID();
2611            
2612            Lock tokenLock = lock.lock(token,getRequestTimeout());
2613            //print.o("outer-lock  :"+token);
2614            try {
2615                    // check session before executing any code
2616                    initSession=applicationContext.isSetSessionManagement() && listener.hasOnSessionStart(this) && !scopeContext.hasExistingSessionScope(this);
2617                    
2618                    // init application
2619                    
2620                    Lock nameLock = lock.lock(name,getRequestTimeout());
2621                    //print.o("inner-lock  :"+token);
2622                    try {
2623                            RefBoolean isNew=new RefBooleanImpl(false);
2624                                application=scopeContext.getApplicationScope(this,isNew);// this is needed that the application scope is initilized
2625                            if(isNew.toBooleanValue()) {
2626                                        try {
2627                                                    if(!listener.onApplicationStart(this)) {
2628                                                            scopeContext.removeApplicationScope(this);
2629                                                        return false;
2630                                                    }
2631                                            } catch (PageException pe) {
2632                                                    scopeContext.removeApplicationScope(this);
2633                                                    throw pe;
2634                                            }
2635                                }
2636                    }
2637                    finally{
2638                            //print.o("inner-unlock:"+token);
2639                            lock.unlock(nameLock);
2640                    }
2641            
2642                    // init session
2643                        if(initSession) {
2644                            scopeContext.getSessionScope(this, DUMMY_BOOL);// this is needed that the session scope is initilized
2645                            listener.onSessionStart(this);
2646                            }
2647            }
2648            finally{
2649                    //print.o("outer-unlock:"+token);
2650                    lock.unlock(tokenLock);
2651            }
2652                return true;
2653        }
2654        
2655    
2656        /**
2657         * @return the scope factory
2658         */
2659        public ScopeFactory getScopeFactory() {
2660            return scopeFactory;
2661        }
2662    
2663        
2664        
2665        
2666        @Override
2667        public Tag getCurrentTag() {
2668            return currentTag;
2669        }
2670    
2671        @Override
2672        public long getStartTime() {
2673            return startTime;
2674        }
2675        
2676        @Override
2677        public Thread getThread() {
2678            return thread;
2679        }
2680        
2681    
2682    
2683            public void setThread(Thread thread) {
2684                    this.thread=thread;
2685            }
2686    
2687        @Override
2688        public int getExecutionTime() {
2689            return executionTime;
2690        }
2691    
2692        @Override
2693        public void setExecutionTime(int executionTime) {
2694            this.executionTime = executionTime;
2695        }
2696    
2697        @Override
2698        public synchronized void compile(PageSource pageSource) throws PageException {
2699            Resource classRootDir = pageSource.getMapping().getClassRootDirectory();
2700            
2701            try {
2702                config.getCompiler().compile(
2703                        config,
2704                        pageSource,
2705                        config.getTLDs(),
2706                        config.getFLDs(),
2707                        classRootDir,
2708                        pageSource.getJavaName()
2709                        );
2710            } catch (Exception e) {
2711                throw Caster.toPageException(e);
2712            }        
2713        }
2714    
2715        @Override
2716        public void compile(String realPath) throws PageException {
2717            SystemOut.printDate("method PageContext.compile(String) should no longer be used!");
2718            compile(PageSourceImpl.best(getRelativePageSources(realPath)));
2719        }
2720        
2721        public HttpServlet getServlet() {
2722            return servlet;
2723        }
2724    
2725        @Override
2726        public railo.runtime.Component loadComponent(String compPath) throws PageException {
2727            return ComponentLoader.loadComponent(this,compPath,null,null);
2728        }
2729    
2730            /**
2731             * @return the base
2732             */
2733            public PageSource getBase() {
2734                    return base;
2735            }
2736    
2737            /**
2738             * @param base the base to set
2739             */
2740            public void setBase(PageSource base) {
2741                    this.base = base;
2742            }
2743    
2744            /**
2745             * @return the isCFCRequest
2746             */
2747            public boolean isCFCRequest() {
2748                    return isCFCRequest;
2749            }
2750            
2751            @Override
2752            public DataSourceManager getDataSourceManager() {
2753                    return manager;
2754            }
2755    
2756            @Override
2757            public Object evaluate(String expression) throws PageException {
2758                    return new CFMLExpressionInterpreter().interpret(this,expression);
2759            }
2760            
2761            @Override
2762            public String serialize(Object expression) throws PageException {
2763                    return Serialize.call(this, expression);
2764            }
2765    
2766            /**
2767             * @return the activeUDF
2768             */
2769            public UDF getActiveUDF() {
2770                    return activeUDF;
2771            }
2772    
2773            /**
2774             * @param activeUDF the activeUDF to set
2775             */
2776            public void setActiveUDF(UDF activeUDF) {
2777                    this.activeUDF = activeUDF;
2778            }
2779    
2780            @Override
2781            public CFMLFactory getCFMLFactory() {
2782                    return config.getFactory();
2783            }
2784    
2785            @Override
2786            public PageContext getParentPageContext() {
2787                    return parent;
2788            }
2789    
2790    
2791            @Override
2792            public String[] getThreadScopeNames() {
2793                    if(threads==null)return new String[0];
2794                    return CollectionUtil.keysAsString(threads);
2795                    //Set ks = threads.keySet();
2796                    //return (String[]) ks.toArray(new String[ks.size()]);
2797            }
2798            
2799            @Override
2800            public Threads getThreadScope(String name) {
2801                    return getThreadScope(KeyImpl.init(name));
2802            }
2803            
2804            public Threads getThreadScope(Collection.Key name) {
2805                    if(threads==null)threads=new StructImpl();
2806                    Object obj = threads.get(name,null);
2807                    if(obj instanceof Threads)return (Threads) obj;
2808                    return null;
2809            }
2810            
2811            public Object getThreadScope(Collection.Key name,Object defaultValue) {
2812                    if(threads==null)threads=new StructImpl();
2813                    if(name.equalsIgnoreCase(KeyConstants._cfthread)) return threads;
2814                    return threads.get(name,defaultValue);
2815            }
2816            
2817            public Object getThreadScope(String name,Object defaultValue) {
2818                    if(threads==null)threads=new StructImpl();
2819                    if(name.equalsIgnoreCase(KeyConstants._cfthread.getLowerString())) return threads;
2820                    return threads.get(KeyImpl.init(name),defaultValue);
2821            }
2822    
2823            @Override
2824            public void setThreadScope(String name,Threads ct) {
2825                    hasFamily=true;
2826                    if(threads==null)       threads=new StructImpl();
2827                    threads.setEL(KeyImpl.init(name), ct);
2828            }
2829            
2830            public void setThreadScope(Collection.Key name,Threads ct) {
2831                    hasFamily=true;
2832                    if(threads==null)       threads=new StructImpl();
2833                    threads.setEL(name, ct);
2834            }
2835    
2836            @Override
2837            public boolean hasFamily() {
2838                    return hasFamily;
2839            }
2840            
2841    
2842            public DatasourceConnection _getConnection(String datasource, String user,String pass) throws PageException {
2843                    return _getConnection(config.getDataSource(datasource),user,pass);
2844            }
2845            
2846            public DatasourceConnection _getConnection(DataSource ds, String user,String pass) throws PageException {
2847                    
2848                    String id=DatasourceConnectionPool.createId(ds,user,pass);
2849                    DatasourceConnection dc=conns.get(id);
2850                    if(dc!=null && DatasourceConnectionPool.isValid(dc,null)){
2851                            return dc;
2852                    }
2853                    dc=config.getDatasourceConnectionPool().getDatasourceConnection(this,ds, user, pass);
2854                    conns.put(id, dc);
2855                    return dc;
2856            }
2857    
2858            @Override
2859            public TimeZone getTimeZone() {
2860                    if(timeZone==null) timeZone=config.getTimeZone();
2861                    return timeZone;
2862            }
2863            @Override
2864            public void  setTimeZone(TimeZone timeZone) {
2865                    this.timeZone=timeZone;
2866            }
2867    
2868    
2869            /**
2870             * @return the requestId
2871             */
2872            public int getRequestId() {
2873                    return requestId;
2874            }
2875    
2876            private Set<String> pagesUsed=new HashSet<String>();
2877    
2878            private Stack<ActiveQuery> activeQueries=new Stack<ActiveQuery>();
2879            private Stack<ActiveLock> activeLocks=new Stack<ActiveLock>();
2880            
2881            
2882    
2883    
2884    
2885            public boolean isTrusted(Page page) {
2886                    if(page==null)return false;
2887                    
2888                    short it = ((MappingImpl)page.getPageSource().getMapping()).getInspectTemplate();
2889                    if(it==ConfigImpl.INSPECT_NEVER)return true;
2890                    if(it==ConfigImpl.INSPECT_ALWAYS)return false;
2891                    
2892                    return pagesUsed.contains(""+page.hashCode());
2893            }
2894            
2895            public void setPageUsed(Page page) {
2896                    pagesUsed.add(""+page.hashCode());
2897            }
2898    
2899            @Override
2900            public void exeLogStart(int position,String id){
2901                    if(execLog!=null)execLog.start(position, id);
2902            }
2903            
2904            @Override
2905            public void exeLogEnd(int position,String id){
2906                    if(execLog!=null)execLog.end(position, id);
2907            }
2908    
2909            
2910            /**
2911             * @param create if set to true, railo creates a session when not exist
2912             * @return
2913             * @throws PageException
2914             */
2915            public ORMSession getORMSession(boolean create) throws PageException {
2916                    if(ormSession==null || !ormSession.isValid())   {
2917                            if(!create) return null;
2918                            ormSession=config.getORMEngine(this).createSession(this);
2919                    }
2920                    DatasourceManagerImpl manager = (DatasourceManagerImpl) getDataSourceManager();
2921                    manager.add(this,ormSession);
2922                    
2923                    return ormSession;
2924                    
2925                    
2926            }
2927    
2928            public ClassLoader getClassLoader() throws IOException {
2929                    return getResourceClassLoader();
2930            }
2931            
2932            public ClassLoader getClassLoader(Resource[] reses) throws IOException{
2933                    return getResourceClassLoader().getCustomResourceClassLoader(reses);
2934            }
2935            
2936            private ResourceClassLoader getResourceClassLoader() throws IOException {
2937                    JavaSettingsImpl js = (JavaSettingsImpl) applicationContext.getJavaSettings();
2938                    if(js!=null) {
2939                            return config.getResourceClassLoader().getCustomResourceClassLoader(js.getResourcesTranslated());
2940                    }
2941                    return config.getResourceClassLoader();
2942            }
2943    
2944            public ClassLoader getRPCClassLoader(boolean reload) throws IOException {
2945                    JavaSettingsImpl js = (JavaSettingsImpl) applicationContext.getJavaSettings();
2946                    if(js!=null) {
2947                            return ((PhysicalClassLoader)config.getRPCClassLoader(reload)).getCustomClassLoader(js.getResourcesTranslated(),reload);
2948                    }
2949                    return config.getRPCClassLoader(reload);
2950            }
2951            
2952            
2953    
2954            public void resetSession() {
2955                    this.session=null;
2956            }
2957            /**
2958             * @return the gatewayContext
2959             */
2960            public boolean isGatewayContext() {
2961                    return gatewayContext;
2962            }
2963    
2964    
2965    
2966            /**
2967             * @param gatewayContext the gatewayContext to set
2968             */
2969            public void setGatewayContext(boolean gatewayContext) {
2970                    this.gatewayContext = gatewayContext;
2971            }
2972    
2973    
2974    
2975            public void setServerPassword(String serverPassword) {
2976                    this.serverPassword=serverPassword;
2977            }
2978            public String getServerPassword() {
2979                    return serverPassword;
2980            }
2981    
2982            public short getSessionType() {
2983                    if(isGatewayContext())return Config.SESSION_TYPE_CFML;
2984                    return applicationContext.getSessionType();
2985            }
2986            
2987            // this is just a wrapper method for ACF
2988            public Scope SymTab_findBuiltinScope(String name) throws PageException {
2989                    return scope(name, null);
2990            }
2991            
2992    // FUTURE add to PageContext
2993            public DataSource getDataSource(String datasource) throws PageException {
2994                    DataSource ds = ((ApplicationContextPro)getApplicationContext()).getDataSource(datasource,null);
2995                    if(ds==null) ds=getConfig().getDataSource(datasource);
2996                    return ds;
2997            }
2998                    
2999    // FUTURE add to PageContext
3000            public DataSource getDataSource(String datasource, DataSource defaultValue) {
3001                    DataSource ds = ((ApplicationContextPro)getApplicationContext()).getDataSource(datasource,null);
3002                    if(ds==null) ds=getConfig().getDataSource(datasource,defaultValue);
3003                    return ds;
3004            }
3005    
3006            public void setActiveQuery(ActiveQuery activeQuery) {
3007                    this.activeQueries.add(activeQuery);
3008            }
3009            
3010            public ActiveQuery[] getActiveQueries() {
3011                    return activeQueries.toArray(new ActiveQuery[activeQueries.size()]);
3012            }
3013    
3014            public ActiveQuery releaseActiveQuery() {
3015                    return activeQueries.pop();
3016            }
3017    
3018            public void setActiveLock(ActiveLock activeLock) {
3019                    this.activeLocks.add(activeLock);
3020            }
3021            
3022            public ActiveLock[] getActiveLocks() {
3023                    return activeLocks.toArray(new ActiveLock[activeLocks.size()]);
3024            }
3025    
3026            public ActiveLock releaseActiveLock() {
3027                    return activeLocks.pop();
3028            }
3029    
3030            public PageException getPageException() {
3031                    return pe;
3032            }
3033    }