I haven't been able to find this explicitly stated anywhere yet, but a bunch of examples I've found online follow what I've been doing.
I have a C# class which uses ODP.net to connect to an Oracle DB and run a procedure that's in a package.
My package has stored procedures which take a ref cursor output parameter. All the procedure does is open up the cursor for a particular select statement.
If I execute this procedure directly on the oracle db, then eventually I'll hit a max number of open cursors error.
So I was wondering if ODP.net does indeed close this cursor that was opened in my procedure?
I'm using the OracleDataApaper.Fill(DataSet) method.
eg.
DataSet ds = new DataSet();
OracleConnection conn = new OracleConnection(this.connStr);
OracleCommand com = new OracleCommand("MYPKG.MYQUERY", conn);
OracleDataAdapter adapter = new OracleDataAdapter(com);
conn.Open();
com.Parameters.Add("searchParam", OracleDbType.Varchar2).Value = "myName";
com.Parameters.Add("outCursor", OracleDbType.RefCursor, ParameterDirection.Output);
com.CommandType = CommandType.StoredProcedure;
adapter.Fill(ds);
conn.Close();
PROCEDURE GETALLEMAILS(searchParamIN VARCHAR2, outCursor OUT sys_refcursor) AS
BEGIN
open outCursor
select
EAEMAL as Email
from
EmailTable
where
EmailName = searchParam;
END GETALLEMAILS;
I'm just afraid of leaving open cursors behind on the DB is all. If anyone can provide links to official documentation, that'd be great!
Updates:
Thanks for the input. I was calling
com.Dispose();
conn.Close();
conn.Dispose();
but left them out of my example.
I found this forum post, which states that the OracleDataAdapter.Fill(Dataset) method does release the ref cursor after the Fill() method has been executed.
http://www.frontoracle.com/oracle-archive/140/386140-close-ref-cursor.html
I wish the Oracle documentation was more explicit in describing this process though.
Best AnswerRefCursor does not need to explicitly closed.
If you open such a cursor, it will stay open until you CLOSE it explicitly or you disconnect your Oracle session.
After all rows have been retrieved from the result set that is associated with a cursor, the cursor must be closed.
Not closing a cursor will keep locks active that it holds on the rows where it is positioned.
ODP.NET requires you to clean up things. So you:
I.o.w.: clean up what you create.
It can be the OracleDataAdapter already does this for you, but that's unclear (and the odp.net docs don't say this, so you've to check the (unreadable) code with reflector to make sure. Though rule of thumb with odp.net: to avoid memory leaks, always call dispose, on everything in the order: parameter, cursor, command, transaction, connection.
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With