/*
 * JOnAS: Java(TM) Open Application Server
 * Copyright (C) 1999 Bull S.A.
 * Contact: jonas-team@objectweb.org
 * 
 * This library is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or any later version.
 * 
 * This library is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
 * Lesser General Public License for more details.
 * 
 * You should have received a copy of the GNU Lesser General Public
 * License along with this library; if not, write to the Free Software
 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307
 * USA
 *
 * --------------------------------------------------------------------------
 * $Id$
 * --------------------------------------------------------------------------
 */

package org.objectweb.jonas.jtests.beans.ffolder;

import java.rmi.RemoteException;
import java.sql.Connection;
import java.sql.SQLException;
import javax.ejb.CreateException;
import javax.ejb.EJBException;
import javax.ejb.FinderException;
import javax.ejb.SessionBean;
import javax.ejb.SessionSynchronization;
import javax.ejb.SessionContext;
import javax.naming.Context;
import javax.naming.InitialContext;
import javax.naming.NamingException;
import javax.rmi.PortableRemoteObject;
import javax.sql.DataSource;

/**
 * FolderSY implementation
 * This bean is a stateful session bean that implements SessionSynchronization
 * @author Philippe Durieux, Philippe Coq
 */
public class FolderSY implements SessionBean, SessionSynchronization {

    //    protected static Logger logger = null;
    SessionContext ejbContext;
    InitialContext ictx;
    Context myEnv;
    FileHome filehome;

    /**
     * Check environment variables
     */
    void checkEnv(String method) {

        // Check directly in my context
        //logger.log(BasicLevel.DEBUG, "Check directly in my context");
        try {
            String value = (String) myEnv.lookup("myname");
            if (!value.equals("mysession")) {
                // logger.log(BasicLevel.ERROR, ": myEnv.lookup failed: myname=" + value);
                throw new EJBException("FolderSY 1: " + method);
            }
        } catch (NamingException e) {
            //logger.log(BasicLevel.ERROR, ": myEnv.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY 2: " + method);
        }
        // Idem with compound name
        //logger.log(BasicLevel.DEBUG, "Idem with compound name");
        try {
            String value = (String) myEnv.lookup("dir1/dir2/name");
            if (!value.equals("sessionvalue")) {
                // logger.log(BasicLevel.ERROR, ": myEnv.lookup failed: dir1/dir2/name=" + value);
                throw new EJBException("FolderSY 3: " + method);
            }
        } catch (NamingException e) {
            //logger.log(BasicLevel.ERROR, ": myEnv.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY 4: " + method);
        } 
        // Check from initial Context
        //logger.log(BasicLevel.DEBUG, "Check from initial Context");
        try {
            String value = (String) ictx.lookup("java:comp/env/myname");
            if (!value.equals("mysession")) {
                //logger.log(BasicLevel.ERROR, ": ictx.lookup failed: myname=" + value);
                throw new EJBException("FolderSY 6: " + method);
            }
        } catch (NamingException e) {
            //  logger.log(BasicLevel.ERROR, ": ictx.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY 7: " + method);
        }

        // Check datasource directly
        //logger.log(BasicLevel.DEBUG, "Check datasource directly");
        DataSource ds1 = null;
        try {
            ds1 = (DataSource) PortableRemoteObject.narrow(ictx.lookup("jdbc_1"), DataSource.class);
        } catch (NamingException e) {
            //logger.log(BasicLevel.ERROR, ": ictx.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY 8: " + method);
        }
        Connection con = null;
        if (!method.equals("afterCompletion")) {
            try {
                con = (Connection) ds1.getConnection();
                if (con.isClosed()) {
                    //logger.log(BasicLevel.ERROR, ": connection is closed");
                    throw new EJBException("FolderSY 8a: " + method);
                }
                con.close();
            } catch (SQLException e) {
                //      logger.log(BasicLevel.ERROR, ": getConnection:\n" + e);
                throw new EJBException("FolderSY 8b: " + method);
            }
        }

        // Check DataSource from resource ref in bean environment
        //logger.log(BasicLevel.DEBUG, "Check DataSource from resource ref");
        DataSource ds2 = null;
        try {
            // The name is the one defined in FolderSY.xml
            ds2 = (DataSource) myEnv.lookup("jdbc/mydb");
        } catch (NamingException e) {
            //logger.log(BasicLevel.ERROR, ": ictx.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY 9: " + method);
        }
        if (!method.equals("afterCompletion")) {
            try {
                con = (Connection) ds2.getConnection();
                if (con.isClosed()) {
                    //logger.log(BasicLevel.ERROR, ": connection is closed");
                    throw new EJBException("FolderSY 9a: " + method);
                }
                con.close();
            } catch (SQLException e) {
                // logger.log(BasicLevel.ERROR, ": getConnection:\n" + e);
                throw new EJBException("FolderSY 9b: " + method);
            }
        }

        // Check boolean values
        //logger.log(BasicLevel.DEBUG, "Check boolean values");
        try {
            Boolean value = (Boolean) ictx.lookup("java:comp/env/bVrai");
            if (!value.booleanValue()) {
                //logger.log(BasicLevel.ERROR, ": ictx.lookup failed: bVrai=" + value);
                throw new EJBException("FolderSY 10a: " + method);
            }
        } catch (NamingException e) {
            //logger.log(BasicLevel.ERROR, ": ictx.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY10a: " + method);
        } catch (ClassCastException e) {
            //logger.log(BasicLevel.ERROR, ": ictx.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY10a1: " + method);
        }
        try {
            Boolean value = (Boolean) ictx.lookup("java:comp/env/bFaux");
            if (value.booleanValue()) {
                // logger.log(BasicLevel.ERROR, ": ictx.lookup failed: bFaux=" + value);
                throw new EJBException("FolderSY 10b: " + method);
            }
        } catch (NamingException e) {
            //logger.log(BasicLevel.ERROR, ": ictx.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY10b: " + method);
        } catch (ClassCastException e) {
            //logger.log(BasicLevel.ERROR, ": ictx.lookup raised exception:\n" + e);
            throw new EJBException("FolderSY10b1: " + method);
        }

        //logger.log(BasicLevel.DEBUG, ": checkEnv OK");
    }

    // ------------------------------------------------------------------
    // SessionBean implementation
    // ------------------------------------------------------------------

    public void setSessionContext(SessionContext ctx) { 
        // if (logger == null) {
        //  logger = Log.getLogger(Log.JONAS_TESTS_PREFIX);
        //}
        //logger.log(BasicLevel.DEBUG, "");
        ejbContext = ctx;
        try {
            // Get initial Context
            ictx = new InitialContext();
            myEnv = (Context) ictx.lookup("java:comp/env");
            // lookup filehome in JNDI
            filehome = (FileHome) ictx.lookup("java:comp/env/ejb/file");
        } catch (NamingException e) {
            throw new EJBException("FolderSY: Cannot get filehome:" + e);
        }
        checkEnv("setSessionContext");
    }

    public void ejbRemove() {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("ejbRemove");
    }
    public void ejbCreate() throws CreateException {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("ejbCreate");
    }
    public void ejbPassivate() {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("ejbPassivate");
    }
    public void ejbActivate() {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("ejbActivate");
    }

    // ------------------------------------------------------------------
    // SessionSynchronization implementation
    // ------------------------------------------------------------------

    public void afterBegin() {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("afterBegin");
    }
    public void beforeCompletion() {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("beforeCompletion");
    }
    public void afterCompletion(boolean committed) {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("afterCompletion");
    }

    // ------------------------------------------------------------------
    // Folder implementation
    // ------------------------------------------------------------------

    public File newFile(String fname) throws RemoteException, CreateException {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("newFile");
        File ret = filehome.create(fname);
        return ret;
    }

    public File getFile(String fname) throws RemoteException, FinderException {
        //logger.log(BasicLevel.DEBUG, "");
        checkEnv("getFile");
        File ret = filehome.findByPrimaryKey(fname);
        return ret;
    }

    public void sendRef(Folder f) throws RemoteException {
    }

    public void sendInt(int i) throws RemoteException {
    }

    public void sendRefTS(Folder f) throws RemoteException {
    }

    public void sendIntTS(int i) throws RemoteException {
    }

    public Folder getRef(Folder f) throws RemoteException {
        return f;
    }

    public int getInt(int i) throws RemoteException {
        return i;
    }

    public Folder getRefTS(Folder f) throws RemoteException {
        return f;
    }

    public int getIntTS(int i) throws RemoteException {
        return i;
    }
}
