Package org.infoglue.cms.controllers.kernel.impl.simple

Source Code of org.infoglue.cms.controllers.kernel.impl.simple.BaseController

/* ===============================================================================
*
* Part of the InfoGlue Content Management Platform (www.infoglue.org)
*
* ===============================================================================
*
*  Copyright (C)
*
* This program is free software; you can redistribute it and/or modify it under
* the terms of the GNU General Public License version 2, as published by the
* Free Software Foundation. See the file LICENSE.html for more information.
*
* This program is distributed in the hope that it will be useful, but WITHOUT
* ANY WARRANTY, including the implied warranty of MERCHANTABILITY or FITNESS
* FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details.
*
* You should have received a copy of the GNU General Public License along with
* this program; if not, write to the Free Software Foundation, Inc. / 59 Temple
* Place, Suite 330 / Boston, MA 02111-1307 / USA.
*
* ===============================================================================
*/

package org.infoglue.cms.controllers.kernel.impl.simple;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Collections;
import java.util.Enumeration;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Locale;
import java.util.Map;

import org.apache.log4j.Category;
import org.apache.log4j.Logger;
import org.exolab.castor.jdo.Database;
import org.exolab.castor.jdo.LockNotGrantedException;
import org.exolab.castor.jdo.OQLQuery;
import org.exolab.castor.jdo.ObjectNotFoundException;
import org.exolab.castor.jdo.PersistenceException;
import org.exolab.castor.jdo.QueryResults;
import org.exolab.castor.jdo.TransactionAbortedException;
import org.infoglue.cms.entities.kernel.BaseEntityVO;
import org.infoglue.cms.entities.kernel.IBaseEntity;
import org.infoglue.cms.entities.kernel.ValidatableEntityVO;
import org.infoglue.cms.entities.management.InterceptionPointVO;
import org.infoglue.cms.entities.management.InterceptorVO;
import org.infoglue.cms.entities.management.TableCount;
import org.infoglue.cms.exception.Bug;
import org.infoglue.cms.exception.ConfigurationError;
import org.infoglue.cms.exception.ConstraintException;
import org.infoglue.cms.exception.SystemException;
import org.infoglue.cms.security.InfoGluePrincipal;
import org.infoglue.cms.security.interceptors.InfoGlueInterceptor;
import org.infoglue.cms.services.InterceptionService;
import org.infoglue.cms.util.CmsPropertyHandler;
import org.infoglue.cms.util.ConstraintExceptionBuffer;
import org.infoglue.cms.util.StringManager;
import org.infoglue.cms.util.StringManagerFactory;
import org.infoglue.cms.util.validators.Constants;
import org.infoglue.cms.util.validators.ConstraintRule;
import org.infoglue.cms.util.validators.EmailValidator;
import org.infoglue.cms.util.validators.StringValidator;
import org.infoglue.deliver.util.CacheController;
import org.infoglue.deliver.util.RequestAnalyser;

import com.opensymphony.module.propertyset.PropertySet;
import com.opensymphony.module.propertyset.PropertySetManager;

/**
* BaseController.java
* Created on 2002-aug-28
* @author Stefan Sik, ss@frovi.com
* @author Mattias Bogeblad, mattias.bogeblad@sprawlsolutions.se
*
* Baseclass for ControllerClasses.
* Various methods to load, create and delete entities
*
* TODO:
* Now that all entities implements BaseEntity clear all reflection and simplify
* arguments...
*
* -matbog 2002-09-15: Added and modified new read-only methods for fetching a VO-object.
*              These method must be called instead of the old ones when just fetching a entity
*              or all entities from a table.
*/

public abstract class BaseController
{
    private final static Logger logger = Logger.getLogger(BaseController.class.getName());

    /**
     * Gets a logger for the action class.
     */
/*
  protected Logger logger
  {
      return Logger.getLogger(this.getClass().getName());
  }
*/
    /**
     * This method is called by the controllers to let interceptors listen to events.
     *
     * @param hashMap
     * @param InterceptionPointName
     * @param infogluePrincipal
     * @throws ConstraintException
     * @throws SystemException
     * @throws Bug
     * @throws Exception
     */
    protected void intercept(Map hashMap, String InterceptionPointName, InfoGluePrincipal infogluePrincipal) throws ConstraintException, SystemException, Bug, Exception
  {
      intercept(hashMap, InterceptionPointName, infogluePrincipal, true, false);
  }

    protected void intercept(Map hashMap, String InterceptionPointName, InfoGluePrincipal infogluePrincipal, boolean allowCreatorAccess, boolean ignoreMissingInterceptionPoint) throws ConstraintException, SystemException, Bug, Exception
  {
    InterceptionPointVO interceptionPointVO = InterceptionPointController.getController().getInterceptionPointVOWithName(InterceptionPointName);
     
    if(interceptionPointVO == null)
    {
      if(ignoreMissingInterceptionPoint)
        return;
      else
        throw new SystemException("The InterceptionPoint " + InterceptionPointName + " was not found. The system will not work unless you restore it.");
    }
   
    List interceptors = InterceptorController.getController().getInterceptorsVOList(interceptionPointVO.getInterceptionPointId());
    Iterator interceptorsIterator = interceptors.iterator();
    while(interceptorsIterator.hasNext())
    {
      InterceptorVO interceptorVO = (InterceptorVO)interceptorsIterator.next();
      logger.info("Adding interceptorVO:" + interceptorVO.getName());
      try
      {
        InfoGlueInterceptor infoGlueInterceptor = (InfoGlueInterceptor)Class.forName(interceptorVO.getClassName()).newInstance();
        infoGlueInterceptor.setInterceptorVO(interceptorVO);
        infoGlueInterceptor.intercept(infogluePrincipal, interceptionPointVO, hashMap, allowCreatorAccess);
      }
      catch(ClassNotFoundException e)
      {
        logger.warn("The interceptor " + interceptorVO.getClassName() + "was not found: " + e.getMessage(), e);
      }
    }
  }
   
    Map<String,InfoGlueInterceptor> cachedInterceptors = new HashMap<String,InfoGlueInterceptor>();
    protected void intercept(Map hashMap, String InterceptionPointName, InfoGluePrincipal infogluePrincipal, boolean allowCreatorAccess) throws ConstraintException, SystemException, Bug, Exception
  {
    InterceptionPointVO interceptionPointVO = InterceptionPointController.getController().getInterceptionPointVOWithName(InterceptionPointName);
     
    if(interceptionPointVO == null)
      throw new SystemException("The InterceptionPoint " + InterceptionPointName + " was not found. The system will not work unless you restore it.");

    List interceptors = InterceptionPointController.getController().getInterceptorsVOList(interceptionPointVO.getInterceptionPointId());
   
    Iterator interceptorsIterator = interceptors.iterator();
    while(interceptorsIterator.hasNext())
    {
      InterceptorVO interceptorVO = (InterceptorVO)interceptorsIterator.next();
      logger.info("Adding interceptorVO:" + interceptorVO.getName());
      try
      {
        InfoGlueInterceptor infoGlueInterceptor = cachedInterceptors.get(interceptorVO.getClassName());
        if(infoGlueInterceptor == null)
        {
          infoGlueInterceptor = (InfoGlueInterceptor)Class.forName(interceptorVO.getClassName()).newInstance();
          infoGlueInterceptor.setInterceptorVO(interceptorVO);
          cachedInterceptors.put(interceptorVO.getClassName(), infoGlueInterceptor);
        }
        infoGlueInterceptor.intercept(infogluePrincipal, interceptionPointVO, hashMap, allowCreatorAccess);
      }
      catch(ClassNotFoundException e)
      {
        logger.warn("The interceptor " + interceptorVO.getClassName() + "was not found: " + e.getMessage(), e);
      }
    }

  }

   
    /**
     * This method is called by the controllers to let interceptors listen to events.
     *
     * @param hashMap
     * @param InterceptionPointName
     * @param infogluePrincipal
     * @throws ConstraintException
     * @throws SystemException
     * @throws Bug
     * @throws Exception
     */

    protected void intercept(Map hashMap, String InterceptionPointName, InfoGluePrincipal infogluePrincipal, Database db) throws ConstraintException, SystemException, Bug, Exception
  {
    InterceptionPointVO interceptionPointVO = InterceptionPointController.getController().getInterceptionPointVOWithName(InterceptionPointName, db);
     
    if(interceptionPointVO == null)
      throw new SystemException("The InterceptionPoint " + InterceptionPointName + " was not found. The system will not work unless you restore it.");

    List interceptors = InterceptionPointController.getController().getInterceptorsVOList(interceptionPointVO.getInterceptionPointId(), db);
    Iterator interceptorsIterator = interceptors.iterator();
    while(interceptorsIterator.hasNext())
    {
      InterceptorVO interceptorVO = (InterceptorVO)interceptorsIterator.next();
      logger.info("Adding interceptorVO:" + interceptorVO.getName());
      try
      {
        InfoGlueInterceptor infoGlueInterceptor = cachedInterceptors.get(interceptorVO.getClassName());
        if(infoGlueInterceptor == null)
        {
          infoGlueInterceptor = (InfoGlueInterceptor)Class.forName(interceptorVO.getClassName()).newInstance();
          infoGlueInterceptor.setInterceptorVO(interceptorVO);
          cachedInterceptors.put(interceptorVO.getClassName(), infoGlueInterceptor);
        }
        //InfoGlueInterceptor infoGlueInterceptor = (InfoGlueInterceptor)Class.forName(interceptorVO.getClassName()).newInstance();
        infoGlueInterceptor.intercept(infogluePrincipal, interceptionPointVO, hashMap, db);
      }
      catch(ClassNotFoundException e)
      {
        logger.warn("The interceptor " + interceptorVO.getClassName() + "was not found: " + e.getMessage(), e);
      }
    }

  }

    protected void intercept(Map hashMap, String InterceptionPointName, InfoGluePrincipal infogluePrincipal, boolean allowCreatorAccess, Database db) throws ConstraintException, SystemException, Bug, Exception
  {
    InterceptionPointVO interceptionPointVO = InterceptionPointController.getController().getInterceptionPointVOWithName(InterceptionPointName, db);
     
    if(interceptionPointVO == null)
      throw new SystemException("The InterceptionPoint " + InterceptionPointName + " was not found. The system will not work unless you restore it.");

    List interceptors = InterceptionPointController.getController().getInterceptorsVOList(interceptionPointVO.getInterceptionPointId(), db);
    Iterator interceptorsIterator = interceptors.iterator();
    while(interceptorsIterator.hasNext())
    {
      InterceptorVO interceptorVO = (InterceptorVO)interceptorsIterator.next();
      logger.info("Adding interceptorVO:" + interceptorVO.getName());
      try
      {
        InfoGlueInterceptor infoGlueInterceptor = cachedInterceptors.get(interceptorVO.getClassName());
        if(infoGlueInterceptor == null)
        {
          infoGlueInterceptor = (InfoGlueInterceptor)Class.forName(interceptorVO.getClassName()).newInstance();
          infoGlueInterceptor.setInterceptorVO(interceptorVO);
          cachedInterceptors.put(interceptorVO.getClassName(), infoGlueInterceptor);
        }
        //InfoGlueInterceptor infoGlueInterceptor = (InfoGlueInterceptor)Class.forName(interceptorVO.getClassName()).newInstance();
        infoGlueInterceptor.intercept(infogluePrincipal, interceptionPointVO, hashMap, allowCreatorAccess, db);
      }
      catch(ClassNotFoundException e)
      {
        logger.warn("The interceptor " + interceptorVO.getClassName() + "was not found: " + e.getMessage(), e);
      }
    }

  }

 
  private static Integer getEntityId(Object entity) throws Bug
  {
    Integer entityId = new Integer(-1);
   
    try
    {
      entityId = ((IBaseEntity) entity).getId();
    }
    catch (Exception e)
    {
      e.printStackTrace();
      throw new Bug("Unable to retrieve object id");
    }
   
    /*
    try {
      entityId = (Integer) entity.getClass().getDeclaredMethod("getId", new Class[0]).invoke(entity, new Object[0]);
    } catch (IllegalAccessException e) {
    } catch (InvocationTargetException e) {
    } catch (NoSuchMethodException e) {
    }

    */   
    return entityId;
  }

  /***************************************************
   * Create, Delete & Update operations
   ***************************************************/

  // Create entity
  // The validation belongs here
    protected static Object createEntity(Object entity) throws SystemException, Bug
    {
        Database db = CastorDatabaseService.getDatabase();
        beginTransaction(db);

        try
        {
            db.create(entity);
            commitTransaction(db);
            //CmsSystem.log(entity,"Created object", CmsSystem.DBG_NORMAL);
      //CmsSystem.transactionLogEntry(entity.getClass().getName(), CmsSystem.TRANS_CREATE, getEntityId(entity), entity.toString());
           
        }
        catch(ObjectNotFoundException e)
        {
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }
        catch(Exception e)
        {
            logger.error("An error occurred so we should not complete the transaction: " + e.getMessage());
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            //CmsSystem.log(entity,"Failed to create object", CmsSystem.DBG_LOW);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }
        return entity;
    }    


  // Create entity inside an existing transaction
    protected static Object createEntity(Object entity, Database db) throws SystemException, Bug, Exception
    {
        db.create(entity);
        return entity;
    }    

  // Delete entity
    public static void deleteEntity(Class entClass, Integer id) throws Bug, SystemException
    {
        Database db = CastorDatabaseService.getDatabase();
        Object entity = null;

        beginTransaction(db);

        try
        {
            entity = getObjectWithId(entClass, id, db);
           
            // Delete the entity
            db.remove(entity);
            commitTransaction(db);
            //CmsSystem.log(entity,"Deleted object", CmsSystem.DBG_NORMAL);          
      //CmsSystem.transactionLogEntry(entClass.getName(), CmsSystem.TRANS_DELETE, id, entity.toString());           
        }
        catch(ObjectNotFoundException e)
        {
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }
        catch(Exception e)
        {
            logger.error("An error occurred so we should not complete the transaction: " + e.getMessage());
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }
    }       


  // Delete entity
  public static void deleteEntity(Class entClass, String id) throws Bug, SystemException
  {
    Database db = CastorDatabaseService.getDatabase();
    Object entity = null;

    beginTransaction(db);

    try
    {
      entity = getObjectWithId(entClass, id, db);
           
      // Delete the entity
      db.remove(entity);
      commitTransaction(db);
      //CmsSystem.log(entity,"Deleted object", CmsSystem.DBG_NORMAL);          
      //CmsSystem.transactionLogEntry(entClass.getName(), CmsSystem.TRANS_DELETE, id, entity.toString());           
    }
        catch(ObjectNotFoundException e)
        {
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }
    catch(Exception e)
    {
            logger.error("An error occurred so we should not complete the transaction:" + e.getMessage());
            logger.warn("An error occurred so we should not complete the transaction:" + e.getMessage(), e);
      rollbackTransaction(db);
      throw new SystemException(e.getMessage());
    }
  }   


  // Delete entity
  public static void deleteEntity(Class entClass, String id, Database db) throws Bug, SystemException, Exception
  {
    Object entity = getObjectWithId(entClass, id, db);
    // Delete the entity
    db.remove(entity);
  }   

 
  // Delete entity
    public static void deleteEntity(Class entClass, Integer id, Database db) throws Bug, SystemException
    {
        Object entity = null;

        try
        {
            entity = getObjectWithId(entClass, id, db);
            // Delete the entity
            db.remove(entity);
        }
        catch(ObjectNotFoundException e)
        {
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }
        catch(Exception e)
        {
            logger.error("An error occurred so we should not complete the transaction:" + e.getMessage());
            logger.warn("An error occurred so we should not complete the transaction:" + e.getMessage(), e);
            throw new SystemException(e.getMessage());
        }
    }       


    public static BaseEntityVO updateEntity(Class arg, BaseEntityVO vo) throws Bug, SystemException
    {
        Database db = CastorDatabaseService.getDatabase();

        IBaseEntity entity = null;

        beginTransaction(db);

        try
        {
            entity = (IBaseEntity) getObjectWithId(arg, vo.getId(), db);
            entity.setVO(vo);

            commitTransaction(db);
        }
        catch(Exception e)
        {
            logger.error("An error occurred so we should not complete the transaction: " + e.getMessage());
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }

        return entity.getVO();
    }       

   
  public static BaseEntityVO updateEntity(Class arg, BaseEntityVO vo, Database db) throws Bug, SystemException
  {
    IBaseEntity entity = null;

    entity = (IBaseEntity) getObjectWithId(arg, vo.getId(), db);
    entity.setVO(vo);

    return entity.getVO();
  }       

 
  /* Update entity and a collection with other entities
   * Experimental, use with caution
   *
   */
    public static BaseEntityVO updateEntity(Class entClass, BaseEntityVO vo, String collectionMethod, Class manyClass, String[] manyIds) throws ConstraintException, SystemException
    {
        Database db = CastorDatabaseService.getDatabase();
        ConstraintExceptionBuffer ceb = new ConstraintExceptionBuffer();

        IBaseEntity entity = null;

        beginTransaction(db);

        try
        {
            //add validation here if needed
            List manyList = new ArrayList();
            if(manyIds != null)
      {
            for (int i=0; i < manyIds.length; i++)
              {
                IBaseEntity manyEntity = (IBaseEntity) getObjectWithId(manyClass, new Integer(manyIds[i]), db);
                logger.info("!!Using experimental code: BaseController::update. getting " + manyEntity.toString());
                manyList.add(manyEntity);
              }
      }
     
   
            entity = (IBaseEntity) getObjectWithId(entClass, vo.getId(), db);
            entity.setVO(vo);
           
            // Now reflect to set the collection
            Object[] arg = {manyList};
            Class[] parm = {Collection.class};
            entity.getClass().getDeclaredMethod(collectionMethod, parm).invoke(entity, arg);
           
      // DONE
     
            //If any of the validations or setMethods reported an error, we throw them up now before create.
            ceb.throwIfNotEmpty();
           
            commitTransaction(db);
            //CmsSystem.transactionLogEntry(entity.getClass().getName(), CmsSystem.TRANS_UPDATE, vo.getId(), entity.toString());

        }
        catch(ConstraintException ce)
        {
            logger.warn("An error occurred so we should not complete the transaction:" + ce.getMessage(), ce);
            rollbackTransaction(db);
            throw ce;
        }
        catch(Exception e)
        {
            logger.error("An error occurred so we should not complete the transaction:" + e.getMessage());
            logger.warn("An error occurred so we should not complete the transaction:" + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }

        return entity.getVO();
    }       

  /*
   * Update entity and a collection with other entities
   * Experimental, use with caution
   */
    public static IBaseEntity updateEntity(Class entClass, BaseEntityVO vo, String collectionMethod, Class manyClass, String[] manyIds, Database db) throws ConstraintException, SystemException, Exception
    {
        IBaseEntity entity = null;

        List manyList = new ArrayList();
        if(manyIds != null)
    {
          for (int i=0; i < manyIds.length; i++)
            {
              IBaseEntity manyEntity = (IBaseEntity) getObjectWithId(manyClass, new Integer(manyIds[i]), db);
              logger.info("!!Using experimental code: BaseController::update. getting " + manyEntity.toString());
              manyList.add(manyEntity);
            }
    }
   
        entity = (IBaseEntity) getObjectWithId(entClass, vo.getId(), db);
        entity.setVO(vo);
       
        // Now reflect to set the collection
        Object[] arg = {manyList};
        Class[] parm = {Collection.class};
        entity.getClass().getDeclaredMethod(collectionMethod, parm).invoke(entity, arg);
           
        return entity;
    }       


  /*
  protected static Object getObjectWithId(Class arg, Integer id) throws SystemException, Bug
  {
    Database db = CastorDatabaseService.getDatabase();   
    Object ret = null;
    try
    {
      beginTransaction(db);
      ret = getObjectWithId(arg, id, db);
      commitTransaction(db);
    }
    catch (Exception e)
    {
      rollbackTransaction(db);
            throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
    }
    return ret;
  }
  */

  /**
   * This method fetches one object / entity within a transaction.
   **/
 
    protected static Object getObjectWithId(Class arg, Integer id, Database db) throws SystemException, Bug
    {
        Object object = null;
        try
        {
            if(logger.isInfoEnabled())
              logger.info("Loading " + arg + " in read/write mode.");
            object = db.load(arg, id);
        }
        catch(Exception e)
        {
            throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
        }
   
        if(object == null)
        {
            throw new Bug("The object with id [" + id + "] was not found. This should never happen.");
        }
      return object;
    }


  /**
   * This method fetches one object / entity within a transaction.
   **/
 
    protected static Object getObjectWithIdAsReadOnly(Class arg, Integer id, Database db) throws SystemException, Bug
    {
        Object object = null;
        try
        {
      RequestAnalyser.getRequestAnalyser().incApproximateNumberOfDatabaseQueries();
            object = db.load(arg, id, Database.READONLY);         
        }
        catch(Exception e)
        {
      logger.warn("Error getting object. Message: " + e.getMessage() + ". No retrying again.");
      throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
        }
    finally
    {
      RequestAnalyser.getRequestAnalyser().decApproximateNumberOfDatabaseQueries();
    }
   
        if(object == null)
        {
            throw new Bug("The object with id [" + id + "] was not found. This should never happen.");
        }
      return object;
    }

  /**
   * This method fetches one object / entity within a transaction.
   **/
 
  protected static Object getObjectWithId(Class arg, String id, Database db) throws SystemException, Bug
  {
    Object object = null;
    try
    {
            logger.info("Loading " + arg + " in read/write mode.");

            object = db.load(arg, id);
    }
    catch(Exception e)
    {
      throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
    }
   
    if(object == null)
    {
      throw new Bug("The object with id [" + id + "] was not found. This should never happen.");
    }
    return object;
  }

     
    /**
   * This method converts a List of entities to a list of value-objects.
   */
 
  public static List toVOList(Collection baseEntities) throws SystemException, Bug
    {
    List resultVOList = new ArrayList();
   
        if(baseEntities != null)
      {
      Object o = null;
        try
      {
        Iterator iterator = baseEntities.iterator();
        while (iterator.hasNext())
            {
          o = (Object)iterator.next();
          // Om metoden getValueObject saknas, kastas ett undantag.             
                  resultVOList.add(o.getClass().getDeclaredMethod("getValueObject", new Class[0]).invoke(o, new Object[0]));
            }
        }
        catch(NoSuchMethodException e)
          {
              throw new Bug("The object in list was of the wrong type: " + o.getClass().getName() + ". This should never happen.", e);
          }
          catch(Exception e)
          {
              throw new SystemException("An error occurred when we tried to convert the collection to a valueList. Reason:" + e.getMessage(), e);   
          }   
    }
       
        return resultVOList;
    }

    /**
   * This method converts a List of entities to a list of value-objects.
   */
 
  public static List toModifiableVOList(Collection baseEntities) throws SystemException, Bug
    {
    List resultVOList = new ArrayList();
   
        if(baseEntities != null)
      {
      Object o = null;
        try
      {
        Iterator iterator = baseEntities.iterator();
        while (iterator.hasNext())
            {
          o = (Object)iterator.next();
          // Om metoden getValueObject saknas, kastas ett undantag.             
                  resultVOList.add(o.getClass().getDeclaredMethod("getValueObject", new Class[0]).invoke(o, new Object[0]));
            }
        }
        catch(NoSuchMethodException e)
          {
              throw new Bug("The object in list was of the wrong type: " + o.getClass().getName() + ". This should never happen.", e);
          }
          catch(Exception e)
          {
              throw new SystemException("An error occurred when we tried to convert the collection to a valueList. Reason:" + e.getMessage(), e);   
          }   
    }
       
        return resultVOList;
    }

  /***************************************************
   * Read only operations
   ***************************************************/

  /**
   * This method is used to fetch a ValueObject from the database.
   */

  public static Object getVOWithId(Class arg, Integer id) throws SystemException, Bug
  {
    Database db = CastorDatabaseService.getDatabase();   
    Object ret = null;
    try
    {
      beginTransaction(db);
      ret = getVOWithId(arg, id, db);
      commitTransaction(db);
    }
    catch (Exception e)
    {
      rollbackTransaction(db);
            throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
    }
    return ret;
  }

  /**
   * This method fetches one object in read only mode and returns it's value object.
   */
 
    public static BaseEntityVO getVOWithId(Class arg, Integer id, Database db) throws SystemException, Bug
    {
        IBaseEntity vo = null;
        try
        {
        vo = (IBaseEntity)db.load(arg, id, Database.READONLY);
        }
        catch(Exception e)
        {
            throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
        }
   
        if(vo == null)
        {
            throw new Bug("The object with id [" + id + "] was not found. This should never happen.");
        }
       
      return vo.getVO();
    }
   
   
  /**
   * This method is used to fetch a ValueObject from the database.
   */

  public static Object getVOWithId(Class arg, String id) throws SystemException, Bug
  {
    Database db = CastorDatabaseService.getDatabase();   
    Object ret = null;
    try
    {
      beginTransaction(db);
      ret = getVOWithId(arg, id, db);
      commitTransaction(db);
    }
    catch (Exception e)
    {
      rollbackTransaction(db);
      throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
    }
    return ret;
  }
 
  /**
   * This method fetches one object in read only mode and returns it's value object.
   */
 
  public static BaseEntityVO getVOWithId(Class arg, String id, Database db) throws SystemException, Bug
  {
    IBaseEntity vo = null;
    try
    {
      vo = (IBaseEntity)db.load(arg, id, Database.READONLY);
    }
    catch(Exception e)
    {
      throw new SystemException("An error occurred when we tried to fetch the object " + arg.getName() + ". Reason:" + e.getMessage(), e);   
    }
   
    if(vo == null)
    {
      throw new Bug("The object with id [" + id + "] was not found. This should never happen.");
    }
       
    return vo.getVO();
  }


  /**
   * This method fetches all object in read only mode and returns a list of value objects.
   */
    /*
    public static List getAllVOObjects(Class arg) throws SystemException, Bug
    {
    Database db = CastorDatabaseService.getDatabase();
    List ret = null;
        try
        {
      beginTransaction(db);
      ret = getAllVOObjects(arg, db);
      commitTransaction(db);
        }
        catch(Exception e)
        {
      rollbackTransaction(db);
            throw new SystemException("An error occurred when we tried to fetch " + arg.getName() + " Reason:" + e.getMessage(), e);   
        }   
        return ret;
    }
    */
   
  /**
   * This method fetches all object in read only mode and returns a list of value objects.
   */
   
  public static List getAllVOObjects(Class arg, String orderByAttribute, String direction) throws SystemException, Bug
  {
    Database db = CastorDatabaseService.getDatabase();
    List ret = null;
    try
    {
      beginTransaction(db);
      ret = getAllVOObjects(arg, orderByAttribute, direction, db);
      commitTransaction(db);
    }
    catch(Exception e)
    {
      rollbackTransaction(db);
      throw new SystemException("An error occurred when we tried to fetch " + arg.getName() + " Reason:" + e.getMessage(), e);   
    }   
    return ret;
  }


   
  /**
   * This method fetches all object in read only mode and returns a list of value objects.
   */

  public static List getAllVOObjects(Class arg, String orderByField, String direction, Database db) throws SystemException, Bug
  {
    ArrayList resultList = new ArrayList();
    OQLQuery  oql;
    try
    {
         
      if(logger.isInfoEnabled())
        logger.info("BaseHelper::GetAllObjects for " + arg.getName());
      oql = db.getOQLQuery( "SELECT u FROM " + arg.getName() + " u ORDER BY u." + orderByField + " " + direction);
      QueryResults results = oql.execute(Database.READONLY);
     
      while (results.hasMore())
      {
        Object o = results.next();

        // Om metoden getValueObject saknas, kastas ett undantag.             
        resultList.add(o.getClass().getDeclaredMethod("getValueObject", new Class[0]).invoke(o, new Object[0]));
      }
    }
    catch(NoSuchMethodException e)
    {
      throw new Bug("The object [" + arg.getName() + "] is of the wrong type. This should never happen.", e);
    }
    catch(Exception e)
    {
      throw new SystemException("An error occurred when we tried to fetch " + arg.getName() + " Reason:" + e.getMessage(), e);   
    }   

    return resultList;
  }
   
  /**
   * This method fetches all object in read only mode and returns a list of value objects sorted on primary Key.
   */
  
  public List getAllVOObjects(Class arg, String primaryKey) throws SystemException, Bug
  {
    Database db = CastorDatabaseService.getDatabase();
    List ret = null;
    try
    {
      beginTransaction(db);
      ret = getAllVOObjects(arg, primaryKey, db);
      commitTransaction(db);
    }
    catch(Exception e)
    {
      rollbackTransaction(db);
      throw new SystemException("An error occurred when we tried to fetch " + arg.getName() + " Reason:" + e.getMessage(), e);   
    }   
    return ret;
  }


  /**
   * This method fetches all object in read only mode and returns a list of value objects.
   */

  public List getAllVOObjects(Class arg, String primaryKey, Database db) throws SystemException, Bug
  {
    ArrayList resultList = new ArrayList();
    OQLQuery  oql;
    try
    {
      oql = db.getOQLQuery( "SELECT u FROM " + arg.getName() + " u ORDER BY u." + primaryKey);
      QueryResults results = oql.execute(Database.READONLY);
     
      while (results.hasMore())
      {
        IBaseEntity baseEntity = (IBaseEntity)results.next();
        resultList.add(baseEntity.getVO());
      }
    }
    catch(ClassCastException e)
    {
      throw new Bug("The object [" + arg.getName() + "] is of the wrong type. This should never happen.", e);
    }
    catch(Exception e)
    {
      throw new SystemException("An error occurred when we tried to fetch " + arg.getName() + " Reason:" + e.getMessage(), e);   
    }   

    return resultList;
  }

  /**
   * This method fetches all object in read only mode and returns a list of objects.
   */

  public List getAllObjects(Class arg, String primaryKey, Database db) throws SystemException, Bug
  {
    ArrayList resultList = new ArrayList();
    OQLQuery  oql;
    try
    {
      oql = db.getOQLQuery( "SELECT u FROM " + arg.getName() + " u ORDER BY u." + primaryKey);
      QueryResults results = oql.execute(Database.READONLY);
     
      while (results.hasMore())
      {
        IBaseEntity baseEntity = (IBaseEntity)results.next();
        resultList.add(baseEntity);
      }
    }
    catch(ClassCastException e)
    {
      throw new Bug("The object [" + arg.getName() + "] is of the wrong type. This should never happen.", e);
    }
    catch(Exception e)
    {
      throw new SystemException("An error occurred when we tried to fetch " + arg.getName() + " Reason:" + e.getMessage(), e);   
    }   

    return resultList;
  }

  //---------------------------------------------------------------------
  // Dynamic Query specific operations
  //---------------------------------------------------------------------
  /**
   * Executes a Query with no parameters
   *
    * @param query An OQL Query
   * @return A VO list of the query results
   * @throws SystemException If an error occurs
   */
  protected static List executeQuery(String query) throws SystemException
  {
    return executeQuery(query, Collections.EMPTY_LIST);
  }

  /**
   * Executes a Query with no parameters
   *
    * @param query An OQL Query
   * @return A VO list of the query results
   * @throws SystemException If an error occurs
   */
  protected static List executeQuery(String query, Database db) throws SystemException
  {
    return executeQuery(query, Collections.EMPTY_LIST, db);
  }

  /**
   * Executes a Query with no parameters
   *
    * @param query An OQL Query
   * @return A VO list of the query results
   * @throws SystemException If an error occurs
   */
  protected static List executeQueryReadOnly(String query, Database db) throws SystemException
  {
    return executeQueryReadOnly(query, Collections.EMPTY_LIST, db);
  }

  /**
   * Executes a Query, also binds the provided parameters
   *
    * @param query An OQL Query
   * @param params A List of paramters
   * @return A VO list of the query results
   * @throws SystemException If an error occurs
   */
  protected static List executeQuery(String query, List params) throws SystemException
  {
    Database db = beginTransaction();

    try
    {
      List results = new ArrayList();
      results = Collections.list(createQuery(db, query, params).execute(Database.READONLY));
      commitTransaction(db);
      return toVOList(results);
    }
    catch (Exception e)
    {
      logger.error("Error executing " + query, e);
      rollbackTransaction(db);
      throw new SystemException(e.getMessage(), e);
    }
  }

 
  /**
   * Executes a Query, also binds the provided parameters
   *
    * @param query An OQL Query
   * @param params A List of paramters
   * @param db A transaction object
   * @return A VO list of the query results
   * @throws SystemException If an error occurs
   */
  protected static List executeQuery(String query, List params, Database db) throws SystemException
  {
      try
    {
      List resultList = new ArrayList();
     
      OQLQuery oql = createQuery(db, query, params);
      QueryResults results = oql.execute();
      resultList = Collections.list(results);

      results.close();
      oql.close();

      return resultList;
    }
    catch (Exception e)
    {
      logger.error("Error executing " + query, e);
      throw new SystemException(e.getMessage(), e);
    }
  }

  /**
   * Executes a Query, also binds the provided parameters
   *
    * @param query An OQL Query
   * @param params A List of paramters
   * @param db A transaction object
   * @return A VO list of the query results
   * @throws SystemException If an error occurs
   */
  protected static List executeQueryReadOnly(String query, List params, Database db) throws SystemException
  {
      try
    {
      List resultList = new ArrayList();
     
      OQLQuery oql = createQuery(db, query, params);
      QueryResults results = oql.execute(Database.READONLY);
      resultList = Collections.list(results);

      results.close();
      oql.close();

      return resultList;
    }
    catch (Exception e)
    {
      logger.error("Error executing " + query, e);
      throw new SystemException(e.getMessage(), e);
    }
  }

 
  /**
   * Creates an OQLQuery for the provided Database and binds the parameters to it.
   *
   * @param db The Database to create the OQLQuery on
   * @param query The String OQL query
   * @param params A List of Objects to bind to the query sequentially
   * @return An OQLQuery instance that can be executer
   * @throws PersistenceException
   */
  protected static OQLQuery createQuery(Database db, String query, List params) throws PersistenceException
  {
    OQLQuery oql = db.getOQLQuery(query);
    if (params != null)
      for (Iterator i = params.iterator(); i.hasNext();)
          oql.bind(i.next());

    return oql;
  }


  /***************************************************
   * Validation and integrity check of entities - cre 2002-09-18 / SS
   * *************************************************/

    public static ConstraintExceptionBuffer validateEntity(ValidatableEntityVO vo)
    {
      // This method loops through the rulelist and creates
      // validators according to the settings in each rule.
      // The old validators are used to do the actual validation
      // but I have changed them to use less constructor
      // parameter passing in favour for setters.
           
      //CmsSystem.log("ValidationController::validate()", CmsSystem.DBG_HIGH);
    ConstraintExceptionBuffer ceb = new ConstraintExceptionBuffer();
   
    // Prepare the object for validation
    vo.PrepareValidation();
   
    // Loop through rules and create validators
      Iterator iterator = vo.getConstraintRules().iterator();
      while (iterator.hasNext())
      {
        ConstraintRule cr = (ConstraintRule) iterator.next();
        Integer intId = vo.getId();
        logger.info("Validating object id: " + intId);

      // an ugly switch for now.       
        switch (cr.getConstraintType())
        {
          case Constants.EMAIL:
          {
          if (cr.getValue() != null)
          {
            // Create validator
              EmailValidator v = new EmailValidator(cr.getFieldName());
             
              // Set properties
              v.setObjectClass(vo.getConstraintRuleList().getEntityClass());
              v.setRange(cr.getValidRange());
              v.setIsRequired(cr.required);
              v.setMustBeUnique(cr.unique);
              v.setExcludeId(intId);

            // Do the limbo
              v.validate((String) cr.getValue(), ceb);
             
              // <todo>
              // Note: the actual value validated should be extracted
              // from the vo using the fieldname with reflection.
              // </todo>
             
          }             
            break;
          }
        case Constants.STRING:
          {
          if (cr.getValue() != null)
          {           
              StringValidator v = new StringValidator(cr.getFieldName());
              v.setObjectClass(vo.getConstraintRuleList().getEntityClass());
              v.setRange(cr.getValidRange());
              v.setIsRequired(cr.required);
              v.setMustBeUnique(cr.unique);
              v.setExcludeId(intId);

              v.validate((String) cr.getValue(), ceb);
          }             
            break;
          }
          case Constants.FLOAT:
          {
            break;
          }
          case Constants.INTEGER:
          {
            break;
          }
          case Constants.PROPERNOUN:
          {
            break;
          }
         
        } // switch
               
      } // while
       
    return ceb;
    }



  /***************************************************
   * Transaction specifik operations
   ***************************************************/

  /**
   * Creates a new database and starts a transaction
   * @return A reference to a castor database with a new transaction
   * @throws SystemException if a database error occurs.
   */
  protected static Database beginTransaction() throws SystemException
  {
    Database db = CastorDatabaseService.getDatabase();
    beginTransaction(db);
    return db;
  }

    /**
     * Begins a transaction on the named database
     */
        
    protected static void beginTransaction(Database db) throws SystemException
    {
        try
        {
            //logger.info("Opening a new Transaction in cms...");
            db.begin();
        }
        catch(Exception e)
        {
      throw new SystemException("An error occurred when we tried to begin an transaction. Reason:" + e.getMessage(), e);   
        }
    }
      
    /**
     * Ends a transaction on the named database
     */
    
    protected static void commitTransaction(Database db) throws SystemException
    {
        try
        {
            //logger.info("Closing a transaction in cms...");

            db.commit();
        db.close();

        //RegistryController.notifyTransactionCommitted();
        }
        catch(TransactionAbortedException tae)
        {
          if(tae.getCause() instanceof LockNotGrantedException)
                throw new SystemException("The resource you tried to modify have just been updated by another user. Please try again later. System message: " + tae.getCause().getMessage());
          else
                 throw new SystemException("An error occurred when we tried to commit an transaction. Reason:" + tae.getMessage(), tae);
        }
        catch(LockNotGrantedException lnge)
        {
            throw new SystemException("The resource you tried to modify have just been updated by another user. Please try again later. System message: " + lnge.getMessage());
        }
        catch(Exception e)
        {
             throw new SystemException("An error occurred when we tried to commit an transaction. Reason:" + e.getMessage(), e);   
        }
    }
    /**
     * Ends a transaction on the named database
     */
    
    protected static void commitRegistryAwareTransaction(Database db) throws SystemException
    {
        try
        {
            //logger.info("Closing a transaction in cms...");

            db.commit();
        db.close();

        RegistryController.notifyTransactionCommitted();
        }
        catch(TransactionAbortedException tae)
        {
          if(tae.getCause() instanceof LockNotGrantedException)
                throw new SystemException("The resource you tried to modify have just been updated by another user. Please try again later. System message: " + tae.getCause().getMessage());
          else
                 throw new SystemException("An error occurred when we tried to commit an transaction. Reason:" + tae.getMessage(), tae);
        }
        catch(LockNotGrantedException lnge)
        {
            throw new SystemException("The resource you tried to modify have just been updated by another user. Please try again later. System message: " + lnge.getMessage());
        }
        catch(Exception e)
        {
             throw new SystemException("An error occurred when we tried to commit an transaction. Reason:" + e.getMessage(), e);   
        }
    }
    /**
     * Rollbacks a transaction on the named database
     */
    
    protected static void rollbackTransaction(Database db) throws SystemException
    {
        try
        {
            //logger.info("rollbackTransaction a transaction in cms...");
           
            if (db != null && db.isActive())
          {
                db.rollback();
        db.close();
          }
        }
        catch(Exception e)
        {
            logger.warn("An error occurred when we tried to rollback an transaction. Reason:" + e.getMessage());
        }
    }

    /**
     * Rollbacks a transaction on the named database
     */
    
    protected static void closeDatabase(Database db) throws SystemException
    {
        try
        {
            if (db != null)
          {
        db.close();
          }
        }
        catch(Exception e)
        {
            logger.warn("An error occurred when we tried to rollback an transaction. Reason:" + e.getMessage());
        }
    }

  public String getLocalizedString(Locale locale, String key)
    {
      StringManager stringManager = StringManagerFactory.getPresentationStringManager("org.infoglue.cms.applications", locale);

      return stringManager.getString(key);
    }

  public String getLocalizedString(Locale locale, String key, Object arg1)
    {
    String message = null;
   
    StringManager stringManager = StringManagerFactory.getPresentationStringManager("org.infoglue.cms.applications", locale);
      try
      {
        message = stringManager.getString(key, arg1);
      }
      catch (ConfigurationError e)
      {
        StringManager stringManagerBackup = StringManagerFactory.getPresentationStringManager("org.infoglue.cms.entities", locale);
          message = stringManagerBackup.getString(key, arg1);
    }
      return message;
    }

  public String getLocalizedString(Locale locale, String key, Object arg1, Object arg2)
    {
      StringManager stringManager = StringManagerFactory.getPresentationStringManager("org.infoglue.cms.applications", locale);

      return stringManager.getString(key, arg1, arg2);
    }

  public String getLocalizedString(Locale locale, String key, Object arg1, Object arg2, Object arg3)
    {
      StringManager stringManager = StringManagerFactory.getPresentationStringManager("org.infoglue.cms.applications", locale);

      return stringManager.getString(key, arg1, arg2, arg3);
    }

  public Locale getUserPrefferedLocale(String userName)
  {
    Locale locale = Locale.ENGLISH;
    try
    {
      List toolLocales = CmsPropertyHandler.getToolLocales();
      if(toolLocales != null && toolLocales.size() > 0)
        locale = (Locale)toolLocales.get(0);
    }
    catch (Exception e)
    {
      logger.warn("Problem getting default tool locale: " + e.getMessage(), e);
    }
   
    if(userName != null)
    {
      try
      {
          Map args = new HashMap();
          args.put("globalKey", "infoglue");
          PropertySet ps = PropertySetManager.getInstance("jdbc", args);
         
          String languageCode = ps.getString("principal_" + userName + "_languageCode");
          locale = getLocaleWithCode(languageCode);
      }
      catch (Exception e)
      {
        logger.warn("Error getting users prefferred language: " + e.getMessage(), e);
      }
    }
   
    return locale;
  }

  /**
   * This method returns language with the languageCode sent in.
   */
 
  public Locale getLocaleWithCode(String languageCode)
  {
    String key = "" + languageCode;
    logger.info("key:" + key);
    Locale locale = (Locale)CacheController.getCachedObject("localeCache", key);
    if(locale != null)
    {
      logger.info("There was an cached locale:" + locale);
    }
    else
    {
      locale = Locale.getDefault();
     
      if (languageCode != null)
      {
        try
        {
          locale = new Locale(languageCode);
        }
        catch (Exception e)
        {
          logger.error("An error occurred in getLocaleWithCode: getting locale with languageCode:" + languageCode + "," + e, e);
       
      }
     
      CacheController.cacheObject("localeCache", key, locale);       
    }
   
    return locale;
  }

  public static TableCount getTableCount(String tableName) throws Exception
  {
    TableCount tableCount = null;
   
    Database db = CastorDatabaseService.getDatabase();

        beginTransaction(db);

        try
        {
          OQLQuery oql = db.getOQLQuery("CALL SQL SELECT count(*) FROM " + tableName + " AS org.infoglue.cms.entities.management.TableCount");

          QueryResults results = oql.execute();
        if(results.hasMore())
            {
          tableCount = (TableCount)results.next();
        }

        results.close();
        oql.close();
         
            commitTransaction(db);
        }
        catch(Exception e)
        {
            logger.error("An error occurred so we should not complete the transaction: " + e.getMessage());
            logger.warn("An error occurred so we should not complete the transaction: " + e.getMessage(), e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }

        return tableCount;
  }

  public static TableCount getTableCount(String tableName, String columnName) throws Exception
  {
    TableCount tableCount = null;
   
    Database db = CastorDatabaseService.getDatabase();

        beginTransaction(db);

        try
        {
          OQLQuery oql = db.getOQLQuery("CALL SQL SELECT count(" + columnName + ") FROM " + tableName + " AS org.infoglue.cms.entities.management.TableCount");

          QueryResults results = oql.execute();
        if(results.hasMore())
            {
          tableCount = (TableCount)results.next();
        }

        results.close();
        oql.close();
         
            commitTransaction(db);
        }
        catch(Exception e)
        {
            logger.error("An error occurred so we should not complete the transaction:" + e);
            logger.warn("An error occurred so we should not complete the transaction:" + e, e);
            rollbackTransaction(db);
            throw new SystemException(e.getMessage());
        }

        return tableCount;
  }
 
    public static Category getCastorCategory()
    {
        Enumeration enumeration = Logger.getCurrentCategories();
        while(enumeration.hasMoreElements())
        {
            Category category = (Category)enumeration.nextElement();
            if(category.getName().equalsIgnoreCase("org.exolab.castor"))
                return category;
        }
       
        return null;
    }

    public static Category getCastorJDOCategory()
    {
        Enumeration enumeration = Logger.getCurrentCategories();
        while(enumeration.hasMoreElements())
        {
            Category category = (Category)enumeration.nextElement();
            if(category.getName().equalsIgnoreCase("org.exolab.castor.jdo"))
                return category;
        }
       
        return null;
    }

  public abstract BaseEntityVO getNewVO();
}
TOP

Related Classes of org.infoglue.cms.controllers.kernel.impl.simple.BaseController

TOP
Copyright © 2018 www.massapi.com. All rights reserved.
All source code are property of their respective owners. Java is a trademark of Sun Microsystems, Inc and owned by ORACLE Inc. Contact coftware#gmail.com.