Page 1 of 1

Entity Framework - Function Imports

Posted: Mon 18 Oct 2010 13:33
by Gruffta
I'm trying to use the entity developer to add a function that returns a number and keep getting the exception

Code: Select all

System.Data.EntityCommandExecutionException: The data reader returned by the store data provider does not have enough columns for the query requested

at System.Data.EntityClient.EntityCommandDefinition.ConstantColumnMapGenerator.System.Data.EntityClient.EntityCommandDefinition.IColumnMapGenerator.CreateColumnMap(DbDataReader reader)
at System.Data.EntityClient.EntityCommandDefinition.CreateColumnMap(DbDataReader storeDataReader)
at System.Data.Objects.ObjectContext.CreateFunctionObjectResult(EntityCommand entityCommand, EntitySet entitySet, EdmType edmType, MergeOption mergeOption)
at System.Data.Objects.ObjectContext.ExecuteFunction(String functionName, MergeOption mergeOption, ObjectParameter[] parameters)
at System.Data.Objects.ObjectContext.ExecuteFunction(String functionName, ObjectParameter[] parameters)
Im attempting to call the function using the ObjectContext ExecuteFunction
like so

Code: Select all

ObjectParameter[] parameters = {
                                                   new ObjectParameter("COMPANY", 3),
                                                   new ObjectParameter("ITEM_CODE", "4130791400352"),
                                                   new ObjectParameter("VAT_CODE", "Z"),
                                                   new ObjectParameter("VAT_LOCATION", 4)
                                               };
                decimal result;

                result = model.ExecuteFunction("GetVatRate", parameters).FirstOrDefault();
I've also tried doing it this way:

Code: Select all

var query =
                    new ObjectQuery(
                        "DfxtestModel.Store.GET_VAT_RATE(@COMPANY, @ITEM_CODE, @VAT_CODE, @VAT_LOCATION)", model);
                query.Parameters.Add(new ObjectParameter("COMPANY", 3));
                query.Parameters.Add(new ObjectParameter("ITEM_CODE", "4130791400352"));
                query.Parameters.Add(new ObjectParameter("VAT_CODE", "Z"));
                query.Parameters.Add(new ObjectParameter("VAT_LOCATION", 4));

                result = query.FirstOrDefault();
which results in the following exception:

Code: Select all


Function metadata used in DbFunctionExpression must allow composition. Non-composable functions or functions that include command text are not allowed in expressions. Such functions can only be executed independently.

at System.Data.Common.CommandTrees.ExpressionBuilder.Internal.ArgumentValidation.ValidateFunction(EdmFunction function, IEnumerable`1 arguments, ref DbExpressionList validArgs)
at System.Data.Common.CommandTrees.ExpressionBuilder.DbExpressionBuilder.InvokeFunction(EdmFunction function, IEnumerable`1 arguments)
at System.Data.Common.CommandTrees.ExpressionBuilder.DbExpressionBuilder.Invoke(EdmFunction function, IEnumerable`1 arguments)
at System.Data.Common.EntitySql.SemanticAnalyzer.CreateModelFunctionCallExpression(MethodExpr methodExpr, MetadataFunctionGroup metadataFunctionGroup, SemanticResolver sr)
at System.Data.Common.EntitySql.SemanticAnalyzer.ConvertModelFunctionCall(MetadataFunctionGroup metadataFunctionGroup, MethodExpr methodExpr, SemanticResolver sr)
at System.Data.Common.EntitySql.SemanticAnalyzer.ConvertMethodExpr(MethodExpr methodExpr, Boolean includeInlineFunctions, SemanticResolver sr)
at System.Data.Common.EntitySql.SemanticAnalyzer.ConvertMethodExpr(Node expr, SemanticResolver sr)
at System.Data.Common.EntitySql.SemanticAnalyzer.Convert(Node astExpr, SemanticResolver sr)
at System.Data.Common.EntitySql.SemanticAnalyzer.ConvertValueExpression(Node astExpr, SemanticResolver sr)
at System.Data.Common.EntitySql.SemanticAnalyzer.ConvertQueryStatementToDbExpression(Statement astStatement, SemanticResolver sr)
at System.Data.Common.EntitySql.SemanticAnalyzer.AnalyzeQueryCommand(Node astExpr)
at System.Data.Common.EntitySql.CqlQuery.b__8(SemanticAnalyzer analyzer, Node astExpr)
at System.Data.Common.EntitySql.CqlQuery.AnalyzeSemanticsCommon(Node astExpr, Perspective perspective, ParserOptions parserOptions, IEnumerable`1 parameters, IEnumerable`1 variables, Func`3 analysisFunction)
at System.Data.Common.EntitySql.CqlQuery.AnalyzeQueryExpressionSemantics(Node astQueryCommand, Perspective perspective, ParserOptions parserOptions, IEnumerable`1 parameters, IEnumerable`1 variables)
at System.Data.Common.EntitySql.CqlQuery.c__DisplayClass4.b__3(Node astCommand, ParserOptions validatedParserOptions)
at System.Data.Common.EntitySql.CqlQuery.CompileCommon(String commandText, Perspective perspective, ParserOptions parserOptions, Func`3 compilationFunction)
at System.Data.Common.EntitySql.CqlQuery.CompileQueryCommandLambda(String queryCommandText, Perspective perspective, ParserOptions parserOptions, IEnumerable`1 parameters, IEnumerable`1 variables)
at System.Data.Objects.EntitySqlQueryState.Parse()
at System.Data.Objects.ELinq.ExpressionConverter.TranslateInlineQueryOfT(ObjectQuery inlineQuery)
at System.Data.Objects.ELinq.ExpressionConverter.ConstantTranslator.TypedTranslate(ExpressionConverter parent, ConstantExpression linq)
at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq)
at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq)
at System.Data.Objects.ELinq.ExpressionConverter.TranslateSet(Expression linq)
at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.UnarySequenceMethodTranslator.Translate(ExpressionConverter parent, MethodCallExpression call)
at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.SequenceMethodTranslator.Translate(ExpressionConverter parent, MethodCallExpression call, SequenceMethod sequenceMethod)
at System.Data.Objects.ELinq.ExpressionConverter.MethodCallTranslator.TypedTranslate(ExpressionConverter parent, MethodCallExpression linq)
at System.Data.Objects.ELinq.ExpressionConverter.TypedTranslator`1.Translate(ExpressionConverter parent, Expression linq)
at System.Data.Objects.ELinq.ExpressionConverter.TranslateExpression(Expression linq)
at System.Data.Objects.ELinq.ExpressionConverter.Convert()
at System.Data.Objects.ELinq.ELinqQueryState.GetExecutionPlan(Nullable`1 forMergeOption)
at System.Data.Objects.ObjectQuery`1.GetResults(Nullable`1 forMergeOption)
at System.Data.Objects.ObjectQuery`1.System.Collections.Generic.IEnumerable.GetEnumerator()
at System.Linq.Enumerable.FirstOrDefault(IEnumerable`1 source)
at System.Data.Objects.ELinq.ObjectQueryProvider.b__1(IEnumerable`1 sequence)
at System.Data.Objects.ELinq.ObjectQueryProvider.ExecuteSingle(IEnumerable`1 query, Expression queryRoot)
at System.Data.Objects.ELinq.ObjectQueryProvider.System.Linq.IQueryProvider.Execute(Expression expression)
at System.Linq.Queryable.FirstOrDefault(IQueryable`1 source)

Code: Select all


    
      
        
        
          
          
          
          
        
      
    
    
    
      
        
          
            
            
            
            
          
        
      
    
Am I doing something wrong or is this just not supported?? I was under the impression it was under EF4

Posted: Mon 18 Oct 2010 13:41
by Gruffta
I also get the exception

Code: Select all

System.Data.EntityCommandExecutionException: The data reader returned by the store data provider does not have enough columns for the query requested.
when calling the generated code method on the ObjectContext

Code: Select all

using (var model = new AutomatedOrderProcessingModelEntities())
		    {
		        model.GetVatRate(3, "4130791400352", "Z", 4);
		    }

Posted: Mon 18 Oct 2010 16:41
by AndreyR
Thank you for the report, I have reproduced the problem.
I will notify you about the results of our investigation.

Posted: Fri 22 Oct 2010 08:01
by Gruffta
Also when calling a stored procedure with 3 input parameters and a output parameter of sys_refcursor, Im also experiencing an issue

Code: Select all

The data reader is incompatible with the specified 'DistributorFx.Model.Module.LightningSource.Entity.GetOriginalOrderDetailResult'. A member of the type, 'NextLineNo', does not have a corresponding column in the data reader with the same name.
   at System.Data.Query.InternalTrees.ColumnMapFactory.GetMemberOrdinalFromReader(DbDataReader storeDataReader, EdmMember member, EdmType currentType, Dictionary`2 renameList)
   at System.Data.Query.InternalTrees.ColumnMapFactory.GetColumnMapsForType(DbDataReader storeDataReader, EdmType edmType, Dictionary`2 renameList)
   at System.Data.Query.InternalTrees.ColumnMapFactory.CreateColumnMapFromReaderAndType(DbDataReader storeDataReader, EdmType edmType, EntitySet entitySet, Dictionary`2 renameList)
   at System.Data.Query.InternalTrees.ColumnMapFactory.CreateFunctionImportStructuralTypeColumnMap(DbDataReader storeDataReader, FunctionImportMapping mapping, EntitySet entitySet, StructuralType baseStructuralType)
   at System.Data.EntityClient.EntityCommandDefinition.FunctionColumnMapGenerator.System.Data.EntityClient.EntityCommandDefinition.IColumnMapGenerator.CreateColumnMap(DbDataReader reader)
   at System.Data.Objects.ObjectContext.CreateFunctionObjectResult[TElement](EntityCommand entityCommand, EntitySet entitySet, EdmType edmType, MergeOption mergeOption)
   at System.Data.Objects.ObjectContext.ExecuteFunction[TElement](String functionName, MergeOption mergeOption, ObjectParameter[] parameters)
   at System.Data.Objects.ObjectContext.ExecuteFunction[TElement](String functionName, ObjectParameter[] parameters)
   at DistributorFx.Model.Module.LightningSource.Entity.LightningSourceProcessingModelEntities.GetOriginalOrderDetail(Nullable`1 COMPANY, Nullable`1 BRANCH, Nullable`1 ORDER_NUMBER) 

Posted: Fri 22 Oct 2010 09:38
by Gruffta
I have found the cause of the last posts issue, the entity developer program is performing the casing,plurization rules and creating a complex type with a property VatLocation then when you execute the function its returning vat_location and causing the error to be thrown, changing the csdl for this field to vat_location fixed this problem but doesn't seem natural when you can do this in Linqconnect with no issues whatsoever.

Posted: Fri 22 Oct 2010 09:40
by Gruffta
As for the first issue a workaround is to add this to your partial objectcontext class

Code: Select all

 base.CreateQuery(
                    "select value DistributorFx.Model.Module.AutomatedOrders.Entity.Store.get_vat_rate(@company, @item_code, @vat_code, @vat_location) from {1}",
                    new[]
                        {
                            new ObjectParameter("COMPANY", company),
                            new ObjectParameter("ITEM_CODE", itemCode),
                            new ObjectParameter("VAT_CODE", vatCode),
                            new ObjectParameter("VAT_LOCATION", vatLocation)
                        }).FirstOrDefault();
again this doesn't seem very natural

Posted: Thu 28 Oct 2010 09:29
by AndreyR
Thank you for the information, we are working on the issues.
I will post here as soon as it is fixed.

Posted: Fri 11 Feb 2011 11:54
by AndreyR
We have made some improvements in the latest 6.10.103 build of dotConnect for Oracle. For example, this post deals with Result Set Mapping, this should help in one of the problems.
The latest build can be downloaded from the Download page (the trial version) or from Registered Users' Area (for users with active subscription only).
For the detailed information about the fixes and improvements available in dotConnect for Oracle 6.10.103, please refer to this post.
Please let us know if the problems persist in the latest build.