1

I'm getting the exception: Method not supported: All on the last line, below:

private static Expression<Func<InstallationSummary, bool>> GetWhereClause(ApplicationServer appServer, ApplicationWithOverrideVariableGroup appWithGroup) { // If we're getting matches that include CustomVariableGroups (CVGs), then the number of CVGs and the IDs must match. return summary => summary.ApplicationServerId == appServer.Id && summary.ApplicationWithOverrideVariableGroup.ApplicationId == appWithGroup.Application.Id && summary.ApplicationWithOverrideVariableGroup != null && summary.ApplicationWithOverrideVariableGroup.CustomVariableGroupIds != null && summary.ApplicationWithOverrideVariableGroup.CustomVariableGroupIds.Count == appWithGroup.CustomVariableGroupIds.Count && summary.ApplicationWithOverrideVariableGroup.CustomVariableGroupIds.All(appWithGroup.CustomVariableGroupIds.Contains); } 

Is there another option to use instead of All(), or do I need to bring back the results and loop through them in memory?

public class ApplicationWithOverrideVariableGroup : EntityBase { // More code here public List<string> CustomVariableGroupIds { get; set; } // More code here } 
5
  • 1
    Show your InstallationSummary class so we can see what CustomVariableGroupIds is. Commented Dec 17, 2014 at 15:03
  • I added it to my question. Commented Dec 17, 2014 at 15:06
  • All can always be replaced by Any with a negated argument. If that's not supported, you can replace it by Where followed by Any(). Would that possibly help? Commented Dec 17, 2014 at 15:09
  • Apparently Any and All are not supported inside expressions. Perhaps calling the Linq extension method manually would do the trick (i.e. transform the All into a plain Call -- though obviously this would require things to be in memory)? Commented Dec 17, 2014 at 15:12
  • Could you retry your code by using a lambda expression in All instead? The way I see it, you are using the Enumerable.All extension method, whereas the extension method that has a chance of working is Queryable.All. (That is, try writing .All(cvg => appWithGroup.CustomVariableGroupIds.Contains(cvg)) Commented Dec 17, 2014 at 15:13

4 Answers 4

1

One option (albeit possibly inefficient) is that you can always pull the query into memory and then perform .All (or any other Linq method) because the records are already loaded into the application space.

To do this in most cases, you just add .AsEnumerable() on your IQueyable object. Because extension methods are defined statically against the specific type, this means you'll be using the Enumerable extension methods, all of which use a foreach, and thus the query evaluates in-memory.

In this case, it may take some restructuring since you're returning a where clause - such an implementation would have to attach this behaviour to the building of the whole query.

Sign up to request clarification or add additional context in comments.

1 Comment

I had to go with the in-memory approach because RavenDB wouldn't work with All() or the negated Any(). Thanks.
0

You can translate All to not Any like:

 summary.ApplicationWithOverrideVariableGroup.CustomVariableGroupIds.All(appWithGroup.CustomVariableGroupIds.Contains); 

to

 !summary.ApplicationWithOverrideVariableGroup.CustomVariableGroupIds.Any(x => !appWithGroup.CustomVariableGroupIds.Contains(x)); 

4 Comments

"All" is not the same as "not any" unless you also negate the inner expression. Example: "No single apple is blue" does not mean "all apples are blue", but "no single apple is a colour other than blue" does.
While not very intuitive (because of the multiple !s), it's at least still just that one line of code. Let me see if I can get that to work...
What's cool about this answer is that ReSharper asks me if I want to simplify it and convert it to the code that Jean provided. I can't, because RavenDB doesn't support it, but it's at least an indication that it's equivalent code.
Apparently RavenDB doesn't allow this approach either. I get: System.InvalidOperationException: Cannot process negated Any(), see RavenDB-732 http://issues.hibernatingrhinos.com/issue/RavenDB-732
0

One problem that I see is that you are not using the correct overloading of .All.

That is, you are using appWithGroup.CustomVariableGroupIds.Contains which is a method group, and as such can be converted to delegate type Func<..., bool>, but not to the Expression<Func<..., bool>> that is required by Queryable.All. Because of that, you are actually using Enumerable.All, which cannot be supported by a LINQ query provider that wants to translate the query expression.

However, you can write your All clause as a lambda expression instead, and then the correct overload will be called:

summary.ApplicationWithOverrideVariableGroup.CustomVariableGroupIds.All(cvg => appWithGroup.CustomVariableGroupIds.Contains(cvg)); 

2 Comments

I tried that and I still get Method not supported: All. Perhaps RavenDB simply doesn't support this yet.
I am also realizing that my explanation is slightly wrong - that is, because CustomVariableGroupIds is probably not an IQueryable, Queryable.All cannot be used.
0

In Raven.Client 3.0 there is a ContainsAll extension method which seem to be what you are searching for.

namespace Raven.Client.Linq { public static class RavenQueryableExtensions { // Summary: // Implementation of the Contains ALL operatior public static bool ContainsAll<T>(this IEnumerable<T> list, IEnumerable<T> items); } } 

Exemple:

string[] parts var query = session.Query<Foo>() .Where(s => s.Keywords.ContainsAll(parts)); return query.ToList(); 

1 Comment

Thank you for the answer. I hope it helps someone. I'm not in a position to try this now.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.