How to include Saturday and Sunday data in Sql query - sql

I would like to pull data into my query for JUST the previous day. When I run the query on Monday I would like to have data for Saturday and Sunday as well.
The below part of the query works fine but it does not include Sat and Sun when ran on a Monday. Can anyone give me an idea of what to add?
where ([ImportDate] = DATEADD(DAY, CASE DATENAME(WEEKDAY, GETDATE())
WHEN 'Sunday' THEN -2
WHEN 'Monday' THEN -3
ELSE -1 END,
DATEDIFF(DAY, 0, GETDATE())))

You were close. But you want to make it a range of dates that would include the previous days you want up to the current date, by using >= < or a BETWEEN.
where [ImportDate] >= DATEADD(DAY, CASE DATENAME(WEEKDAY, GETDATE()) WHEN 'Sunday' THEN -2 WHEN 'Monday' THEN -3 ELSE -1 END, DATEDIFF(DAY, 0, GETDATE()))
and [ImportDate] < CONVERT(DATE,GETDATE())

Related

Get the date of Sunday and Saturday 2 weeks ago

I have a stored procedure that produces a report each night. This SP references a view that takes a snapshot of data from 2 weeks ago (Sunday to Saturday).
I need to get the dates of the Saturday and Sunday from two weeks ago (so for today that would be 23/24 of December.
I have searched through many solutions but I am unable to find a decent response to this - any one able to help with an answer as well as explaining a little bit of the reason for doing it that way (it seems like there are a thousand ways to do it).
Thanks
Here is the answer in case any one needs it in future.
SELECT DATEADD(wk, -2, DATEADD(wk, DATEDIFF(wk, 6, GETDATE()), 6))
Try this (for Saturday) is the same for Sunday:
DECLARE #today datetime
SET #today = GETDATE()
SELECT
CASE
WHEN DATENAME(weekday, #today) = 'Monday' THEN DATEADD(day, -15, #today)
WHEN DATENAME(weekday, #today) = 'Tuesday' THEN DATEADD(day, -16, #today)
WHEN DATENAME(weekday, #today) = 'Wednesday' THEN DATEADD(day, -17, #today)
WHEN DATENAME(weekday, #today) = 'Thursday' THEN DATEADD(day, -18, #today)
WHEN DATENAME(weekday, #today) = 'Friday' THEN DATEADD(day, -19, #today)
WHEN DATENAME(weekday, #today) = 'Saturday' THEN DATEADD(day, -13, #today)
WHEN DATENAME(weekday, #today) = 'Sunday' THEN DATEADD(day, -14, #today)
END
DATENAME with weekday parameter returns the name of the day, so if you are on Monday you must subtract 15 days to reach Saturday and so on.
Pay attention: If you have another language set you can change it for your query using:
SET LANGUAGE us_english
You can see SqlFiddle
Since the day of week value can differ on different machines you either need to set it using the set datefirst 1 command as suggeste in Podiluska's answer,
or you can do it by first determining the actual value for sunday and add that to the days you are subtracting.
To determine the actual value for sunday simply ask the value for a know sunday, like 2018-01-07 for example
Below example should return 2017-12-23 / 2017-12-24
It will also return this if you are running this on friday, or thursday, or whatever day...
-- this will contain are test date
declare #date date = getdate() - 2
-- determine the number for sunday
declare #Sunday int = (select datepart(dw, '20180107'))
select convert(date,dateadd(d, -15 - datepart(dw, #date) + (datepart(dw, #date) - #Sunday), getdate())),
convert(date,dateadd(d, -14 - datepart(dw, #date) + (datepart(dw, #date) - #Sunday), getdate()))
That depends on how you define when your week starts, but the basic principle is to find the start of this week, and take away 14 days.
eg:
set datefirst 1
select convert(date,dateadd(d, -15-datepart(dw, getdate()), getdate())),
convert(date,dateadd(d, -14-datepart(dw, getdate()), getdate()))
Sorry, I'll work on a general form for these; this is the quick and dirty.
I like the NEXT_DAY function. Simple, and obvious as to what it does.
declare
vFromDate date := trunc( sysdate ) - 9 ; -- '27 Feb 2019'
vSatDate date ;
vSunDate date ;
begin
-- test a range of dates
while vFromDate <= sysdate -- '3 Mar 2019'
loop
select NEXT_DAY ( TRUNC ( vFromDate) - 21, 'SAT') -- 7: general form for these?
-- keep or discard the " - 1" depending on if the 2 wk Sunday is the desired Sunday
, NEXT_DAY ( TRUNC ( vFromDate) - 20 - 1, 'SUN') -- 1:
into vSatDate, vSunDate
from dual ;
dbms_output.put_line( to_char( vFromDate, 'dd Mon": "' )
|| to_char( vSatDate, 'dd Mon' )
|| to_char( vSunDate, '", "dd Mon' )
);
vFromDate := vFromDate + 1 ;
end loop ;
dbms_output.put_line( rpad('*', 21, '*' ) );
end ;

Getting SQL to return data ONLY for the last business day

I have tried about a thousand different ways to attempt this after hours of scouring the internet and finding things that seem like they would work, I still have not been able to get this to come up correctly.
I have a query that I am running in SQL via Tableau that I need to be dynamic and change to look at ONLY business days. When I updated my query this morning, since our server looks at one day prior, it was looking for Sunday data which in my company there is no processing going on on Saturday or Sunday, I need it to know when today is Monday, (basically) do getdate()-3, otherwise, getdate()-1.
I have tried declaring a variable, I have tried something like this:
SELECT DATEADD(DAY, CASE DATENAME(WEEKDAY, GETDATE())
WHEN 'Sunday' THEN -2
WHEN 'Monday' THEN -3
ELSE -1 END, DATEDIFF(DAY, 0, GETDATE()))
which doesn't work because the column from my table called create_date to be set to the correct dynamic date. This works if I run it alone without trying to incorporate into a query (gives me the date for Friday) but I can not figure out how to then take that date and apply it to my query.
This is the closest I have been able to get
DECLARE #CREATIONDAY DATE
SET #CREATIONDAY = DAY, CASE DATENAME(WEEKDAY, convert(date,GETDATE()))
WHEN 'Sunday' THEN -2
WHEN 'Monday' THEN -3
ELSE -1 END, DATEDIFF(DAY, 0, GETDATE()));
SELECT CREATION_DATE, COUNT(*)
FROM [dbo].[workflow_document]
WHERE CREATION_DATE = #CREATIONDAY
GROUP BY CREATION_DATE
but still getting an error "Msg 102, Level 15, State 1, Line 3
Incorrect syntax near ','."
Not sure what could be wrong with the comma, but I am about at the end of my rope with getting this to work. Anything is appreciated!
Your method is fine. Your variable definition has DAY, in it. So:
SET #CREATIONDAY = DATEADD(DAY,
(CASE DATENAME(WEEKDAY, convert(date,GETDATE()))
WHEN 'Sunday' THEN -2
WHEN 'Monday' THEN -3
ELSE -1
END),
GETDATE());
Or, just add the logic into the WHERE clause:
WHERE (DATENAME(WEEKDAY, GETDATE()) = 'Sunday' AND
CREATION_DATE = DATEADD(DAY, -2, CAST(GETDATE as DATE))
) OR
(DATENAME(WEEKDAY, GETDATE()) = 'Monday' AND
CREATION_DATE = DATEADD(DAY, -3, CAST(GETDATE as DATE))
) OR
(DATENAME(WEEKDAY, GETDATE()) = 'Sunday' AND
CREATION_DATE = DATEADD(DAY, -2, CAST(GETDATE as DATE))
) OR
(DATENAME(WEEKDAY, GETDATE()) NOT IN ('Sunday', 'Monday') AND
CREATION_DATE = DATEADD(DAY, -1, CAST(GETDATE as DATE))
)
When dealing with day-of-week calculations, it's important to take account of the current DATEFIRST settings. This query will always correctly exclude weekend days, using ##DATEFIRST to account for any possible setting for the first day of the week.
SELECT *
FROM your_table
WHERE ((DATEPART(dw, date_created) + ##DATEFIRST) % 7) NOT IN (0, 1)

Conditional where statement: select different time period when query date varies

I have a query need to select different time period. The logic is:
if today is Tuesday, select Saturday 00:00:00 ~ Monday 23:99;
if today is other weekdays, select the previous working day (00:00:00 ~ 23:99).
Here is the query I have:
Select *
From ...
WHERE
(DATENAME(DW,GETDATE())= 'Tuesday'
AND (<#SalesDate> BETWEEN DATEADD(DAY, -3, GETDATE()) and DATEADD(DAY, -1, GETDATE())))
OR
(DATENAME(DW,GETDATE())<> 'Tuesday'
AND (<#SalesDate> BETWEEN DATEADD(DAY, -1, GETDATE())and DATEADD(DAY, -1, GETDATE())))
It didn't return the result that I want. Anyone can help me? thank you.
BETWEEN is a bit finicky when it comes to date datatypes. See this question.
GETDATE() will return the time for today. You need to strips it off.
-- Today's date, stripped of time
DECLARE #Today datetime = CONVERT(datetime,CONVERT(date,GETDATE()))
Select *
From ...
WHERE
(DATENAME(DW,GETDATE())= 'Tuesday'
AND (#SalesDate >= DATEADD(DAY, -3, #Today) and #SalesDate < DATEADD(DAY, -1, #Today)))
OR
(DATENAME(DW,GETDATE())<> 'Tuesday'
AND (#SalesDate >= DATEADD(DAY, -1, #Today) and #SalesDate < DATEADD(DAY, -1, #Today)))

How can I set a datetime after 4:00 or on weekend to 8:00am the next business day?

I am trying to make this a trigger, but so fat this is all I've got:
CREATE TRIGGER trg_SetDateToNextBusinessDay
ON dbo.Orders
AFTER INSERT
AS
UPDATE dbo.Orders
SET OrderDateTime = {next day that is Monday-Friday, 8:00 am}
WHERE OrderDateTime {is after 4:00} OR OrderDateTime {is on a saturday or sunday}
What is the easiest way to do this?
Try this:
CREATE TRIGGER trg_SetDateToNextBusinessDay
ON dbo.Orders
AFTER INSERT
AS
UPDATE dbo.Orders
SET OrderDateTime =
(CASE DATENAME(DW, OrderDateTime)
WHEN 'Friday' THEN DATEADD(DAY, DATEDIFF(DAY, -3, OrderDateTime), '08:00:00') -- if friday, add 3 days
WHEN 'Saturday' THEN DATEADD(DAY, DATEDIFF(DAY, -2, OrderDateTime), '08:00:00') -- if saturday add 2 days
ELSE DATEADD(DAY, DATEDIFF(DAY, -1, OrderDateTime), '08:00:00') -- on all other days just add one day
END) -- {next day that is Monday-Friday, 8:00 am}
WHERE DATEPART(HH, OrderDateTime) > 3 OR-- {is after 4:00} (this includes 4:00!)
DATENAME(DW, OrderDateTime) IN ('Saturday', 'Sunday') -- {is on a saturday or sunday}
To check if the date is a Saturday or Sunady I suggest datename.
You can check:
datename("dw", OrderDateTime) in ("Saturday", "Sunday").
You can use datepart to get the hour and check if it is after four.
datepart(hh, OrderDateTime) >= 4
For your set statement you can use a case:
case datename("dw", OrderDateTime)
when "Saturday"
then DATEADD(hh, 56,cast(OrderDateTime As Date))
when "Friday"
then DATEADD(hh, 80,cast(OrderDateTime As Date))
else DATEADD(hh, 32,cast(OrderDateTime As Date))
In all cases we are getting rid of the time. Then, if it is Saturday, add two days worth of hours to get us to Monday and add an additional eight hours to get us to eight am.
If it is Friday, add three days plus eight hours. Otherwise add a single day plus eight hours.

SQL/SSRS select first weekday on or prior to date

Hello I've converted a spreadsheet into a SSRS report which is run on the 20th of month and I need to pass the 20th of the current month as a default value (start date) either through a custom expression or dataset. If the 20th falls on a Saturday, default to friday 19th. If the 20th falls on Sunday default to Friday 18th. How do I do this and what is the best way of doing it?
How about this:
DECLARE #daytwenty date;
SET #daytwenty = DATEADD(mm, DATEDIFF(mm, 0, getdate()) ,19) --Get Twentieth Day of current month
SELECT
CASE DATEPART(DW,#daytwenty)
WHEN 1 THEN DATEADD(dd, -2, #daytwenty) --When the twentieth day is a Sunday, take two days off
WHEN 7 THEN DATEADD(dd, -1, #daytwenty) --When the twentieth day is a Saturday, take one day off
ELSE #daytwenty --Else the twentieth day is a weekday already
END
You should use Datetime for 2008 version. By writing
DECLARE #LatestDate date;
in previous version of Sql Server gives compilation error.
Column, parameter, or variable #1: Cannot find data type date.
So below is the code Sql server 2008
DECLARE #LatestDate datetime;
SET #LatestDate = DATEADD(mm, DATEDIFF(mm, 0, getdate()) ,19) --Get Twentieth Day of current month
SELECT
CASE DATEPART(DW,#LatestDate)
WHEN 1 THEN DATEADD(dd, -2, #LatestDate) --When the twentieth day is a Sunday, take two days off
WHEN 7 THEN DATEADD(dd, -1, #LatestDate) --When the twentieth day is a Saturday, take one day off
ELSE #LatestDate --Else the twentieth day is a weekday already
END
I hope this is what u want,
select case datename(dw, getdate())
when 'Monday' then 'Friday'
when 'Tuesday' then 'Monday'
when 'Wednesday' then 'Tuesday'
when 'Thursday' then 'Wednesday'
when 'Friday' then 'Thursday'
when 'Saturday' then 'Friday'
when 'Sunday' then 'Friday'
end