I have written following stored procedure
CREATE procedure [dbo].[findUSerID]
#Column_name varchar(50),
#TR_ID int
AS
DECLARE #sql nvarchar(max) = 'SELECT ' +#Column_name+ '
FROM Transfer_TB
WHERE TID =' + CAST(#TR_ID AS VARCHAR(10))
EXEC sp_executesql #sql
Table definition :
CREATE TABLE [dbo].[Transfer_TB]
(
[TID] [int] NULL,
[ABC] [varchar](20) NULL,
[XYZ] [varchar](50) NULL,
[LMN] [varchar](50) NULL,
[PQR] [varchar](50) NULL,
)
But it does not return the proper output.
Like I have called it from my asp page code for that using n tier architecture.
public string check_validID(string branch,int trId)
{
string user_Br_ID;
clsBranch_TB objbr = new clsBranch_TB();
clsUserTB objuser = new clsUserTB();
objuser.User_Branch = 'XYZ';
objuser.Extra_Int = 32;
DataSet ds = clsAdminLogic.findUSerID(objuser);
if (ds.Tables[0].Rows.Count == 0)
{
user_Br_ID = clsAdminLogic.getno_of_Emp(objbr);
}
else
{
user_Br_ID = ds.Tables[0].Rows[0][0].ToString();
}
return user_Br_ID;
}
public static DataSet findUSerID(clsUserTB objuser)
{
DataSet ds = DataAccessLayer.clsLogs.findUSerID(objuser);
return ds;
}
public static DataSet findUSerID(clsUserTB objuser)
{
SqlParameter[] param = {
new SqlParameter("#TR_ID",objuser.Extra_Int),
new SqlParameter("#Column_name",objuser.User_Branch)
};
DataSet ds = DataAccessLayer.SqlHelper.FillDataNewRJ(
DataAccessLayer.clsDataAccessLayer.con.ConnectionString.ToString(),
CommandType.StoredProcedure, "findUSerID", (param)
);
return ds;
}
As it executes it, there is value present in database, but still it enters into if part of that function.
Please help me and guide if something wrong in above code
Your stored procedure is prone to Sql-Injection. do the following to protect yourself against it.
CREATE procedure [dbo].[findUSerID]
#Column_name SYSNAME
,#TR_ID INT
AS
BEGIN
SET NOCOUNT ON;
DECLARE #sql nvarchar(max);
SET #sql = N' SELECT ' + QUOTENAME(#Column_name)
+ N' FROM Transfer_TB '
+ N' WHERE TID = #TR_ID '
exec sp_executesql #sql
,N'#TR_ID int'
,#TR_ID
END
If your Stored procedure is returning a scalar value "UserID" as the name suggest you should be doing something like......
CREATE procedure [dbo].[findUSerID]
#Column_name SYSNAME
,#TR_ID INT
,#UserID INT OUTPUT
AS
BEGIN
SET NOCOUNT ON;
DECLARE #sql nvarchar(max);
SET #sql = N' SELECT #UserID = ' + QUOTENAME(#Column_name)
+ N' FROM Transfer_TB '
+ N' WHERE TID = #TR_ID '
exec sp_executesql #sql
,N'#TR_ID int , #UserID INT OUTPUT'
,#TR_ID
,#UserID OUTPUT
END
there is value present in database, but still it enters into else part of that function
I assume this is the part you're talking about (there are 3 functions in that code)
if (ds.Tables[0].Rows.Count == 0)
{
user_Br_ID = clsAdminLogic.getno_of_Emp(objbr);
}
else
{
user_Br_ID = ds.Tables[0].Rows[0][0].ToString();
}
Yes. Your if goes into the else if the rows are not 0. It's doing exactly what its being told. That basic logic error is the least of your worries though. You're storing branches as columns?
i found solution for this problem, actually that particular record contains values instead of selective column that's why query returning the null value.
So i just have added one condition my stored procedure to fix it .
ALTER procedure [dbo].[findUSerID]
#Column_name varchar(50),
#TR_ID int
AS
DECLARE #sql nvarchar(max) = 'SELECT ' +#Column_name+ '
FROM Transfer_TB where TID =' + CAST(#TR_ID AS VARCHAR(10))+'
and '+#Column_name+'<> null'
exec sp_executesql #sql
Related
I have created a stored procedure that is using forms from ASP.NET to create a keyword search of thousands of books we have in our database.
The problem is that I have inherited code from another developer, and must use her code. I cannot rewrite the stored procedure.
As a result, I have to find a way to add the LIKE operator to the following part of the stored procedure:
Books = #Books OR #Books IS NULL
This is because the #Books is the part of the form where the user enters in a keyword search. I have looked up how to use the LIKE operator in a stored procedure, but nothing applies to this type of code.
The complete stored procedure is listed below:
Create Procedure spSearchAuthors
#FirstName nvarchar(100) = NULL,
#LastName nvarchar(100) = NULL,
#Books nvarchar(50) = NULL
As
Begin
Select FirstName, LastName, Books from Authors where
(FirstName = #FirstName OR #FirstName IS NULL) AND
(LastName = #LastName OR #LastName IS NULL) AND
(Books = #Books OR #Books IS NULL)
End
Go
A LIKE has simple syntax: %, _, [...]
In this case you could keep it simple.
By concatinating a % to both ends of the string variables.
CREATE Procedure spSearchAuthors
#FirstName NVARCHAR(100) = NULL,
#LastName NVARCHAR(100) = NULL,
#Books NVARCHAR(50) = NULL
AS
BEGIN
SELECT FirstName, LastName, Books
FROM Authors
WHERE (#FirstName IS NULL OR FirstName LIKE '%'+#FirstName+'%')
AND (#LastName IS NULL OR LastName LIKE '%'+#LastName+'%')
AND (#Books IS NULL OR Books LIKE '%'+#Books+'%');
END;
GO
Using Dynamic SQL is more complicated.
CREATE Procedure spSearchAuthors
#FirstName NVARCHAR(100) = NULL,
#LastName NVARCHAR(100) = NULL,
#Books NVARCHAR(50) = NULL
AS
BEGIN
DECLARE #DynSql NVARCHAR(800);
DECLARE #ParmDefinition NVARCHAR(100);
SET #DynSql = N'SELECT FirstName, LastName, Books FROM Authors';
IF #FirstName IS NOT NULL
BEGIN
SET #DynSql += CHAR(10)+'WHERE FirstName LIKE #FirstName';
SET #FirstName = N'%'+#FirstName+N'%';
END;
IF #LastName IS NOT NULL
BEGIN
IF #FirstName IS NULL
SET #DynSql += CHAR(10)+'WHERE ';
ELSE
SET #DynSql += CHAR(10)+'AND ';
SET #DynSql += 'LastName LIKE #LastName';
SET #LastName = N'%'+#LastName+N'%';
END;
IF #Books IS NOT NULL
BEGIN
IF #FirstName IS NULL AND #LastName IS NULL
SET #DynSql += CHAR(10)+'WHERE ';
ELSE
SET #DynSql += CHAR(10)+'AND ';
SET #DynSql += 'Books LIKE #Books';
SET #Books = N'%'+#Books+N'%';
END;
SET #ParmDefinition = N'#FirstName NVARCHAR(102), #LastName NVARCHAR(102), #Books NVARCHAR(52)';
EXECUTE sp_executesql #DynSql, #ParmDefinition,
#FirstName = #FirstName,
#LastName = #LastName,
#Books = #Books;
END;
GO
I am trying to concatenate the large number of id'd and to update the status of all id's.
For example:
aclid in (4604019,4604018,4604017,4604016,4604015,4604014,4604013,4604012,4604011,4604010,4604009,4604008,4604007,4604006,4604005,4604004,4604003,4604002,4604001,4604000,4603999,4603998,4603997,4603996,4603995,4603994,4603993,4603992,4603991,4603990,4603989,4603988)`
Please check my stored procedure:
ALTER PROCEDURE [dbo].[VT_ACLReportChangeStatus]
(#ChangeStatus nvarchar(50) = null,
#ACLId nvarchar(max))
AS
/* Exec VT_ACLReportChangeStatus 'Complete','4599473,4599472,4599471,4599469,4599468' */
BEGIN
UPDATE VT_ACLReport
SET Status = #ChangeStatus
WHERE ACLId IN (SELECT * FROM SplitDelimiterString(#ACLId,','))
END
Please check my code behind:
ACLId = ACLId.ToString().Trim(',');
using (SqlConnection con = new SqlConnection(cs))
{
cmd = new SqlCommand("VT_ACLReportChangeStatus", con);
cmd.CommandType = System.Data.CommandType.StoredProcedure;
cmd.CommandTimeout = 3600;
cmd.Parameters.Add(new SqlParameter("#ACLId", SqlDbType.NVarChar,-1));
cmd.Parameters.Add(new SqlParameter("#ChangeStatus", SqlDbType.NVarChar, 50));
cmd.Parameters["#ACLId"].Value = ACLId;
cmd.Parameters["#ChangeStatus"].Value = ddlChangeStatus.SelectedItem.Text.ToString();
con.Open();
cmd.ExecuteNonQuery();
con.Close();
}
AclId column data type is bigint identity.
Please can you help me in concatenating large string and to update all rows whose aclid is present.
I would suggest, create one user defined table type in sql and one class in sourecode with your respective data. You can pass object of this class to sql and in your SP you can use join between main table and this table(which is received as input parameter) to update data.
Thanks all of you for your answers.. Actually it was silly mistake,while calling splitting function in Stored procedure. In function it was varchar(8000). :) solved it.
ALTER FUNCTION [dbo].[SplitDelimiterString] (#StringWithDelimiter VARCHAR(max), #Delimiter VARCHAR(max))
RETURNS #ItemTable TABLE (Item VARCHAR(max))
AS
BEGIN
DECLARE #StartingPosition INT;
DECLARE #ItemInString VARCHAR(max);
SELECT #StartingPosition = 1;
--Return if string is null or empty
IF LEN(#StringWithDelimiter) = 0 OR #StringWithDelimiter IS NULL RETURN;
WHILE #StartingPosition > 0
BEGIN
--Get starting index of delimiter .. If string
--doesn't contain any delimiter than it will returl 0
SET #StartingPosition = CHARINDEX(#Delimiter,#StringWithDelimiter);
--Get item from string
IF #StartingPosition > 0
SET #ItemInString = SUBSTRING(#StringWithDelimiter,0,#StartingPosition)
ELSE
SET #ItemInString = #StringWithDelimiter;
--If item isn't empty than add to return table
IF( LEN(#ItemInString) > 0)
INSERT INTO #ItemTable(Item) VALUES (#ItemInString);
--Remove inserted item from string
SET #StringWithDelimiter = SUBSTRING(#StringWithDelimiter,#StartingPosition +
LEN(#Delimiter),LEN(#StringWithDelimiter) - #StartingPosition)
--Break loop if string is empty
IF LEN(#StringWithDelimiter) = 0 BREAK;
END
RETURN
END
Having a total blonde moment here so apologies in advance...!
I want to carry out two COUNT conditions prior to entering a new customer recorded into a DB. The below code checks to see if the Username is already in use and rejects the registration if this is applicable. I would like to add an additional COUNT to check if the "CustomerEmail", taken from txtEmail already exists in the DB as well.
I would use a stored procedure to do this something like....
And obviously use appropriate data types for the params
CREATE PROCEDURE usp_InsertUser
#FirstName VARCHAR(100)
, #Surname VARCHAR(100)
, #Email VARCHAR(100)
, #Address VARCHAR(100)
, #Town VARCHAR(100)
, #City VARCHAR(100)
, #Postcode VARCHAR(100)
, #ContactNumber VARCHAR(100)
, #Username VARCHAR(100)
, #Password VARCHAR(100)
, #UserAdded INT OUTPUT
AS
BEGIN
SET NOCOUNT ON;
IF NOT EXISTS (SELECT *
FROM [Customer] WITH (UPDLOCK)
WHERE CustomerUserName = #Username)
BEGIN
INSERT INTO [Customer] (CustomerFirstName,CustomerSurname,CustomerEmailAddress,CustomerAddress,CustomerAddressTown,CustomerAddressCity,CustomerAddressPostcode,CustomerContactNumber,CustomerUserName,CustomerPassword)
VALUES (#FirstName, #Surname,#Email, #Address, #Town, #City, #Postcode,#ContactNumber,#Username,#Password)
SET #UserAdded = 1;
END
ELSE
BEGIN
SET #UserAdded = 0;
END
END
Application code would look something like.....
// define connection and command, in using blocks to ensure disposal
using(SqlConnection conn = new SqlConnection(pvConnectionString ))
using(SqlCommand cmd = new SqlCommand("dbo.usp_InsertUser", conn))
{
cmd.CommandType = CommandType.StoredProcedure;
// set up the parameters
cmd.Parameters.Add("#UserAdded", SqlDbType.Int).Direction = ParameterDirection.Output;
cmd.Parameters.Add("#FirstName", SqlDbType.VarChar, 100);
cmd.Parameters.Add("#Surname", SqlDbType.VarChar, 100);
cmd.Parameters.Add("#Email", SqlDbType.VarChar, 100);
// and so on.....
// set parameter values
cmd.Parameters["#FirstName"].Value = txtFirstName.Text;
cmd.Parameters["#Surname"].Value = txtSurname.Text;
cmd.Parameters["#Email"].Value = txtEmail.Text;
// and so on.....
// open connection and execute stored procedure
conn.Open();
cmd.ExecuteNonQuery();
// read output value from #NewId
int UserAdded = Convert.ToInt32(cmd.Parameters["#UserAdded"].Value);
if (UserAdded == 1)
{
Response.Write("User already exists.");
}
conn.Close();
}
Instead of counting all users and adding 2 check just do one exists statement with 2 conditions.
IF NOT EXISTS(select count(*) from [Customer] where CustomerUserName= #name AND CustomerEmail = #email)
BEGIN
INSERT INTO [Customer] (CustomerFirstName,CustomerSurname,CustomerEmailAddress,CustomerAddress,CustomerAddressTown,CustomerAddressCity,CustomerAddressPostcode,CustomerContactNumber,CustomerUserName,CustomerPassword) VALUES (#FirstName, #Surname,#Email, #Address, #Town, #City, #Postcode,#ContactNumber,#Username,#Password)
END
I have written a stored procedure for inserting and updating values in a table. The issue is that when I update the form it I get this error
Procedure or function 'sp_AddUpdatePages' expects parameter '#Id', which was not supplied.
My Id column is set to Identity in the SQL Server table. Also please see my stored procedure for your reference:
ALTER PROCEDURE Sp_addupdatepages
(#Id INT,
#page_title NVARCHAR(100),
#page_description NVARCHAR(max),
#meta_title NVARCHAR(255),
#meta_keywords NVARCHAR(255),
#meta_description NVARCHAR(1000),
#Active BIT)
AS
BEGIN
SET nocount ON;
IF EXISTS(SELECT *
FROM tbl_pages
WHERE id = #Id)
BEGIN
UPDATE [tbl_pages]
SET [page_title] = #page_title,
[page_description] = #page_description,
[meta_title] = #meta_title,
[meta_keywords] = #meta_keywords,
[meta_description] = #meta_description,
[active] = #Active
WHERE id = #Id
END
ELSE
BEGIN
INSERT INTO [tbl_pages]
([page_title],
[page_description],
[meta_title],
[meta_keywords],
[meta_description],
[active])
VALUES (#page_title,
#page_description,
#meta_title,
#meta_keywords,
#meta_description,
#Active)
END
SELECT [page_title],
[page_description],
[meta_title],
[meta_keywords],
[meta_description],
[active]
FROM tbl_pages
END
This is my code behind:
protected void btnAdd_Click(object sender, EventArgs e)
{
using (SqlCommand cmd = new SqlCommand())
{
cmd.CommandType = CommandType.StoredProcedure;
cmd.CommandText = "sp_AddUpdatePages";
cmd.Parameters.AddWithValue("#page_title", txtPageTitle.Text);
cmd.Parameters.AddWithValue("#page_description", txtPagedesc.Text);
cmd.Parameters.AddWithValue("#meta_title", txtmetatitle.Text);
cmd.Parameters.AddWithValue("#meta_keywords", txtMetakeywords.Text);
cmd.Parameters.AddWithValue("#meta_description", txtMetadesc.Text);
cmd.Parameters.AddWithValue("#Active", ddlActiveInactive.SelectedIndex);
grdCSRPageData.DataSource = this.GetData(cmd);
grdCSRPageData.DataBind();
ClientScript.RegisterStartupScript(Page.GetType(), "validation", "<script language='javascript'>alert('Page Added succesfully')</script>");
}
}
SQL Server table tbl_Pages:
Id int unchecked
page_title nvarchar(100) unchecked
page_description nvarchar(max) unchecked
meta_title nvarchar(255) unchecked
meta_keywords nvarchar(255) unchecked
meta_description nvarchar(1000) unchecked
active bit checked unchecked
if you dont have an ID to sent to the procedure.
you should set default value to #ID parameter in the procedure:
ALTER PROCEDURE Sp_addupdatepages (#Id INT=NULL,
#page_title NVARCHAR(100),
#page_description NVARCHAR(max),
#meta_title NVARCHAR(255),
#meta_keywords NVARCHAR(255),
#meta_description NVARCHAR(1000),
#Active BIT)
and then it wont through exception
How to return 1 if username exists and 0 in other case? Here is what I've tried.
IF EXISTS (SELECT * FROM [User] WHERE UserName = #UserName and EmailID=#EmailID)
begin
return 1;
end
else
begin
declare #CreatedOn datetime
select #CreatedOn = getdate()
insert into [User](UserName,Password,EmailID,ContactNo,CreatedOn) values(#UserName,#Password,#EmailID,#ContactNo,#CreatedOn)
CREATE PROCEDURE CheckUserExists
AS
#UserName NVARCHAR(MAX),
#Email NVARCHAR(MAX)
BEGIN
IF EXISTS (SELECT 1 FROM [User] WHERE UserName = #UserName OR EmailID=#EmailID)
BEGIN
RETURN 1
END
ELSE BEGIN
RETURN 0
END
END
Maybe you could try this query:
Select count(*) from [user] where UserName = #UserName and EmailID=#EmailID
and if user name exists count(*) will be larger then 0
I see a bigger problem here. you stated you want to know if the user exists or not. but the query shows a side affect, that if the user doesn't exist you will create the user in the same call. these should be separate sqlcommands. one for the query/reading and another for the command/insert.
to determine if the user exists a simple select 1 from [users] where [username] = #user should suffice. if any (1?) rows are returned the user exists, otherwise the user does not exist.
you can then issue the command to create the user
insert into [User](UserName,Password,EmailID,ContactNo,CreatedOn) values(#UserName,#Password,#EmailID,#ContactNo,getdate())
Try this:
IF EXISTS (SELECT 1 FROM [User] WHERE UserName = #UserName and EmailID=#EmailID)
begin
return 1;
end
else
return 0;
/* Execute the SP As*/
DECLARE #return_value int
EXEC #return_value = [dbo].[CheckUserExists]
Select #return_value
/*STORED PROCEDURE*/
CREATE PROCEDURE CheckUserExists
AS
#UserName NVARCHAR(MAX),
#Password NVARCHAR(MAX)
#EmailID NVARCHAR(MAX),
#ContactNo NVARCHAR(MAX)
BEGIN
IF EXISTS (SELECT 1 FROM [User] WHERE UserName = #UserName and EmailID=#EmailID)
BEGIN
RETURN 1;
END
ELSE
BEGIN
DECLARE #CreatedOn DATETIME
SELECT #CreatedOn = GETDATE()
INSERT INTO [User](UserName,Password,EmailID,ContactNo,CreatedOn)
VALUES(#UserName,#Password,#EmailID,#ContactNo,#CreatedOn)
RETURN 0;
END
CREATE PROCEDURE CheckUserExists
AS
#UserName NVARCHAR(MAX),
#Email NVARCHAR(MAX)
BEGIN
declare #usercount int
Select #usercount = count(UserName) from [user] where UserName = #UserName and EmailID=#EmailID
IF (#usercount = 1)
BEGIN
RETURN 1
END
ELSE BEGIN
RETURN 0
END
END