Reputation: 2295
I'm working on a web form that validates data that the user uploads in the form of an Excel file. The code iterates through each row in the spreadsheet and checks against various rules, one of which is that the reference must be a unique value. I have a stored procedure that takes the userID
and referenceNum
as parameters:
BEGIN
SET NOCOUNT ON;
DECLARE @Status AS BIT
IF EXISTS (SELECT [TransactionMstID]
FROM [dbo].[tbl_TransactionMst]
WHERE [TransactionRef] = @DocumentNumber
AND [SupplierID] = @SupplierID)
BEGIN
SET @Status = 0
END
ELSE
BEGIN
SET @Status = 1
END
SELECT @Status AS [Status]
END
When I try different scenarios in SQL Server Management Studio (SSMS), I get the desired outputs e.g. a "0" when the reference exists and a "1" when it doesn't.
The problem arises in my C# code, it executes the stored procedure, but in my testing I get the same result irrespective of whether the data exists or not.
Here's the core of the C#:
bool returnValue = true;
if (Docnumber != null)
{
SqlConnection con = new SqlConnection(GlobalSettings.connection);
con.Open();
SqlCommand Cmd = new SqlCommand("p_ValRefNumber", con);
Cmd.CommandType = System.Data.CommandType.StoredProcedure;
Cmd.Parameters.AddWithValue("@DocumentNumber", Docnumber);
Cmd.Parameters.AddWithValue("@SupplierID", SupplierID);
Cmd.ExecuteNonQuery();
SqlDataReader dr = Cmd.ExecuteReader();
while (dr.Read())
{
bool Status = convertor.ConvertToBool(dr["Status"]);
string test = dr["Status"].ToString();
int testint = convertor.ConvertToInt(dr["Status"].ToString());
if (Status == false)
{
//throw new System.Exception(CEObj.GetErrorDesc(101));
returnValue = false;
}
}
dr.Close();
con.Close();
}
return returnValue;
}
No matter what the value of docnumber
is in testing, it always shows as True
. I've added a breakpoint so that I can check each time and then test in SSMS and I get conflicting results.
Is my logic wrong? Does Visual Studio treat the values differently? How is the result not consistent when converting it to a string
- at the very least? It always seems to read a value of "1" in VS but varies in SSMS
Edit: here's my converter method's code:
public static bool ConvertToBool(object value)
{
bool result = false;
if (value != null)
{
bool.TryParse(value.ToString(), out result);
}
return result;
}
Upvotes: 1
Views: 172
Reputation: 2197
bool.TryParse
isn't doing what the convertor (sic) code thinks it does.
bool.TryParse
returns true if the value parameter equals bool.TrueString
, which is the literal string "True". It returns false for any other value, which means it returns false for both 0 and 1.
Also, T-SQL bit values are numbers. The converter code isn't really necessary - just convert the return value to an Int32 and do a comparison.
using (var con = new SqlConnection(GlobalSettings.connection))
{
con.Open();
using (var cmd = new SqlCommand() { Connection = con, CommandType = CommandType.StoredProcedure, CommandText = "p_ValRefNumber" })
{
/* Assuming both parameters are integers.
Change SqlDbType if necessary. */
cmd.Parameters.Add(new SqlParameter() { ParameterName = "@DocumentNumber", SqlDbType = SqlDbType.Int, Value = Docnumber });
cmd.Parameters.Add(new SqlParameter() { ParameterName = "@SupplierID", SqlDbType = SqlDbType.Int, Value = SupplierID });
using (var reader = cmd.ExecuteReader(CommandBehavior.CloseConnection))
{
return dr.Read() && (Convert.ToInt32(dr["Status"]) == 1)
}
}
}
Upvotes: 2