PowerPlatform-DataverseServiceClient icon indicating copy to clipboard operation
PowerPlatform-DataverseServiceClient copied to clipboard

Linq query selecting only Id requests all columns from CDS

Open filcole opened this issue 4 years ago • 5 comments

The following Linq query will return all columns from CDS, I'd only expect the Id column to be returned.

                Guid accountId = (from a in context.AccountSet
                                  where a.Name.Equals("Wonka Chocolate Factory")
                                  select a.Id).FirstOrDefault();

This occurs with latest versions of both clients:

  • Microsoft.PowerPlatform.Cds.Client, Version 0.2.31-Alpha
  • Microsoft.CrmSdk.XrmTooling.CoreAssembly, Version 9.1.0.51

Request: image

Response: image

The following query does not return all columns from CDS.

                Guid? accountId = (from a in context.AccountSet
                                   where a.Name.Equals("Wonka Chocolate Factory")
                                   select a.AccountId).FirstOrDefault();

Request: image

Response: image

To eliminate the cause being the Early Bound Generator in XrmToolbox I tested again with classes generated by CrmSvcUtil and received the same result.

Test code used for CrmServiceClient, CdsServiceClient and CdsServiceClientWithOOTBCrmSvcUtil are here: https://github.com/filcole/LinqDriverTest

filcole avatar Nov 15 '20 13:11 filcole

Yes, this is long standing behavior of the Linq Client in our SDK. (since version 5 I believe ) the ID itself is always returned, thus if you ask for just the ID, the system translates that into the All. if you ask for ID and name, you will get only those 2 columns.

I will bring it up to the core team to see if they want to explore changing this behavior.

thanks MattB

MattB-msft avatar Nov 16 '20 18:11 MattB-msft

Is this because the .Id property is not actually an attribute like .AccountId but a computed property?

(PS: I have always used the primary key attribute (.AccountId) for the very same reasons)

jordimontana82 avatar Nov 22 '20 11:11 jordimontana82

The reason I preferred using .Id instead of .AccountId is that .Id is a non-nullable Guid whereas .AccountId is generated as a nullable 'Guid?' by CrmSvcUtil (and Early Bound Generator).

This means we often have to introduce an unnecessary cast to 'Guid' which is ugly.

I expected the linq driver to only request the one field since that was all that's being requested. The results of the linq query just provide the one field, even though all fields are being transferred over the network.

With the current functionality I'd hope this code be reported by the solution checker, but it's not at the moment.

filcole avatar Nov 27 '20 19:11 filcole

.AccountId.Value (which is what I do) is also an option there without casting, although if it's a primary key, then it should always have a value and so CrmSvcUtil could maybe generate it as just "Guid" ?

jordimontana82 avatar Nov 27 '20 21:11 jordimontana82

Tagging this an "Enhancement request"... this seems like something the team can make better in the core and we will try to get this done in the future,

MattB-msft avatar Nov 30 '20 18:11 MattB-msft