Entity Framework prevent insert date between two dates - c#

In my project user can select 2 dates startDate and endDate. The selected startDate must be greater than the largest endDate stored in SQL Server:
How can I check this using an Entity Framework Linq statement?
_context.tableName.where(p => p.startDate >= ??);

Something like this could work for you, adapt it to your needs
if (startDate > _context.tableName.Max(p => p.endDate))

Related

Specifying where clause format in Entity Framework with System.Data.SQLite

I have an Entity Framwework 4.0 Model running against an SQLite database to which I connect via System.Data.SQLite. I have one field in the database which is typed "Date", and formatted as yyyy-MM-dd. (As we know, SQLite has no internal Date or DateTime type).
The Entity Framework wizard happily translated that Date type to DateTime. When running queries against this date field, I was surprised to find out no results came.
Suppose a table "MyTable":
Create Table MyTable
(
Id Integer Not Null Primary Key,
ADate Date Not Null
);
With System.Data.SQLite and LINQ:
var date = new DateTime(2013, 1, 1);
context.MyTables.AddObject(new MyTable { Id = 0, ADate = date });
context.SaveChanges();
context.MyTables.Where(r => r.ADate == date).Count; // -> returns 0
Looking further with ToTraceQuery, I found out that the query became:
SELECT
[Extent1].[Id] AS [Id],
[Extent1].[ADate] AS [ADate]
FROM [TestDate] AS [Extent1]
WHERE [Extent1].[ADate] = #p__linq__0
With testing, I discovered that the mapped variable p__linq__0 was transformed to a fixed format of yyyy-MM-dd hh:mm:ss, so that asking for DateTime(2013,1,1) meant the query was looking for '2013-01-01 00:00:00' when all that was to be found was '2013-01-01'.
If the folks who make 'System.Data.SQLite' had been nice about this, they'd have used the built in SQLite functions and done the comparison like:
WHERE datetime([Extent1].[ADate]) = datetime(#p__linq__0)
or even
WHERE date([Extent1].[ADate]) = date(#p__linq__0)
for just the date type. And indeed in System.Data.SQLite's SqlGenerator.cs, we find this formatting for all DateTime types:
((System.DateTime)e.Value).ToString("yyyy-MM-dd HH:mm:ss.fff", CultureInfo.InvariantCulture), false /* IsUnicode */)
All this to say, is there a way to specify the format for this where clause in this context?
Notes: SQLite is what I'm stuck with, and the recorded format of 'yyyy-MM-dd' cannot be changed as other software relies on it.
One alternative to ExecuteStoreQuery is to pass other where clauses first (if any) then force the query to run (for example with ToList()), and finally to apply standard LINQ filters on the special format Date field afterwards.

SQL Query with Long Date Time?

I am trying to pass a SQL query through c# , currently it is based on just the day month and year with time always set to 0 EG 1997-10-28 00.00.00.000 which is great as the time never changes it easy for me to just Select Where date equals the calendar date.
However with the Start Field , the time is different on each record , eg 1899-12-30 14.14:00.00.000 , 1899-12-30 15.14:30.00.000 . (Seconds downwards are always the same) .
So I need to have a query that will return all the results of the selected date on the "Start" field . How would I do this?.
E.G IF i click the calendar which passes 1997-10-28 00.00.00.000 , I would like the results of every time in that day!. How do I go about that?.
Thanks for any input.
EDIT: Is there a way to format the date that i have in SQL ?. This comes from an old access database!. and as you can see above it is 1899-12-30 ?. not 1998 , I don't know why this has happened!.
WHERE DATEDIFF(dd, your_start_field, #your_param) = 0
You need to select all record between today and tomorrow without including tomorrow's date.
WHERE EventDate >= StartDate AND EventDate < DATEADD(d, 1, StartDate)
Can you not just query the date part. I think this should work...
SELECT * FROM Table1 WHERE StartDate = '1997-10-28'
EDIT: Above may not work but following should cover needs
SELECT * FROM Table1 WHERE StartDate >= '1997-10-28 00:00:00.000' AND StartDate < '1997-10-29 00:00:00.000'
(notice the second date is the following date)
This SQL DATEADD(d,datediff(d,0,startdate),startdate) will convert a date with time to just the date;
eg
Select field1,field2 from mytable where DATEADD(d,datediff(d,0,startdate),startdate)='1997-10-28'

How to determine closest date

I am a little confused about how or what the best way to determine what the closest date is to DateTime.Now is.
In my table, everything needs to be timestamped. And on a page, I need to be able to retrieve everything from the table only if the date is the closest date to now.
How would I go about this?
I am using DateTime.Now when inserting dates into the Database, and the format is like:
5/07/2011 5:28:57 PM
Here's my suggestion:
declare #DateTimeNow datetime = getdate()
select TOP (1)
RecordId
,MyDateColumn
,abs(datediff(s, MyDateColumn, #DateTimeNow)) as Diff
from
MyTable
order by
abs(datediff(s, MyDateColumn, #DateTimeNow)) asc
Do not forget to use ABS()!
How about
SELECT TOP 1 *
FROM MyTable
ORDER BY TimestampColumn DESC
Consider storing time in UTC - DateTime.UtcNow
In T-SQL you could use DateDiff:
DATEDIFF ( datepart , startdate , enddate )
http://msdn.microsoft.com/en-us/library/ms189794.aspx
or in C# you could use TimeSpan:
http://msdn.microsoft.com/en-us/library/system.timespan.aspx#Y3719
Do you only have past dates, meaning, will you ever have a date that is newer than DateTime.Now? If not, you could get by with a simple Order By on the date column selecting the newest date. Otherwise, you'll need to get a date difference between your DateTime.Now, and order by that result. e.g.
SELECT TOP 1
columnDate
FROM table1
ORDER BY DATEDIFF (ss,#passedInDate,columnDate)
This would essentially look for all future and past dates using your #passedInDate (DateTime.Now) as the qualifier or base date. I'm using seconds as the time interval to compare in my example, but you can change that to whatever makes the most sense for you.
Also, you shouldn't need to pass in DateTime.Now to SQL server, as you can use the built in GetDate() function.
Something like this should work:
SELECT TOP 1 * FROM MyTable ORDER BY ABS(DATEDIFF(DD, getdate(), DATE))
This should sort your rows by the closest date, past or future. If you need it more precise then just days, change DD to something else, as specified here

Getting data from mssql table based on startdate and enddate

I am writing a query to select data from a table called contest.
each contest has start date and enddate. I want to select all the contest details from the contest table if the current date is between start date and end date.
select * from contest
where getDate() between startdate and enddate
getDate() returns you the current date and time.
select * from contest
where dtBegin <= getDate() and getDate() <= dtEnd
out of interest why is this tagged c# what are you trying to achieve with this?
if your trying to get this into an app some how you could use either a SqlDataReader or LinqtoSQL (plus others)

Cursor to return multiple rows

I've been working on this for the past few days and I can't find my way out of it. I have a C# web application that needs to print reports on screen. This same application calls a stored procedure on the database (Oracle) and it returns a cursor. Here is the procedure
PROCEDURE report_total(beginDate IN DATE, endDate IN DATE, c OUT REF CURSOR)
AS
BEGIN
OPEN
c
FOR
SELECT
month
,sum(field1)
-- + a lot of other fields
FROM
view1 v
WHERE
beginDate <= v.date
AND v.Date < endDate
GROUP BY
month
END;
This works fine, it gives me the sum of field1 (and others) per months. Assuming you enter, at least, a complete year range you'll get, at most, 12 rows. Howhever. I would like to make something a similar stored procedure that would give me the detail of these months.
Let's say beginDate = '2003-01-01' and the endDate = '2005-01-05' (YYYY-MM-DD), I would need 25 rows. One per month, per year. And I would like to get these results with the cursor OUT. If you have a simplest idea that wouldn't involve a cursor please suggest me.
SELECT TRUNC(v.date, 'MONTH'), SUM(field1)
FROM view1 v
WHERE v.date BETWEEN beginDate and endDate
GROUP BY
TRUNC(v.date, 'MONTH')

Categories

Resources