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.tag;
020
021import java.io.IOException;
022
023import lucee.runtime.coder.Base64Coder;
024import lucee.runtime.exp.PageException;
025import lucee.runtime.ext.tag.BodyTagImpl;
026import lucee.runtime.listener.ApplicationContext;
027import lucee.runtime.op.Caster;
028import lucee.runtime.security.Credential;
029import lucee.runtime.type.Array;
030import lucee.runtime.type.Collection.Key;
031import lucee.runtime.type.KeyImpl;
032import lucee.runtime.type.Struct;
033import lucee.runtime.type.StructImpl;
034import lucee.runtime.type.util.KeyConstants;
035import lucee.runtime.type.util.ListUtil;
036
037/**
038 * 
039 */
040public final class Login extends BodyTagImpl {
041    
042    private static final Key CFLOGIN = KeyImpl.intern("cflogin");
043        private int idletimeout=1800;
044    private String applicationtoken;
045    private String cookiedomain;
046    
047    @Override
048    public void release() {
049        super.release();
050        idletimeout=1800;
051        applicationtoken=null;
052        cookiedomain=null;
053    }
054    
055    /**
056     * @param applicationtoken The applicationtoken to set.
057     */
058    public void setApplicationtoken(String applicationtoken) {
059        this.applicationtoken = applicationtoken;
060    }
061    /**
062     * @param cookiedomain The cookiedomain to set.
063     */
064    public void setCookiedomain(String cookiedomain) {
065        this.cookiedomain = cookiedomain;
066    }
067    /**
068     * @param idletimeout The idletimout to set.
069     */
070    public void setIdletimeout(double idletimeout) {
071        this.idletimeout = (int) idletimeout;
072    }
073    
074
075    @Override
076    public int doStartTag() throws PageException  {
077        
078        ApplicationContext ac=pageContext.getApplicationContext();
079        ac.setSecuritySettings(applicationtoken,cookiedomain,idletimeout);
080        
081        Credential remoteUser = pageContext.getRemoteUser();
082        if(remoteUser==null) {
083            
084            // Form
085            Object name=pageContext.formScope().get("j_username",null);
086            Object password=pageContext.formScope().get("j_password",null);
087            if(name!=null) {
088                setCFLogin(name,password);
089                return EVAL_BODY_INCLUDE;
090            }
091            // Header
092            String strAuth = pageContext. getHttpServletRequest().getHeader("authorization");
093            if(strAuth!=null) {
094                int pos=strAuth.indexOf(' ');
095                if(pos!=-1) {
096                    String format=strAuth.substring(0,pos).toLowerCase();
097                    if(format.equals("basic")) {
098                        String encoded=strAuth.substring(pos+1);
099                        String dec;
100                        try {
101                                                        dec=Base64Coder.decodeToString(encoded,"UTF-8");
102                                                } catch (IOException e) {
103                                                        throw Caster.toPageException(e);
104                                                }
105                        
106                        //print.ln("encoded:"+encoded);
107                        //print.ln("decoded:"+Base64Util.decodeBase64(encoded));
108                        Array arr=ListUtil.listToArray(dec,":");
109                        if(arr.size()<3) {
110                            if(arr.size()==1) setCFLogin(arr.get(1,null),"");
111                            else setCFLogin(arr.get(1,null),arr.get(2,null));
112                        }
113                    }
114                    
115                }
116            }
117            return EVAL_BODY_INCLUDE;
118        }
119        return SKIP_BODY;
120    }
121    
122    /**
123     * @param username
124     * @param password
125     */
126    private void setCFLogin(Object username, Object password) {
127        if(username==null) return;
128        if(password==null) password="";
129        
130        Struct sct=new StructImpl();
131        sct.setEL(KeyConstants._name,username);
132        sct.setEL(KeyConstants._password,password);
133        pageContext.undefinedScope().setEL(CFLOGIN,sct);
134    }
135
136    @Override
137    public int doEndTag() {
138        pageContext.undefinedScope().removeEL(CFLOGIN);
139        return EVAL_PAGE;
140    }
141
142        public static String getApplicationName(ApplicationContext appContext) {
143                return "cfauthorization_"+appContext.getSecurityApplicationToken();
144        }
145
146        public static String getCookieDomain(ApplicationContext appContext) {
147                return appContext.getSecurityCookieDomain();
148        }
149
150        public static int getIdleTimeout(ApplicationContext appContext) {
151                return appContext.getSecurityIdleTimeout();
152        }
153}