⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 whereparser.java

📁 一个Java持久层类库
💻 JAVA
📖 第 1 页 / 共 2 页
字号:
//$Id: WhereParser.java 7825 2005-08-10 20:23:55Z oneovthafew $package org.hibernate.hql.classic;import java.util.HashMap;import java.util.HashSet;import java.util.LinkedList;import java.util.Map;import java.util.Set;import java.util.StringTokenizer;import org.hibernate.MappingException;import org.hibernate.QueryException;import org.hibernate.engine.JoinSequence;import org.hibernate.hql.QueryTranslator;import org.hibernate.persister.collection.CollectionPropertyNames;import org.hibernate.persister.entity.Queryable;import org.hibernate.sql.InFragment;import org.hibernate.type.EntityType;import org.hibernate.type.LiteralType;import org.hibernate.type.Type;import org.hibernate.type.TypeFactory;import org.hibernate.util.ReflectHelper;import org.hibernate.util.StringHelper;/** * Parses the where clause of a hibernate query and translates it to an * SQL where clause. */// We should reengineer this class so that, rather than the current ad -// hoc linear approach to processing a stream of tokens, we instead// build up a tree of expressions.// We would probably refactor to have LogicParser (builds a tree of simple// expressions connected by and, or, not), ExpressionParser (translates// from OO terms like foo, foo.Bar, foo.Bar.Baz to SQL terms like// FOOS.ID, FOOS.BAR_ID, etc) and PathExpressionParser (which does much// the same thing it does now)public class WhereParser implements Parser {	private final PathExpressionParser pathExpressionParser;	{		pathExpressionParser = new PathExpressionParser();		pathExpressionParser.setUseThetaStyleJoin( true ); //Need this, since join condition can appear inside parens!	}	private static final Set EXPRESSION_TERMINATORS = new HashSet();   //tokens that close a sub expression	private static final Set EXPRESSION_OPENERS = new HashSet();       //tokens that open a sub expression	private static final Set BOOLEAN_OPERATORS = new HashSet();        //tokens that would indicate a sub expression is a boolean expression	private static final Map NEGATIONS = new HashMap();	static {		EXPRESSION_TERMINATORS.add( "and" );		EXPRESSION_TERMINATORS.add( "or" );		EXPRESSION_TERMINATORS.add( ")" );		//expressionTerminators.add(","); // deliberately excluded		EXPRESSION_OPENERS.add( "and" );		EXPRESSION_OPENERS.add( "or" );		EXPRESSION_OPENERS.add( "(" );		//expressionOpeners.add(","); // deliberately excluded		BOOLEAN_OPERATORS.add( "<" );		BOOLEAN_OPERATORS.add( "=" );		BOOLEAN_OPERATORS.add( ">" );		BOOLEAN_OPERATORS.add( "#" );		BOOLEAN_OPERATORS.add( "~" );		BOOLEAN_OPERATORS.add( "like" );		BOOLEAN_OPERATORS.add( "ilike" );		BOOLEAN_OPERATORS.add( "regexp" );		BOOLEAN_OPERATORS.add( "rlike" );		BOOLEAN_OPERATORS.add( "is" );		BOOLEAN_OPERATORS.add( "in" );		BOOLEAN_OPERATORS.add( "any" );		BOOLEAN_OPERATORS.add( "some" );		BOOLEAN_OPERATORS.add( "all" );		BOOLEAN_OPERATORS.add( "exists" );		BOOLEAN_OPERATORS.add( "between" );		BOOLEAN_OPERATORS.add( "<=" );		BOOLEAN_OPERATORS.add( ">=" );		BOOLEAN_OPERATORS.add( "=>" );		BOOLEAN_OPERATORS.add( "=<" );		BOOLEAN_OPERATORS.add( "!=" );		BOOLEAN_OPERATORS.add( "<>" );		BOOLEAN_OPERATORS.add( "!#" );		BOOLEAN_OPERATORS.add( "!~" );		BOOLEAN_OPERATORS.add( "!<" );		BOOLEAN_OPERATORS.add( "!>" );		BOOLEAN_OPERATORS.add( "is not" );		BOOLEAN_OPERATORS.add( "not like" );		BOOLEAN_OPERATORS.add( "not ilike" );		BOOLEAN_OPERATORS.add( "not regexp" );		BOOLEAN_OPERATORS.add( "not rlike" );		BOOLEAN_OPERATORS.add( "not in" );		BOOLEAN_OPERATORS.add( "not between" );		BOOLEAN_OPERATORS.add( "not exists" );		NEGATIONS.put( "and", "or" );		NEGATIONS.put( "or", "and" );		NEGATIONS.put( "<", ">=" );		NEGATIONS.put( "=", "<>" );		NEGATIONS.put( ">", "<=" );		NEGATIONS.put( "#", "!#" );		NEGATIONS.put( "~", "!~" );		NEGATIONS.put( "like", "not like" );		NEGATIONS.put( "ilike", "not ilike" );		NEGATIONS.put( "regexp", "not regexp" );		NEGATIONS.put( "rlike", "not rlike" );		NEGATIONS.put( "is", "is not" );		NEGATIONS.put( "in", "not in" );		NEGATIONS.put( "exists", "not exists" );		NEGATIONS.put( "between", "not between" );		NEGATIONS.put( "<=", ">" );		NEGATIONS.put( ">=", "<" );		NEGATIONS.put( "=>", "<" );		NEGATIONS.put( "=<", ">" );		NEGATIONS.put( "!=", "=" );		NEGATIONS.put( "<>", "=" );		NEGATIONS.put( "!#", "#" );		NEGATIONS.put( "!~", "~" );		NEGATIONS.put( "!<", "<" );		NEGATIONS.put( "!>", ">" );		NEGATIONS.put( "is not", "is" );		NEGATIONS.put( "not like", "like" );		NEGATIONS.put( "not ilike", "ilike" );		NEGATIONS.put( "not regexp", "regexp" );		NEGATIONS.put( "not rlike", "rlike" );		NEGATIONS.put( "not in", "in" );		NEGATIONS.put( "not between", "between" );		NEGATIONS.put( "not exists", "exists" );	}	// Handles things like:	// a and b or c	// a and ( b or c )	// not a and not b	// not ( a and b )	// x between y and z            (overloaded "and")	// x in ( a, b, c )             (overloaded brackets)	// not not a	// a is not null                (overloaded "not")	// etc......	// and expressions like	// foo = bar                    (maps to: foo.id = bar.id)	// foo.Bar = 'foo'              (maps to: foo.bar = 'foo')	// foo.Bar.Baz = 1.0            (maps to: foo.bar = bar.id and bar.baz = 1.0)	// 1.0 = foo.Bar.Baz            (maps to: bar.baz = 1.0 and foo.Bar = bar.id)	// foo.Bar.Baz = a.B.C          (maps to: bar.Baz = b.C and foo.Bar = bar.id and a.B = b.id)	// foo.Bar.Baz + a.B.C          (maps to: bar.Baz + b.C and foo.Bar = bar.id and a.B = b.id)	// ( foo.Bar.Baz + 1.0 ) < 2.0  (maps to: ( bar.Baz + 1.0 ) < 2.0 and foo.Bar = bar.id)	private boolean betweenSpecialCase = false;       //Inside a BETWEEN ... AND ... expression	private boolean negated = false;	private boolean inSubselect = false;	private int bracketsSinceSelect = 0;	private StringBuffer subselect;	private boolean expectingPathContinuation = false;	private int expectingIndex = 0;	// The following variables are stacks that keep information about each subexpression	// in the list of nested subexpressions we are currently processing.	private LinkedList nots = new LinkedList();           //were an odd or even number of NOTs encountered	private LinkedList joins = new LinkedList();          //the join string built up by compound paths inside this expression	private LinkedList booleanTests = new LinkedList();   //a flag indicating if the subexpression is known to be boolean	private String getElementName(PathExpressionParser.CollectionElement element, QueryTranslatorImpl q) throws QueryException {		String name;		if ( element.isOneToMany ) {			name = element.alias;		}		else {			Type type = element.elementType;			if ( type.isEntityType() ) { //ie. a many-to-many				String entityName = ( ( EntityType ) type ).getAssociatedEntityName();				name = pathExpressionParser.continueFromManyToMany( entityName, element.elementColumns, q );			}			else {				throw new QueryException( "illegally dereferenced collection element" );			}		}		return name;	}	public void token(String token, QueryTranslatorImpl q) throws QueryException {		String lcToken = token.toLowerCase();		//Cope with [,]		if ( token.equals( "[" ) && !expectingPathContinuation ) {			expectingPathContinuation = false;			if ( expectingIndex == 0 ) throw new QueryException( "unexpected [" );			return;		}		else if ( token.equals( "]" ) ) {			expectingIndex--;			expectingPathContinuation = true;			return;		}		//Cope with a continued path expression (ie. ].baz)		if ( expectingPathContinuation ) {			boolean pathExpressionContinuesFurther = continuePathExpression( token, q );			if ( pathExpressionContinuesFurther ) return; //NOTE: early return		}		//Cope with a subselect		if ( !inSubselect && ( lcToken.equals( "select" ) || lcToken.equals( "from" ) ) ) {			inSubselect = true;			subselect = new StringBuffer( 20 );		}		if ( inSubselect && token.equals( ")" ) ) {			bracketsSinceSelect--;			if ( bracketsSinceSelect == -1 ) {				QueryTranslatorImpl subq = new QueryTranslatorImpl(				        subselect.toString(),						q.getEnabledFilters(),						q.getFactory()				);				try {					subq.compile( q );				}				catch ( MappingException me ) {					throw new QueryException( "MappingException occurred compiling subquery", me );				}				appendToken( q, subq.getSQLString() );				inSubselect = false;				bracketsSinceSelect = 0;			}		}		if ( inSubselect ) {			if ( token.equals( "(" ) ) bracketsSinceSelect++;			subselect.append( token ).append( ' ' );			return;		}		//Cope with special cases of AND, NOT, ()		specialCasesBefore( lcToken );		//Close extra brackets we opened		if ( !betweenSpecialCase && EXPRESSION_TERMINATORS.contains( lcToken ) ) {			closeExpression( q, lcToken );

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -