I didn't get error when try to connect SQL Server - c#

I have a Virtual Machine in Windows Azure with SQL Server 2016. This VM has a firewall with Azure, where I allow the IP to connect to the server. And also my project is an ASP.NET Web API 2 with ADO.NET for Data Access Layer.
The thing is all set; everything is working fine (Good!). But If I try to connect from another place with an IP that is not added to the firewall rules, I don't get any error, only still to try to execute the command. Normally if I use the SQL Managment I get an error.
This is my parameter in my connection string
Server=vm.XXXXXX.azure.com;Database={database};User ID={userid};Password={password};Encrypt=True;TrustServerCertificate=True;Connection Timeout=300;ConnectRetryCount=4;ConnectRetryInterval=1
So, this is extract code that I executed:
using (SqlConnection dbConnection = new SqlConnection(myCString))
{
using (SqlCommand dbCommand = new SqlCommand())
{
string queryString;
queryString = "SELECT * FROM table WHERE (ID = #ID) ";
dbCommand.Parameters.Add(Utilities.GetSQLParameter("ID", 1234, SqlDbType.VarChar));
dbCommand.CommandText = queryString;
dbCommand.Connection = dbConnection;
dbConnection.Open();
using (SqlDataReader dr = dbCommand.ExecuteReader())
{
if (dr.Read())
{
Value = dr[Field].ToString();
}
else
{
Value = "";
}
}
}
}
In summary, I want to get the error if I cannot find the VM because the firewall is blocking the access.

The connection failure occurs at dbConnection.Open.
Wrap your code in atry/catch block and treat the error if it occurs.
A list of available catchable exceptions can be found at https://msdn.microsoft.com/en-us/library/system.data.sqlclient.sqlconnection.open(v=vs.110).aspx
try
{
dbConnection.Open();
using (SqlDataReader dr = dbCommand.ExecuteReader())
{
if (dr.Read())
{
Value = dr[Field].ToString();
}
else
{
Value = "";
}
}
}
catch(Exception ex)
{
//Do some treatment
}
finally
{
//If connection has been opened, close it.
if(dbConnection.ConnectionState == ConnectionState.Open)
{
dbConnection.Close();
}
}

I will recommend you use USING clear all your "managed resources"
https://learn.microsoft.com/en-us/dotnet/csharp/language-reference/keywords/using-statement
using (SqlConnection conn = new SqlConnection(System.Configuration.ConfigurationManager.ConnectionStrings["ConnStringName"].ToString()))
using (SqlCommand mySqlCommand = new SqlCommand())
{
try
{
conn.Open();
mySqlCommand.Connection = conn;
mySqlCommand.CommandType = CommandType.StoredProcedure;
mySqlCommand.CommandText = "getCities";
mySqlCommand.CommandTimeout = Convert.ToInt32(System.Configuration.ConfigurationManager.AppSettings["ConnectionTimeout"].ToString());
mySqlCommand.Parameters.Add("#param", SqlDbType.VarChar).Value = param;
da.SelectCommand = mySqlCommand;
da.Fill(ds, "cities");
}
catch (Exception ex)
{
// LOG HERE the errors
}
} // end using

Related

Question about SQL connection and statement in C#

I currently have my SQL statements like this in my C# program.
SqlConnection connection = DataBase.GetConnection();
string deleteStatement = "DELETE FROM People WHERE ID = #ID";
SqlCommand deleteCommand = new SqlCommand(deleteStatement, connection);
deleteCommand.Parameters.AddWithValue("#ID", Id);
try
{
connection.Open();
deleteCommand.ExecuteNonQuery();
}
catch (SqlException ex)
{
throw ex;
}
finally
{
connection.Close();
}
But visual studio 2019 is suggesting to use a using statement instead. Is there any benefit to using ether or?
In addition to the accepted answer:
You could/should dispose SqlCommand as well and using will handle it.
using (var connection = DataBase.GetConnection())
using (var command = connection.CreateCommand())
{
command.CommandText = "DELETE FROM People WHERE ID = #ID";
var parameter = new SqlParameter
{
ParameterName = "#ID",
SqlDbType = SqlDbType.Int,
Value = Id
};
command.Parameters.Add(parameter);
connection.Open();
command.ExecuteNonQuery();
}
using will automatically dispose of the connection (which also closes the connection).

Unable to Get value from MySQL and print to TextBox

So this method is supposed to get the ipaddress of the logged in user from a MySQL Database and print it to a textbox. However, I cant seem to get it right as the program just closes after I execute this method.
public void readIPAddress()
{
string username = GlobalData._sharedUserName;
String connString = System.Configuration.ConfigurationManager.ConnectionStrings["WebAppConnString"].ToString();
conn = new MySql.Data.MySqlClient.MySqlConnection(connString);
conn.Open();
queryStr = "";
queryStr = "SELECT ipaddress FROM webappdemo.userregistration WHERE username=?username";
cmd = new MySql.Data.MySqlClient.MySqlCommand(queryStr, conn);
cmd.Parameters.AddWithValue("?username", username);
cmd.ExecuteReader();
while (cmd.ExecuteReader().Read())
{
textBoxIPAddress.Text = reader["ipaddress"].ToString();
}
conn.Close();
}
If anyone could point out where I went wrong, I greatly appreciate your help!
Edit: After using try and catch I get this:
MySql.Data.MySqlClient.MySqlException (0x80004005): There is already an open DataReader associated with this Connection which must be closed first.
at MySql.Data.MySqlClient.ExceptionInterceptor.Throw(Exception exception)
at MySql.Data.MySqlClient.MySqlConnection.Throw(Exception ex)
at MySql.Data.MySqlClient.MySqlCommand.CheckState()
at MySql.Data.MySqlClient.MySqlCommand.ExecuteReader(CommandBehavior behavior)
at MySql.Data.MySqlClient.MySqlCommand.ExecuteReader()
at ConnectToDataBase.Form2.readIPAddress() in C:\Users\ee\Dropbox\ConnectToDataBase\ConnectToDataBase\Form2.cs:line 95
Quick Fix:
You are executing the command two times, using ExecuteReader that's why you are getting such exception. If you execute the code like this means your code will works fine:
string queryStr = "SELECT ipaddress FROM webappdemo.userregistration WHERE username=#username";
using (MySqlConnection conn = new MySqlConnection(connString))
{
conn.Open();
using (MySqlCommand cmd = new MySqlCommand(queryStr, conn))
{
cmd.Parameters.AddWithValue("#username", username);
var reader = cmd.ExecuteReader();
while (reader.Read())
{
textBoxIPAddress.Text = reader["ipaddress"].ToString();
}
}
}
Smart Fix:
Here you are fetching a single value from the database in such situations you need not to use reader at all. you can simply access those value by using ExecuteScalar() method, which will give you the required object. if so You can use the following code:
using(MySqlConnection conn = new MySqlConnection(connString))
{
using(MySqlCommand cmd= new MySqlCommand(query, conn))
{
cmd.Parameters.Add("#username", username);
conn.Open();
object ipAddress= cmd.ExecuteScalar();
if (ipAddress!= null)
textBoxIPAddress.Text = ipAddress.ToString();
else
textBoxIPAddress.Text = "No data found";
}
}
Hope that you wont forget to add MySql.Data.MySqlClient; to the using section
you are executing reader two times by calling ExecuteReader(), why you need Reader here, if you only need one value from database. use ExecuteScalar that will return first value of the first record from the result. Sample code:
try
{
string query = "SELECT ipaddress FROM webappdemo.userregistration WHERE username = #username";
string connString =ConfigurationManager.ConnectionStrings["WebAppConnString"].ToString();
using(MySqlConnection connection = new MySqlConnection(connString))
{
using(MySqlCommand command = new MySqlCommand(query, connection))
{
command.Parameters.Add("#username", username);
connection.Open();
object ip= command.ExecuteScalar();
if (ip != null) {
textBoxIPAddress.Text = ip.ToString();
}
}
}
}
catch(MySqlException ex)
{
// do something with the exception
}
Problem:
cmd.ExecuteReader(); //Executing reader and not assigning to anything
while (cmd.ExecuteReader().Read()) //Executing reader again and not assigning to anything again
{
//There is nothing assigned to reader.
textBoxIPAddress.Text = reader["ipaddress"].ToString();
}
Quick Solution:
//assuming reader is defined
reader = cmd.ExecuteReader();
while (reader.Read()) //read from the reader
{
textBoxIPAddress.Text = reader["ipaddress"].ToString();
}
Alternative Solutions using MySql.Data.MySqlClient.MySqlHelper:
try {
object ip = MySqlHelper.ExecuteScalar(connString, query, new MySqlParameter[] {
new MySqlParameter("?username", username)
}));
if (ip != null) {
textBoxIPAddress.Text = ip.ToString();
}
} catch (Exception ex) {
// do something with the exceptio
}
If you insist on using reader:
//assuming reader is defined
reader = MySqlHelper.ExecuteReader(connString, query, new MySqlParameter[] {
new MySqlParameter("?username", username)
}));
while (reader.Read()) //read from the reader
{
textBoxIPAddress.Text = reader["ipaddress"].ToString();
}
Note: the above code is just typed in here and may contain syntax errors. take this a a guideline.

How to solve the SQLite "Database is locked" in C#?

When I update some data, sometimes it throws a exception: Database is locked.
The code below:
public int DisableSalesBySalesID(string SalesID)
{
int count = 0;
try
{
using (SQLiteConnection conn = new SQLiteConnection(ConnectionString))
{
conn.Open();
string sql = #"update SalesMaster set Disabled = '1' where SalesID=#SalesID";
using (SQLiteCommand cmd = new SQLiteCommand(sql, conn))
{
cmd.Parameters.Add(new SQLiteParameter("#SalesID", SalesID));
count = cmd.ExecuteNonQuery();
}
}
}
catch (Exception ex)
{
}
return count;
}
And, it depends on SalesID. Some SalesID will be OK, but the others will make the exception. Why?
a common cause is that you have a dangling sqlcommand. sqlcommands hold locks on the database. same for sqlreaders. Make sure they are all in using blocks

Packaging System.Data.SqlClient with a class library in C#

I have a scanner add-in that I'm working on that uses C#.
My code works on the emulator, but not on the scanner hardware itself. Could it be because the scanner doesn't have System.Data.SqlClient on it? I'm not sure. Is there a way I can specify that System.Data.SqlClient be included in my generated dll file?
The error I get is Named Pipes Provider error 40 on con.Open(). If it were a problem with the scanner not having the library though, woudln't it throw on error at the first reference to a SqlConnection? The source code is as follows:
String clientName = "";
try
{
// Setting up the SqlConnectionStringBuilder
SqlConnectionStringBuilder buildIt = new SqlConnectionStringBuilder();
buildIt.DataSource = "xxx.xx.x.xx";
buildIt.InitialCatalog = "database";
buildIt.IntegratedSecurity = true;
using (SqlConnection con = new SqlConnection(buildIt.ConnectionString))
{
con.Open();
using (SqlCommand command = new SqlCommand("SELECT First_Name, Last_Name FROM background WHERE Patient_No=#Patient_No", con))
{
command.Parameters.AddWithValue("#Patient_No", clientID);
SqlDataReader reader = command.ExecuteReader();
if (reader.HasRows)
{
reader.Read();
clientName = reader.GetString(0).Trim() + " " + reader.GetString(1).Trim();
} // end if (reader.hasRows)
else
{
// No client found for this ID.
return false;
} // end else
} // end using (SqlCommand command = new SqlCommand("SELECT First_Name, Last_Name FROM background WHERE Patient_No=#Patient_No", con))
}
} // end try
catch (Exception err)
{
// Test code.
// MessageBox.Show(err.Message);
exporterHost.WriteSystemLog(LogType.Error, "E9999999", "SQL ERROR: " + err.Message);
return false;
}
Thanks!

update a mySQL table using C#

I have written some C# to update a MySql table but I get an exception every time I call the method ExecuteNonQuery(). I have researched this on the web and every solution I find produces the same error. I have an open connection to the database and the update query to the database is written correctly. The code that I have so far come up with is :
public int executeUpdate()
{
int result = 0;
if (isConnected)
{
try
{
MySqlConnection cn = new MySqlConnection(connection.ConnectionString);
MySqlCommand cmd = new MySqlCommand();
cmd.Connection = cn;
cmd.CommandText = "UPDATE test SET status_id = 1 WHERE test_id = 1";
int numRowsUpdated = cmd.ExecuteNonQuery();
}
catch (MySqlException exSql)
{
Console.Error.WriteLine("Error - SafeMySql: SQL Exception: " + query);
Console.Error.WriteLine(exSql.StackTrace);
}
catch (Exception ex)
{
Console.Error.WriteLine("Error - SafeMySql: Exception: " + query);
Console.Error.WriteLine(ex.StackTrace);
}
}
else
Console.Error.WriteLine("Error - SafeMySql: executeQuery failed. Not connected to DB");
}
Change your try section to the code below:
try
{
using(MySqlConnection cn = new MySqlConnection(connection.ConnectionString))
{
MySqlCommand cmd = new MySqlCommand();
cmd.Connection = cn;
cmd.CommandText = "UPDATE test SET status_id = 1 WHERE test_id = 1";
cn.Open();
int numRowsUpdated = cmd.ExecuteNonQuery();
cmd.Dispose();
}
}
The connection must be opened before you execute a command. In the example above the command object will immediately be disposed and the connection object will implcitly be closed and disposed when you leave the using section.
I don't see the connection being opened.
Here is an example from MSDN: even inside a using block, they open the connection explicitly
private static void CreateCommand(string queryString,
string connectionString)
{
using (SqlConnection connection = new SqlConnection(
connectionString))
{
SqlCommand command = new SqlCommand(queryString, connection);
command.Connection.Open();
command.ExecuteNonQuery();
}
}
Edit: The principle is the same for MySQL as it is for SQL Server:
public void CreateMySqlCommand(string myExecuteQuery, MySqlConnection myConnection)
{
MySqlCommand myCommand = new MySqlCommand(myExecuteQuery, myConnection);
myCommand.Connection.Open();
myCommand.ExecuteNonQuery();
myConnection.Close();
}

Categories

Resources