Закрывает ли ODP.net курсор ссылки при закрытии соединения?

StackOverflow https://stackoverflow.com/questions/358135

  •  21-08-2019
  •  | 
  •  

Вопрос

Мне пока не удалось найти нигде явных указаний на это, но я нашел в Интернете множество примеров, отражающих то, что я делал.

У меня есть класс C#, который использует ODP.net для подключения к базе данных Oracle и запуска процедуры, находящейся в пакете.

В моем пакете есть хранимые процедуры, которые принимают выходной параметр курсора ref.Все, что делает процедура, — это открывает курсор для определенного оператора выбора.

Если я выполню эту процедуру непосредственно в базе данных Oracle, то в конечном итоге я получу ошибку максимального количества открытых курсоров.

Итак, мне было интересно, действительно ли ODP.net закрывает этот курсор, открытый в моей процедуре?

Я использую метод OracleDataApaper.Fill(DataSet).

например.

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;

Я просто боюсь оставить открытые курсоры в БД, вот и все.Если кто-нибудь может предоставить ссылки на официальную документацию, это было бы здорово!


Обновления:

Спасибо за вклад.я звонил

com.Dispose();
conn.Close();
conn.Dispose();

но исключил их из своего примера.

Я нашел это сообщение на форуме, в котором говорится, что метод OracleDataAdapter.Fill(Dataset) освобождает курсор ссылки после выполнения метода Fill().
http://www.frontoracle.com/oracle-archive/140/386140-close-ref-cursor.html

Однако мне бы хотелось, чтобы документация Oracle более подробно описывала этот процесс.

Это было полезно?

Решение

ODP.NET требует от вас навести порядок.Так что вы:

  • приходится удалять экземпляры OracleParameter, поскольку они содержат неуправляемые ресурсы (!), а Odp.net этого не делает.
  • приходится удалять объекты OracleCommand, поскольку они тоже содержат неуправляемые ресурсы, и закрытие соединения не закрывает их.
  • открытые курсоры не могут жить без открытого соединения, хотя в odp.net ничего не очищается после закрытия соединения (или его удаления), поэтому вам придется очистить и их (и, конечно, до закрытия соединения).

И.о.в.:очистите то, что вы создаете.

Возможно, OracleDataAdapter уже делает это за вас, но это неясно (и в документах odp.net этого не говорится, поэтому вам нужно проверить (нечитаемый) код с помощью рефлектора, чтобы убедиться в этом.Хотя практическое правило с odp.net:чтобы избежать утечек памяти, всегда вызывайте Dispose для всего по порядку:параметр, курсор, команда, транзакция, соединение.

Другие советы

Я не уверен, что вы наткнулись на этот статья, и она не имеет прямого отношения к вашему вопросу, но иллюстрирует то, что я узнал при работе с ODP.Net:в случае сомнений всегда закрывайте (соединения) и утилизируйте.Каждый метод, который я пишу, который использует экземпляр ODP-соединений, команд и/или курсоров, имеет предложениеfinally, удаляющее все.

Лицензировано под: CC-BY-SA с атрибуция
Не связан с StackOverflow
scroll top