This question is locked. New answers and comments are not allowed.
Hi.
An excellent feature, which I really miss and think would be absolutely fabolus, is the abillity to serialize LINQ Expression trees.
In n-tier applications this would play out as follows:
1. A client creates a LINQ query for all clients
var result = from c in scope.Extent<Client>() select c; |
2. The expression is serialized
XElement xmlExpression = new ExpressionSerializer().Serialize(result.Expression); |
3. Using whatever means of transportation, the serialized xml expression is sent to the server.
ObjectContainer container = Server.Extent<Client>.Execute(xmlExpression); |
4. On the server side, the xml expression is replayed, filled in an object container and returned to the client.
// Deserialize the xml expression tree |
Expression expression = new ExpressionSerializer().Deserialize(xmlExpression); |
// Execute expression |
var result = objectScope.Extent<T>().Provider.Execute<T>(expression); |
// Copy result into an object container |
objectContainer.copyFrom(objectScope, "Items", result.ToList<T>, null); |
// Return the object Container |
return objectContainer; |
I have played some around with this, but it fails on deserialization since it's impossible to create instances of "Telerik.OpenAccess.Query.ExtentQueryImpl<T>" unless you work at Telerik...
Check out this link at MSDN blogs. They have already created ways to do this, and it contains source code and samples.
Expression Tree Serialization
Waiting in anticipation.
Thanks
Pål
5 Answers, 1 is accepted
0
Hi Pål,
It just occurred to me that although you cannot serialize the whole OpenAccess query, you can serialize the smaller expressions that are used to build it. These smaller expressions are the projection expression used in the Select extension method, the predicate expression used by the Where extension method, etc.
In this way you should be able to serialize the expressions from which you will later be able to easily construct the query like in the code sample bellow:
I hope this helps.
All the best,
Jordan
the Telerik team
Instantly find answers to your questions on the new Telerik Support Portal.
Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
It just occurred to me that although you cannot serialize the whole OpenAccess query, you can serialize the smaller expressions that are used to build it. These smaller expressions are the projection expression used in the Select extension method, the predicate expression used by the Where extension method, etc.
In this way you should be able to serialize the expressions from which you will later be able to easily construct the query like in the code sample bellow:
ExpressionSerializer serializer =
new
ExpressionSerializer();
XElement predicateXml = serializer.Serialize(filter);
// persist the serialized expression
// some more code
// load the serialized expression
filter = serializer.Deserialize<Func<Customer,
bool
>>(predicateXml);
IObjectScope objectScope = ObjectScopeProvider1.GetNewObjectScope();
IQueryable<Customer> query = objectScope.Extent<Customer>().Where(filter);
IList<Customer> customers = query.ToList();
I hope this helps.
All the best,
Jordan
the Telerik team
Instantly find answers to your questions on the new Telerik Support Portal.
Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
0
Pål
Top achievements
Rank 1
answered on 26 Jan 2010, 06:31 PM
Hi!
Thanks for the reply, but I'm not quite sure how to retrieve the "filter" you are talking about. I have tried using the .Expression property of the query and serialize this, but that failes.
Could you give an example on how to retrieve the "filter".
Thanks
Pål
Thanks for the reply, but I'm not quite sure how to retrieve the "filter" you are talking about. I have tried using the .Expression property of the query and serialize this, but that failes.
Could you give an example on how to retrieve the "filter".
Thanks
Pål
0
Hi Pål,
In the code from my previous post the filter parameter is defined earlier in the code as:
Of course in your case the way of defining the predicate expressions may be different.
Can you please share more details with us?
All the best,
Jordan
the Telerik team
Instantly find answers to your questions on the new Telerik Support Portal.
Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
In the code from my previous post the filter parameter is defined earlier in the code as:
Expression<Func<Customer,
bool
>> filter = c => c.City.StartsWith(
"S"
);
Of course in your case the way of defining the predicate expressions may be different.
Can you please share more details with us?
All the best,
Jordan
the Telerik team
Instantly find answers to your questions on the new Telerik Support Portal.
Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
0
Pål
Top achievements
Rank 1
answered on 27 Jan 2010, 04:56 PM
Hi!
Certainly, I'm trying to serialize a complete Expression tree obtained from objectScope.Extent<T>().
The expression could be anything, depending on the LINQ query entered by the developer in the presentation layer.
For this thread, i used as an example the LINQ query:
which when "query.Expression" is serialized to XML, produces the following output:
This is all fine and it can be transferred accross the wire to the business layer.
However, on she server side, this needs to be deserialized into a query/expression which can be processed by OpenAccess, and if you take a look at this part of the XML:
It requires the creation of a "Telerik.OpenAccess.Query.ExtentQueryImpl<T>".
I did however, find a way to hook into the deserialization process and instantiate the type using "Telerik.OpenAccess.ExtensionMethods.Extent<T>(IObjectScope scope)" method.
I Have only tried some simple LINQ queries, but will try and test some more.
You wouldn't happen to have a set of LINQ 101 test for c# so I can run some tests?
Anyway, I'll be happy to post any findings and how to extend the soultion (see link above) to work with OA.
Regards
Pål
Certainly, I'm trying to serialize a complete Expression tree obtained from objectScope.Extent<T>().
The expression could be anything, depending on the LINQ query entered by the developer in the presentation layer.
For this thread, i used as an example the LINQ query:
var query = from c in objectScope.Extent<Client>() |
select c; |
which when "query.Expression" is serialized to XML, produces the following output:
<MethodCallExpression NodeType="Call"> |
<Method MemberType="Method" MethodName="Select"> |
<DeclaringType> |
<Type Name="System.Linq.Queryable" /> |
</DeclaringType> |
<Parameters> |
<Type> |
<Type Name="System.Linq.IQueryable`1"> |
<Type Name="Navita.Client" /> |
</Type> |
</Type> |
<Type> |
<Type Name="System.Linq.Expressions.Expression`1"> |
<Type Name="System.Func`2"> |
<Type Name="Navita.Client" /> |
<Type Name="Navita.Client" /> |
</Type> |
</Type> |
</Type> |
</Parameters> |
<GenericArgTypes> |
<Type> |
<Type Name="Navita.Client" /> |
</Type> |
<Type> |
<Type Name="Navita.Client" /> |
</Type> |
</GenericArgTypes> |
</Method> |
<Object /> |
<Arguments> |
<ConstantExpression NodeType="Constant"> |
<Value>Extent<Navita.Client></Value> |
<Type> |
<Type Name="Telerik.OpenAccess.Query.ExtentQueryImpl`1"> |
<Type Name="Navita.Client" /> |
</Type> |
</Type> |
</ConstantExpression> |
<UnaryExpression IsLifted="false" IsLiftedToNull="false" NodeType="Quote"> |
<Operand> |
<LambdaExpression NodeType="Lambda"> |
<Body> |
<ParameterExpression Name="c" NodeType="Parameter"> |
<Type> |
<Type Name="Navita.Client" /> |
</Type> |
</ParameterExpression> |
</Body> |
<Parameters> |
<ParameterExpression Name="c" NodeType="Parameter"> |
<Type> |
<Type Name="Navita.Client" /> |
</Type> |
</ParameterExpression> |
</Parameters> |
<Type> |
<Type Name="System.Func`2"> |
<Type Name="Navita.Client" /> |
<Type Name="Navita.Client" /> |
</Type> |
</Type> |
</LambdaExpression> |
</Operand> |
<Method /> |
<Type> |
<Type Name="System.Linq.Expressions.Expression`1"> |
<Type Name="System.Func`2"> |
<Type Name="Navita.Client" /> |
<Type Name="Navita.Client" /> |
</Type> |
</Type> |
</Type> |
</UnaryExpression> |
</Arguments> |
<Type> |
<Type Name="System.Linq.IQueryable`1"> |
<Type Name="Navita.Client" /> |
</Type> |
</Type> |
</MethodCallExpression> |
This is all fine and it can be transferred accross the wire to the business layer.
However, on she server side, this needs to be deserialized into a query/expression which can be processed by OpenAccess, and if you take a look at this part of the XML:
<ConstantExpression NodeType="Constant"> |
<Value>Extent<Navita.Client></Value> |
<Type> |
<Type Name="Telerik.OpenAccess.Query.ExtentQueryImpl`1"> |
<Type Name="Navita.Client" /> |
</Type> |
</Type> |
</ConstantExpression> |
I did however, find a way to hook into the deserialization process and instantiate the type using "Telerik.OpenAccess.ExtensionMethods.Extent<T>(IObjectScope scope)" method.
I Have only tried some simple LINQ queries, but will try and test some more.
You wouldn't happen to have a set of LINQ 101 test for c# so I can run some tests?
Anyway, I'll be happy to post any findings and how to extend the soultion (see link above) to work with OA.
Regards
Pål
0
Hello Pål,
What we have is a sample application that demonstrates the LINQ 101 queries with OpenAccess.
You can find it here:
http://www.telerik.com/community/code-library/orm/general/telerik-openaccess-orm-1-1-linq-samples.aspx
I guess that if you modify it a little you could use it for your tests.
It will be great if you can share your findings with the community.
Regards,
Jordan
the Telerik team
Instantly find answers to your questions on the new Telerik Support Portal.
Watch a video on how to optimize your support resource searches and check out more tips on the blogs.
What we have is a sample application that demonstrates the LINQ 101 queries with OpenAccess.
You can find it here:
http://www.telerik.com/community/code-library/orm/general/telerik-openaccess-orm-1-1-linq-samples.aspx
I guess that if you modify it a little you could use it for your tests.
It will be great if you can share your findings with the community.
Regards,
Jordan
the Telerik team
Instantly find answers to your questions on the new Telerik Support Portal.
Watch a video on how to optimize your support resource searches and check out more tips on the blogs.