Archief - [DotNet C#] Entity Framework: probleempje met SQL Stored procedures

Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.

Recipe4hate

Legacy Member
Hallo allemaal,

ik ben een tijdje terug begonnen met het leren van Entity Framework.
Op het moment heb ik een verbinding met onze SQL-server en roep ik hier enkele stored procedures uit op (T-SQL).

Deze worden in dotnet gegenereerd op basis van Database Model.
-Van de 4 SP's die ik gebruik, krijg ik er 2 terug met iets in de aard van ObjectResult<SP_EDIBrowser_GetDataByCASEID_Result>.
(dit zijn de simpelere SP's met één parameter en een simpele SELECT)

De andere 2 geven mij een int terug, terwijl ik toch ook een IEnumerable Result verwacht, zoals bovenstaande.
(Dit zijn echter ingewikkeldere SP's met meerdere input parameters en die eerst bepaalde SELECT INTO's doen maar uiteindelijk wel een SELECT teruggeven).

Zou het kunnen dat entity hier de correct SP returnvalue niet kent en daardoor maar een int teruggeeft? Dat de SP te complex of niet goed opgebouwd is?

Wat de werking van de DB en de rest van de code betreft: dit lijkt me goed, aangezien ik toch 2 vd. 4 SP's correct kan oproepen.


Zouden jullie me op de goeie weg kunnen helpen?
Ik zou natuurlijk de methods voor de 2 foutieve SP's kunnen gaan herschrijven, maar met zo'n autogenerated code ben ik niet zeker of deze stand gaat houden.
(+ ik zou 2 Result classes moeten gaan bijvoegen in mijn Model, wat het autogenereren een beetje redundant maakt :crazy:)


Alvast bedankt!


Eenvoudige SP:
Code:
ALTER PROCEDURE [dbo].[SP_EDIBrowser_GetDataByCASEID]
(
	@CASEID varchar(max)
)
AS BEGIN
	SELECT 
		SPD.SOLDTOCODE,
		SPD.SOLDTONAME,
		SPD.SOLDTOCITY,
		SPD.SOLDTOCOUNTRY,
		SPD.SHIPTOCODE,
		SPD.SHIPTONAME,
		SPD.SHIPTOCITY,
		SPD.SHIPTOCOUNTRY,
		SPD.SAPSALESNUM,
		SPD.HDSALESNUM,
		SPD.[ROUTE],
		SPD.SHIPREF,
		SPD.MATERIALNUM,
		SPD.MATERIALEXTNUM,
		SPD.MATERIALHAZ,
		SPD.MATERIALDESC,
		SPD.CASEID,
		SPD.CASEWIDTH,
		SPD.CASEHEIGHT,
		SPD.CASELENGTH,
		SPD.CASEDIMUNIT,
		SPD.CASEWEIGHT,
		SPD.CASEWEIGHTID,
		SPD.HUID,
		SPD.DATEADDED,
		SPD.COUNTRYOFORIGIN,
		SPD.HTC,
		SPD.CARRIER
	FROM dbo.SAPDATA AS SPD
	WHERE SPD.CASEID = @CASEID;
END

Complexe SP:
Code:
ALTER PROCEDURE [dbo].[SP_EDIBrowser_GetDataByDateAndRoute]
(
	@StartDate date,
	@EndDate date,
	@Route varchar(max)
)
AS BEGIN
	IF EXISTS
	(
		SELECT * FROM sys.objects
		WHERE sys.objects.object_id = OBJECT_ID('#CWEIGHT')
	)
	DROP TABLE #CWEIGHT;
	
	IF EXISTS
	(
		SELECT * FROM sys.objects
		WHERE sys.objects.object_id = OBJECT_ID('#CSWEIGHT')
	)
	DROP TABLE #CSWEIGHT;

	SELECT DISTINCT 
			SAPSALESNUM, 
			HUID, 
			CASEWEIGHT
	INTO #CWEIGHT
	FROM dbo.[SAPDATA] 
	WHERE 
	(
		(CONVERT(date, DATEADDED) BETWEEN @StartDate AND @EndDate) AND ([ROUTE] = @Route)
	)		

	SELECT 
			HUID, 
			SUM(CASEWEIGHT) AS CASEWEIGHT
	INTO #CSWEIGHT
	FROM #CWEIGHT
	GROUP BY HUID;

	SELECT 
		SPD.SOLDTOCODE,
		SPD.SOLDTOCITY,
		SPD.SOLDTOCOUNTRY,
		SPD.SHIPTOCODE,
		SPD.SHIPTOCITY,
		SPD.SHIPTOCOUNTRY,
		SPD.[ROUTE],
		SPD.SHIPREF,
		SPD.CASEWIDTH,
		SPD.CASEHEIGHT,
		SPD.CASELENGTH,
		SPD.CASEDIMUNIT,
		WGT.CASEWEIGHT,
		SPD.CASEWEIGHTID,
		SPD.HUID,
		SPD.DATEADDED,
		SPD.CARRIER,
		SPD.CASEID
	FROM dbo.SAPDATA AS SPD
		INNER JOIN #CSWEIGHT AS WGT
		ON SPD.HUID = WGT.HUID
	WHERE 
	(
		(CONVERT(date, SPD.DATEADDED) BETWEEN @StartDate AND @EndDate) AND
		(SPD.[ROUTE] = @Route)
	)
	GROUP BY 		
		SPD.SOLDTOCODE,
		SPD.SOLDTOCITY,
		SPD.SOLDTOCOUNTRY,
		SPD.SHIPTOCODE,
		SPD.SHIPTOCITY,
		SPD.SHIPTOCOUNTRY,
		SPD.[ROUTE],
		SPD.SHIPREF,
		SPD.CASEWIDTH,
		SPD.CASEHEIGHT,
		SPD.CASELENGTH,
		SPD.CASEDIMUNIT,
		WGT.CASEWEIGHT,
		SPD.CASEWEIGHTID,
		SPD.HUID,
		SPD.DATEADDED,
		SPD.CARRIER,
		SPD.CASEID;
END

EntityModel code (autogenerated).
Het enige wat ik zelf heb toegevoegd is een extra contructor die ook een connectionstring aanvaardt.
Code:
//------------------------------------------------------------------------------
// <auto-generated>
//    This code was generated from a template.
//
//    Manual changes to this file may cause unexpected behavior in your application.
//    Manual changes to this file will be overwritten if the code is regenerated.
// </auto-generated>
//------------------------------------------------------------------------------

namespace SapdataBrowserService.EntityFramework
{
    using System;
    using System.Data.Entity;
    using System.Data.Entity.Infrastructure;
    using System.Data.Objects;
    using System.Data.Objects.DataClasses;
    using System.Linq;
    
    public partial class HDCarrierEntities : DbContext
    {
        public HDCarrierEntities()
            : base("name=HDCarrierEntities")
        {
        }
        public HDCarrierEntities(string Connectionstring)
            : base(Connectionstring)
        {
        }
    
        protected override void OnModelCreating(DbModelBuilder modelBuilder)
        {
            throw new UnintentionalCodeFirstException();
        }
    
    
        public virtual ObjectResult<SP_EDIBrowser_GetDataByCASEID_Result> SP_EDIBrowser_GetDataByCASEID(string cASEID)
        {
            var cASEIDParameter = cASEID != null ?
                new ObjectParameter("CASEID", cASEID) :
                new ObjectParameter("CASEID", typeof(string));
    
            return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction<SP_EDIBrowser_GetDataByCASEID_Result>("SP_EDIBrowser_GetDataByCASEID", cASEIDParameter);
        }
    
        public virtual int SP_EDIBrowser_GetDataByDateAndCarrier(Nullable<System.DateTime> startDate, Nullable<System.DateTime> endDate, string carrier)
        {
            var startDateParameter = startDate.HasValue ?
                new ObjectParameter("StartDate", startDate) :
                new ObjectParameter("StartDate", typeof(System.DateTime));
    
            var endDateParameter = endDate.HasValue ?
                new ObjectParameter("EndDate", endDate) :
                new ObjectParameter("EndDate", typeof(System.DateTime));
    
            var carrierParameter = carrier != null ?
                new ObjectParameter("Carrier", carrier) :
                new ObjectParameter("Carrier", typeof(string));
    
            return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction("SP_EDIBrowser_GetDataByDateAndCarrier", startDateParameter, endDateParameter, carrierParameter);
        }
    
        public virtual int SP_EDIBrowser_GetDataByDateAndRoute(Nullable<System.DateTime> startDate, Nullable<System.DateTime> endDate, string route)
        {
            var startDateParameter = startDate.HasValue ?
                new ObjectParameter("StartDate", startDate) :
                new ObjectParameter("StartDate", typeof(System.DateTime));
    
            var endDateParameter = endDate.HasValue ?
                new ObjectParameter("EndDate", endDate) :
                new ObjectParameter("EndDate", typeof(System.DateTime));
    
            var routeParameter = route != null ?
                new ObjectParameter("Route", route) :
                new ObjectParameter("Route", typeof(string));
    
            return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction("SP_EDIBrowser_GetDataByDateAndRoute", startDateParameter, endDateParameter, routeParameter);
        }
    
        public virtual ObjectResult<SP_EDIBrowser_GetDataByHUID_Result> SP_EDIBrowser_GetDataByHUID(string hUID)
        {
            var hUIDParameter = hUID != null ?
                new ObjectParameter("HUID", hUID) :
                new ObjectParameter("HUID", typeof(string));
    
            return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction<SP_EDIBrowser_GetDataByHUID_Result>("SP_EDIBrowser_GetDataByHUID", hUIDParameter);
        }
    
        public virtual int SP_EDIBrowser_GetDataByShipment(Nullable<int> sHIPREF)
        {
            var sHIPREFParameter = sHIPREF.HasValue ?
                new ObjectParameter("SHIPREF", sHIPREF) :
                new ObjectParameter("SHIPREF", typeof(int));
    
            return ((IObjectContextAdapter)this).ObjectContext.ExecuteFunction("SP_EDIBrowser_GetDataByShipment", sHIPREFParameter);
        }
    }
}

Recipe4hate

Legacy Member
Ik heb enkele dagen cursus gehad van een .NET expert. Die hamerde op het entity framework... dus ik wilde dat zeker gaan gebruiken in mijn nieuwe project.

Op zich bevalt deze mij wel als ORM hoor.

Moto

Legacy Member
En als .Net expert hamer ik erop dat ge duidelijk weet waar ge mee begint met EF

Als het echt bedoeld is om daar serieuze applicaties mee te schrijven en het u ook intresseerd
om een goed applicatie te schrijven (dus niet waar bijna elke actie meer dan 2 seconden duurt)
dan is EF niet iets dat daarvoor simpel te gebruiken is

als ge bv de entity tracking en lazy loading features gebruikt moet echt wel een besef hebben over wat er intern in
het framework allemaal gebeurd, het is nog al vrij gemakkelijk om sommige features te gebruiken, maar die kunnen
snel zorgen voor zeer grote SQL statements, zoals het bekende N+1 probleem en dus slechte performance.

Is dus wat ge noemt een Leaky Abstraction
The Law of Leaky Abstractions - Joel on Software

Recipe4hate

Legacy Member
Alright, dan zal ik er rekening mee moeten houden dat EF geen voor de hand liggende keuze is. :)
Het archief is een bevroren moment uit een vorige versie van dit forum, met andere regels en andere bazen. Deze posts weerspiegelen op geen enkele manier onze huidige ideeën, waarden of wereldbeelden en zijn op sommige plaatsen gecensureerd wegens ontoelaatbaar. Veel zijn in een andere tijdsgeest gemaakt, al dan niet ironisch - zoals in het ironische subforum Off-Topic - en zouden op dit moment niet meer gepost (mogen) worden. Toch bieden we dit archief nog graag aan als informatiedatabank en naslagwerk. Lees er hier meer over of start een gesprek met anderen.
Terug
Bovenaan