ASP page not displaying Stored Procedure OUTPUT - sql

I have an ASP page calling a stored procedure with returned values AND OUTPUT parameters.
The output parameters aren't displaying and I'm not understanding why:
<%
dim Objrs, cmd
set Objrs = Server.CreateObject("ADODB.RecordSet")
set cmd = Server.CreateObject("ADODB.Command")
set conn = Server.CreateObject("ADODB.Connection")
conn.Open strConnect
set cmd.ActiveConnection = conn
cmd.CommandText="MKTG_Current"
cmd.CommandType=adCmdStoredProc
cmd.Parameters.Append cmd.CreateParameter("#added", 135, 2)
cmd.Parameters.Append cmd.CreateParameter("#named", 200, 2, 50)
set Objrs = cmd.Execute
%>
</div>
<div id="recent-news-box" class="rounded-corners-top dropshadow">
<h3 class="border-dashed-b">Updated on: <%=Objrs.state%></h3>
<div>
<%
While Not Objrs.EOF
Response.Write Objrs("Subject")
Objrs.MoveNext
Wend
name_of_table = cmd.Parameters("#named").value
added = cmd.Parameters("#added").value
set cmd = nothing
set Objrs = nothing
conn.close
set conn = nothing
Response.Write name_of_table
Response.Write added
%>
</div>
</div>
</div>
I've tried changing the position of the output items to no avail.

There is some clunkiness because of the way ADO returns command results to both a recordset and as output paramaters.
They are available after the returned recordset is closed, so this order should work:
set Objrs = nothing
name_of_table = cmd.Parameters("#named").value
added = cmd.Parameters("#added").value
set cmd = nothing
conn.close
set conn = nothing
Response.Write name_of_table
Response.Write added
An alternative is to leave the code as it is add switch to a client side cursor with:
conn.Open strConnect
conn.CursorLocation = 3 '//aduseclient
set cmd.ActiveConnection = conn
(Also check that your use of adCmdStoredProc should not be replaced with its numeric value if your not linked to a typelib)

Related

ASP SQL Server Connection

<%
DIM objConn
Set objConn = Server.CreateObject("ADODB.Connection")
objConn.ConnectionString = "Data Source=123.123.12.123,1234;Database=DatabaseName;User Id=Usernm;Password=abcd1234;"
objConn.Open
DIM mySQL
mySQL = "SELECT * FROM [Users] WHERE [User ID]='1'"
DIM objRS
Set objRS = Server.CreateObject("ADODB.Recordset")
objRS.open(mySQL, objConn)
Response.Write objRS("FullName")
objRS.Close
Set objRS = Nothing
objConn.Close
Set objConn = Nothing
%>
I want to connect to a SQL Server Database, read the data and close the connection. I have studied the examples and came up with this. But its not working. Please guide me. Where am I going wrong?
Some answers have suggested wrapping logic into functions there is no need for this.
It's just a lot of fluff that isn't needed, just use the ADODB.Command object. There are hundreds of ways to approach this but a method I have found to work time and again is let the ADODB.Command object do the work then return your results into an Array using .GetRows() method of the ADODB.Recordset object.
That way you can close off both the ADODB.Recordset and ADODB.Command objects quickly and work just with the Array.
Dim conn, cmd, rs, sql, data, search
'Assume value to query comes from a Request Collection.
search = Request("myvalue") & ""
conn = "Data Source=123.123.12.123,1234;Database=DatabaseName;User Id=Usernm;Password=abcd1234;"
sql = "select from mytable where this = ?"
Set cmd = Server.CreateObject("ADODB.Command")
With cmd
'No need to handle connection let ADODB.Command create and destory it.
.ActiveConnection = conn
.CommandType = adCmdText
.CommandText = sql
.Parameters.Append(.CreateParameter("#myparam", adVarWChar, adParamInput, 50))
.Parameters("#myparam").Value = search
Set rs = .Execute()
If Not rs.EOF Then data = rs.GetRows()
Call rs.Close()
Set rs = Nothing
End with
Set cmd = Nothing
'ADODB.Connection is closed when ADODB.Command is destroyed.
If IsArray(data) Then
rows = UBound(data, 2)
For row = 0 To rows
'Return first column of the current row
Call Response.Write("First Column of Row " & row & " is '" & data(0, row) & "'<br />"
Next
Else
Call Response.Write("No records")
End If
Dim rs, dbConn
Function OpenDB()
Set dbConn = Server.CreateObject("ADODB.Connection")
dbConn.ConnectionTimeout = 300
dbConn.CommandTimeout = 300
dbConn.Open "Data Source=123.123.12.123,1234;Database=DatabaseName;User Id=Usernm;Password=abcd1234;"
End Function
Function CloseDB()
Set rs = Nothing
if ucase(TypeName(dbConn)) = "CONNECTION" then
dbConn.Close
Set dbConn = Nothing
end if
End Function
Function OpenRecordSet(recset, tablename)
Call OpenDB()
Set recset = Server.CreateObject("ADODB.Recordset")
recset.Open tablename, dbConn, 0, 1
End Function
Function CloseRecordSet(recset)
Set recset = Nothing
Call CloseDB()
End Function
Then use
<%
Call OpenDB()
sql = "select from mytable where this = 'that'"
Set rs = dbConn.Execute(sql)
if not rs.EOF then
' do your stuff!
end if
Call CloseDB()
%>
http://www.shiningstar.net/articles/articles/database/datafunctions.asp?ID=AW

Classic ASP - Stored Procedure Error

I've written a stored procedure ("UpdateTable") that takes one parameter and inserts a new row into a table when run.
I've got the following code in an asp page:-
dim conn
dim cmd
set conn = server.createobject("ADODB.Connection")
conn.open "Provider=SQLNCLI11;Data Source=(localdb)\Projects;Persist Security Info=False;Password=password;User ID=username;Initial Catalog=SQLLearning"
set cmd = server.createobject("ADODB.Command")
cmd.ActiveConnection = conn
cmd.CommandText = "UpdateTable"
cmd.CommandType =adCmdStoredProc
cmd.Parameters.Append cmd.CreateParameter("Text",adVarChar,adParamInput, 100)
cmd("Text") = "Jessica"
cmd.Execute
When I run this I get the following error:-
ADODB.Command error '800a0bb9'
Arguments are of the wrong type, are out of acceptable range, or are in conflict with one another.
/sp.asp, line 14
Where line 14 is the cmd.CommandType =adCmdStoredProc line. I've tried numerous things, including declaring a constant called adCmdStoredProc with the value of 4, and this still doesn't work. Can somebody please point me in the right direction?
The 'UpdateTable' code is:-
ALTER PROCEDURE UpdateTable
#Text varchar(100)
AS
BEGIN
SET NOCOUNT ON;
INSERT INTO StoredProcTest (Text)
OUTPUT inserted.ID, inserted.Text
VALUES (#Text)
END
GO
Set cmd = Server.CreateObject("ADODB.Command")
With cmd
.ActiveConnection = conn
.CommandType = adCmdStoredProc
.CommandText = "UpdateTable"
.Parameters.Append .CreateParameter("#Text",adVarChar,adParamInput, 100)
.Parameters("#Text") = "Jessica"
set rs = .Execute
End With
set cmd = nothing
You should then be able to get the result doing something similar to;
if not rs.eof then
response.write rs("ID")
end if

Using Stored Procedure in Classical ASP .. execute and get results

I tried to solve this all day long but it doesn't seem to work for me. I would like to execute a command and get the result back to a recordset.
The problem is one of two things: either I'm getting an empty response or there is a problem with my code. I know for sure that this command should fetch few lines from the DB. I added response.write inside the loop, but they are never printed.
Here is the code:
Set conn = Server.CreateObject("ADODB.Connection")
conn.open "PROVIDER=SQLOLEDB;DATA SOURCE=X;DATABASE=Y;UID=Z;PWD=W;"
Set objCommandSec = CreateObject("ADODB.Command")
With objCommandSec
Set .ActiveConnection = Conn
.CommandType = 4
.CommandText = "usp_Targets_DataEntry_Display"
.Parameters.Append .CreateParameter("#userinumber ", 200, 1, 10, inumber)
.Parameters.Append .CreateParameter("#group ", 200, 1, 50, "ISM")
.Parameters.Append .CreateParameter("#groupvalue", 200, 1, 50, ismID)
.Parameters.Append .CreateParameter("#targettypeparam ", 200, 1, 50, targetType)
End With
set rs = Server.CreateObject("ADODB.RecordSet")
rs = objCommandSec.Execute
while not rs.eof
response.write (1)
response.write (rs("1_Q1"))
rs.MoveNext
wend
response.write (2)
EDITED
After revising the code, following #Joel Coehoorn answer, the solution is:
set rs = Server.CreateObject("ADODB.RecordSet")
rs.oppen objCommandSec
instead of...
set rs = Server.CreateObject("ADODB.RecordSet")
rs = objCommandSec.Execute
Couple of tips after working with asp-classic for years
There is no need to create a ADODB.Connection you can pass a connection string direct to .ActiveConnection property of the ADODB.Command object. This has two benefits, you don't have instantiate and open another object and because the context is tied to the ADODB.Command it will be released with Set objCommandSec = Nothing.
A common reason for .Execute returning a closed recordset is due to SET NOCOUNT ON not being set in your SQL Stored Procedure, as an INSERT or UPDATE will generate a records affected count and closed recordset. Setting SET NOCOUNT ON will stop these outputs and only your expected recordset will be returned.
Using ADODB.Recordset to cycle through your data is overkill unless you need to move backwards and forwards through and support some of the more lesser used methods that are not needed for standard functions like displaying a recordset to screen. Instead try using an Array.
Const adParamInput = 1
Const adVarChar = 200
Dim conn_string, row, rows, ary_data
conn_string = "PROVIDER=SQLOLEDB;DATA SOURCE=X;DATABASE=Y;UID=Z;PWD=W;"
Set objCommandSec = CreateObject("ADODB.Command")
With objCommandSec
.ActiveConnection = conn_string
.CommandType = 4
.CommandText = "usp_Targets_DataEntry_Display"
.Parameters.Append .CreateParameter("#userinumber", adVarChar, adParamInput, 10, inumber)
.Parameters.Append .CreateParameter("#group", adVarChar, adParamInput, 50, "ISM")
.Parameters.Append .CreateParameter("#groupvalue", adVarChar, adParamInput, 50, ismID)
.Parameters.Append .CreateParameter("#targettypeparam", adVarChar, adParamInput, 50, targetType)
Set rs = .Execute()
If Not rs.EOF Then ary_data = rs.GetRows()
Call rs.Close()
Set rs = Nothing
End With
Set objCommandSec = Nothing
'Command and Recordset no longer needed as ary_data contains our data.
If IsArray(ary_data) Then
' Iterate through array
rows = UBound(ary_data, 2)
For row = 0 to rows
' Return our row data
' Row N column 2 (index starts from 0)
Call Response.Write(ary_data(1, row) & "")
Next
Else
' Nothing returned
Call Response.Write("No data returned")
End If
Looked at this for a few minutes, and it's been a long time since I've worked with classic asp, but I did see three things to look at:
Do you need to Open the connection before calling objCommandSec.Execute?
Can you try writing out a string literal inside the loop, that does not depend at all on the recordset... only that you are in fact looping through the code, so see if records are coming back to the recordset.
Have you checked the html source, to see if perhaps malformed html is hiding your results? I remember this happening a few times with tables in classic asp loops, where data would be hidden somehow between two rows, or a closing table tag in the wrong place would end the table, and later rows would not be visible.
Although this might not answer OPs question directly, it might help someone else looking for a solution.
recently I had a maintenance job that required me to modify something in a running ASP classic code (which I haven't write in ages). Procedure calls were written the same way as OP did and that wasn't how I did it in the past.
Here is the syntax I used in the past and I think it is a little more clean than other solutions provided here.
The following code shows how to read an output parameter, pass parameters to stored procedure, pass null value to parameter, read record count, and iterate in RecordSet.
dim conn, cmd, rs
set conn = Server.CreateObject("ADODB.Connection")
conn.Open "Driver={SQL Server};Server=servername;Uid=username;Pwd=password;Database=dbname;"
set cmd = Server.CreateObject("ADODB.Command")
cmd.ActiveConnection = conn
cmd.CommandType = adCmdStoredProc
cmd.CommandText = "procedurename"
cmd.Parameters.Refresh
cmd.Parameters("#nullparam") = null
cmd.Parameters("#strparam") = "1"
cmd.Parameters("#numparam") = 100
set rs = Server.CreateObject ("ADODB.RecordSet")
rs.CursorLocation = adUseClient ' to read recordcount'
rs.open cmd, , adOpenStatic, adLockReadOnly
Response.Write "Return Value: " & cmd.Parameters("#RETURN_VALUE") & "<br />"
Response.Write "Record count: " & rs.RecordCount & "<br />"
while not rs.EOF
' or do whatever you like with data'
Response.Write rs("colname") & "<br>"
rs.MoveNext
wend

Connecting to sql server 2008 using vb

Function DBConnect()
Dim vConnString, wfConnection, objConn
set objConn = Server.CreateObject("ADODB.Connection")
objConn.Open Application("DB_CONNECT")
set DBConnect = objConn
exit function
Response.Write("connected to Server 2008")
End Function
Function GetValue()
Dim objCmd, objRS
Set objCMD = Server.CreateObject("ADODB.Command")
Set objRs = Server.CreateObject("ADODB.Recordset")
With (objCMD)
.ActiveConnection = DBConnect()
.CommandType = adCmdStoredProc
.CommandText = "select * from Acc.dbo.table"
set ObjRS = .Execute()
End With
if err.number = 0 then
if not objRs.EOF then
arrData = objRs.GetRows
vDesc = arrData(5,0)
else
vDesc = vValue
end if
GetDescFromCode = True
end if
Response is Coming as
connected to Server 2008
While debuging, i got that its not going inside objRs.EOF if loop...any idea whats wrong
In DBConnect, check the status of objConn to make sure it's really being opened.
In DBConnect, you have exit function before response.write.
In GetValue, check value of err.number.

How to call a stored procedure using asp classic?

I am using sql server and asp classic, and am currently calling queries like this:
newHireSQL = "select * from NewHire where Archived = 0 order by HireID desc"
Set rsGetHireID = Server.CreateObject("ADODB.Recordset")
rsGetHireID.Open newHireSQL,ConnectionString,adOpenStatic
NumOfHireID = rsGetHireID.RecordCount
But instead of having the query statement here, I want to call a stored procedure called dbo.sp_selectNewHireSQL. How can I do that?
Thanks
EDIT:
I tried this
Dim Conn
SET Conn = Server.CreateObject("ADODB.Connection")
SET rsGetHireID = Server.CreateObject("ADODB.RecordSet")
Conn.Open ConnectionString
set rsGetHireID=Conn.Execute("Exec sp_selectNewHireSQL")
NumOfHireID = rsGetHireID.RecordCount
Response.Write (NumOfHireID)
But I am getting a -1 value for the record count.
It's just use exec or execute statement:
Set Conn = Server.CreateObject("ADODB.Connection")
Conn.Open ConnectionString
Conn.Execute "Exec sp_selectNewHireSQL"
Reference: http://msdn.microsoft.com/en-us/library/ms188332(v=sql.90).aspx
To have the RecordCount working you need to use proper cursor:
Set rsGetHireID = Server.CreateObject("ADODB.RecordSet")
Conn.Open ConnectionString
rsGetHireID.CursorLocation = 3 'adUseClient
rsGetHireID.Open "Exec sp_selectNewHireSQL", Conn
NumOfHireID = rsGetHireID.RecordCount
Instead of using ADODB.Connection, try using ADODB.Command instead like this:
Set objCommand = Server.CreateObject("ADODB.Command")
objCommand.ActiveConnection = ConnectionString
objCommand.CommandText = "dbo.sp_selectNewHireSQL"
objCommand.CommandType = adCmdStoredProc ' you have to include adovbs.inc file or you can use 4
Set rsGetHireID = objCommand.Execute()
NumOfHireID = rsGetHireID.RecordCount
Response.Write (NumOfHireID)
<%
dim db_conn
db_conn = "Provider=SQLOLEDB.1;Server=server name;Database=dbname;Uid=sa; Pwd=123;"
set conn = server.createobject("adodb.connection")
set Cmd = Server.CreateObject("ADODB.Command")
'-------------------------------------------------------
conn.open (db_conn)
'-------------------------------------------------------
set rs = Server.CreateObject("ADODB.RecordSet")
sSQL = "EXEC sp_countrylist #countryname ='" & countryname & "'"
set rs = conn.execute(sSQL)
if (rs.bof and rs.eof) then
response.Write "<span class=""error"">No Record Found</span>"
response.End
end if %>