DbIsNullExpression exception in linq to EF4 query - c#

I have writed linq EF4 query, but it failed with exception The argument to "DbIsNullExpression must refer to a primitive, enumeration or reference type." The query written bellow:
from listing in ctx.listingSource
join listingFile in ctx.ListingFiles
.Where(x => companyIds.Contains(x.CompanyID.Value))
.GroupBy(x => x.ListingID)
.Select(x => new { ListingId = x.Key, Count = x.Count() }) on listing.ListingID equals listingFile.ListingId into listingFilesJoined
from listingFileJoined in listingFilesJoined.DefaultIfEmpty()
select new ListingDTO
{
fileCount = listingFileJoined == null ? 0 : listingFileJoined.Count,
}
How can I resolve this issue without creating class instead anonymous type ?

fileCount = (int?)listingFileJoined.Count ?? 0

There are no way to select data without creating concrete type =\
There is fix bellow:
.Select(x => new ConcreteType { ListingId = x.Key, Count = x.Count() })
Maybe this answer help someone.

Related

Convert Sql to linq with groupby

I have view on which I use this request
Select Spendband, SUM(SpendCurrencyJob), SUM(SpendDocumentCount)
From analysis.vwJobSupplierMetrics
Where JobId = '500E0DD1-E3D3-4887-95EF-01D3C9EA8FD0'
Group by SpendBand
And it's running sucessfully
and get me this data
How I need to write it using linq to get same data?
I tried like this
var data = await _dbContext.VwJobSupplierMetrics.Where(x => x.JobId == jobId)
.GroupBy(x => x.SpendBand)
.Select(x => new HumpChartDto() {SpendBand = x.SpendBand}).ToListAsync();
But on new HumpChartDto() {SpendBand = x.SpendBand} I got Cannot resolve symbol 'SpendBand
How I can solve this?
First, after grouping on SpendBand, you need to access it via Key property. Second, to compute Sum, you can use Sum method.
var data = await _dbContext.VwJobSupplierMetrics.Where(x => x.JobId == jobId)
.GroupBy(x => x.SpendBand)
.Select(x => new HumpChartDto()
{
SpendBand = x.Key,
SumOfSpendCurrencyJob = x.Sum(s => s.SpendCurrencyJob),
SumOfSpendDocumentCount= x.Sum(s => s.SpendDocumentCount),
})
.ToListAsync();
Note - change the property name accordingly for name I've used for SumOfSpendCurrencyJob and SumOfSpendDocumentCount as don't know the definition of HumpChartDto class.

Entity Framework exception from query. Only primitive types or enumeration types are supported in this contex

No sure why I'm getting this error running this query below
Unable to create a constant value of type 'YogaBandy2017.Models.Profile.YogaProfile'. Only primitive types or enumeration types are supported in this context.
var requestedEvents = dbContext.YogaSpaceEvents
.Where(i => i.RequestedInstructor == yogaProfile)
.OrderByDescending(i => i.EventDateTime)
.Select(i => new PendingEvent
{
SpaceName = i.YogaSpace.Overview.Title,
SpaceImage = i.YogaSpace.YogaSpaceImages
.Where(j => j.IsMainImage)
.Select(j => j.ImageThumbnailCropped11)
.FirstOrDefault(),
SpaceId = i.YogaSpace.YogaSpaceId,
SpaceEventsHosted = i.YogaSpace.ClassesHosted,
SpaceReviewNumber = i.YogaSpace.ReviewNumber,
SpaceReviewPercent = i.YogaSpace.ReviewPercentage,
SpaceNumberOfReviews = i.YogaSpace.NumberOfReviews,
HostImage = i.YogaSpace.YogaProfile.YogaProfileImages
.Where(k => k.IsMainImage)
.Select(k => k.ImageThumbnailCropped)
.FirstOrDefault(),
HostId = i.YogaSpace.YogaProfile.YogaProfileId,
HostName = i.YogaSpace.YogaProfile.FirstName,
EventDateTime = i.EventDateTime,
Style = i.StyleMain.ToString(),
Duration = i.Duration,
EventId = i.YogaSpaceEventId
})
.ToList();
You cant use Entities like that in an Where clause (it has no idea how to convert it to SQL)
However, most likely they will have an Id property. So you should be able to do the following
dbContext.YogaSpaceEvents.Where(i => i.RequestedInstructor.Id == yogaProfile.Id)

Using contains in linq

I have a filtered list which returns all the distinctIds from MenuTable
var _parentList = _employee.Designation.Role.MenuRoles
.Select(x => new
{
MenuParentID = x.Menu.ParentID
})
.DistinctBy(x => x.MenuParentID)
.OrderBy(x => x.MenuParentID)
.ToList();
I want to select all the items from menutable which is in _parentList
This is what i have tried and an error is coming on _parentList.Contains(x.Id) which says Best overloaded match for System.Generic.contains has some invalid arguments.
MenuParentList = _db.Menus.Where(x => _parentList.Contains(x.Id))
.Select(x => new SMS.Models.ViewModel.DashboardVM.MenuParent
{
MenuParentID = x.Id,
MenuParentName = x.MenuName
})
.ToList()
Any help will be appreciated
Cf. this code:
.Select(x => new
{
MenuParentID = x.Menu.ParentID
})
This results in a list of anonymous objects with one property called MenuParentID, instead of a list of integers. The compiler creates a type for you that structurally looks like this (note that the compiler generates a non-usable class name behind the scenes instead of AnonymousType1, but you get the idea):
class AnonymousType1
{
public int MenuParentID {get;set;}
}
And _parentList would be of type List<AnonymousType1>.
Adjust your code as follows:
var _parentList = _employee.Designation.Role.MenuRoles
.Select(x => x.Menu.ParentID)
.Distinct()
.OrderBy(id => id)
.ToList();
Now _parentList is of type List<int>.
You can read more about the concept of anonymous types on msdn: https://msdn.microsoft.com/en-us/library/bb397696.aspx

Issue with initializing new object in LINQ

This code builds without problems but fails when executed:
var query =
_db.STEWARDSHIP
.OrderByDescending(r => r.VisitDate)
.Where(r => SiteId == null || r.SiteAssoc.Id == iSiteId)
.Where(r => r.MarkedForDeletion == false)
.Select(r => new SearchResults(r.Id,
r.SiteAssoc.Name,
r.VisitDate,
r.VisitTypeValAssoc.Description));
The error message is:
Only parameterless constructors and initializers are supported in LINQ to Entities.
What am I doing wrong here? I must pass info to the constructor to build the SearchResults objects. Is there a way to do this or do I have to make this a 2-step thing where I get the results and then iterate over the results to create the new objects?
UPDATE:
Changing the select to this fixes the issue:
.Select(r => new SearchResults(){Id = r.Id,
Name = r.SiteAssoc.Name,
VisitDate = r.VisitDate,
VisitType = r.VisitTypeValAssoc.Description});
Try this
.OrderByDescending(r => r.VisitDate)
.Where(r => SiteId == null || r.SiteAssoc.Id == iSiteId)
.Where(r => r.MarkedForDeletion == false)
.Select(r => new SearchResults()
{
ID = Ir.Id,
Name = r.SiteAssoc.Name,
VisitDate = r.VisitDate,
Description = r.VisitTypeValAssoc.Description
});
Entities can be created outside of queries and inserted into the data
store using a DataContext. You can then retrieve them using queries.
However, you can't create entities as part of a query.
See this post Explicit construction of entity type '###' in query is not allowed.
LINQ doesn't allow the explicit construction of objects within the select statements.

Is it possible to use Select(l=> new{}) with SelectMany in EntityFramework

I am trying something that i not really sure but i want to ask here if it s possible.
Is it able to be done ?
public IQueryable<Info> GetInfo(int count, byte languageId)
{
return db.Info.SelectMany(i => i.LanguageInfo)
.Where(l => l.Language.id == languageId)
.Select(l => new Info { AddDate = l.Info.AddDate,
Description = l.Description,
EntityKey = l.Info.EntityKey,
id = l.Info.id,
Title = l.Title,
ViewCount = l.Info.ViewCount }
)
.OrderByDescending(i => i.id)
.Take(count);
}
When this method is executed i got an error
The entity or complex type
'GuideModel.Info' cannot be
constructed in a LINQ to Entities
query.
Does it mean "not possible" ?
Thank you
The error essentially indicates that the Entity Framework doesn't know how to create an Info object, since it is not bound to a table object. (Put another way, the Select call on the IQueryable cannot be translated into equivalent SQL.) You could perform the Select projection on the client via:
public IQueryable<Info> GetInfo(int count, byte languageId)
{
return db.Info.SelectMany(i => i.LanguageInfo)
.Where(l => l.Language.id == languageId)
.Take(count)
.AsEnumerable()
.Select(l => new Info { AddDate = l.Info.AddDate,
Description = l.Description,
EntityKey = l.Info.EntityKey,
id = l.Info.id,
Title = l.Title,
ViewCount = l.Info.ViewCount }
)
.OrderByDescending(i => i.id);
}
It is possible to use Select(l => new ...), but not with an Entity type. You need to use an anonymous type or a POCO type with a parameterless constructor. Entity types are "special" because of the way they interact with the ObjectContext. You can select them, but not new them up in a query.
The code below worked for me. Here "SearchTerm" is a complex type. Thanks Jason :)
var lstSynonym = TechContext.TermSynonyms
.Where(p => p.Name.StartsWith(startLetter))
.AsEnumerable()
.Select(u => new SearchTerm
{
ContentId = u.ContentId,
Title = u.Name,
Url = u.Url
});

Categories