My stored procedure:
PROCEDURE [dbo].[addMasterTransaksi]
#kodeSuplier varchar(10),
#Total money,
#kodeUser varchar(10),
#isLunas varchar (2),
#Dp money,
#kodeTrans varchar(10) output
AS
BEGIN
Declare #KdTrans as varchar(10);
Declare #Kode as int;
Declare #thisYear as varchar(10);
select #thisyear = RIGHT(YEAR(getDate()),2)
SELECT TOP(1) #KdTrans = SUBSTRING(kodeTransaksi,5,6) FROM TblMasterPembelian WHERE YEAR(Tanggal) = YEAR(getDate()) order by kodeTransaksi desc;
--print #KdTrans
IF #KdTrans IS Null
SET #KdTrans = 'TB'+ #thisYear +'000001'
else
begin
select #Kode = convert(int,#KdTrans);
select #Kode = #Kode + 1;
select #KdTrans = convert(int,#Kode);
select #KdTrans = '00000' + #KdTrans;
select #KdTrans = right(#KdTrans,6)
select #KdTrans ='TB' + #thisYear + #KdTrans
end
SET NOCOUNT ON;
--ke Master Pembelian
INSERT INTO TblMasterPembelian(kodeTransaksi,Tanggal,Total,kodeSuplier,kodeUser,isLunas,DP)
VALUES (#KdTrans,getDate(),#Total,#kodeSuplier,#kodeUser,#isLunas,#Dp)
set #kodeTrans =#KdTrans
--print #kodeTrans
return #kodetrans
END
VB.NET code:
Public Function addMasterPembelianny(ByVal kodesup As String, ByVal total As Long, ByVal kodeUser As String, ByVal isLunas As String, ByVal dp As Long)
Dim kodeTransaksi As String
modKoneksi.bukaKoneksi()
command.Connection = modKoneksi.koneksidb
command.CommandType = CommandType.StoredProcedure
command.CommandText = "addMasterTransaksi"
command.Parameters.Add("#kodeSuplier", OleDbType.VarChar, 10, ParameterDirection.Input).Value = kodesup
command.Parameters.Add("#Total", OleDbType.BigInt, 10, ParameterDirection.Input).Value = total
command.Parameters.Add("#kodeUser", OleDbType.VarChar, 10, ParameterDirection.Input).Value = kodeUser
command.Parameters.Add("#isLunas", OleDbType.VarChar, 2, ParameterDirection.Input).Value = isLunas
command.Parameters.Add("#Dp", OleDbType.BigInt, 10, ParameterDirection.Input).Value = dp
command.Parameters.Add("#kodeTrans", OleDbType.Char, 10)
command.Parameters("#kodeTrans").Direction = ParameterDirection.Output
command.ExecuteReader()
kodeTransaksi = command.Parameters("#kodeTrans").Value
modKoneksi.tutupKoneksi()
Return kodeTransaksi
End Function
I have problem when I want to retrieve parameter from a stored procedure..
When I run that code, there appear an error like this message ..
Conversion failed when converting the varchar value 'TB13000005' to data type int.
Why they said that failed converting to data type int??
What's wrong with my code..?
master help me please..
I believe it is this line in your stored procedure which is causing the error:
return #kodetrans
Stored procedures can only return integers as part of the RETURN statement so the line fails (as #kodetrans is a VARCHAR). You can just remove that line completely...For output parameters, what you have done here:
set #kodeTrans =#KdTrans
In the stored proc is fine and should be sufficient/OK.
Related
I have stored procedure which seems to be working fine when executing directly from management studio, but when it comes o vb.net code i always get 0. Can anyone look at that and tell me what is missing here. I read documentation and seems that should work as expected however it is not somehow.
stored procedure:
ALTER PROCEDURE [dbo].[IsPhraseConnectedAlready]
#PhraseId INT,
#KatSubkatId INT,
#WordId INT,
#SubsubkatId INT = NULL
AS
BEGIN
SET NOCOUNT ON;
DECLARE #temp_T_Html_Word_Categories TABLE(Id INT)
DECLARE #temp_T_Html_WordCat_Phrase TABLE(FK_Phrase_ID INT)
DECLARE #temp_T_Html_Phrase TABLE(Id INT, [Name] varchar(max))
IF #SubsubkatId IS NULL
BEGIN
INSERT INTO #temp_T_Html_Word_Categories(Id) SELECT Id FROM T_Html_Word_Categories WHERE FK_KatSubkat_ID = #KatSubkatId And FK_Word_ID = #WordId And FK_Subsubkat_ID IS NULL;
END
ELSE
BEGIN
INSERT INTO #temp_T_Html_Word_Categories(Id) SELECT Id FROM T_Html_Word_Categories WHERE FK_KatSubkat_ID = #KatSubkatId And FK_Word_ID = #WordId And FK_Subsubkat_ID = #SubsubkatId;
END
Declare #Id int;
Select #Id = Id From #temp_T_Html_Word_Categories;
INSERT INTO #temp_T_Html_WordCat_Phrase(FK_Phrase_ID) SELECT FK_Phrase_ID FROM T_Html_WordCat_Phrase WHERE FK_Word_Categorie_ID = #Id;
IF (##ROWCOUNT > 0)
BEGIN
Declare #FK_Phrase_ID int;
--it makes no difference what you SELECT in an EXISTS sub-query as it is just syntactical sugar. (ie Nothing is actually selected.) SELECT * or SELECT 1 ...
WHILE EXISTS(SELECT * FROM #temp_T_Html_WordCat_Phrase)
BEGIN
Select Top 1 #FK_Phrase_ID = FK_Phrase_ID From #temp_T_Html_WordCat_Phrase;
INSERT INTO #temp_T_Html_Phrase(Id, [Name]) SELECT Id, [Name] FROM T_Html_Phrase WHERE Id = #FK_Phrase_ID;
IF (#PhraseId = #FK_Phrase_ID)
RETURN 1
Delete #temp_T_Html_WordCat_Phrase Where FK_Phrase_ID = #FK_Phrase_ID;
END;
END
ELSE
BEGIN
Delete #temp_T_Html_Word_Categories;
RETURN 0
END
RETURN 0
END
This is my visual basic.net code below:
Public Function IsPhraseConnectedAlready(phraseId As Integer, katsubkatid As Integer, wordid As Integer, subsubkatid As Integer?) As Integer
Using con As New SqlConnection(_strcon)
Using cmd As New SqlCommand("IsPhraseConnectedAlready", con)
cmd.CommandType = CommandType.StoredProcedure
cmd.Parameters.AddWithValue("#PhraseId", phraseId)
cmd.Parameters.AddWithValue("#KatSubkatId", katsubkatid)
cmd.Parameters.AddWithValue("#WordId", wordid)
If subsubkatid.HasValue Then 'check whether nullable field contain value
cmd.Parameters.AddWithValue("#SubsubkatId", subsubkatid.Value)
Else
cmd.Parameters.AddWithValue("#SubsubkatId", DBNull.Value)
End If
con.Open()
Dim i = CType(cmd.ExecuteScalar(), Integer)
If i = 1 Then
Return True
ElseIf i = 0 Then
Return False
End If
End Using
End Using
End Function
Executed from ssms directly shows it reaches RETURN 1, however with same values passed from vb.net i am getting 0:
in vb.net working with same values:
seems the resolution was to do like this:
instead of this:
RETURN 1 or RETURN 0
make it as:
SELECT 1 or SELECT 0
however to break execution when it reaches first select to add additional return after each SELECT.
Does anyone sees any issues with that? To me it works and wonder why just RETURN was not from vb.net
cmd.ExecuteScalar() will execute the query, and return the first column of the first row in the result set returned by the query. However, you're not returning a column/row, you're just returning a value.
So, either convert RETURN 1 to SELECT 1 or else declare a return parameter in your VB.Net code like so:
...
Dim returnParameter As SqlParameter = cmd.Parameters.Add("#ReturnVal", SqlDbType.Int)
returnParameter.Direction = ParameterDirection.ReturnValue
con.Open()
cmd.ExecuteNonQuery()
Dim i = CType(returnParameter.Value, Integer)
...
I've been stumped with the following error for the past hour:
"Procedure or function 'write_call' expects parameter '#Date', which was not supplied."
The #date parameter is a smalldatetime. I am trying to pass the value #1/27/2009 04:32:00 PM#
I am using SQLExpress 2014.
The same stored proc has been in production on SQLExpress 2008
T-SQL Stored Proc:
ALTER proc [dbo].[write_call]
(
#Date smalldatetime, #Duration smallint, #Ring tinyint, #Extension smallint = null, #Number varchar(20) = null, #LineID smallint,
#AccountID smallint = null, #AccountName varchar(30) = null, #UnitID smallint = null, #UnitName varchar(30) = null, #AreaName varchar(100) = null, #CallType char(1) = null,
#CallCode varchar(6) = null, #Rate numeric(5,2) = 0.0, #Cost numeric(12,2) = 0.0, #TAC varchar(10) = null
)
as
declare #id int=0, #old_acctid int=0 --, #old_rate numeric(5,2)=0.0, #old_cost numeric(12,2)=0.0
select #id=o.ID,#old_acctid=o.AccountID from OutboundCalls o where o.Date=#Date and o.Duration=#Duration and o.Number=#Number
if #id=0
begin
insert into _OutboundCalls (Date, Duration, Ring, Extension, Number, LineID, AccountID, AccountName, UnitID, UnitName, AreaName, CallType,CallCode, Rate, Cost, TAC,redirected,contactid,CompanyID,CompanyName)
values (#Date, #Duration, #Ring, #Extension, #Number, #LineID, #AccountID, #AccountName, #UnitID, #UnitName, #AreaName, #CallType, #CallCode, #Rate, #Cost, #TAC,1,0,1,'PricewaterhouseCoopers')
end
else if #id>0 and #old_acctid<>#AccountID
update OutboundCalls set AccountID=#AccountID, UnitID=#UnitID,AccountName=#AccountName,UnitName=#UnitName
where OutboundCalls.ID=#id
VB.NET 2015:
Private Sub write_call(c As CallInfo)
Using cnn = New SqlClient.SqlConnection(connString)
Using cmd = New SqlClient.SqlCommand("write_call", cnn)
cmd.Parameters.AddWithValue("#Date", c.dt)
cmd.Parameters.AddWithValue("#Duration", c.secDurn)
cmd.Parameters.AddWithValue("#Ring", 0)
cmd.Parameters.AddWithValue("#Extension", c.src)
cmd.Parameters.AddWithValue("#Number", c.dst)
cmd.Parameters.AddWithValue("#LineID", c.lineId)
cmd.Parameters.AddWithValue("#AccountID", c.account_id)
cmd.Parameters.AddWithValue("#AccountName", c.account_name)
cmd.Parameters.AddWithValue("#UnitID", c.unit_id)
cmd.Parameters.AddWithValue("#UnitName", c.unit_name)
cmd.Parameters.AddWithValue("#AreaName", c.area?.Name)
cmd.Parameters.AddWithValue("#CallType", c.dst_type)
cmd.Parameters.AddWithValue("#CallCode", c.callcode)
cmd.Parameters.AddWithValue("#Rate", c.rate?.rate)
cmd.Parameters.AddWithValue("#Cost", c.Cost)
cmd.Parameters.AddWithValue("#TAC", c._oC)
cnn.Open()
Try
cmd.ExecuteNonQuery()
Catch ex As Exception
Stop
End Try
End Using
End Using
End Sub
It seems that your code misses to set the CommandType property. This property defaults to CommandType.Text and it is appropriate when you pass a sql string as the CommandText.
If you pass the name of a stored procedure you need to set
cmd.CommandType = CommandType.StoredProcedure
without this setting the behavior of the SqlCommand is unpredictable.
I use this stored procedure for get the number of records
ALTER PROCEDURE [dbo].[Asbabbazi_A]
#count int output
AS
BEGIN
if(#count=0)
set #count =( select count(*) from dbo.Table_asbabbazi where (active= 0))
end
now I want use the #count in my project.I wrote this codes for use the #count in method.
SqlConnection con = new SqlConnection(constr);
cmd.Connection = con;
con.Open();
DataAdapter.SelectCommand = cmd;
DataSet ds = new DataSet("haftehbazardb");
SqlCommandBuilder bldr = new SqlCommandBuilder(DataAdapter);
SqlParameter returnParameter = cmd.Parameters.Add("count", SqlDbType.Int);
returnParameter.Direction = ParameterDirection.ReturnValue;
cmd.ExecuteNonQuery();
DataAdapter.Fill(ds, Table_asbabbazi);
countrecords = (int)returnParameter.Value;
this codes have no error but when i use the (countrecords ) in my project the value of (countrecords ) is zero that is not right .
Please help
If you want to get the value as the output of the stored procedure, you will need to return it.
ALTER PROCEDURE [dbo].[Asbabbazi_A]
#count int output
AS
BEGIN
if(#count=0)
set #count =( select count(*) from dbo.Table_asbabbazi where (active= 0))
return #count
end
You are confusing output parameters with a return value.
Return value is generally used to indicate the status of your procedure, it will be 0 if not specified, e.g.
CREATE PROCEDURE dbo.TestProc #Out INT OUTPUT
AS
BEGIN
BEGIN TRY
SET #Out = 1 / 0;
RETURN 0;
END TRY
BEGIN CATCH
SET #Out = 0;
RETURN 1;
END CATCH
END
Then calling this with T-SQL;
DECLARE #out INT, #return INT;
EXECUTE #Return = dbo.TestProc #out OUT;
SELECT [Return] = #return, [out] = #out;
Will give:
Return | out
-------+-----
1 | 0
Since 0 is the default return value, this is why you are getting 0 out from returnParameter, you need to use ParameterDirection.Output:
SqlParameter returnParameter = cmd.Parameters.Add("count", SqlDbType.Int);
returnParameter.Direction = ParameterDirection.Output;
I have an Stored Procedure like below..
CREATE PROCEDURE [dbo].[spMYSPDetails]
#Id VarChar(6),
#Name VarChar(50),
#Limit Money,
#Status VarChar(1),
#Accounts As SmallInt
AS BEGIN
IF(LEN(ISNULL(#strDebtorId, '')) = 0) BEGIN
WHILE 0 = 0 BEGIN
SET #Id = '9' + dbo.fnGenerateRandomCode(5, '0123456789')
IF NOT EXISTS (SELECT 1 FROM mytbl WITH (NOLOCK) WHERE s_Id = #Id) BEGIN
INSERT INTO Mytbl
(D_Id,
D_Name,
D_Limit,
D_Status,
D_Accounts,
D_dtmStamp,
D_Balance)
VALUES
(#Id,
#Name,
#Limit,
#Status,
#Accounts,
GETDATE(),
#Limit)
BREAK
END
I have c# sharp code to call this SP like this...
try
{
string Id = "";
if (hdDId.Value.ToString() != "")
{
Id = hdDId.Value.ToString();
}
objDB.blnParamClear();
objDB.blnParamAdd(ParameterDirection.Input, "#Id", SqlDbType.VarChar, 6, Id.ToString());
objDB.blnParamAdd(ParameterDirection.Input, "#Name", SqlDbType.VarChar, 50, txtName.Value.ToString());
objDB.blnParamAdd(ParameterDirection.Input, "#Limit", SqlDbType.Money, 8, decimal.Parse(txtLimit.Value.ToString()));
objDB.blnParamAdd(ParameterDirection.Input, "#Status", SqlDbType.VarChar, 1, cboStatus.Value);
objDB.blnParamAdd(ParameterDirection.Input, "#intMaxAccounts", SqlDbType.SmallInt, 4, txtAccnts.Value.ToString());
blnResult = (objDB.lngExecuteSP("spMYSPDetails") == 0);
}
Now I want to catch that auto generated(random) ID in C# for my reference. I tried but am unable to Catch.. Is there any way to catch the same id that is generated by SP in SQL.Suggest me something...
Use your #ID as output variable.
#Id VarChar(6) output
Then set your C# parameter
SqlParameter paramOutput = new SqlParameter("#Output", SqlDbType.nVarChar);
paramOutput.Direction = ParameterDirection.Output;
Stored procedures can have return values and output parameters in addition to input parameters.
Use an Output Parameter.
Change ParameterDirection.Input to ParameterDirection.Output when defining a param "#Id".
PS. What are you passing right now to the sproc (Id.ToString()) if the id is generated in the DB? Why aren't you just using autoincrement column?
I have a vb.net application that inserts records into a db table using a stored procedure that is supposed to return a value. This stored procedure was setup by someone else and initially was linked to a webservice through which my application made the insert and got the return value in the returned xml. I now have access to the db table and not sure how to receive the return value in my vb.net method.
SQl stored procedure snippet;
#urlname varchar(500),
#siteid varchar(16),
#origin varchar(50),
#queryid varchar(25)
AS
SET NOCOUNT ON;
declare #cnt int
declare #serverip varchar(16)
declare #mincnt int
declare #siteservercnt int
select #cnt=COUNT(*) from sites
where urlname=#urlname
if #cnt = 0
begin
insert into sites (urlname,siteid,exported,origin,queryid)
values(#urlname,#siteid,1,#origin,#queryid)
select #siteservercnt = COUNT(*) from siteserverip where siteid=#siteid
if #siteservercnt=0
begin
select top 1 #mincnt=COUNT(*),#serverip=serverip from siteserverip
group by serverip
order by COUNT(*)
select top 1 #mincnt=sitecount,
#serverip=serverip from serveripcounts
order by sitecount
insert into siteserverip values(#siteid,#serverip)
update serveripcounts set sitecount=sitecount+1
where serverip=#serverip
end
end
SELECT siteid from sites
where urlname=#urlname
return
and my vb.net code to do the insert
CommandObj.CommandText = "Getsite"
CommandObj.CommandTimeout = 90
Dim newUrl As String = String.Empty
CommandObj.Parameters.Clear()
Dim m_param As SqlParameter
m_param = CommandObj.Parameters.Add("#urlname", SqlDbType.VarChar, 500)
m_param.Direction = ParameterDirection.Input
m_param.Value = name
m_param = CommandObj.Parameters.Add("#siteid", SqlDbType.VarChar, 16)
m_param.Direction = ParameterDirection.Input
m_param.Value = siteid
m_param = CommandObj.Parameters.Add("#origin", SqlDbType.VarChar, 50)
m_param.Direction = ParameterDirection.Input
m_param.Value = method
m_param = CommandObj.Parameters.Add("#queryId", SqlDbType.VarChar, 25)
m_param.Direction = ParameterDirection.Input
m_param.Value = forumID
Dim recordsAffected As Integer = CommandObj.ExecuteNonQuery
You can use ExecuteScalar to get that value. ExecuteNonQuery returns number of rows affected while you want to get the value generated by last select. You could use ExecuteReader as well but that is useful when your SP might be returning more columns and/or more rows.
'Populate first column and first row value in siteID
Dim siteID As Integer = CommandObj.ExecuteScalar