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.type.scope;
020
021
022import java.util.ArrayList;
023import java.util.Enumeration;
024import java.util.Iterator;
025import java.util.List;
026
027import javax.servlet.http.HttpServletRequest;
028
029import lucee.runtime.PageContext;
030import lucee.runtime.config.NullSupportHelper;
031import lucee.runtime.dump.DumpData;
032import lucee.runtime.dump.DumpProperties;
033import lucee.runtime.exp.ExpressionException;
034import lucee.runtime.exp.PageException;
035import lucee.runtime.type.Collection;
036import lucee.runtime.type.KeyImpl;
037import lucee.runtime.type.Struct;
038import lucee.runtime.type.StructImpl;
039import lucee.runtime.type.it.EntryIterator;
040import lucee.runtime.type.util.StructSupport;
041
042public final class RequestImpl extends StructSupport implements Request {
043
044        
045        private HttpServletRequest _req;
046        private boolean init;
047        private static int _id=0;
048        private int id=0;
049
050        public RequestImpl() {
051        id=++_id;
052                //super("request",SCOPE_REQUEST,Struct.TYPE_REGULAR);
053                
054        }
055        
056    /**
057     * @return Returns the id.
058     */
059    public int _getId() {
060        return id;
061    }
062
063        public void initialize(PageContext pc) {
064                _req = pc.getHttpServletRequest();//HTTPServletRequestWrap.pure(pc.getHttpServletRequest());
065                init=true;
066                
067        }
068
069        @Override
070        public boolean isInitalized() {
071                return init;
072        }
073
074        @Override
075        public void release() {
076                init = false;
077        }
078
079        @Override
080        public void release(PageContext pc) {
081                init = false;
082        }
083
084        @Override
085        public int getType() {
086                return SCOPE_REQUEST;
087        }
088
089        @Override
090        public String getTypeAsString() {
091                return "request";
092        }
093
094        @Override
095        public int size() {
096                int size=0;
097                synchronized (_req) {
098                        Enumeration<String> names = _req.getAttributeNames();
099                        while(names.hasMoreElements()){
100                                names.nextElement();
101                                size++;
102                        }
103                }
104                return size;
105        }
106        
107        @Override
108        public Iterator<Collection.Key> keyIterator() {
109                return keyList().iterator();
110        }
111        
112        
113
114        private List<Key> keyList() {
115                synchronized (_req) {
116                        Enumeration<String> names = _req.getAttributeNames();
117                        List<Key> list=new ArrayList<Key>();
118                        while(names.hasMoreElements()){
119                                list.add(KeyImpl.getInstance(names.nextElement()));
120                        }
121                        return list;
122                }
123        }
124        
125        @Override
126        public Iterator<Entry<Key, Object>> entryIterator() {
127                return new EntryIterator(this,keys());
128        }
129        
130        @Override
131        public Iterator<Object> valueIterator() {
132                synchronized (_req) {
133                        Enumeration<String> names = _req.getAttributeNames();
134                        List<Object> list=new ArrayList<Object>();
135                        while(names.hasMoreElements()){
136                                list.add(_req.getAttribute(names.nextElement()));
137                        }
138                        return list.iterator();
139                }
140        }
141        
142        
143        @Override
144        public Key[] keys() {
145                List<Key> list = keyList();
146                return list.toArray(new Key[list.size()]);
147        }
148
149        @Override
150        public Object remove(Key key) throws PageException {
151                Object value = remove(key,NullSupportHelper.NULL());
152                if(value!=NullSupportHelper.NULL())return value;
153                throw new ExpressionException("can't remove key ["+key+"] from struct, key doesn't exist");
154        }
155
156        @Override
157        public void clear() {
158                synchronized (_req) {
159                        Enumeration<String> names = _req.getAttributeNames();
160                        while(names.hasMoreElements()){
161                                _req.removeAttribute(names.nextElement());
162                        }
163                }
164        }
165
166        public Object get(Key key) throws PageException {
167                Object value = get(key,NullSupportHelper.NULL());
168                if(value==NullSupportHelper.NULL()) throw invalidKey(null,this,key);
169                return value;
170        }
171        
172
173
174        public Object removeEL(Key key) {
175                return remove(key,null);
176        }
177
178        private Object remove(Key key, Object defaultValue) {
179                synchronized (_req) {
180                        Object value = _req.getAttribute(key.getLowerString()); 
181                        if(value!=null) {
182                                _req.removeAttribute(key.getLowerString());
183                                return value;
184                        }
185                        
186                        value=defaultValue;
187                        Enumeration<String> names = _req.getAttributeNames();
188                        String k;
189                        while(names.hasMoreElements()){
190                                k=names.nextElement();
191                                if(k.equalsIgnoreCase(key.getString())) {
192                                        value= _req.getAttribute(k);
193                                        _req.removeAttribute(k);
194                                        return value;
195                                }
196                        }
197                        return defaultValue;
198                }
199        }
200        
201        @Override
202        public Object get(Key key, Object defaultValue) {
203                synchronized (_req) {
204                        Object value = _req.getAttribute(key.getLowerString()); 
205                        if(value!=null) return value;
206                        
207                        Enumeration<String> names = _req.getAttributeNames();
208                        Collection.Key k;
209                        while(names.hasMoreElements()){
210                                k=KeyImpl.init(names.nextElement());
211                                if(key.equals(k)) return _req.getAttribute(k.getString());
212                        }
213                        return defaultValue;
214                }
215        }
216
217        @Override
218        public Object setEL(Key key, Object value) {
219                synchronized (_req) {
220                        _req.setAttribute(key.getLowerString(), value);
221                }
222                return value;
223        }
224
225        @Override
226        public Object set(Key key, Object value) throws PageException {
227                return setEL(key, value);
228        }
229
230        @Override
231        public Collection duplicate(boolean deepCopy) {
232                Struct trg=new StructImpl();
233                StructImpl.copy(this, trg,deepCopy);
234                return trg;
235        }
236
237        @Override
238        public boolean containsKey(Key key) {
239                return get(key,NullSupportHelper.NULL())!=NullSupportHelper.NULL();
240        }
241        
242        public DumpData toDumpData(PageContext pageContext, int maxlevel, DumpProperties dp) {
243                return ScopeSupport.toDumpData(pageContext, maxlevel, dp, this, getTypeAsString());
244        }
245}