Package org.objectweb.speedo.query.jdo

Source Code of org.objectweb.speedo.query.jdo.JDOQueryEvalContext

/**
* Copyright (C) 2001-2004 France Telecom R&D
*
* 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 of the License, or (at your option) 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
*/
package org.objectweb.speedo.query.jdo;

import org.objectweb.jorm.api.PClassMapping;
import org.objectweb.jorm.mapper.rdb.lib.RdbPPolymorphicClass;
import org.objectweb.medor.api.EvaluationException;
import org.objectweb.medor.api.MedorException;
import org.objectweb.medor.eval.api.ConnectionResources;
import org.objectweb.medor.eval.api.QueryEvaluator;
import org.objectweb.medor.eval.lib.BasicEvaluationMetaData;
import org.objectweb.medor.eval.prefetch.api.IntermediaryPrefetchBuffer;
import org.objectweb.medor.eval.prefetch.api.PrefetchBuffer;
import org.objectweb.medor.eval.prefetch.lib.IntermediaryPrefetchBufferImpl;
import org.objectweb.medor.expression.api.ParameterOperand;
import org.objectweb.medor.query.api.QueryLeaf;
import org.objectweb.medor.query.api.QueryTree;
import org.objectweb.medor.tuple.api.TupleCollection;
import org.objectweb.speedo.api.ExceptionHelper;
import org.objectweb.speedo.pm.jdo.api.JDOPOManagerItf;
import org.objectweb.speedo.query.api.QueryDefinition;
import org.objectweb.util.monolog.api.BasicLevel;

import java.util.HashMap;
import java.util.Map;

import javax.jdo.JDOFatalException;

/**
* Represent a Medor query executed for a JDO query. It contains the query, the
* evaluator, a link to the SpeedoCompiledQuery and some information about
* the data prefetching. A JDO can correspond to several Medor query in case of
* inheritance for example.
*
* @author S.Chassande-Barrioz
*/
public class JDOQueryEvalContext {
  /**
   * The medor querytree representing the query
   */
  public QueryTree query;

  /**
   * the evaluator of the query
   */
  public QueryEvaluator evaluator;

  /**
   * is the index of the identifier (prefetch index too)
   */
  public int pnIndex;

  /**
   * the PClassMapping of the prefetched class
   */
  public PClassMapping pcm;

  /**
   * The original speedo compiled query
   */
  public JDOCompiledSelectQuery sqc;

  /**
   * @param qt is the medor querytree representing the query
   * @param sqc is the original speedo compiled query
   */
  public JDOQueryEvalContext(QueryTree qt,
              JDOCompiledSelectQuery sqc) {
    query = qt;
    this.sqc = sqc;
  }

  /**
   * Executes the sub query
   * @param pm is the current persistence manager
   * @param pos is the parameter of the query
   * @param connection is the way to reach the persistence support
   * @return a TupleCollection containing the result
   * @throws MedorException
   *
   */
  public TupleCollection eval(JDOPOManagerItf pm,
                ParameterOperand[] pos,
                Object connection,
                QueryDefinition userqd) throws MedorException {
    // Calculates and gets the required connection ressources for this query
    ConnectionResources connRess =
      evaluator.getRequiredConnectionResources();

      Map evalMDMap = null;
      if (userqd != null && (userqd.getIndexFirst() > 0
              || userqd.getIndexLast() < Integer.MAX_VALUE)) {
        //range values specified
          evalMDMap = new HashMap();
      }

      // Gets the QueryLeafs that require connections
    QueryLeaf[] leafs = connRess.getRequiredQueryLeafConnection();
    // Setting QueryLeaf's appropriated connection Object
    for (int cpt = 0; (cpt < leafs.length); cpt++) {
      connRess.setConnection(leafs[cpt], connection);
      if (evalMDMap != null) {
          //range values specified
            BasicEvaluationMetaData evalMD = new BasicEvaluationMetaData();
            evalMD.setLimitedRangeStartAt((int) userqd.getIndexFirst());
            evalMD.setLimitedRangeSize((int) (userqd.getIndexLast() - userqd.getIndexFirst()));
          evalMDMap.put(leafs[cpt], evalMD);
      }
    }
   
    PrefetchBuffer prefetchBuffer = null;
    if (pcm != null) {
      boolean isPolymorphic = (pcm instanceof RdbPPolymorphicClass)
                && ((JDOQueryDefinitionImpl) sqc.getDefinition()).getIncludeSubClasses();
      prefetchBuffer = sqc.getMapper().getPrefetchCache().createPrefetchBuffer(
        sqc.getPrefetchBufferFactory(),
        pcm, pm.currentTransaction(),
        pnIndex,
        pm.getMultithreaded(),
        !isPolymorphic);
      //if the class is polymorphic, register an intermediary prefetch buffer
      if (isPolymorphic) {
        IntermediaryPrefetchBuffer ipb = new IntermediaryPrefetchBufferImpl(
                      prefetchBuffer,
                      pcm.getIndexesTable(pcm));
        if (!pcm.getPMapper().getPrefetchCache().registerPrefetchBuffer(
            ipb, pcm, pm.currentTransaction())) {
          throw new MedorException("No prefetch buffer registered for the pcm " + pcm.getClassName() + ".");
        }
        //register the prefetch buffer for all the subclasses
        try{
          //get the list of all the sub pclassmappings
          PClassMapping[] subPCMs = pcm.getSubPCMs();
          if (subPCMs != null) {
            for (int i = 0; i < subPCMs.length; i++) {
              //create an intermediary prefetchBuffer that has the prefetchBuffer
              //of the superclass as delegate prefetch buffer
              //and the association table for the pcm of the superclass
              IntermediaryPrefetchBuffer intermediaryPb = new IntermediaryPrefetchBufferImpl(
                                  prefetchBuffer,
                                  subPCMs[i].getIndexesTable(pcm));
              if (!subPCMs[i].getPMapper().getPrefetchCache().registerPrefetchBuffer(
                  intermediaryPb, subPCMs[i], pm.currentTransaction())) {
                throw new MedorException("No prefetch buffer registered for the pcm " + subPCMs[i].getClassName() + ".");
              }
            }
          }
        }
        catch(Exception e){
          throw new MedorException("Error while trying to register the prefetchBuffer with the subclasses. ", e);
        }
      }
    }
    // Launching Medor Evaluator...
    if (sqc.getLogger().isLoggable(BasicLevel.DEBUG)) {
      sqc.getLogger().log(BasicLevel.DEBUG, "Parameters: " + posToString(pos));
    }
    TupleCollection queryResult = null;
    try {
      queryResult = evaluator.evaluate(pos, connRess, prefetchBuffer, evalMDMap);
    } catch (EvaluationException e) {
      throw new JDOFatalException(
        "Impossible to evaluate the query: ",
        ExceptionHelper.getNested(e)
      );
    }
    return queryResult;
  }

  /**
   * Produces a String representation of parameter for logging.
   */
  protected String posToString(ParameterOperand[] pos) {
    if (pos == null) {
      return "null";
    }
    StringBuffer sb = new StringBuffer("[");
    String sep = "";
    for(int i=0; i<pos.length; i++) {
      sb.append(sep);
      sb.append("(name='");
      sb.append("'");
      sb.append(pos[i].getName());
      sb.append("', value=");
      sb.append(pos[i]);
      sb.append(")");
    }
    sb.append("]");
    return sb.toString();
  }
}
TOP

Related Classes of org.objectweb.speedo.query.jdo.JDOQueryEvalContext

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.