views:

34

answers:

0

I am working on create an Extension Method in the Linq.Dynamic project for GroupJoin. But, for some reason it will not run. The signatures seem to match.

public static IQueryable GroupJoin(this IQueryable outer, IEnumerable inner, string outerSelector, string innerSelector, string resultsSelector, params object[] values)
    {
        if (inner == null) throw new ArgumentNullException("inner");
        if (outerSelector == null) throw new ArgumentNullException("outerSelector");
        if (innerSelector == null) throw new ArgumentNullException("innerSelector");
        if (resultsSelector == null) throw new ArgumentNullException("resultsSelctor");

        LambdaExpression outerSelectorLambda = DynamicExpression.ParseLambda(outer.ElementType, null, outerSelector, values);
        Type enumType = GetList(inner.AsQueryable().ElementType).GetType();

        LambdaExpression innerSelectorLambda = DynamicExpression.ParseLambda(inner.AsQueryable().ElementType, null, innerSelector, values);

        ParameterExpression[] parameters = new ParameterExpression[] { 
        Expression.Parameter(outer.ElementType, "outer"), Expression.Parameter(enumType, "inner") };
        LambdaExpression resultsSelectorLambda = DynamicExpression.ParseLambda(parameters, null, resultsSelector, values);


        return outer.Provider.CreateQuery(
            Expression.Call(
                typeof(Queryable), "GroupJoin",
                new Type[] { outer.ElementType, inner.AsQueryable().ElementType, outerSelectorLambda.Body.Type, resultsSelectorLambda.Body.Type },
                outer.Expression, inner.AsQueryable().Expression, Expression.Quote(outerSelectorLambda), Expression.Quote(innerSelectorLambda), Expression.Quote(resultsSelectorLambda)));
    }
public static System.Collections.IEnumerable GetList(System.Type type)
    {
        return (System.Collections.IEnumerable)Activator.CreateInstance(typeof(List<>).MakeGenericType(type));
    }

This code gives me the following error:

No generic method 'GroupJoin' on type 'System.Linq.Queryable' is compatible with the supplied type arguments and arguments. No type arguments should be provided if the method is non-generic.

In looking at the results of each piece they seem to match: Writing the follwing GroupJoin:

man.Contacts.GroupJoin(man.ContactAddresses, param_0 => param_0.ContactId, param_0 => param_0.ContactId, 
                (outer, inner) => new { ContactId = outer.ContactId, FirstName = outer.FirstName, LastName = outer.LastName, MI = outer.MiddleInitial, ContactAddresses = inner });

I get the debug of:

.Call System.Linq.Queryable.GroupJoin(
.Constant<IdeaBlade.EntityModel.EntityQueryProxy`1[LOC.AMP.Data.DomainModel.Contact]>(IdeaBlade.EntityModel.EntityQueryProxy`1[LOC.AMP.Data.DomainModel.Contact]),
.Constant<IdeaBlade.EntityModel.EntityQueryProxy`1[LOC.AMP.Data.DomainModel.ContactAddress]>(IdeaBlade.EntityModel.EntityQueryProxy`1[LOC.AMP.Data.DomainModel.ContactAddress]),
'(.Lambda #Lambda1<System.Func`2[LOC.AMP.Data.DomainModel.Contact,System.Int64]>),
'(.Lambda #Lambda2<System.Func`2[LOC.AMP.Data.DomainModel.ContactAddress,System.Int64]>),
'(.Lambda #Lambda3<System.Func`3[LOC.AMP.Data.DomainModel.Contact,System.Collections.Generic.IEnumerable`1[LOC.AMP.Data.DomainModel.ContactAddress],
<>f__AnonymousType0`5[System.Int64,System.String,System.String,System.String,System.Collections.Generic.IEnumerable`1[LOC.AMP.Data.DomainModel.ContactAddress]]]>))
.Lambda #Lambda1<System.Func`2[LOC.AMP.Data.DomainModel.Contact,System.Int64]>(LOC.AMP.Data.DomainModel.Contact $param_0)
{
    $param_0.ContactId
}

.Lambda #Lambda2<System.Func`2[LOC.AMP.Data.DomainModel.ContactAddress,System.Int64]>(LOC.AMP.Data.DomainModel.ContactAddress $param_0)
{
    $param_0.ContactId
}

.Lambda 
    #Lambda3<System.Func`3
    [
        LOC.AMP.Data.DomainModel.Contact, System.Collections.Generic.IEnumerable`1[LOC.AMP.Data.DomainModel.ContactAddress],
        <>f__AnonymousType0`5
        [
            System.Int64,System.String,System.String,System.String, System.Collections.Generic.IEnumerable`1
            [
                LOC.AMP.Data.DomainModel.ContactAddress
            ]
        ]
    ]>
    (LOC.AMP.Data.DomainModel.Contact $outer, System.Collections.Generic.IEnumerable`1
        [LOC.AMP.Data.DomainModel.ContactAddress] $inner) 

    {
    .New <>f__AnonymousType0`5[System.Int64,System.String,System.String,System.String,System.Collections.Generic.IEnumerable`1[LOC.AMP.Data.DomainModel.ContactAddress]](
        $outer.ContactId,
        $outer.FirstName,
        $outer.LastName,
        $outer.MiddleInitial,
        $inner)
}

With the following GroupJoin:

man.Contacts.GroupJoin(man.ContactAddresses, "ContactId", "ContactId", "new (outer.ContactId as ContactId, outer.FirstName as FirstName, outer.LastName as LastName, outer.MiddleInitial as MI, inner as ContactAddresses)");

Then looking at the debug:

.Call GroupJoin (
{value(IdeaBlade.EntityModel.EntityQueryProxy`1[LOC.AMP.Data.DomainModel.Contact])},
{value(IdeaBlade.EntityModel.EntityQueryProxy`1[LOC.AMP.Data.DomainModel.ContactAddress])},
'(.Lambda #Lambda1<System.Func`2[LOC.AMP.Data.DomainModel.Contact,System.Int64]>),
'(.Lambda #Lambda1<System.Func`2[LOC.AMP.Data.DomainModel.ContactAddress,System.Int64]>),
'(.Lambda #Lambda1<System.Func`3[LOC.AMP.Data.DomainModel.Contact,System.Collections.Generic.List`1[LOC.AMP.Data.DomainModel.ContactAddress],DynamicClass1]>)



//ContactId
.Lambda #Lambda1<System.Func`2[LOC.AMP.Data.DomainModel.Contact,System.Int64]>(LOC.AMP.Data.DomainModel.Contact $var1) 
{
    $var1.ContactId
}

//CA.ContactId
.Lambda #Lambda1<System.Func`2[LOC.AMP.Data.DomainModel.ContactAddress,System.Int64]>(LOC.AMP.Data.DomainModel.ContactAddress $var1)
{
    $var1.ContactId
}


    //Dynamic Result
    .Lambda #Lambda1<System.Func`3[LOC.AMP.Data.DomainModel.Contact,System.Collections.Generic.List`1[LOC.AMP.Data.DomainModel.ContactAddress],DynamicClass1]>(
        LOC.AMP.Data.DomainModel.Contact $outer,
        System.Collections.Generic.List`1[LOC.AMP.Data.DomainModel.ContactAddress] $inner) {
    .New DynamicClass1(){
        ContactId = $outer.ContactId,
        FirstName = $outer.FirstName,
        LastName = $outer.LastName,
        MI = $outer.MiddleInitial,
        ContactAddresses = $inner
    }
}

The only thing different is List<> compared to IEnumerable. But List<> is IEnumerable. The error reads like the signature is wrong. I just can't figure it out.

Any incite would be great.