001/**
002 *
003 * Copyright (c) 2014, the Railo Company Ltd. All rights reserved.
004 *
005 * This library is free software; you can redistribute it and/or
006 * modify it under the terms of the GNU Lesser General Public
007 * License as published by the Free Software Foundation; either 
008 * version 2.1 of the License, or (at your option) any later version.
009 * 
010 * This library is distributed in the hope that it will be useful,
011 * but WITHOUT ANY WARRANTY; without even the implied warranty of
012 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
013 * Lesser General Public License for more details.
014 * 
015 * You should have received a copy of the GNU Lesser General Public 
016 * License along with this library.  If not, see <http://www.gnu.org/licenses/>.
017 * 
018 **/
019package lucee.runtime.gateway;
020
021import java.io.IOException;
022import java.util.Iterator;
023import java.util.Map.Entry;
024
025import lucee.commons.lang.ClassException;
026import lucee.commons.lang.ClassUtil;
027import lucee.commons.lang.StringUtil;
028import lucee.runtime.config.Config;
029import lucee.runtime.exp.ApplicationException;
030import lucee.runtime.exp.PageException;
031import lucee.runtime.gateway.proxy.GatewayProFactory;
032import lucee.runtime.op.Caster;
033import lucee.runtime.op.Duplicator;
034import lucee.runtime.type.Collection.Key;
035import lucee.runtime.type.Struct;
036
037public class GatewayEntryImpl implements GatewayEntry {
038
039        private String id;
040        private Struct custom;
041        private boolean readOnly;
042        private String listenerCfcPath;
043        private int startupMode;
044        private GatewayPro gateway;
045        private String cfcPath;
046        private String className;
047        private GatewayEnginePro engine;
048
049        public GatewayEntryImpl(GatewayEnginePro engine,String id, String className, String cfcPath, String listenerCfcPath, String startupMode,Struct custom, boolean readOnly) {
050                this.engine=engine;
051                this.id=id;
052                this.listenerCfcPath=listenerCfcPath;
053                this.className=className;
054                this.custom=custom;
055                this.readOnly=readOnly;
056                this.cfcPath=cfcPath;
057                startupMode=startupMode.trim().toLowerCase();
058                if("manual".equals(startupMode))this.startupMode=STARTUP_MODE_MANUAL;
059                else if("disabled".equals(startupMode))this.startupMode=STARTUP_MODE_DISABLED;
060                else this.startupMode=STARTUP_MODE_AUTOMATIC;
061        }
062        
063
064        /**
065         * @return the gateway
066         * @throws ClassException 
067         * @throws PageException 
068         */
069        public void createGateway(Config config) throws ClassException, PageException {
070                if(gateway==null){
071                        if(!StringUtil.isEmpty(className)){
072                                Class clazz = ClassUtil.loadClass(config.getClassLoader(),className);
073                                
074                                gateway=GatewayProFactory.toGatewayPro(ClassUtil.loadInstance(clazz));
075                        }
076                        else if(!StringUtil.isEmpty(cfcPath)){
077                                gateway=new CFCGateway(cfcPath);
078                        }
079                        else throw new ApplicationException("missing gateway source definitions");
080                        try{
081                                //new GatewayThread(engine,gateway,GatewayThread.START).run();
082                                gateway.init(engine,getId(), getListenerCfcPath(),getCustom());
083                                if(getStartupMode()==GatewayEntry.STARTUP_MODE_AUTOMATIC){
084                                        new GatewayThread(engine,gateway,GatewayThread.START).start();
085                                        /*try{
086                                                //gateway.doStart();
087                                        }
088                                        catch(GatewayException ge){
089                                                engine.log(gateway,GatewayEngine.LOGLEVEL_ERROR, ge.getMessage());
090                                        }*/
091                                }
092                        }
093                        catch(IOException ioe){
094                                throw Caster.toPageException(ioe);
095                        }
096                }
097        }
098        
099        @Override
100        public GatewayPro getGateway() {
101                return gateway;
102        }
103        
104        @Override
105        public String getId() {
106                return id;
107        }
108
109        @Override
110        public Struct getCustom() {
111                return (Struct) Duplicator.duplicate(custom,true);
112        }
113
114        @Override
115        public boolean isReadOnly() {
116                return readOnly;
117        }
118        
119
120        /**
121         * @return the cfcPath
122         */
123        public String getListenerCfcPath() {
124                return listenerCfcPath;
125        }
126        
127        @Override
128        public String getCfcPath() {
129                return cfcPath;
130        }
131
132
133        /**
134         * @return the className
135         */
136        public String getClassName() {
137                return className;
138        }
139
140        /**
141         * @return the startupMode
142         */
143        public int getStartupMode() {
144                return startupMode;
145        }
146
147        public static String toStartup(int mode,String defautValue) {
148                if(mode==STARTUP_MODE_MANUAL) return "manual";
149                else if(mode==STARTUP_MODE_DISABLED) return "disabled";
150                else if(mode==STARTUP_MODE_AUTOMATIC) return "automatic";
151                return defautValue;
152        }
153
154        public static int toStartup(String strMode, int defaultValue) {
155                strMode=strMode.trim().toLowerCase();
156                if("manual".equals(strMode)) return STARTUP_MODE_MANUAL;
157                else if("disabled".equals(strMode)) return STARTUP_MODE_DISABLED;
158                else if("automatic".equals(strMode)) return STARTUP_MODE_AUTOMATIC;
159                return defaultValue;
160        }
161        
162        @Override
163        public boolean equals(Object obj){
164                if(obj==this) return true;
165                if(!(obj instanceof GatewayEntryImpl))return false;
166                
167                GatewayEntryImpl other=(GatewayEntryImpl) obj;
168                if(!other.getId().equals(id)) return false;
169                if(!equal(other.className,className)) return false;
170                if(!equal(other.cfcPath,cfcPath)) return false;
171                if(!equal(other.listenerCfcPath,listenerCfcPath)) return false;
172                if(other.getStartupMode()!=startupMode) return false;
173                
174                Struct otherCustom = other.getCustom();
175                if(otherCustom.size()!=custom.size()) return false;
176                
177                //Key[] keys = otherCustom.keys();
178                Iterator<Entry<Key, Object>> it = otherCustom.entryIterator();
179                Entry<Key, Object> e;
180                Object ot,oc;
181                while(it.hasNext()){
182                        e = it.next();
183                        ot=custom.get(e.getKey(),null);
184                        oc=e.getValue();
185                        if(ot==null) return false;
186                        if(!ot.equals(oc)) return false;
187                }
188                return true;
189        }
190
191
192        private static boolean equal(String left, String right) {
193                if(left==null && right==null) return true;
194                if(left!=null && right!=null) return left.equals(right);
195                return false;
196        }
197}