public SubselectOneToManyLoader(IQueryableCollection persister, SqlString subquery, ICollection<EntityKey> entityKeys, QueryParameters queryParameters, ISessionFactoryImplementor factory, IDictionary<string, IFilter> enabledFilters) : base(persister, BatchSizeForSubselectFetching, factory, enabledFilters) { keys = new object[entityKeys.Count]; int i = 0; foreach (EntityKey entityKey in entityKeys) { keys[i++] = entityKey.Identifier; } // NH Different behavior: to deal with positionslParameter+NamedParameter+ParameterOfFilters namedParameters = new Dictionary<string, TypedValue>(queryParameters.NamedParameters); parametersSpecifications = queryParameters.ProcessedSqlParameters.ToList(); var processedRowSelection = queryParameters.ProcessedRowSelection; SqlString finalSubquery = subquery; if (queryParameters.ProcessedRowSelection != null && !SubselectClauseExtractor.HasOrderBy(queryParameters.ProcessedSql)) { // when the original query has an "ORDER BY" we can't re-apply the pagination. // This is a simplification, we should actually check which is the "ORDER BY" clause because when the "ORDER BY" is just for the PK we can re-apply "ORDER BY" and pagination. finalSubquery = GetSubSelectWithLimits(subquery, parametersSpecifications, processedRowSelection, namedParameters); } InitializeFromWalker(persister, finalSubquery, BatchSizeForSubselectFetching, enabledFilters, factory); types = queryParameters.PositionalParameterTypes; values = queryParameters.PositionalParameterValues; }
public SqlCommandImpl(SqlString query, ICollection<IParameterSpecification> specifications, QueryParameters queryParameters, ISessionFactoryImplementor factory) { this.query = query; this.specifications = specifications; this.queryParameters = queryParameters; this.factory = factory; }
public void ValidateFailureDifferentLengths() { QueryParameters qp = new QueryParameters( new IType[] { NHibernateUtil.String }, new object[] { }); qp.ValidateParameters(); }
public void ValidateOk() { QueryParameters qp = new QueryParameters( new IType[] {NHibernateUtil.String}, new object[] {"string"}); qp.ValidateParameters(); }
public void ValidateFailureDifferentLengths() { QueryParameters qp = new QueryParameters( new IType[] {NHibernateUtil.String}, new object[] {}); Assert.Throws<QueryException>(() => qp.ValidateParameters()); }
public static void ResetEffectiveExpectedType(this IEnumerable<IParameterSpecification> parameterSpecs, QueryParameters queryParameters) { // TODO: remove this method when we can infer the type during the parse foreach (var parameterSpecification in parameterSpecs.OfType<IExplicitParameterSpecification>()) { parameterSpecification.SetEffectiveType(queryParameters); } }
public override SqlString ToSqlString(ICriteria criteria, ICriteriaQuery criteriaQuery, IDictionary<string, IFilter> enabledFilters) { ISessionFactoryImplementor factory = criteriaQuery.Factory; var innerQuery = new CriteriaQueryTranslator( factory, criteriaImpl, //implicit polymorphism not supported (would need a union) criteriaImpl.EntityOrClassName, criteriaQuery.GenerateSQLAlias(), criteriaQuery); types = innerQuery.HasProjection ? innerQuery.ProjectedTypes : null; if (innerQuery.HasProjection == false) { throw new QueryException("Cannot use subqueries on a criteria without a projection."); } IOuterJoinLoadable persister = (IOuterJoinLoadable) factory.GetEntityPersister(criteriaImpl.EntityOrClassName); //patch to generate joins on subqueries //stolen from CriteriaLoader CriteriaJoinWalker walker = new CriteriaJoinWalker(persister, innerQuery, factory, criteriaImpl, criteriaImpl.EntityOrClassName, enabledFilters); parameters = innerQuery.GetQueryParameters(); // parameters can be inferred only after initialize the walker SqlString sql = walker.SqlString; if (criteriaImpl.FirstResult != 0 || criteriaImpl.MaxResults != RowSelection.NoValue) { int? offset = Loader.Loader.GetOffsetUsingDialect(parameters.RowSelection, factory.Dialect); int? limit = Loader.Loader.GetLimitUsingDialect(parameters.RowSelection, factory.Dialect); Parameter offsetParameter = offset.HasValue ? innerQuery.CreateSkipParameter(offset.Value) : null; Parameter limitParameter = limit.HasValue ? innerQuery.CreateTakeParameter(limit.Value) : null; sql = factory.Dialect.GetLimitString(sql, offset, limit, offsetParameter, limitParameter); } SqlStringBuilder buf = new SqlStringBuilder().Add(ToLeftSqlString(criteria, criteriaQuery)); if (op != null) { buf.Add(" ").Add(op).Add(" "); } if (quantifier != null && prefixOp) { buf.Add(quantifier).Add(" "); } buf.Add("(").Add(sql).Add(")"); if (quantifier != null && prefixOp == false) { buf.Add(" ").Add(quantifier); } return buf.ToSqlString(); }
public void Bind(IDbCommand command, IList<Parameter> multiSqlQueryParametersList, int singleSqlParametersOffset, IList<Parameter> sqlQueryParametersList, QueryParameters queryParameters, ISessionImplementor session) { IType type = keyType; object value = queryParameters.PositionalParameterValues[queryParameterPosition]; string backTrackId = GetIdsForBackTrack(session.Factory).First(); // just the first because IType suppose the oders in certain sequence int position = sqlQueryParametersList.GetEffectiveParameterLocations(backTrackId).Single(); // an HQL positional parameter can't appear more than once type.NullSafeSet(command, value, position + singleSqlParametersOffset, session); }
protected virtual int BindLimitParametersLastIfNeccesary(IDbCommand command, QueryParameters parameter, int colIndex) { RowSelection selection = parameter.RowSelection; if (Loader.Loader.UseLimit(selection, dialect) && !dialect.BindLimitParametersFirst) { return Loader.Loader.BindLimitParameters(command, colIndex, selection, session); } return 0; }
public override void Bind(IDbCommand command, IList<Parameter> multiSqlQueryParametersList, int singleSqlParametersOffset, IList<Parameter> sqlQueryParametersList, QueryParameters queryParameters, ISessionImplementor session) { TypedValue typedValue = queryParameters.NamedParameters[name]; string backTrackId = GetIdsForBackTrack(session.Factory).First(); // just the first because IType suppose the oders in certain sequence foreach (int position in sqlQueryParametersList.GetEffectiveParameterLocations(backTrackId)) { ExpectedType.NullSafeSet(command, GetPagingValue(typedValue.Value, session.Factory.Dialect, queryParameters), position + singleSqlParametersOffset, session); } }
public void Bind(IDbCommand command, IList<Parameter> multiSqlQueryParametersList, int singleSqlParametersOffset, IList<Parameter> sqlQueryParametersList, QueryParameters queryParameters, ISessionImplementor session) { TypedValue typedValue = queryParameters.NamedParameters[name]; string backTrackId = GetIdsForBackTrack(session.Factory).First(); foreach (int position in sqlQueryParametersList.GetEffectiveParameterLocations(backTrackId)) { ExpectedType.NullSafeSet(command, typedValue.Value, position + singleSqlParametersOffset, session); } }
public override SqlString ToSqlString(ICriteria criteria, ICriteriaQuery criteriaQuery, IDictionary<string, IFilter> enabledFilters) { InitializeInnerQueryAndParameters(criteriaQuery); if (innerQuery.HasProjection == false) { throw new QueryException("Cannot use subqueries on a criteria without a projection."); } ISessionFactoryImplementor factory = criteriaQuery.Factory; IOuterJoinLoadable persister = (IOuterJoinLoadable)factory.GetEntityPersister(criteriaImpl.EntityOrClassName); //patch to generate joins on subqueries //stolen from CriteriaLoader CriteriaJoinWalker walker = new CriteriaJoinWalker(persister, innerQuery, factory, criteriaImpl, criteriaImpl.EntityOrClassName, enabledFilters); parameters = innerQuery.GetQueryParameters(); // parameters can be inferred only after initialize the walker SqlString sql = walker.SqlString; if (criteriaImpl.FirstResult != 0 || criteriaImpl.MaxResults != RowSelection.NoValue) { int? offset = Loader.Loader.GetOffsetUsingDialect(parameters.RowSelection, factory.Dialect); int? limit = Loader.Loader.GetLimitUsingDialect(parameters.RowSelection, factory.Dialect); Parameter offsetParameter = offset.HasValue ? innerQuery.CreateSkipParameter(offset.Value) : null; Parameter limitParameter = limit.HasValue ? innerQuery.CreateTakeParameter(limit.Value) : null; sql = factory.Dialect.GetLimitString(sql, offset, limit, offsetParameter, limitParameter); } // during CriteriaImpl.Clone we are doing a shallow copy of each criterion. // this is not a problem for common criterion but not for SubqueryExpression because here we are holding the state of inner CriteriaTraslator (ICriteriaQuery). // After execution (ToSqlString) we have to clean the internal state because the next execution may be performed in a different tree reusing the same istance of SubqueryExpression. innerQuery = null; SqlStringBuilder buf = new SqlStringBuilder().Add(ToLeftSqlString(criteria, criteriaQuery)); if (op != null) { buf.Add(" ").Add(op).Add(" "); } if (quantifier != null && prefixOp) { buf.Add(quantifier).Add(" "); } buf.Add("(").Add(sql).Add(")"); if (quantifier != null && prefixOp == false) { buf.Add(" ").Add(quantifier); } return buf.ToSqlString(); }
public int Bind( IDbCommand statement, QueryParameters qp, ISessionImplementor session, int position) { object value = qp.PositionalParameterValues[_queryParameterPosition]; _keyType.NullSafeSet(statement, value, position, session); return _keyType.GetColumnSpan(session.Factory); }
public int Bind(IDbCommand statement, QueryParameters qp, ISessionImplementor session, int position) { int bindCount = 0; foreach (IParameterSpecification spec in _paramSpecs) { bindCount += spec.Bind(statement, qp, session, position + bindCount); } return bindCount; }
public SubselectFetch(string alias, ILoadable loadable, QueryParameters queryParameters, ISet<EntityKey> resultingEntityKeys) { this.resultingEntityKeys = resultingEntityKeys; this.queryParameters = queryParameters; this.loadable = loadable; this.alias = alias; queryString = queryParameters.ProcessedSql.GetSubselectString(); }
public SubselectFetch(string alias, ILoadable loadable, QueryParameters queryParameters, ISet<EntityKey> resultingEntityKeys, IDictionary<string, int[]> namedParameterLocMap) { this.resultingEntityKeys = resultingEntityKeys; this.queryParameters = queryParameters; this.namedParameterLocMap = namedParameterLocMap; this.loadable = loadable; this.alias = alias; queryString = queryParameters.FilteredSQL.GetSubselectString(); }
protected virtual void BindParameters(IDbCommand command, QueryParameters[] queryParameters) { int colIndex = 0; for (int queryIndex = 0; queryIndex < resultSetsCount; queryIndex++) { int limitParameterSpan = BindLimitParametersFirstIfNeccesary(command, queryParameters[queryIndex], colIndex); colIndex = BindQueryParameters(command, queryParameters[queryIndex], colIndex + limitParameterSpan); colIndex += BindLimitParametersLastIfNeccesary(command, queryParameters[queryIndex], colIndex); } }
public void Bind(IDbCommand command, IList<Parameter> multiSqlQueryParametersList, int singleSqlParametersOffset, IList<Parameter> sqlQueryParametersList, QueryParameters queryParameters, ISessionImplementor session) { string backTrackId = GetIdsForBackTrack(session.Factory).First(); // just the first because IType suppose the oders in certain sequence // The same filterName-parameterName can appear more than once in the whole query object value = session.GetFilterParameterValue(filterParameterFullName); foreach (int position in multiSqlQueryParametersList.GetEffectiveParameterLocations(backTrackId)) { ExpectedType.NullSafeSet(command, value, position, session); } }
public void Bind(IDbCommand command, IList<Parameter> multiSqlQueryParametersList, int singleSqlParametersOffset, IList<Parameter> sqlQueryParametersList, QueryParameters queryParameters, ISessionImplementor session) { // The QuerySkipParameterSpecification is unique so we can use multiSqlQueryParametersList var effectiveParameterLocations = multiSqlQueryParametersList.GetEffectiveParameterLocations(limitParametersNameForThisQuery).ToArray(); if (effectiveParameterLocations.Length > 0) { // if the dialect does not support variable limits the parameter may was removed int value = Loader.Loader.GetOffsetUsingDialect(queryParameters.RowSelection, session.Factory.Dialect) ?? queryParameters.RowSelection.FirstRow; int position = effectiveParameterLocations[0]; type.NullSafeSet(command, value, position, session); } }
public override void Bind(IDbCommand command, IList<Parameter> multiSqlQueryParametersList, int singleSqlParametersOffset, IList<Parameter> sqlQueryParametersList, QueryParameters queryParameters, ISessionImplementor session) { IType type = ExpectedType; object value = queryParameters.PositionalParameterValues[hqlPosition]; string backTrackId = GetIdsForBackTrack(session.Factory).First(); // just the first because IType suppose the oders in certain sequence // an HQL positional parameter can appear more than once because a custom HQL-Function can duplicate it foreach (int position in sqlQueryParametersList.GetEffectiveParameterLocations(backTrackId)) { type.NullSafeSet(command, GetPagingValue(value, session.Factory.Dialect, queryParameters), position + singleSqlParametersOffset, session); } }
public override int Execute(QueryParameters parameters, ISessionImplementor session) { CoordinateSharedCacheCleanup(session); IDbCommand st = null; RowSelection selection = parameters.RowSelection; try { try { CheckParametersExpectedType(parameters); // NH Different behavior (NH-1898) var parameterTypes = new List<SqlType>(Parameters.Count); foreach (var parameterSpecification in Parameters) { if (parameterSpecification.ExpectedType == null) { throw new QuerySyntaxException("Can't determine SqlType of parameter " + parameterSpecification.RenderDisplayInfo()+"\n Possible cause: wrong case-sensitive property-name."); } parameterTypes.AddRange(parameterSpecification.ExpectedType.SqlTypes(Factory)); } st = session.Batcher.PrepareCommand(CommandType.Text, sql, parameterTypes.ToArray()); IEnumerator<IParameterSpecification> paramSpecifications = Parameters.GetEnumerator(); // NH Different behavior: The inital value is 0 (initialized to 1 in JAVA) int pos = 0; while (paramSpecifications.MoveNext()) { var paramSpec = paramSpecifications.Current; pos += paramSpec.Bind(st, parameters, session, pos); } if (selection != null) { if (selection.Timeout != RowSelection.NoValue) { st.CommandTimeout = selection.Timeout; } } return session.Batcher.ExecuteNonQuery(st); } finally { if (st != null) { session.Batcher.CloseCommand(st, null); } } } catch (DbException sqle) { throw ADOExceptionHelper.Convert(session.Factory.SQLExceptionConverter, sqle, "could not execute update query", sql); } }
public void Bind(IDbCommand command, IList<Parameter> multiSqlQueryParametersList, int singleSqlParametersOffset, IList<Parameter> sqlQueryParametersList, QueryParameters queryParameters, ISessionImplementor session) { // The QueryTakeParameterSpecification is unique so we can use multiSqlQueryParametersList var effectiveParameterLocations = multiSqlQueryParametersList.GetEffectiveParameterLocations(limitParametersNameForThisQuery).ToArray(); if (effectiveParameterLocations.Any()) { // if the dialect does not support variable limits the parameter may was removed int value = queryParameters.RowSelection.MaxRows; int position = effectiveParameterLocations.Single(); type.NullSafeSet(command, value, position, session); } }
public virtual IDataReader GetReader(QueryParameters[] queryParameters, int? commandTimeout) { SqlType[] sqlTypes = types.ToArray(); var command= batcher.PrepareQueryCommand(CommandType.Text, sqlString, sqlTypes); if(commandTimeout.HasValue) { command.CommandTimeout = commandTimeout.Value; } log.Info(command.CommandText); BindParameters(command, queryParameters); return new BatcherDataReaderWrapper(batcher, command); }
protected object GetPagingValue(object value, Dialect.Dialect dialect, QueryParameters queryParameters) { if (isTakeParameter) { int skipParameterValue = 0; if (skipParameter != null) skipParameterValue = skipParameter.GetSkipValue(queryParameters); return dialect.GetLimitValue(skipParameterValue , (int)value); } if (isSkipParameter) return dialect.GetOffsetValue((int)value); return value; }
public IList GetResultFromQueryCache(ISessionImplementor session, QueryParameters queryParameters, ISet<string> querySpaces, IQueryCache queryCache, QueryKey key) { if (!queryParameters.ForceCacheRefresh) { IList list = queryCache.Get(key, new ICacheAssembler[] {this}, queryParameters.NaturalKeyLookup, querySpaces, session); //we had to wrap the query results in another list in order to save all //the queries in the same bucket, now we need to do it the other way around. if (list != null) { list = (IList) list[0]; } return list; } return null; }
public override int Execute(QueryParameters parameters, ISessionImplementor session) { CoordinateSharedCacheCleanup(session); IDbCommand st = null; RowSelection selection = parameters.RowSelection; try { try { CheckParametersExpectedType(parameters); // NH Different behavior (NH-1898) var sqlQueryParametersList = sql.GetParameters().ToList(); SqlType[] parameterTypes = Parameters.GetQueryParameterTypes(sqlQueryParametersList, session.Factory); st = session.Batcher.PrepareCommand(CommandType.Text, sql, parameterTypes); foreach (var parameterSpecification in Parameters) { parameterSpecification.Bind(st, sqlQueryParametersList, parameters, session); } if (selection != null) { if (selection.Timeout != RowSelection.NoValue) { st.CommandTimeout = selection.Timeout; } } return session.Batcher.ExecuteNonQuery(st); } finally { if (st != null) { session.Batcher.CloseCommand(st, null); } } } catch (DbException sqle) { throw ADOExceptionHelper.Convert(session.Factory.SQLExceptionConverter, sqle, "could not execute update query", sql); } }
public SubselectOneToManyLoader(IQueryableCollection persister, SqlString subquery, ICollection<EntityKey> entityKeys, QueryParameters queryParameters, IDictionary<string, int[]> namedParameterLocMap, ISessionFactoryImplementor factory, IDictionary<string, IFilter> enabledFilters) : base(persister, 1, subquery, factory, enabledFilters) { keys = new object[entityKeys.Count]; int i = 0; foreach (EntityKey entityKey in entityKeys) { keys[i++] = entityKey.Identifier; } namedParameters = queryParameters.NamedParameters; // NH Different behavior: to deal with positionslParameter+NamedParameter+ParameterOfFilters types = queryParameters.PositionalParameterTypes; values = queryParameters.PositionalParameterValues; this.namedParameterLocMap = namedParameterLocMap; }
public SubselectCollectionLoader( IQueryableCollection persister, SqlString subquery, ICollection entityKeys, QueryParameters queryParameters, IDictionary namedParameterLocMap, ISessionFactoryImplementor factory, IDictionary<string, IFilter> enabledFilters) : base(persister, 1, subquery, factory, enabledFilters) { keys = new object[entityKeys.Count]; int i = 0; foreach (EntityKey entityKey in entityKeys) { keys[i++] = entityKey.Identifier; } namedParameters = queryParameters.NamedParameters; types = queryParameters.FilteredPositionalParameterTypes; values = queryParameters.FilteredPositionalParameterValues; this.namedParameterLocMap = namedParameterLocMap; }
/// <summary> /// Initializes a new instance of the <see cref="QueryKey"/> class. /// </summary> /// <param name="factory">the session factory for this query key, required to get the identifiers of entities that are used as values.</param> /// <param name="queryString">The query string.</param> /// <param name="queryParameters">The query parameters.</param> /// <param name="filters">The filters.</param> public QueryKey(ISessionFactoryImplementor factory, SqlString queryString, QueryParameters queryParameters, ISet filters) { this.factory = factory; sqlQueryString = queryString; types = queryParameters.PositionalParameterTypes; values = queryParameters.PositionalParameterValues; RowSelection selection = queryParameters.RowSelection; if (selection != null) { firstRow = selection.FirstRow; maxRows = selection.MaxRows; } else { firstRow = RowSelection.NoValue; maxRows = RowSelection.NoValue; } namedParameters = queryParameters.NamedParameters; this.filters = filters; this.customTransformer = queryParameters.ResultTransformer; this.hashCode = ComputeHashCode(); }
/// <summary> /// Initializes a new instance of the <see cref="QueryKey"/> class. /// </summary> /// <param name="factory">the session factory for this query key, required to get the identifiers of entities that are used as values.</param> /// <param name="queryString">The query string.</param> /// <param name="queryParameters">The query parameters.</param> /// <param name="filters">The filters.</param> public QueryKey(ISessionFactoryImplementor factory, SqlString queryString, QueryParameters queryParameters, ISet<FilterKey> filters) { _factory = factory; _sqlQueryString = queryString; _types = queryParameters.PositionalParameterTypes; _values = queryParameters.PositionalParameterValues; RowSelection selection = queryParameters.RowSelection; if (selection != null) { _firstRow = selection.FirstRow; _maxRows = selection.MaxRows; } else { _firstRow = RowSelection.NoValue; _maxRows = RowSelection.NoValue; } _namedParameters = queryParameters.NamedParameters; _filters = filters; _customTransformer = queryParameters.ResultTransformer; _hashCode = ComputeHashCode(); }