SQL Query: Each GROUP BY expression must contain at least one column that is not an outer reference
Getting this error: Each GROUP BY expression must contain at least one column that is not an outer reference.
RowId ErrorDatetime ErrorNum ErrorMessage
824 2010-09-24 08:01:42.000 9001 Account 55 not found
823 2010-09-24 08:00:56.000 9001 Account 22222222222 not found
822 2010-09-24 05:06:27.000 9001 Account 55 not found
821 2010-09-24 05:05:42.000 9001 Account 22222222222 not found
I'm trying to get the errormessage, and 开发者_Python百科the first time it occurred for the current day, and that's working because I just do "Group by ErrorMessage".
However, if I want to find the first for each day:
SELECT Min(ErrorDateTime) as 'ErrorDateTime', Min(ErrorMessage) as 'ErrorMessage'
FROM CommonError
WHERE dbo.StripTimeFromDate(ErrorDateTime) = dbo.StripTimeFromDate(getdate())
and ErrorNumber = '9001'
GROUP BY dbo.StripTimeFromDate(getdate()), ErrorMessage
The handy-dandy function (from http://bloggingabout.net/blogs/jschreuder/archive/2007/03/13/useful-t-sql-date-functions.aspx):
ALTER FUNCTION [dbo].[StripTimeFromDate] (@inputDate DATETIME)
RETURNS DATETIME
BEGIN
RETURN DATEADD(d, DATEDIFF(d, 0, @inputDate), 0)
END
First, you don't need the MIN(ErrorMessage) in your SELECT. Simply SELECT ErrorMessage. Second, GROUP BY ErrorMessage only.
SELECT Min(ErrorDateTime) as 'ErrorDateTime', ErrorMessage
FROM CommonError
WHERE dbo.StripTimeFromDate(ErrorDateTime) = dbo.StripTimeFromDate(getdate())
and ErrorNumber = '9001'
GROUP BY ErrorMessage
Use:
SELECT t.errormessage, MIN(t.errordatetime) AS dt
FROM COMMONERROR t
GROUP BY t.errormessage, DATEADD(d, DATEDIFF(d, 0, t.errordatetime), 0)
Check the references in the GROUP BY; it wasn't getting caught because MIN was being applied to the same column.
Assuming SQL Server 2005+, this is easier to handle with analytics:
WITH base AS (
SELECT t.*,
ROW_NUMBER() OVER(PARTITION BY t.errormessage, DATEADD(d, DATEDIFF(d, 0, t.errordatetime), 0)
ORDER BY t.errordatetime) AS rk
FROM dbo.COMMONERROR t)
SELECT b.*
FROM base b
WHERE b.rk = 1
AND b.errornumber = '9001'
AND DATEADD(d, DATEDIFF(d, 0, b.errordatetime), 0) = DATEADD(d, DATEDIFF(d, 0, GETDATE()), 0)
I had getdate() instead of ErrorDate in the "group by". I think I saw similar issues in other forums where people had a literal in the "group by".
Correction is:
GROUP BY dbo.StripTimeFromDate(ErrorDate), ErrorMessage
精彩评论