问题
I am having some troubles running a query from a Controller on my ASP.NET MVC6 EF7 web app...
The Model and DbContext are in this previous ask: EF7 Incorrect configuration of the DBContext?
The problem appears when I try to run the following Linq query which contains a couple of joins and tries to get some entries from a Database for a particular date...
public IActionResult GetEntries(int year, int month, int day)
{
//_context.Database.SetCommandTimeout(180);
string dateTest = new DateTime(year, month, day).ToString("yyyy-MM-dd");
var results = (from c in _context.Comments
join r in _context.Reviews on c.ReviewId equals r.ReviewId
join f in _context.Films on c.ReviewId equals f.ReviewId
where c.Author.Equals("AuthorTest")
&& (c.Created.CompareTo(new DateTime(year, month, day, 0, 0, 0)) >= 0) && (c.Created.CompareTo(new DateTime(year, month, day, 23, 59, 59)) < 0)
&& !r.Status.Contains("Enabled")
select new
{
ReviewId = c.ReviewId,
ReviewStatus = r.Status,
Author = c.Author
});
var results2 = results.ToList();
return View(results2);
}
The Exception that I get is...
An exception of type 'System.Data.SqlClient.SqlException' occurred in EntityFramework.Core.dll but was not handled in user code
Additional information: Timeout expired. The timeout period elapsed prior to completion of the operation or the server is not responding.
The funny thing is.... if I run the EXACT same query without the following line, then it works perfectly
&& (c.Created.CompareTo(new DateTime(year, month, day, 0, 0, 0)) >= 0) && (c.Created.CompareTo(new DateTime(year, month, day, 23, 59, 59)) < 0)
So... the timeout exception thing doesn't make too much sense to me because once I remove the AND condition, it returns thousand of entries.
Also, if I plug that same query on a ASP.NET MVC5 EF6, the query works like a charm with the AND condition...
What am I missing here?
Finally, another thing that I tried was to create a single Linq query with no join and with the date condition and it works also perfectly...
public IActionResult GetEntries(int year, int month, int day)
{
//_context.Database.SetCommandTimeout(180);
string dateTest = new DateTime(year, month, day).ToString("yyyy-MM-dd");
var results = (from c in _context.Comments
where c.Author.Equals("AuthorTest")
&& (c.Created.CompareTo(new DateTime(year, month, day, 0, 0, 0)) >= 0) && (c.Created.CompareTo(new DateTime(year, month, day, 23, 59, 59)) < 0)
select new
{
ReviewId = c.ReviewId,
Author = c.Author
});
var results2 = results.ToList();
return View(results2);
}
Any pointers?
Thanks!
回答1:
I think this is because your Linq to Entities provider doesn't know how to translate the CompareTo
method to SQL. Try creating the dates you want to compare outside of your query and later try to compare them in your query as I show below:
var d1=new DateTime(year, month, day, 0, 0, 0);
var d2=new DateTime(year, month, day, 23, 59, 59);
var results = (from c in _context.Comments
join r in _context.Reviews on c.ReviewId equals r.ReviewId
join f in _context.Films on c.ReviewId equals f.ReviewId
where c.Author.Equals("AuthorTest")
&& c.Created >= d1 && c.Created<d2)
&& !r.Status.Contains("Enabled")
select new
{
ReviewId = c.ReviewId,
ReviewStatus = r.Status,
Author = c.Author
});
来源:https://stackoverflow.com/questions/34186304/linq-on-ef7-doesnt-work-with-joins-and-dates