Say you have WIDGETS table:
- WidgetID int
- ColorID int (Lookup values: Red, Blue, Green, Yellow, Black, Brown)
- SizeID int (Lookup values: Small, Med, Big, Large)
- Weight int (Lookup values: UltraLight, Light, Normal, Heavy, UltraHeavy
Ok that’s the general idea of the table. I don’t need the lookup names, what I do have is the lookupvalue ID’s. So from this table, I would to be able pull lists back that meet say the following crieria:
- Show me all widgets who are Red, or Blue, or Black
- Show me all widgets who are Red or Blue, and Small or Med
- Show me all widgets who are Heavy only
- Show me all widgets who are heavy and Yellow
- Show me all widgets who are heavy and yellow and small or big
- Show me all widgets who are Large only
- Show me all widgets who are Green only
Get the idea? I’ve been trying to work on a Stored Proc that allowed me to send in some type of parameters. Even tried dynamic sql but getting weird errors. can’t remember now.
My Attempt #3, sort of works if I could get it working in a Proc and be able to condition out which Join’s I want
Examples of what I’ve tried:
Note: In my examples: (CourseID is WidgetID) and (StateID is ColorID) and (CreditTypeID is SizeID) and (SubjectID is WeightID)
Attempt Method 1
ALTER PROCEDURE [dbo].[CourseListFullInfoByStateCreditSubject]
@StateIDs VARCHAR(200) = '',
@CreditTypeIDs VARCHAR(200) = '',
@SubjectTypeIDs VARCHAR(200) = ''
AS
BEGIN
DECLARE @SQL AS NVARCHAR(MAX)
SET @SQL = 'SELECT DISTINCT
C.CourseID,
LU.FirstName,
LU.LastName,
(SELECT COUNT(ReviewID) FROM Review AS R WHERE R.CourseID = C.CourseID) AS ReviewCount
FROM [Course] AS C WITH(NOLOCK)
JOIN LexUser AS LU ON LU.LexUserID = C.PresenterID '
If @StateIDs IS NOT NULL AND @StateIDs <> '''' AND @StateIDs <> '0'
BEGIN
SET @SQL = @SQL + ' JOIN CourseToState AS CS ON CS.CourseID = C.CourseID AND CHARINDEX('','' + CAST(CS.StateID AS VARCHAR) + '','', '','' + @StateIDs + '','') > 0 '
END
If @CreditTypeIDs IS NOT NULL AND @CreditTypeIDs <> '' AND @CreditTypeIDs <> '0'
BEGIN
SET @SQL = @SQL + 'JOIN CourseToCreditType As CC ON CC.CourseID = C.CourseID AND CHARINDEX('','' + CAST(CC.CreditTypeID AS VARCHAR) + '','', '','' + @CreditTypeIDs + '','') > 0 '
END
If @SubjectTypeIDs IS NOT NULL AND @SubjectTypeIDs <> '' AND @SubjectTypeIDs <> '0'
BEGIN
SET @SQL = @SQL + 'JOIN CourseToSubject As CSu ON CSu.CourseID = C.CourseID AND CHARINDEX('','' + CAST(CSu.SubjectID AS VARCHAR) + '','', '','' + @SubjectTypeIDs + '','') > 0 '
END
EXEC sp_executesql @SQL
With Attempt 1 I try and send in the ID’s:
[CourseListFullInfoByStateCreditSubject] ''1,2,4'', ''0'', ''0''
…but I get an error, “Incorrect syntax near ‘1’.”
Attempt Method 2, gives same error
DECLARE @SQL AS NVARCHAR(MAX)
SET @SQL = 'SELECT DISTINCT
C.CourseID,
LU.FirstName,
LU.LastName,
(SELECT COUNT(ReviewID)
FROM Review AS R
WHERE R.CourseID = C.CourseID) AS ReviewCount
FROM [Course] AS C WITH(NOLOCK)
JOIN LexUser AS LU ON LU.LexUserID = C.PresenterID '
If @StateIDs IS NOT NULL AND @StateIDs <> '''' AND @StateIDs <> '0'
BEGIN
SET @SQL = @SQL + ' JOIN CourseToState AS CS ON CS.CourseID = C.CourseID AND CHARINDEX('','' + CAST(CS.StateID AS VARCHAR) + '','', '','' + @StateIDs + '','') > 0 '
END
If @CreditTypeIDs IS NOT NULL AND @CreditTypeIDs <> '' AND @CreditTypeIDs <> '0'
BEGIN
SET @SQL = @SQL + 'JOIN CourseToCreditType As CC ON CC.CourseID = C.CourseID AND CHARINDEX('','' + CAST(CC.CreditTypeID AS VARCHAR) + '','', '','' + @CreditTypeIDs + '','') > 0'
END
If @SubjectTypeIDs IS NOT NULL AND @SubjectTypeIDs <> '' AND @SubjectTypeIDs <> '0'
BEGIN
SET @SQL = @SQL + 'JOIN CourseToSubject As CSu ON CSu.CourseID = C.CourseID AND CHARINDEX('','' + CAST(CSu.SubjectID AS VARCHAR) + '','', '','' + @SubjectTypeIDs + '','') > 0'
END
Attempt Method 3 – Sort of Works
This method only works if I send it ID’s for each feld, I can’t leave one blank to get “all” and I can’t get it working in a stored proc, which is what I tried to do in Attempt #2
DECLARE @StateIDs VARCHAR(200) = ''
DECLARE @CreditTypeIDs VARCHAR(200) = ''
DECLARE @SubjectTypeIDs VARCHAR(200) = ''
SET @StateIDs = '1,3,2,'
SET @CreditTypeIDs = '1,3'
SET @SubjectTypeIDs = '1,2,3,4'
SELECT DISTINCT
C.CourseID,
LU.FirstName,
LU.LastName,
(SELECT COUNT(ReviewID) FROM Review AS R WHERE R.CourseID = C.CourseID) AS ReviewCount
FROM [Course] AS C WITH(NOLOCK)
JOIN LexUser AS LU ON LU.LexUserID = C.PresenterID
JOIN CourseToState AS CS ON CS.CourseID = C.CourseID AND CHARINDEX(',' + CAST(CS.StateID AS VARCHAR) + ',', ',' + @StateIDs + ',') > 0
JOIN CourseToCreditType As CC ON CC.CourseID = C.CourseID AND CHARINDEX(',' + CAST(CC.CreditTypeID AS VARCHAR) + ',', ',' + @CreditTypeIDs + ',') > 0
JOIN CourseToSubject As CSu ON CSu.CourseID = C.CourseID AND CHARINDEX(',' + CAST(CSu.SubjectID AS VARCHAR) + ',', ',' + @SubjectTypeIDs + ',') > 0
How about something like this:
Make a stored procedure with a comma-separated list of conditions, should look like
Nothing special here. All it does is match each trait (Color, Size, Weight) against a comma-separated list of qualifying conditions. If you want to filter on Blue items, you should pass the string ‘ Blue, ‘. The flanking spaces and commas should be present because it’s easier to have them there then to fight with SQL. The condition string is then compared to each color value like so:
This must be executed dynamically, unless you split the conditions out somehow to a temporary table and use the
INoperator.