10
votes

I am supporting some classic ASP pages, one of which uses and re-uses an object conn and disposes of it either when the .asp page finishes processing or right before the page redirects to another page.

<%
dim conn
...
set conn = server.CreateObject("adodb.connection")
...
sub cleanUp()
    conn.Close
    set conn = nothing
end sub
...
sub pageRedirect(url)
    call cleanUp()
    response.Redirect url : response.End
end sub
...
' very end of file
call cleanUp()%>

I've found that if there is a redirect, I get a server error right at the line conn.Close, Microsoft VBScript runtime error '800a01a8' Object required. I figure there's no reason why that line would execute more than once but to be safe I rewrote the function

sub cleanUp()
    if(not (conn Is Nothing)) then
        conn.Close
        set conn = Nothing
    end if
end sub

But I still get that exact error, now at the line if(not (conn Is Nothing))!! I thought the purpose of Is Nothing was to do a test before using the variable name conn precisely to prevent that 'object required' error, but the test is throwing the same error.

What other test can I use to make sure conn isn't referenced if it'd already been set to Nothing?

3
Give space after if condition "if (not ("Siva Charan
Empty is for value variables, Nothing is for objects. conn is an object. And spacing doesn't matter.East of Nowhere

3 Answers

16
votes

is nothing is used to test for an object reference, if the variable does not contain such then the test is invalid & raises an error, so conn can only be tested after its been set to something.

You can;

if isobject(conn) then
   if not (conn Is Nothing) then set conn = nothing
end if
3
votes
  1. Use option explicit (each time a script runs without option explicit, a puppie dies out there), you probably would have detected the problem earlier as Nilpo mentioned.
  2. When you dim a variable that you are going to use as an object reference and test it on Nothing, make it a habbit to set it to Nothing at initialization time(*): dim myObject : Set myObject = Nothing.

(*) Not really at initialization, because the dim's are handled before a routine starts, but when you put all your dim's at the top of a routine, it will practically be the same.

-1
votes

Use the IsNothing function. You should also check that it is an object.

sub cleanUp()
    if Not IsNothing(conn) then
        if IsObject(conn) then
            conn.Close
        end if
        set conn = nothing
    end if
end sub

That being said, I would do it like this since setting a variable to nothing does no harm.

sub cleanUp()
    if IsObject(conn) then
        conn.Close
    end if
    set conn = nothing
end sub

More importantly though, your problem is that conn is not in scope for your subroutine. You should probably pass it in as a parameter.