Multi select List Box ‘OR’ search using Stored procedure

It is common requirement to allow multiple List Items selection and selecting the ‘Search’ button returns all the records where each List Item Text matches with record as explained below.

Example: Multiple selection List Box

Multi_Select_ListBox

User Interface

Selecting the Button should return all records WHERE VB.NET ‘OR’ ASP.NET ‘OR’ ‘VBA’ matches using IN clause as this is OR search rather than AND search.

Database:

Say ‘Technology’ column consists of below rows in database table.

Technology_Tbl

Search results:- Search should return all the 5 rows from above table.

Lets explore further to achieve the above requirement using Stored procedure.

I. ASP.NET

<asp:ListBox ID="ddlTechnology" runat="server"     
SelectionMode="Multiple">
<asp:ListItem Value="" Text="Select single or multiple Systems" />
<asp:ListItem Value="ASP.NET" Text="ASP.NET" />
<asp:ListItem Value="VB.NET" Text="VB.NET" />
<asp:ListItem Value="VBA" Text="VBA" />
</asp:ListBox>

II. In code behind build a string with selected List Items Text delimited with a comma as below.

//Loop through List Items list and add selected items
// with comma in between
foreach (ListItem item in ddlTechnology.Items)
{
  if (item.Selected)
  {
  selectedTechnologies +=  "," + item.Text.Trim();
  selectedTechnologiesList.
Add(ddlTechnology.Items.IndexOf(item));
            }
        }
if (selectedTechnologies.Length != 0)
  {
selectedTechnologies = 
selectedTechnologies.Substring(1);
        }
//Store in session
Session["Technologies"] = selectedTechnologies;

//In this example selectedTechnologies String 
//consists of "VB.NET,ASP.NET,VBA"

III. Pass to Stored procedure as parameterized query

/// <summary>Pass search parameters to Stored procedure and ///return DataTable
/// </summary>
/// <returns>DataTable</returns>
private DataTable Search()
    {
string procedure = "spSearchTechnologies";

        SqlConnection con = new SqlConnection(ConnectionString);
//DataTable 
DataTable dtTechnologies = new DataTable();
try
{
SqlCommand cmd = new SqlCommand(procedure, con);
cmd.CommandType = CommandType.StoredProcedure;
//Pass search criteria with parameters
cmd.Parameters.AddWithValue("@Technologies", 
Convert.ToString(Session["Technologies"]));
//Data adapter
SqlDataAdapter adapter = new SqlDataAdapter(cmd);
//fill the data table with results
adapter.Fill(dtTechnologies);
//Display number of records returned
if (dtTechnologies.Rows.Count != 0)
{
lblRecCount.Text = "Total Number of records returned:" 
+ " " + dtTechnologies.Rows.Count.ToString() + "\n";
}
else
{
lblRecCount.Text = "No records matched your search criteria";
}
}

catch (Exception ex)
{
lblRecCount.Text = ex.InnerException.Message;
}

finally
{
if (con != null)
{
con.Close();
}
}
//return the data table
return dtTechnologies;
}
#endregion

 

IV. Stored Procedure source

ALTER PROCEDURE [dbo].[spSearchTechnologies]
(
	--parameters
	@Technologies nvarchar(100)= NULL;
	
)
AS BEGIN

If @Technologies	IS NOT NULL AND 
Len(@Technologies)=0 Set @Technologies  = NULL

--Select
SELECT id,technologies	
FROM technology t 
WHERE

--StringSplit is T-SQL function that splits passed
--string into separate ones where COMMA (,) appears
--StringSplit function source is copied below
(@Technologies IS NULL OR t.technology
COLLATE DATABASE_DEFAULT IN (SELECT technology
FROM dbo.StringSplit(@Technologies,',') t1,
technology t WHERE 
CHARINDEX(t1.items,t.technology) > 0 ))
)
ORDER BY t.technology

END

V. StringSplit T-SQL Function

FUNCTION [dbo].[StringSplit](@String varchar(8000),
@Delimiter char(1))      
returns @temptable TABLE (items varchar(8000))      
as      
begin      
declare @idx int      
declare @slice varchar(8000)      
     
select @idx = 1      
if len(@String)<1 or @String is null  return      
     
while @idx!= 0      
begin      
set @idx = charindex(@Delimiter,@String)      
if @idx!=0      
set @slice = left(@String,@idx - 1)      
else      
set @slice = @String      
                
if(len(@slice)>0) 
insert into @temptable(Items) values(@slice)      
 
set @String = right(@String,len(@String) - @idx)      
if len(@String) = 0 break      
end  
return      
end

Thats it. Search returns DataTable object with accurate results.

There are number of approaches to handle the requirement, one of the good resources that I come across is at http://vyaskn.tripod.com/passing_arrays_to_stored_procedures.htm

2 Comments

Comments have been disabled for this content.