public virtual void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
        {
            ArgumentUtility.CheckNotNull ("joinClause", joinClause);
              ArgumentUtility.CheckNotNull ("queryModel", queryModel);

              // nothing to do here
        }
        public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
        {
            var subQueryExpression = joinClause.InnerSequence as SubQueryExpression;

            if (subQueryExpression != null)
            {
                VisitQueryModel(subQueryExpression.QueryModel);

                if (subQueryExpression.QueryModel.IsIdentityQuery()
                    && !subQueryExpression.QueryModel.ResultOperators.Any())
                {
                    joinClause.InnerSequence
                        = subQueryExpression.QueryModel.MainFromClause.FromExpression;

                    foreach (var queryAnnotation
                        in _queryAnnotations
                            .Where(qa => qa.QuerySource == subQueryExpression.QueryModel.MainFromClause))
                    {
                        queryAnnotation.QuerySource = joinClause;
                    }
                }
            }

            base.VisitJoinClause(joinClause, queryModel, index);
        }
Example #3
0
    public GroupJoinClause (string itemName, Type itemType, JoinClause joinClause)
    {
      ArgumentUtility.CheckNotNullOrEmpty ("itemName", itemName);
      ArgumentUtility.CheckNotNull ("itemType", itemType);
      ArgumentUtility.CheckNotNull ("joinClause", joinClause);

      ItemName = itemName;
      ItemType = itemType;
      JoinClause = joinClause;
    }
    public override void SetUp ()
    {
      base.SetUp ();

      _innerSequence = ExpressionHelper.CreateExpression();
      _outerKeySelector = ExpressionHelper.CreateLambdaExpression<string, string> (o => o.ToString ());
      _innerKeySelector = ExpressionHelper.CreateLambdaExpression<string, string> (i => i.ToString ());
      _resultSelector = ExpressionHelper.CreateLambdaExpression<string, string, string> ((o, i) => o.ToString () + i.ToString ());

      _node = new JoinExpressionNode (CreateParseInfo (SourceNode, "join"), _innerSequence, _outerKeySelector, _innerKeySelector, _resultSelector);
      _joinClause = ExpressionHelper.CreateJoinClause<Cook> ();
    }
        public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
        {
            throw new NotSupportedException ();
            /*
            // HQL joins work differently, need to simulate using a cross join with a where condition
            queryParts.AddFromPart (joinClause);
            queryParts.AddWherePart (
                "({0} = {1})",
                GetHqlExpression (joinClause.OuterKeySelector),
                GetHqlExpression (joinClause.InnerKeySelector));

            base.VisitJoinClause (joinClause, queryModel, index);
            */
        }
Example #6
0
    public void Intialize()
    {
      Expression innerSequence = ExpressionHelper.CreateExpression ();
      Expression outerKeySelector = ExpressionHelper.CreateExpression ();
      Expression innerKeySelector = ExpressionHelper.CreateExpression ();

      var joinClause = new JoinClause ("x", typeof(Cook), innerSequence, outerKeySelector, innerKeySelector);

      Assert.That (joinClause.ItemName, Is.SameAs ("x"));
      Assert.That (joinClause.ItemType, Is.SameAs (typeof (Cook)));
      Assert.That (joinClause.InnerSequence, Is.SameAs (innerSequence));
      Assert.That (joinClause.InnerKeySelector, Is.SameAs (innerKeySelector));
      Assert.That (joinClause.OuterKeySelector, Is.SameAs (outerKeySelector));
    }
Example #7
0
        /// <summary>
        /// Clones this clause, registering its clone with the <paramref name="cloneContext"/>.
        /// </summary>
        /// <param name="cloneContext">The clones of all query source clauses are registered with this <see cref="CloneContext"/>.</param>
        /// <returns>A clone of this clause.</returns>
        public JoinClause Clone(CloneContext cloneContext)
        {
            ArgumentUtility.CheckNotNull ("cloneContext", cloneContext);

              var clone = new JoinClause (ItemName, ItemType, InnerSequence, OuterKeySelector, InnerKeySelector);
              cloneContext.QuerySourceMapping.AddMapping (this, new QuerySourceReferenceExpression (clone));
              return clone;
        }
Example #8
0
 public void AddJoin(JoinClause join)
 {
     Joins.Add(join);
 }
Example #9
0
        public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
        {
            base.VisitJoinClause(joinClause, queryModel, index);

            var subQuery = joinClause.InnerSequence as SubQueryExpression;

            if (subQuery != null)
            {
                var isOuter = subQuery.QueryModel.ResultOperators.OfType<DefaultIfEmptyResultOperator>().Any();

                _builder.AppendFormat("{0} join (", isOuter ? "left outer" : "inner");

                VisitQueryModel(subQuery.QueryModel, true);

                var alias = _aliases.GetTableAlias(subQuery.QueryModel.MainFromClause);
                _builder.AppendFormat(") as {0} on (", alias);
            }
            else
            {
                var innerExpr = joinClause.InnerSequence as ConstantExpression;

                if (innerExpr == null)
                    throw new NotSupportedException("Unexpected JOIN inner sequence (subqueries are not supported): " +
                                                    joinClause.InnerSequence);

                if (!(innerExpr.Value is ICacheQueryable))
                    throw new NotSupportedException("Unexpected JOIN inner sequence " +
                                                    "(only results of cache.ToQueryable() are supported): " +
                                                    innerExpr.Value);

                var queryable = ExpressionWalker.GetCacheQueryable(joinClause);
                var tableName = ExpressionWalker.GetTableNameWithSchema(queryable);
                var alias = _aliases.GetTableAlias(joinClause);
                _builder.AppendFormat("inner join {0} as {1} on (", tableName, alias);
            }

            BuildJoinCondition(joinClause.InnerKeySelector, joinClause.OuterKeySelector);

            _builder.Append(") ");
        }
		public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
		{
			var equalityVisitor = new EqualityHqlGenerator(VisitorParameters);
			var whereClause = equalityVisitor.Visit(joinClause.InnerKeySelector, joinClause.OuterKeySelector);

			_hqlTree.AddWhereClause(whereClause);

			_hqlTree.AddFromClause(
				_hqlTree.TreeBuilder.Range(
					HqlGeneratorExpressionTreeVisitor.Visit(joinClause.InnerSequence, VisitorParameters),
					_hqlTree.TreeBuilder.Alias(joinClause.ItemName)));
		}
 /// <summary>
 ///     This API supports the Entity Framework Core infrastructure and is not intended to be used
 ///     directly from your code. This API may change or be removed in future releases.
 /// </summary>
 public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, GroupJoinClause groupJoinClause)
     => joinClause.TransformExpressions(TransformingVisitor.Visit);
Example #12
0
 public void SetUp ()
 {
   _joinClause = ExpressionHelper.CreateJoinClause<Cook> ();
   _cloneContext = new CloneContext (new QuerySourceMapping());
 }
    public void VisitQuerySourceReferenceExpression_WithNonNullWhereCondition ()
    {
      var memberInfo = typeof (Cook).GetProperty ("Assistants");
      var sqlTableReferenceExpression = new SqlTableReferenceExpression (SqlStatementModelObjectMother.CreateSqlTable (typeof (Cook)));
      var innerSequenceExpression =
          Expression.MakeMemberAccess (
              sqlTableReferenceExpression, memberInfo);
      var joinClause = new JoinClause (
          "x",
          typeof (Cook[]),
          innerSequenceExpression,
          Expression.Constant (new Cook()),
          Expression.Constant (new Cook()));
      var groupJoinClause = new GroupJoinClause ("g", typeof (Cook[]), joinClause);
      var querySourceReferenceExpression = new QuerySourceReferenceExpression (groupJoinClause);
      var fakeWhereExpression = Expression.Constant (true);

      _stageMock
          .Expect (mock => mock.PrepareWhereExpression (Arg<Expression>.Matches (e => e is BinaryExpression), Arg.Is (_context)))
          .WhenCalled (
              mi =>
              SqlExpressionTreeComparer.CheckAreEqualTrees (
                  Expression.Equal (groupJoinClause.JoinClause.OuterKeySelector, groupJoinClause.JoinClause.InnerKeySelector),
                  (Expression) mi.Arguments[0]))
          .Return (fakeWhereExpression);
      _stageMock.Replay();

      _visitor.VisitQuerySourceReferenceExpression (querySourceReferenceExpression);

      _stageMock.VerifyAllExpectations();

      Assert.That (_visitor.FromExpressionInfo != null); // inline condition because of ReSharper
      var fromExpressionInfo = (FromExpressionInfo) _visitor.FromExpressionInfo;

      Assert.That (fromExpressionInfo.WhereCondition, Is.AssignableTo (typeof (BinaryExpression)));
      Assert.That (fromExpressionInfo.WhereCondition.NodeType, Is.EqualTo(ExpressionType.AndAlso));
      Assert.That (((BinaryExpression) fromExpressionInfo.WhereCondition).Left, Is.TypeOf(typeof(JoinConditionExpression)));
      Assert.That (((JoinConditionExpression) ((BinaryExpression) fromExpressionInfo.WhereCondition).Left).JoinedTable.JoinInfo, Is.TypeOf (typeof (UnresolvedCollectionJoinInfo)));
      Assert.That (
          ((UnresolvedCollectionJoinInfo) ((JoinConditionExpression) ((BinaryExpression) fromExpressionInfo.WhereCondition).Left).JoinedTable.JoinInfo).SourceExpression, Is.SameAs(sqlTableReferenceExpression));
      Assert.That (
          ((UnresolvedCollectionJoinInfo) ((JoinConditionExpression) ((BinaryExpression) fromExpressionInfo.WhereCondition).Left).JoinedTable.JoinInfo).MemberInfo, Is.SameAs (memberInfo));
      Assert.That (((JoinConditionExpression) ((BinaryExpression) fromExpressionInfo.WhereCondition).Left).JoinedTable.JoinSemantics, Is.EqualTo(JoinSemantics.Inner));
      Assert.That (((BinaryExpression) fromExpressionInfo.WhereCondition).Right, Is.SameAs (fakeWhereExpression));
    }
        public JoinClause CreateJoinClause(ClauseGenerationContext clauseGenerationContext)
        {
            var dummyInnerKeySelector = Expression.Constant (null);
              var joinClause = new JoinClause (
              ResultSelector.Parameters[1].Name,
              ResultSelector.Parameters[1].Type,
              InnerSequence,
              GetResolvedOuterKeySelector (clauseGenerationContext),
              dummyInnerKeySelector);

              clauseGenerationContext.AddContextInfo (this, joinClause);

              joinClause.InnerKeySelector = GetResolvedInnerKeySelector (clauseGenerationContext);
              return joinClause;
        }
 //TODO: Implement Joins
 public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel,
     GroupJoinClause groupJoinClause)
 {
     base.VisitJoinClause(joinClause, queryModel, groupJoinClause);
 }
        /// <summary>
        /// Visits a join against either a constant expression of IBucketQueryable, or a subquery based on an IBucketQueryable
        /// </summary>
        /// <param name="joinClause">Join clause being visited</param>
        /// <returns>N1QlFromQueryPart to be added to the QueryPartsAggregator.  JoinType is defaulted to INNER JOIN.</returns>
        /// <remarks>The InnerKeySelector must be selecting the N1QlFunctions.Key of the InnerSequence</remarks>
        private N1QlFromQueryPart ParseJoinClause(JoinClause joinClause)
        {
            switch (joinClause.InnerSequence.NodeType)
            {
                case ExpressionType.Constant:
                    return VisitConstantExpressionJoinClause(joinClause, joinClause.InnerSequence as ConstantExpression);

                case SubQueryExpression.ExpressionType:
                    var subQuery = joinClause.InnerSequence as SubQueryExpression;
                    if ((subQuery == null) || subQuery.QueryModel.ResultOperators.Any() || subQuery.QueryModel.MainFromClause.FromExpression.NodeType != ExpressionType.Constant)
                    {
                        throw new NotSupportedException("Unsupported Join Inner Sequence");
                    }

                    // be sure the subquery clauses use the same name
                    _queryGenerationContext.ExtentNameProvider.LinkExtents(joinClause,
                        subQuery.QueryModel.MainFromClause);

                    var fromPart = VisitConstantExpressionJoinClause(joinClause,
                        subQuery.QueryModel.MainFromClause.FromExpression as ConstantExpression);

                    VisitBodyClauses(subQuery.QueryModel.BodyClauses, subQuery.QueryModel);

                    return fromPart;

                default:
                    throw new NotSupportedException("Unsupported Join Inner Sequence");
            }
        }
        /// <summary>
        /// Visits a join against a constant expression, which must be an IBucketQueryable implementation
        /// </summary>
        /// <param name="joinClause">Join clause being visited</param>
        /// <param name="constantExpression">Constant expression that is the InnerSequence of the JoinClause</param>
        /// <returns>N1QlFromQueryPart to be added to the QueryPartsAggregator.  JoinType is defaulted to INNER JOIN.</returns>
        /// <remarks>The InnerKeySelector must be selecting the N1QlFunctions.Key of the InnerSequence</remarks>
        private N1QlFromQueryPart VisitConstantExpressionJoinClause(JoinClause joinClause, ConstantExpression constantExpression)
        {
            string bucketName = null;

            if (constantExpression != null)
            {
                var bucketQueryable = constantExpression.Value as IBucketQueryable;
                if (bucketQueryable != null)
                {
                    bucketName = bucketQueryable.BucketName;
                }
            }

            if (bucketName == null)
            {
                throw new NotSupportedException("N1QL Joins Must Be Against IBucketQueryable");
            }

            var keyExpression = joinClause.InnerKeySelector as MethodCallExpression;
            if ((keyExpression == null) ||
                (keyExpression.Method != typeof(N1QlFunctions).GetMethod("Key")) ||
                (keyExpression.Arguments.Count != 1))
            {
                throw new NotSupportedException("N1QL Join Selector Must Be A Call To N1QlFunctions.Key");
            }

            if (!(keyExpression.Arguments[0] is QuerySourceReferenceExpression))
            {
                throw new NotSupportedException("N1QL Join Selector Call To N1QlFunctions.Key Must Reference The Inner Sequence");
            }

            return new N1QlFromQueryPart()
            {
                Source = N1QlHelpers.EscapeIdentifier(bucketName),
                ItemName = GetExtentName(joinClause),
                OnKeys = GetN1QlExpression(joinClause.OuterKeySelector),
                JoinType = "INNER JOIN"
            };
        }
        public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
        {
            // basic join clause is an INNER JOIN against another bucket

            EnsureNotArraySubquery();

            var fromQueryPart = ParseJoinClause(joinClause);

            _queryPartsAggregator.AddFromPart(fromQueryPart);

            base.VisitJoinClause(joinClause, queryModel, index);
        }
        public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel,
            GroupJoinClause groupJoinClause)
        {
            // Store the group join with the expectation it will be used later by an additional from clause

            EnsureNotArraySubquery();

            _unclaimedGroupJoins.Add(new UnclaimedGroupJoin()
            {
                JoinClause = joinClause,
                GroupJoinClause = groupJoinClause
            });

            base.VisitJoinClause(joinClause, queryModel, groupJoinClause);
        }
    public void VisitQuerySourceReferenceExpression_WithExtractedOrderings ()
    {
      var sqlTable = SqlStatementModelObjectMother.CreateSqlTable (typeof (Cook));
      var sqlTableReferenceExpression = new SqlTableReferenceExpression (sqlTable);
      var selectProjection = new NamedExpression("test", Expression.MakeMemberAccess (sqlTableReferenceExpression, typeof (Cook).GetProperty ("Name")));
      var orderingExpression = Expression.MakeMemberAccess (sqlTableReferenceExpression, typeof (Cook).GetProperty ("ID"));
      var sqlStatement = new SqlStatementBuilder
                         {
                             DataInfo = new StreamedSequenceInfo(typeof (DateTime[]), Expression.Constant (new DateTime (2000, 1, 1))),
                             SelectProjection = selectProjection,
                             SqlTables = { sqlTable },
                             Orderings =
                                 { new Ordering (orderingExpression, OrderingDirection.Asc) }
                         }.GetSqlStatement();
      var fakeSelectExpression = Expression.Constant (new KeyValuePair<string, int>("test", 5));
      var fakeWhereExpression = Expression.Constant (true);

      var innerSequenceExpression = new SqlSubStatementExpression (sqlStatement);
          
      var joinClause = new JoinClause (
          "x",
          typeof (Cook[]),
          innerSequenceExpression,
          Expression.Constant (new Cook ()),
          Expression.Constant (new Cook ()));
      var groupJoinClause = new GroupJoinClause ("g", typeof (Cook[]), joinClause);
      var querySourceReferenceExpression = new QuerySourceReferenceExpression (groupJoinClause);

      _stageMock
          .Expect (mock => mock.PrepareSelectExpression(Arg<Expression>.Is.Anything, Arg<ISqlPreparationContext>.Is.Anything))
          .Return (fakeSelectExpression);
      _stageMock
          .Expect (mock => mock.PrepareWhereExpression (Arg<Expression>.Matches (e => e is BinaryExpression), Arg.Is (_context)))
          .WhenCalled (
              mi =>
              SqlExpressionTreeComparer.CheckAreEqualTrees (
                  Expression.Equal (groupJoinClause.JoinClause.OuterKeySelector, groupJoinClause.JoinClause.InnerKeySelector),
                  (Expression) mi.Arguments[0]))
          .Return (fakeWhereExpression);
      _stageMock.Replay ();

      _visitor.VisitQuerySourceReferenceExpression (querySourceReferenceExpression);

      _stageMock.VerifyAllExpectations ();

      Assert.That (_visitor.FromExpressionInfo != null); // inline condition because of ReSharper
      var fromExpressionInfo = (FromExpressionInfo) _visitor.FromExpressionInfo;

      Assert.That (fromExpressionInfo.ExtractedOrderings.Count, Is.EqualTo(1));
      Assert.That (fromExpressionInfo.ExtractedOrderings[0].Expression, Is.AssignableTo(typeof(MemberExpression)));
      Assert.That (((MemberExpression) fromExpressionInfo.ExtractedOrderings[0].Expression).Expression, Is.TypeOf(typeof(SqlTableReferenceExpression)));
      Assert.That (
          ((SqlTableReferenceExpression) ((MemberExpression) fromExpressionInfo.ExtractedOrderings[0].Expression).Expression).SqlTable, Is.TypeOf (typeof (SqlTable)));
      Assert.That (
          ((SqlTable) ((SqlTableReferenceExpression) ((MemberExpression) fromExpressionInfo.ExtractedOrderings[0].Expression).Expression).SqlTable).TableInfo, Is.TypeOf (typeof (ResolvedSubStatementTableInfo)));
      var resolvedSubStatementtableInfo =
         (ResolvedSubStatementTableInfo) ((SqlTable) ((SqlTableReferenceExpression) ((MemberExpression) fromExpressionInfo.ExtractedOrderings[0].Expression).Expression).SqlTable).TableInfo;
      Assert.That (resolvedSubStatementtableInfo.SqlStatement.SelectProjection, Is.SameAs(fakeSelectExpression));
      Assert.That (resolvedSubStatementtableInfo.SqlStatement.Orderings.Count, Is.EqualTo (0));
      Assert.That (((MemberExpression) fromExpressionInfo.ExtractedOrderings[0].Expression).Member, Is.EqualTo(typeof(KeyValuePair<,>).MakeGenericType(typeof(string), typeof(int)).GetProperty("Value")));
      Assert.That (fromExpressionInfo.ItemSelector, Is.AssignableTo (typeof (MemberExpression)));
      Assert.That (((MemberExpression) fromExpressionInfo.ItemSelector).Expression, Is.TypeOf(typeof(SqlTableReferenceExpression)));
      Assert.That (((SqlTableReferenceExpression) ((MemberExpression) fromExpressionInfo.ItemSelector).Expression).SqlTable, Is.TypeOf (typeof (SqlTable)));
      Assert.That (
          ((SqlTable) ((SqlTableReferenceExpression) ((MemberExpression) fromExpressionInfo.ItemSelector).Expression).SqlTable).TableInfo, Is.TypeOf (typeof (ResolvedSubStatementTableInfo)));
      Assert.That (((MemberExpression) fromExpressionInfo.ItemSelector).Member, Is.EqualTo (typeof (KeyValuePair<,>).MakeGenericType (typeof (string), typeof (int)).GetProperty ("Key")));
    }
Example #21
0
    public void TransformExpressions ()
    {
      var oldInnerSequence = ExpressionHelper.CreateExpression ();
      var oldOuterKeySelector = ExpressionHelper.CreateExpression ();
      var oldInnerKeySelector = ExpressionHelper.CreateExpression ();
      var newInnerSequence = ExpressionHelper.CreateExpression ();
      var newOuterKeySelector = ExpressionHelper.CreateExpression ();
      var newInnerKeySelector = ExpressionHelper.CreateExpression ();

      var clause = new JoinClause ("x", typeof (Cook), oldInnerSequence, oldOuterKeySelector, oldInnerKeySelector);

      clause.TransformExpressions (ex =>
          {
            if (ex == oldInnerSequence)
              return newInnerSequence;
            else if (ex == oldOuterKeySelector)
              return newOuterKeySelector;
            else if (ex == oldInnerKeySelector)
              return newInnerKeySelector;
            else
            {
              Assert.Fail();
              return null;
            }
          });

      Assert.That (clause.InnerSequence, Is.SameAs (newInnerSequence));
      Assert.That (clause.OuterKeySelector, Is.SameAs (newOuterKeySelector));
      Assert.That (clause.InnerKeySelector, Is.SameAs (newInnerKeySelector));
    }
    public SqlTableBase AddJoinClause (JoinClause joinClause)
    {
      ArgumentUtility.CheckNotNull ("joinClause", joinClause);

      var table = AddQuerySource (joinClause, joinClause.InnerSequence);

      var whereCondition = Expression.Equal (joinClause.OuterKeySelector, joinClause.InnerKeySelector);
      SqlStatementBuilder.AddWhereCondition (_stage.PrepareWhereExpression (whereCondition, _context));

      return table;
    }
Example #23
0
 public new void ToString ()
 {
   var joinClause = new JoinClause ("x", typeof (Cook), Expression.Constant (0), Expression.Constant (1), Expression.Constant (2));
   Assert.That (joinClause.ToString (), Is.EqualTo ("join Cook x in 0 on 1 equals 2"));
 }
 public new void ToString ()
 {
   var joinClause = new JoinClause ("x", typeof (Cook), Expression.Constant (0), Expression.Constant (1), Expression.Constant (2));
   var groupJoinClause = new GroupJoinClause ("y", typeof (IEnumerable<Cook>), joinClause);
   Assert.That (groupJoinClause.ToString (), Is.EqualTo ("join Cook x in 0 on 1 equals 2 into IEnumerable`1 y"));
 }
 public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, GroupJoinClause groupJoinClause)
 {
     throw new NotSupportedException("Join clauses not supported");
 }
    public void VisitQuerySourceReferenceExpression ()
    {
      var innerSequenceExpression = Expression.Constant (new[] { new Cook() });
      var joinClause = new JoinClause (
          "x",
          typeof (Cook[]),
          innerSequenceExpression,
          Expression.Constant (new Cook()),
          Expression.Constant (new Cook()));
      var groupJoinClause = new GroupJoinClause ("g", typeof (Cook[]), joinClause);
      var querySourceReferenceExpression = new QuerySourceReferenceExpression (groupJoinClause);
      var fakeWhereExpression = Expression.Constant (true);

      _stageMock
          .Expect (mock => mock.PrepareWhereExpression (Arg<Expression>.Matches (e => e is BinaryExpression), Arg.Is (_context)))
          .WhenCalled (
              mi =>
              SqlExpressionTreeComparer.CheckAreEqualTrees (
                  Expression.Equal (groupJoinClause.JoinClause.OuterKeySelector, groupJoinClause.JoinClause.InnerKeySelector),
                  (Expression) mi.Arguments[0]))
          .Return (fakeWhereExpression);
      _stageMock.Replay();

      var result = _visitor.VisitQuerySourceReferenceExpression (querySourceReferenceExpression);

      _stageMock.VerifyAllExpectations();

      Assert.That (_visitor.FromExpressionInfo, Is.Not.Null);
      var fromExpressionInfo = (FromExpressionInfo) _visitor.FromExpressionInfo;

      SqlExpressionTreeComparer.CheckAreEqualTrees (
          new SqlTableReferenceExpression (fromExpressionInfo.SqlTable),
          _context.GetExpressionMapping (new QuerySourceReferenceExpression (groupJoinClause.JoinClause)));
      SqlExpressionTreeComparer.CheckAreEqualTrees (fromExpressionInfo.ItemSelector, result);
      Assert.That (((UnresolvedTableInfo) ((SqlTable) fromExpressionInfo.SqlTable).TableInfo).ItemType, Is.EqualTo (typeof (Cook)));
      Assert.That (fromExpressionInfo.WhereCondition, Is.SameAs (fakeWhereExpression));
      Assert.That (fromExpressionInfo.ExtractedOrderings.Count, Is.EqualTo (0));
    }
		public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
		{
			QueryParts.AddJoin(joinClause);

			base.VisitJoinClause(joinClause, queryModel, index);
		}
		public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, GroupJoinClause groupJoinClause)
		{
			_namer.Add(joinClause);
		}
        public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
        {
            _queryPartsAggregator.AddFromPart(new N1QlFromQueryPart()
            {
                Source = joinClause.ItemType.Name.ToLower(),
                ItemName = joinClause.ItemName
            });

            _queryPartsAggregator.AddWherePart("ON KEYS ARRAY {0} FOR {1} IN {2} END",
                joinClause.OuterKeySelector,
                joinClause.InnerKeySelector,
                joinClause.ItemName);

            base.VisitJoinClause(joinClause, queryModel, index);
        }
		public override void VisitJoinClause(JoinClause joinClause, QueryModel queryModel, int index)
		{
			_namer.Add(joinClause);
		}