I know this is one of the most popular questions on SO: The Famous "SQL error 26" the difference is that my C# application establishes a connection successfully the first time and then refuses to establish a connection the second time. I restart my computer and the application establishes a connection the first time and then requires a restart again.
The fact that I can establish a connection the first time makes me feel confident that: My server name is correct, My instance name is correct, the username and password combination I use are correct, the server machine is on, the SQL Browser service on the server is running, and I can get through the firewall.
I have a bunch of methods that all look very similar to the following:
private static string connection_string = #"Server=my_server\MS_SQL;User Id=user1;Password=password1"
public static List<string> GetListOfExistingItems(int item_id)
{
List<string> list_items = new List<string>();
try
{
using (SqlConnection sql_conn = new SqlConnection(connection_string))
{
sql_conn.Open();
SqlCommand sql_comm = new SqlCommand("SELECT Name FROM dbo.table1 WHERE ID=" + item_id,
sql_conn);
using (SqlDataReader sql_reader = sql_comm.ExecuteReader())
{
while (sql_reader.Read())
{
list_items.Add(sql_reader["Name"].ToString());
}
sql_reader.Close();
}
}
}
catch (Exception excp)
{
throw new Exception(excp.Message);
}
return list_items;
}
A few interesting facts:
A restart fixes the problem (once).
A log out and log in does NOT fix the problem.
If I do not close the application but instead run the query multiple times, the error does not show up.
I cannot connect to my database from SQL Server Management Studio after I run my application and close it once.
When I restart my computer I see the "Waiting for background programs to close" without any programs being listed. I wait for some time (maybe 10-20 seconds) and the message goes away and the computer eventually restarts.
Thanks in advance.
Somewhere you're not closing your connection.
My next troubleshooting step would be to string-search your code (all of it) for sql_conn.Open();, and find the one(s) not in a using block, or otherwise not getting explicitly closed.
Related
I developed a simple app that allows users to input data in a local database, but eventually it will have many simultaneous connections in a production environment, which includes data being stored in a data center.
Right now my app can read (from two different tables) and write in one of them, but it has at least one problem: I close the connection right after a user has ended submitting data for one employee, and I actually want to the app to allow the input for many of them in a single session, so the flow would be:
(1) . user enters the app > (2) . user saves an employee > (3) . the
app informs the user about the result of the entry (might be
duplicates value for several fields which would show an error, a
successfully saved employee message, etc) [here I close the connection] > (4) . goes back to (2), if the user chooses to, and I try to open it again.
EDIT:
The error I get when I try to enter a new user right after I close the connection is "connection must be valid and open"
I'm expecting that a Singleton object handles this, but is not actually doing it.
private MySQLDataAccess()
{
this.openConnection();
}
private MySqlConnection Connection;
private static MySQLDataAccess instance;
public static MySQLDataAccess GetInstance()
{
if(instance == null)
{
instance = new MySQLDataAccess();
}
return instance;
}
So, my question is...
Should the app close the connection with the db right after the application ends? this might include a user that saves more than 50 employees in one sit.
Or should I close the connection every time a user is saved, and then opening it again to save a new user? (this is what I'm trying to do right now, but I'm not doing it properly)
The best practice is to not keep connections open (or even re-used) for more than one "unit of work". The most effective way to do that is with using blocks:
using(MySqlConnection conn = ...)
{
using(MySqlCommand cmd = ...)
{
// open connection
// execute command
// close connection (optional - the connection will be closed when
// it gets disposed, but it's more explicit this way)
}
}
The connection will be closed automatically even if there is an exception.
Also, don't do any retrying that requires user input within the blocks (e.g. "you've entered a duplicate value - try again"). If you get an error, dispose of the connection, get new inputs, then create a new connection and try again.
Or use a connection factory, assuming your connection information in your web.config:
var settings = ConfigurationManager.ConnectionStrings[connectionStringName];
var factory = DbProviderFactories.GetFactory(settings.ProviderName);
using (var conn = factory.CreateConnection())
using (var cmd = conn.CreateCommand())
{
conn.ConnectionString = settings.ConnectionString;
conn.Open();
...
conn.Close();
}
More often than not however, I'm just using Dapper on the DbConnection, which abstracts away most of the pain of mapping and opening/closing for me.
I've got problem with the connection pulling with continuously running program. The problem occurs when I'm doing a lot of queries (every 4 minutes 5x (querying 3 tables and saving result to one)) to DB in the Tasks. The connection pools run out of max pool connection size. The strange thing about this that I have on DB 100 of AWAITING COMMAND entries for that particular connection string / machine / user entries. My understanding is that AWAITING COMMAND means that this connection can be reused, but from some strange unknown reason to me when running commands from Tasks cannot reuse available connections and they just wait for no one, and after some time got error that I've reached the max pool connections size.
Assumptions so far:
When running commands from tasks DB interpret this as invalid to reuse available connections
Connections aren't closing, but why? Seems to closing them with using keyword. More over that is 100 AWAITING COMMANDS one the DB.
The handlers aren't garbage collected for some reason? But the 100 AC telling sth else.
UPDATE: LOCALDB OBSERVATIONS/SUMMARY:
When I'm trying to replicate this on local DB SQL Server Express this problem happen in very awkward situation. I had to add the Thread.Sleep(600000) to kind a simulate the situation. And eventually after that I was able to get the max pool error, but in this case all connections are open so its rather self explanatory.
In local -> server scenario, I don't think so that I could have 100 connections open in one time, they rather stay open for some reason. When launching this program on the localMachine -> serverDB situation I don't even need to add the Thread.Sleep(600000) in order to crash program.
All those are my assumptions based on observations. I can't think of what casing this in my continuous running service where querying the DB every 4 minutes.
PS. After my full local testing I'm confused if COMMAND AWAITING means that this connection can be reused?
UPDATE 2 Forgot to mention that my initial program can run couple of days before I eventually encounter this max pool error.
Below is the program that can generate this kind of problem:
using System;
using System.Data.SqlClient;
using System.Threading;
using System.Threading.Tasks;
namespace Pooling
{
class Program
{
private static int connectionIterations;
private static string connectionString = "Data Source=localhost;Initial Catalog=localDB;Integrated Security=True";
static void Main(string[] args)
{
try
{
Iterations();
while(true)
{
ConnectionSnowball();
}
}
catch (Exception e)
{
Console.WriteLine(e);
throw;
}
}
private static void ConnectionSnowball()
{
Parallel.For(0, connectionIterations, i =>
{
try
{
Console.WriteLine($"Connection id: {i}");
using (SqlConnection connection = new SqlConnection(connectionString))
{
SqlCommand cmd = new SqlCommand("SELECT 1 FROM test_table", connection);
connection.Open();
cmd.ExecuteNonQuery();
Thread.Sleep(600000);
}
}
catch (Exception e)
{
Console.WriteLine(e);
throw;
}
});
}
private static void Iterations()
{
connectionIterations = 200;
}
}
}
I debugged your code and found no connection leaks. You just have a connection pool overflow. I checked two possible solutions for you.
Disable pooling connections
private static string connectionString = "Data Source=localhost;Initial Catalog=localDB;Integrated Security=True;Pooling=False";
Increase connection pool
private static string connectionString = "Data Source=localhost;Initial Catalog=localDB;Integrated Security=True;Max Pool Size=200";
To test how the connections will increase and decrease before, during and after the ConnectionSnowball() call, you can use this SQL query
select count(1) from sys.dm_exec_sessions where database_id = DB_ID(N'localDB')
More details about connection string parameters
SqlConnection.ConnectionString Property
Other possible solutions is the use of SQL jobs. For this task, this may be a more appropriate solution, since a large number of connections are very resource intensive.
As there are no connection leaks in your code, Did you try Restarting IIS?
I am creating a console application and keep the SQL operations in a separate class file. When I execute the application it raises an exception:
ExecuteNonQuery requires an open and available Connection. The connection's current state is closed.
However, in SQL class file's constructor I wrote the code for SqlConnection.Open().
Code for Main application:
using SQL;
class MyClass
{
SQL.executeSQL runSQL=new SQL.executeSQL();
static void Main(string[] args)
{
CheckCounts();
}
public void CheckCounts()
{
string sql="select count(*) from table_name";
runSQL.executeQuery(sql);
}
}
Code for SQL class file:
public class executeSQL
{
SqlConnection con=new SqlConnection(ConfigurationManager.ConnectionString["dbConnection"].ToString());
public executeSQL()
{
if(con.State!=ConnectionState.Open)
{
con.Open();
}
}
public void executeQuery(string sql)
{
SqlCommand cmd=new SqlCommand(sql,con);
cmd.ExecuteNonQuery();
}
}
When I execute the application for the first time for that day it raises the exceptions as follows
ExecuteNonQuery requires an open and available Connection. The connection's current state is closed.
But for next time it runs properly without any exception for the whole day.
Again if I run the application for the next day it raises the same exception and consecutive successful execution.
What should I do to run the application successfully for the first time of the day?
I created a batch file for the application and I scheduled the task using the Task Scheduler with the batch file. If I run the application manually I do not get the error. Using the Task Scheduler, I am getting the error.
This can happen for a few reasons.
Chances are, you're connecting to a remote SQL server.
If this is the case, then there are a variety of reasons why the connection may be closed on you by the time you make your call.
Things like network dropouts etc can cause the connection between your app and SQL to break and require reconnection.
It can also be caused by the agreed timeout between your app and SQL being exceed, however I doubt this is the case given your code sample.
I have personally experienced issues where I have made what appears to be a valid connection to the server, and then on the very next line attempt to make a SQL query, only to receive the same error as yourself.
In those instances, I've added a check before making my SQL query around the SQLConnection.State property, which can return any of the following:
Broken
The connection to the data source is broken. This can occur only after
the connection has been opened. A connection in this state may be
closed and then re-opened. (This value is reserved for future versions
of the product.)
Closed
The connection is closed.
Connecting
The connection object is connecting to the data source.
Executing
The connection object is executing a command. (This value is reserved
for future versions of the product.)
Fetching
The connection object is retrieving data. (This value is reserved for
future versions of the product.)
Open
The connection is open.
If the SqlConnection.State is Open, then I run my SQL query as intended.
If it's Closed, I attempt to re-open it then re-call my SQL query.
If it's Connecting, I pause for a specific amount of time, then retest.
Depending on how you want your app to perform, I would look at either moving the creation of the SQLConnection into the method that makes the SQL call, as follows:
public class executeSQL
{
private void CheckSQLConnection(SqlConnection con)
{
...
}
public void executeQuery(string sql)
{
using (var con = new SqlConnection(ConfigurationManager.ConnectionStrings["dbConnection"].ToString()))
{
con.Open();
using (var cmd = new SqlCommand(sql, con))
{
CheckSQLConnection();
cmd.ExecuteNonQuery();
}
con.Close();
}
}
}
As in my example, it's also worth implementing using statements around your SQLConnection and SQLCommand objects to ensure they're properly disposed of and don't hang around, potentially holding onto SQL connections you might need.
Hope this helps!
I am getting error
80004005 There is a file sharing violation. A different process might be using the file.
when trying to open a SqlCeConnection.
Is there a way to close a SQL Server CE database programmatically, to try to nip that problem in the bud? Something like (pseudocode):
SqlCeDatabase SQLCeDb = "\My Documents\HHSDB003.sdf";
if (SQLCeDb.IsOpen)
{
SQLCeDb.Close();
}
?
Or a way to set the connection so that it doesn't care if the database is open elsewhere/wise, such as:
SqlCeConnection conn = new SqlCeConnection(#"Data Source=\My Documents\HHSDB003.sdf;File Mode = 'shared read'");
...or:
SqlCeConnection conn = new SqlCeConnection(#"Data Source=\My Documents\HHSDB003.sdf;File Mode = 'read write'");
I can't test these at present, because I'm back to getting
Cannot copy HHS.exe The device has either stopped responding or has been disconnected
when I attempt to copy over a new version of the .exe to the handheld.
If there's something more frustrating to program against (and "against" is the correct word here, I think) than the prehistoric versions of Windows CE / Compact Framework / .NET, I'm not at all sure I want to know what it is.
UPDATE
Adding to my frustrusion (haywire combination of confusion and frustration), I found the following at http://www.pocketpcfaq.com/faqs/activesync/exchange_errors.php:
0x80004005 N/A Synchronization failed due to a device software error. Contact your network administrator.
1. Obtain the latest Pocket PC End User Update from your service provider.
UPDATE 2
Is this possibly problematic (than all but the first setting is blank):
UPDATE 3
With this code:
private void menuItemTestSendingXML_Click(object sender, System.EventArgs e)
{
string connStr = "Data Source=My Documents\\HHSDB003.SDF";
SqlCeConnection conn = null;
try
{
try
{
conn = new SqlCeConnection(connStr);
conn.Open();
MessageBox.Show("it must have opened okay");
}
finally
{
conn.Close();
}
}
catch (Exception ex)
{
if (null == ex.InnerException)
{
MessageBox.Show("inner Ex is null");
}
MessageBox.Show(String.Format("msg is {0}", ex.Message));
}
}
...I am now seeing "it must have opened okay" (that's a good thing, but...why it's now working, I have no idea, because the code has not changed since I last ran it and it failed. Something beyond the code must have been at play.
The only thing I can think of that happened that MAY have had a bearing on this change is that, thinking there may have been a rogue instance of either the .exe or its ancillary dll in memory on the handheld device, I wrote an quick-and-dirty utility that looped through the running processes, looking for them and, if finding them, killing them, but they were not there, so the utility really did "nothing" (maybe the Hawthorne effect?).
That is the way working with this combination of tools and technologies seems to go, though: everything is working fine one minute and the next, BAM! It no longer is. Then the reverse can also happen: for no apparent reason it seems to "heal itself".
In the interests of "full disclosure," here is the utility code:
// Got this from http://www.codeproject.com/Articles/36841/Compact-Framework-Process-class-that-supports-full
private void btnKillRogue_Click(object sender, EventArgs e)
{
ProcessInfo[] list = ProcessCE.GetProcesses();
foreach (ProcessInfo item in list)
{
MessageBox.Show("Process item: " + item.FullPath);
if (item.FullPath == #"\Windows\iexplore.exe") item.Kill(); //<= this was the example search; it probably could be a problem, so I'll use it, too
if (item.FullPath.EndsWith("HHS.exe"))
{
MessageBox.Show("about to kill hhs.exe");
item.Kill();
}
if (item.FullPath.EndsWith("HUtilCE.dll"))
{
MessageBox.Show("about to kill hutilce.dll");
item.Kill();
}
}
}
Maybe there was an instance of iexplore.exe resident in memory that was problematic (I'm not showing a messagebox if that is what is found)...?
As an attempt to claim unused bounty ... do not, however, feel obligated to pass around free points on my behalf ...
Aside from force killing of possible tasks, had you rebooted the system amidst your search for an answer? If your tool did not return the message, it is certainly possible that a reboot would have done the very thing that you had attempted with the kill utility - or possible iexplore.exe had something to do with it ... the lack of the additional messagebox may leave you never knowing - unless this issue occurs again.
If no rebooting occurred, then perhaps whatever program/dll was held in memory by some other process concluded its task and released it hold.
There are several scenarios that might have occurred, it is certainly hard to determine with absolution; hence the lack of answers. I would be interested, though, if this problem occurred again.
I've got an error in my C# application. I'm not sure if it's my program or my website. It's a gaming emulator and it says after 1-2 hours running 'Too many connections'. It also says it on my website.
The line this code is erroring on is below, and it errors and highlights the words connection.Open(); when it crashes. I think it has something to do with not closing the connections.
//C# Coding (In VB)
private static SqlDatabaseClient CreateClient(int Id)
{
MySqlConnection connection = new MySqlConnection(GenerateConnectionString());
connection.Open();
return new SqlDatabaseClient(Id, connection);
}
//Application error
[04:51] Exception - Session -> To many connection[]MySqlData.MySqlClient.MySqlPacket ReadPacket<> # at MysqlData.MySqlClient.MySqlStream.Readpacket<>
at MySql.Data.MySqlClient.NativeDriver.Open<>
at MySql.Data.MySqlClient.Driver.Open<>
at MySql.Data.MySqlClient.Driver.Create
at MySql.Data.MySqlClient.MySqlPool.GtPooledConnection<>
at MySql.Data.MySqlClient.MySqlPool.TryToGetDriver<>
at MySql.Data.MySqlClient.MySqlPool.GetConnection<>
at MySql.Data.MySqlClient.MySqlConnection.Open<>
at Reality.Storage.SqlDatabaeManager.CreateClient in C:\iRP\SqlDatabaseClient.cs:line 24d
It's good practice to place the code accessing your database within a using clause. By doing this you will ensure that your connections are disposed of when it is not used anymore.
C# Too many connections in MySQL
Take a look at that link. You need to use the 'using' statement so the connections are opened and closed properly.