Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

DbFunctions invoked without DbContext references are always executed on the client #21228

Closed
MaxG117 opened this issue Jun 11, 2020 · 4 comments
Labels
closed-no-further-action The issue is closed and no further action is planned. customer-reported

Comments

@MaxG117
Copy link

MaxG117 commented Jun 11, 2020

The DbFunctions that do not have any references to DbContext are now always executing on the client for some reason. No attempt is made to translate them with IMethodCallTranslator.

Steps to reproduce

Consider the following DbFunctions extension:

        public static Double Degrees(
            [CanBeNull] this DbFunctions _,
            [NotNull] Object value)
            => throw new InvalidOperationException(MyStrings.DBFunctionOnClient)

If the application does the following:

            var rows = myContext.myTables
                .Where (e => e.Id == 3)
                .Select(r => new
                {
                    deg = EF.Functions.Degrees(r.Id),

then EF.Functions.Degrees is translated by my IMethodCallTranslator into the desired server-side function call. But if the application does this:

            var rows = myContext.myTables
                .Where (e => e.Id == 3)
                .Select(r => new
                {
                    deg = EF.Functions.Degrees(2),

then no translation is performed and EF tries to execute it locally, resulting in exception. Niladic functions meant to execute on the server also do not work (since they don't have any references to DbContext).

This worked correctly in 2.2, but it's not working in 3.1. Is this a bug in EF or do I need to do something on my end to make it work again?

I do not see this mentioned in 3.0 breaking changes as it does not appear to be related to #12757. I also don't think it's related to #9022.

Further technical details

EF Core version: 3.1.4
Database provider: the one I'm writing

@smitpatel
Copy link
Contributor

EF.Functions.Degrees(2) is not correlated with server in anyway and it will always be evaluated on client and converted to parameter. That is how parameter extraction works on a query to aid query caching. See #13524 & #13549

If you want the function to evaluate on client side then you can body for the method.

@smitpatel smitpatel added the closed-no-further-action The issue is closed and no further action is planned. label Jun 11, 2020
@MaxG117
Copy link
Author

MaxG117 commented Jun 11, 2020

If you want the function to evaluate on client side then you can body for the method.

@smitpatel could you clarify please? I want certain DbFunctions to always evaluate on the server.

@smitpatel
Copy link
Contributor

I suggest reading this thread, it capture everything. #12527
You can register your function to be not evaluatable on client side by using IExpressionEvaluatbleFilter service.
In our providers, we don't do it. If EF.Functions.Degrees(2) is not server correlated then there is very little value in sending it to server rather than using direct value.

@MaxG117
Copy link
Author

MaxG117 commented Jun 11, 2020

I'm sorry, I introduced a bug while upgrading our IEvaluatableExpressionFilter implementation to 3.x and forgot that it was involved in this. Thanks very much!

EF.Functions.Degrees was just a bad example, since there is such a function in most providers for converting radians to degrees. I was just talking about any function that must be evaluated on the server.

@MaxG117 MaxG117 closed this as completed Jun 11, 2020
@ajcvickers ajcvickers reopened this Oct 16, 2022
@ajcvickers ajcvickers closed this as not planned Won't fix, can't repro, duplicate, stale Oct 16, 2022
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
closed-no-further-action The issue is closed and no further action is planned. customer-reported
Projects
None yet
Development

No branches or pull requests

3 participants