1

我的 ASP.NET C# 应用程序连接到 Oracle 数据库,运行存储过程,并返回具有 CloseConnection 命令行为的读取器。阅读器本身已被处理,但是 - Oracle 会话在 V$SESSION 中保持为非活动状态。几个小时后,当另一个客户使用该应用程序时,这会变成一个错误,并且我们收到错误“ORA-02399:超出最大连接时间,您正在注销”。进一步尝试连接到 Oracle 返回“ORA-01012:未登录”

这是连接字符串:

User Id=UserID;Password=userPass;Data Source=(DESCRIPTION=(ADDRESS=(PROTOCOL=TCP)  (HOST=IP.IP.IP.IP)(PORT=XXXX))(CONNECT_DATA=(SID=SID)));;Max Pool Size=5;Connection Timeout=60;Connection Lifetime=120;

以下是阅读器的使用方法:

using (OracleDataReader dr = OraFunctions.ExecuteReader(input.ConnectionString,
                                                                    CommandType.Text,
                                                                    input.SqlStmt,
                                                                    null))
{
 while (dr.Read())
 {
 //do stuff here 
 }
 dr.Dispose();
}

这是连接到 Oracle 的类:

public static OracleDataReader ExecuteReader(string connectionString, CommandType commandType, string commandText, OracleParameter[] commandParameters) {
        OracleConnection connection = null;
        OracleCommand command = new OracleCommand();
        try {
            connection = new OracleConnection(connectionString);
            connection.Open();
            command.Connection = connection;
            command.CommandType = commandType;
            command.CommandText = commandText;

            if (commandParameters != null) {
                foreach (OracleParameter param in commandParameters) {
                    command.Parameters.Add(param);
                }
            }
            //Passing CommandBehavior.CloseConnection flag to the ExecuteReader method makes the DataReader connection to be closed when the DataReader is closed. 
            OracleDataReader reader = command.ExecuteReader(CommandBehavior.CloseConnection);
            command.Dispose();
            return reader;
        } catch {
            if (connection != null) {
                command.Dispose();
                connection.Close();                    
            }
            throw;
        }
    }

I'm looking for any hints on why the connections aren't actually closing. I'm using Oracle.DataAccess.Client. My guess is that the datareader's command behavior isn't working and that I need to recode this as a dataset where I can explitictly close the connection without having to rely on the CommandBehavior.

Thoughts? Thanks!

4

3 回答 3

1

since you have connection.Open();

why didn't proper close it?

于 2014-04-23T09:52:15.283 回答
0

We never could get this worked out. We ended up disabling connection pooling and the open/inactive sessions went away in Oracle. If anyone reads this and has a suggestion on what was going wrong, I would definitely appreciate your input.

于 2012-12-10T20:36:45.370 回答
0

The possible solution I'm evaluating right now is to set Connection Lifetime parameter below the server's value.

The idea is when connection returned to the pool after performing query, it's lifetime is checked, and connection is closed if both conditions are met:

  • Connection's lifetime exceeded Connection Lifetime parameter value
  • Number of connections opened would not be lower than Min Pool Size parameter value

Kudos to Joao Morais for ODP.NET pooling details.

于 2013-02-12T13:46:07.147 回答