Can a SSRS report contain double date/time parameters? - sql

Is it possible to have two date/time parameters in a report?
I have a simple dataset with the 'where' clause:
where RequestSource in (#reqsource)
and EntryDay between #startdate and #finishdate
and EntryDay between #periodstart and #periodend
In the report there is a calendar date/time parameter (using #startdate and #finishdate) and I wanted to add a second one (two part parameter) (using #periodstart and #periodend).
The dataset for the #periodstart parameter contains:
select DATEADD(qq, DATEDIFF(qq, 0, GETDATE()) - 1, 0) as time, 'last quarter start' as timename
union all
select DATEADD(qq, DATEDIFF(qq, 0, GETDATE()), 0) as time, 'this quarter start' as timename
union all
select DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), 0) as time, 'this year start' as timename
union all
select DATEADD(yy, DATEDIFF(yy, 0, GETDATE()) - 1, 0) as time, 'last year start' as timename
The dataset #periodend parameter contains:
select DATEADD(dd, -1, DATEADD(qq, DATEDIFF(qq, 0, GETDATE()), 0)) as time, 'last quarter end' as timename
union all
select DATEADD (dd, -1, DATEADD(qq, DATEDIFF(qq, 0, GETDATE()) +1, 0)) as time, 'this quarter end' as timename
union all
select DATEADD(yy, DATEDIFF(yy, 0, GETDATE()) + 1, -1) as time, 'this year end' as timename
union all
select DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), -1) as time, 'last year end' as timename
Is it possible to have the #startdate and #finishdate parameters in null and use the #periodstart and #periodend parameters which have pre-defined values?
report parameter view

I'm not really sure what your issue is, you are asking if it's possible to have more than one start date and end date?
Yes it is, you just need to accommodate this in your dataset query.
Unless I'm missing something I would do it something like this.
DECLARE #sDate datetime
DECLARE #eDate datetime
SET #sDate = ISNULL(#startdate, #periodstart)
SET #eDate = ISNULL(#finishdate, #periodend)
SELECT *
FROM myTable
WHERE RequestSource IN (#reqsource)
AND EntryDay BETWEEN #sDate AND #eDate

Related

SQL setting start date to Friday, and read Data between 2 dates

I'm trying to set the start date to friday on a sql query. Which I have done as you can see below. What I need to do now is show all the GameID's between Friday and Saturday, and it refreshes every week (so that every week it shows other games that have been played in that week).
I'm a complete beginner at SQL so any help is greatly appreciated!
I have tried the sql query below.
DECLARE #StartFriday datetime
DECLARE #EndSaturday datetime
SET DATEFIRST 6 -- Set the start of the week to Friday
SELECT *
FROM
(
SELECT GameDate,
DATEADD(w, 0, DATEADD(w, DATEDIFF(w, 0,GETDATE()), -5)) AS 'StartFriday',
DATEADD(w, 0, DATEADD(w, DATEDIFF(w, 0,GETDATE()), 1)) AS 'EndSaturday'
FROM VW_Resultaat_Score
WHERE GameDate BETWEEN 'StartFriday' AND 'EndSaturday' --Show all GameDates between #StartFriday and #EndSaturday
)
I would love any help I can get!
Cheers
Perhaps this will work better:
DECLARE #StartFriday datetime
DECLARE #EndSaturday datetime
SET DATEFIRST 6
Set #StartFriday = DATEADD(w, 0, DATEADD(w, DATEDIFF(w, 0,GETDATE()), -5))
Set #EndSaturday = DATEADD(w, 0, DATEADD(w, DATEDIFF(w, 0,GETDATE()), 1))
SELECT *
FROM
(
SELECT GameDate
FROM VW_Resultaat_Score
WHERE GameDate BETWEEN #StartFriday AND #EndSaturday
)
If you will only ever need the weekend previous, this code will work:
SELECT *
FROM VW_Resultaat_Score
WHERE GameDate BETWEEN
(SELECT DATEADD(d, 1 - datepart(weekday, dateadd(d, 2, getdate())), getdate()))
AND
(SELECT DATEADD(d, 1 - datepart(weekday, dateadd(d, 1, getdate())), getdate()))
Code looks a little crazy, but it works. If you may need to query other specific weekends, this may be an option:
DECLARE #getdate date
SET #getdate='2017-05-16'
SELECT *
FROM VW_Resultaat_Score
WHERE GameDate BETWEEN
(SELECT DATEADD(d, 1 - datepart(weekday, dateadd(d, 2, #getdate)), #getdate))
AND
(SELECT DATEADD(d, 1 - datepart(weekday, dateadd(d, 1, #getdate)), #getdate))
Taking it a step further, you may need to report on each of these weekends. The following code gives you all the Friday Saturdays of each week for 2017.
WITH Fri as
(SELECT DATEPART(YEAR,DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), n.num)) yyyy, DATEPART(wk,DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), n.num)) weeknumber, Fridays = CAST(DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), n.num) as Date)
FROM (SELECT TOP 366 num = ROW_NUMBER() OVER(ORDER BY a.NAME)-1 FROM dbo.syscolumns a, dbo.syscolumns b) n
WHERE DATENAME(weekday, DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), n.num)) = 'Friday')
,
Sat as
(SELECT weeknumber=DATEPART(wk,DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), n.num)), Saturdays = CAST(DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), n.num) as Date)
FROM (SELECT TOP 366 num = ROW_NUMBER() OVER(ORDER BY a.NAME)-1 FROM dbo.syscolumns a, dbo.syscolumns b) n
WHERE DATENAME(weekday, DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), n.num)) = 'Saturday')
Select Fri.weeknumber, fri.yyyy, Fridays, Saturdays
FROM Fri
JOIN Sat on Fri.weeknumber=Sat.weeknumber

How to run a query for year to date based on end date

I have a query that runs based on the "end date" picked. Essentially the user picks the end date, and the query will run the report for the entire YTD based on the end date. So for example if I select "12/3/12" it should run the report from 1/1/12 - 12/3/12. This works if you run it ON the day... Today I tried to run it for end date "12/31/12" however I return no results because I think it's trying to get the start date based on today's date? Below is my query:
SELECT Store_Number, COUNT(DISTINCT Customer_Email_Address) AS Customer_email_address, COUNT(DISTINCT Invoice_Number) AS [Total Cars],
#enddate AS End_Date, DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), 0) AS Start_Date
FROM Invoice_Tb
WHERE (Invoice_Date BETWEEN DATEADD(yy, DATEDIFF(yy, 0, GETDATE()), 0) AND CONVERT(Datetime, #enddate, 102))
GROUP BY Store_Number
Replace the GetDate() with the #enddate parameter and it should work:
SELECT
Store_Number,
COUNT(DISTINCT Customer_Email_Address) AS Customer_email_address,
COUNT(DISTINCT Invoice_Number) AS [Total Cars],
#enddate AS End_Date,
DATEADD(yy, DATEDIFF(yy, 0, #enddate), 0) AS Start_Date
FROM Invoice_Tb
WHERE (Invoice_Date BETWEEN DATEADD(yy, DATEDIFF(yy, 0, #enddate), 0)
AND CONVERT(Datetime, #enddate, 102))
GROUP BY Store_Number
If you query:
declare #enddate datetime = '12/31/2012'
select DATEADD(yy, DATEDIFF(yy, 0, #enddate), 0)
It will return 2012-01-01 which is what you want.

SQL - Get data based on months form a dateTime column

With SQL Server, I have a column with a launch date (dateTime). I want to report on everything that is being launched between all of last month (from viewing date) thru all of this month and next month.
So basically a full 3 month period.
What is the best way to write that?
Are you looking for something like this?
DECLARE
#StartDate DATETIME,
#EndDate DATETIME
SELECT
#StartDate = DATEADD(MM, DATEDIFF(MM, 0, GETDATE()) - 1, 0),
#EndDate = DATEADD(MM, DATEDIFF(MM, 0, GETDATE()) + 2, 0)
-- DATEADD(MM, DATEDIFF(MM, 0, GETDATE()), 0), -- beginning of this month
-- DATEADD(MM, DATEDIFF(MM, 0, GETDATE()) - 1, 0), -- beginning of last month
-- DATEADD(MM, DATEDIFF(MM, 0, GETDATE()) + 1, 0) -- beginning of next month
-- DATEADD(MM, DATEDIFF(MM, 0, GETDATE()) + 2, 0) -- beginning of two months from now
SELECT
*
FROM
[Table]
WHERE
[LaunchDate] >= #StartDate
AND [LaunchDate] < #EndDate
This will give you all the results starting from the beginning of the previous month and before the beginning of two months from now (a full 3 month range)
Maybe something like SELECT /*what_you_want*/ from launches WHERE lauchDate BETWEEN DATEADD(MONTH, DATEDIFF(MONTH, '19000101', GETDATE()) - 1, '19000101') AND DATEADD(MONTH, DATEDIFF(MONTH, '19000101', GETDATE()) + 2, '19000101')
SELECT Foo
FROM Bar
WHERE LaunchDate >= DATEADD(mm, -1, GETDATE())
AND LaunchDate <= DATEADD(mm, 1, GETDATE())

SQL Query for YTD, MTD, WTD totals

I would like this query to be able to automagically know today's date & time as well as the first of the year (or month) (or week)...
SELECT TicketID
FROM Ticket
WHERE (Ticket.DtCheckOut > '1/1/2011 12:00:00 AM')
AND (Ticket.DtCheckOut < '8/27/2011 12:00:00 AM')
I know it will use GETDATE() in some form, but you don't want to see what I've come up with, I promise!
Here is what I was reading on GETDATE() MDSN: GETDATE(Transact-SQL)
I looked around here and Google - and didn't find anything 'clean' - so any input would be awesome!
DECLARE #now DATETIME
SET #now = GETDATE()
SELECT
DATEADD(yy, DATEDIFF(yy, 0, #now), 0) AS FirstDayOfYear,
DATEADD(mm, DATEDIFF(mm, 0, #now), 0) AS FirstDayOfMonth,
DATEADD(DAY, -DATEDIFF(dd, ##DATEFIRST - 1, #now) % 7, #now) AS FirstDayOfWeek
##DATEFIRST is SQL Server's first day of the week, which defaults to Sunday if you are using U.S. English.
For the first day of the week it can be a bit tricky, depending on your actual requirements (whether you want to obey the user's datefirst setting or not, use Sunday regardless of the setting, etc.), see this question: Get first day of week in SQL Server. Here is one way to do it:
DECLARE
#today DATE = CURRENT_TIMESTAMP,
#y DATE,
#m DATE,
#w DATE;
SELECT
#y = DATEADD(YEAR, DATEDIFF(YEAR, 0, #today), 0),
#m = DATEADD(MONTH, DATEDIFF(MONTH, 0, #today), 0),
#w = DATEADD(DAY, 1-DATEPART(WEEKDAY, #today), #today);
SELECT
[First day of year] = #y,
[First day of month] = #m,
[First day of week] = #w;
Whichever one you are after, you can use in the query, e.g. for YTD you would use:
SELECT TicketCount = COUNT(TicketID)
FROM dbo.Ticket
WHERE DtCheckOut >= #y;
Don't really think you need the < portion of the query if you're trying to get a count up to right now. How many tickets will have been checked out tomorrow if I'm running the query today? If you want to protect yourself against that you can use:
SELECT COUNT(TicketID)
FROM dbo.Ticket
WHERE DtCheckOut >= #y
AND DtCheckOut < DATEADD(DAY, 1, #now);
You could make it a little more dynamic and pass in a parameter that says 'YTD', 'MTD' or 'WTD', e.g.
CREATE PROCEDURE dbo.CountTickets
#Range CHAR(3) = 'YTD'
AS
BEGIN
SET NOCOUNT ON;
-- you may want to handle invalid ranges, e.g.
IF #Range NOT IN ('YTD', 'MTD', 'WTD')
BEGIN
RAISERROR('Please enter a valid range.', 11, 1);
RETURN;
END
DECLARE
#today DATE = CURRENT_TIMESTAMP,
#start DATE;
SELECT
#start = CASE #range
WHEN 'YTD' THEN DATEADD(YEAR, DATEDIFF(YEAR, 0, #today), 0)
WHEN 'MTD' THEN DATEADD(MONTH, DATEDIFF(MONTH, 0, #today), 0)
WHEN 'WTD' THEN DATEADD(DAY, 1-DATEPART(WEEKDAY, #today), #today)
END;
SELECT
Range = #range,
TicketCount = COUNT(TicketID)
FROM dbo.Ticket
WHERE dtCheckOUt >= #start;
END
GO

GETDATE last month

I am trying to list last a website's statistics.
I listed Last 30 days with;
CONVERT(VARCHAR(10), S.DATEENTERED, 101)
BETWEEN
CONVERT(VARCHAR(10), GETDATE()-30, 101)
AND
CONVERT(VARCHAR(10), GETDATE(), 101)
and this month with;
RIGHT(CONVERT(VARCHAR(10), S.DATEENTERED, 103), 7) =
RIGHT(CONVERT(VARCHAR(10), GETDATE(), 103), 7)
but I have no idea what query to use for last month. I tried with;
RIGHT(CONVERT(VARCHAR(10), S.DATEENTERED, 103), 7) =
RIGHT(CONVERT(VARCHAR(10), GETDATE()-1, 103), 7)
Did not work.
Dates are always a joy to work with in any programming language, SQL not excluded.
To answer your question to find all records that occurred last month
select S.DATEENTERED
,*
from sometable S
where S.DATEENTERED
between dateadd(mm, datediff(mm, 0, dateadd(MM, -1, getdate())), 0)
and dateadd(ms, -3, dateadd(mm, datediff(mm, 0, dateadd(MM, -1, getdate())) + 1, 0))
order by 1
To expand the best means for getting records within a certain time-frame is by utilizing the datediff function, dateadd function, and the between condition in the where clause.
select 'howdy'
,getdate()
where getdate()
between dateadd(mm, 0, 0)
and dateadd(ms, -3, dateadd(mm, datediff(mm, 0, dateadd(mm,-1,getutcdate())) + 1, 0))
The above code will result in no records returned because it is checking to see if today's date is between 1900-01-01 00:00:00.000 and the last possible recorded date of last month (the last day and 23:59:59.997 - SQL Server DATETIME columns have at most a 3 millisecond resolution).
The following code will return a record as the date we are searching for is one month ago.
select 'howdy'
,dateadd(mm, -1, getdate())
where dateadd(mm, -1, getdate())
between dateadd(mm, 0, 0)
and dateadd(ms, -3, dateadd(mm, datediff(mm, 0, dateadd(mm,-1,getutcdate())) + 1, 0))
A break down of the where clause:
WHERE getdate() -- date to check
between dateadd(mm, 0, 0) -- begin date
and dateadd(ms, -3, dateadd(mm, datediff(mm, 0, dateadd(mm,-1,getutcdate())) + 1, 0)) -- end date
Finally, a variety of dates can be ascertained in this manner here is a pretty complete list:
select dateadd(mm, 0, 0) as BeginningOfTime
,dateadd(dd, datediff(dd, 0, getdate()), 0) as Today
,dateadd(wk, datediff(wk, 0, getdate()), 0) as ThisWeekStart
,dateadd(mm, datediff(mm, 0, getdate()), 0) as ThisMonthStart
,dateadd(qq, datediff(qq, 0, getdate()), 0) as ThisQuarterStart
,dateadd(yy, datediff(yy, 0, getdate()), 0) as ThisYearStart
,dateadd(dd, datediff(dd, 0, getdate()) + 1, 0) as Tomorrow
,dateadd(wk, datediff(wk, 0, getdate()) + 1, 0) as NextWeekStart
,dateadd(mm, datediff(mm, 0, getdate()) + 1, 0) as NextMonthStart
,dateadd(qq, datediff(qq, 0, getdate()) + 1, 0) as NextQuarterStart
,dateadd(yy, datediff(yy, 0, getdate()) + 1, 0) as NextYearStart
,dateadd(ms, -3, dateadd(dd, datediff(dd, 0, getdate()) + 1, 0)) as TodayEnd
,dateadd(ms, -3, dateadd(wk, datediff(wk, 0, getdate()) + 1, 0)) as ThisWeekEnd
,dateadd(ms, -3, dateadd(mm, datediff(mm, 0, getdate()) + 1, 0)) as ThisMonthEnd
,dateadd(ms, -3, dateadd(qq, datediff(qq, 0, getdate()) + 1, 0)) as ThisQuarterEnd
,dateadd(ms, -3, dateadd(yy, datediff(yy, 0, getdate()) + 1, 0)) as ThisYearEnd
Using the above list a range of any type can be determined.
The following will find you the start of the last month:
-- Start of last month
SELECT CAST('01 '+ RIGHT(CONVERT(CHAR(11),DATEADD(MONTH,-1,GETDATE()),113),8) AS datetime)
You would then find the start of this month, using the following, minus one.
-- Start of the month
SELECT CAST('01 '+ RIGHT(CONVERT(CHAR(11),GETDATE(),113),8) AS datetime)
When I have to work with dates in SQL Server I often reference Robyn Page's SQL Server DATE/TIME Workbench. The workbench (tutorial) is well laid out and contains just about everything I have ever needed when working with dates on SQL Server.
How about this?
select DATEADD(month, -1, GETDATE())
I would suggest using the first day of last month and the first day of the current month for the operation and rather than using BETWEEN use >= and <. That's my personal opinion, but I believe you will find there are performance and maintainability benefits to this approach.
Here's the sql. You will notice I've included the last day of the last month value just in case you end up going with another approach.
Keep in mind, these dates are based off of 12:00AM that day. In other words, getting values between 6/1/2009 and 6/30/2009 won't get you what you want as all of 6/30/2009 is excluded. If you use the first day of July (7/1/2009) you are covered.
Again, I recommend avoiding BETWEEN all together as shown below. Best of luck.
Declare #LastMonthFirstDay datetime
Declare #LastMonthLastDay datetime
Declare #ThisMonthFirstDay datetime
Set #LastMonthFirstDay = DATEADD(MONTH, DATEDIFF(MONTH, 0, CURRENT_TIMESTAMP) - 1, 0);
Set #ThisMonthFirstDay = DATEADD(MONTH, DATEDIFF(MONTH, 0, CURRENT_TIMESTAMP), 0);
Set #LastMonthLastDay = DATEADD(DAY, -1, DATEADD(MONTH, DATEDIFF(MONTH, 0, CURRENT_TIMESTAMP), 0));
Select * From Table
Where DateEntered >= #LastMonthFirstDay
And DateEntered < #ThisMonthFirstDay;
Try using the DATEADD function. You can add a -1 with the MONTH (mm) datepart and it should work. Here is a link
where year(S.DATEENTERED) = year(dateadd(mm, -1, getdate())) and month(S.DATEENTERED) = month(dateadd(mm, -1, getdate()))
Might not be good performance-wise but you've got the idea.
GET FIRST DAY OF LAST MONTH
SELECT DATEADD(MM, DATEDIFF(MM, '01/01/2000', DATEADD(MM, -1,GETDATE())), '01/01/2000')
GET LAST DAY OF LAST MONTH
SELECT DATEADD(SS,-1,DATEADD(MM, DATEDIFF(MM,'01/01/2000',GETDATE()),'01/01/2000'))
Then search based on this range.
Try:
declare #lastm int
set #lastm = datepart(mm,getdate()) - 1
...
where datepart(mm,s.dateentered) = #lastm