MySqlCommand.Parameters.Add adds slashes to commandtext in c# - c#

I'm trying to do a parametrized Insert query in C#, console application. DB = MYSQL 8.
StringBuilder commandString = new StringBuilder("INSERT INTO testtable (testcol) VALUES ");
string testparam = "testvalue";
commandString.Append(string.Format("('{0}')", testparam));
commandString.Append(";");
string ConnString = "server = localhost; database = xxxxx; User = xxxxx; Password = xxxxx; port = 3306";
MySqlConnection conn = new MySqlConnection();
conn.ConnectionString = ConnString;
conn.Open();
Console.WriteLine(commandString); //if I copy the commandstring from the console and into Mysql workbench it works.
using (MySqlCommand cmd = new MySqlCommand("#str", conn))
{
cmd.Parameters.Add("#str",MySqlDbType.Text).Value=commandString.ToString();
cmd.ExecuteNonQuery();
}
Everything looks good, commandString is ok: INSERT INTO testtable (testcol) VALUES ('testvalue');
I get an exception stating the following:
MySql.Data.MySqlClient.MySqlException: 'You have an error in your SQL syntax; check the manual that corresponds to your MySQL server version for the right syntax to use near ''INSERT INTO testtable (testcol) VALUES (\'testvalue\');'' at line 1'
Please note the escape slashes in the message around 'testvalue'. I did not put them there and they do not show up in the commandstring prior to this line. Is this causing the error? And If so, why?
If I use cmd.Parameters.AddWithValue, I get the same working commandstring, but an error: System.FormatException: 'Input string was not in a correct format.' However if I copy paste the generated commandstring from the debugger to MySQL workbennch and execute it, it works.

You aren't using parameterised queries correctly, you shouldn't covert the entire SQL string into a parameter as you do here:
using (MySqlCommand cmd = new MySqlCommand("#str", conn))
{
cmd.Parameters.Add("#str",MySqlDbType.Text).Value=commandString.ToString();
cmd.ExecuteNonQuery();
}
It doesn't do a straight text replacement, and you are in fact making things a bit more complicated than they need to be. An example might be:
string ConnString = "server = localhost; database = xxxxx; User = xxxxx; Password = xxxxx; port = 3306";
string testparam = "testvalue"; // realistically this might come from user input
string sql = "INSERT INTO testtable (testcol) VALUES (#testcol)";
using (var conn = new MySqlConnection(ConnString))
using (var cmd = new MySqlCommand(sql, conn))
{
conn.Open();
cmd.Parameters.Add("#testcol", MySqlDbType.Text).Value = testparam;
cmd.ExecuteNonQuery();
}

Related

C# SQL Connection not found

How can I connect a SQL database in C#?
My code:
const string connectionString = "Data Source=127.0.0.1;User ID=root;Database=MyDatabase;Password=MyPassword";
var conn = new SqlConnection(connectionString);
conn.Open();
conn.Close();
I get: Error: 40 - could not open a connection to sql server. I tried also in Python and it worked well:
cnx = mysql.connector.connect(user='root', password='MyPassword', host='127.0.0.1', database='MyDatabase')
cursor = cnx.cursor()
What am I missing in C#?
Please use MySqlConnection for MySql DB.
const string connectionString = "Data Source=127.0.0.1;User ID=root;Database=MyDatabase;Password=MyPassword";
MySqlConnection conn = new MySqlConnection(connectionString );
conn.Open();
string sqlcommand = "SELECT Query";
MySqlCommand cmd = new MySqlCommand(sqlcommand , conn);
please follow this example
using MySql.Data.MySqlClient;
var connectionString = "server=serveradress;database=dbName;user id=sqluser;password=abc;";
using (var connection = new MySqlConnection(connectionString))
{
connection.Open();
using var command = new MySqlCommand("SELECT COUNT(*) FROM tableName ", connection);
var Count = command.ExecuteScalar();
Console.WriteLine($"There are {Count } movies");
}
server adress in general is 127.0.0.1 ,if you are working locally
here the source page :
example
and also consider reading this page here docs

How to retrieve ##Identity following an ExecuteNonQuery?

I'm using the ExecuteNonQuery function and stored procedure to insert a new record in an MSSQL database.
During testing the insert of the new record is successful. But my second call to ExecuteScalar and get the newly inserted record's ID fails. The reason for the failure according to the debugger is:
ExecuteScalar requires an open and available Connection. The
connection's current state is closed.
Looking at this error it explains that the connection has been closed after the initial call to ExecuteNonQuery. Meaning that my code to get the ID won't have a valid connection to query with.
Question:
How can you retrieve ##Identity following an ExecuteNonQuery?
This is the piece of code that performs the insert in the DAL:
Database db = GetConnectionString();
string sqlCommand = "CREATE_RECORD";
string idQuery= "Select ##Identity";
int recID = 0;
using (DbCommand dbCommand = db.GetStoredProcCommand(sqlCommand))
{
db.AddInParameter(dbCommand, "#Application", DbType.String, escalation.Application);
db.AddInParameter(dbCommand, "#UpdatedTime", DbType.DateTime, escalation.UpdatedTime);
db.ExecuteNonQuery(dbCommand);
dbCommand.CommandText = idQuery;
recID = (int)dbCommand.ExecuteScalar();
return recID ;
}
DISCLAIMER: This is a bad idea - the correct solution is server-side (server in this case is SQL Server).
You may be able to do this if you use SCOPE_IDENTITY() (which you should anyway - ##IDENTITY is not guaranteed to be your insert's identity) and execute your command as CommandType.Text instead of CommandType.StoredProcedure
WARNING: Serious security implications here, most notably SQL Injection Attack possibility:
Database db = GetConnectionString();
string sqlCommand = $"CREATE_RECORD '{escalation.Application}', '{escalation.UpdatedTime}'";
string idQuery= "Select SCOPE_IDENTITY()"
int recID = 0;
using (DbCommand dbCommand = db.GetStoredProcCommand(sqlCommand))
{
dbCommand.CommandType = commandType.Text;
db.ExecuteNonQuery(dbCommand);
dbCommand.CommandText = idQuery;
recID = (int)dbCommand.ExecuteScalar();
return recID;
}
Of course, if you go this route, you might as well combine both commands into a single query:
Database db = GetConnectionString();
string sqlCommand = $"CREATE_RECORD '{escalation.Application}', '{escalation.UpdatedTime}'; Select SCOPE_IDENTITY()";
int recID = 0;
using (DbCommand dbCommand = db.GetStoredProcCommand(sqlCommand))
{
dbCommand.CommandType = commandType.Text;
//TODO: Open connection using your db object
recID = (int)dbCommand.ExecuteScalar();
//TODO: Close connection using your db object
return recID;
}
Again, I stress that the correct solution is to fix this in SQL, not in C#. Use at your own risk!
You should create and open connection for each query and dispose it after query. Don't worry, there are connection pool in ADO and connection will not be physically established and closed each time. It's only a hint for ADO.NET.
int recID = 0;
string connStr = ProcThatGivesYouConnectionString();
using (SqlConnection con = new SqlConnection(connStr))
{
con.Open();
SqlCommand command = new SqlCommand("CREATE_RECORD", con);
command.CommandType = CommandType.StoredProcedure;
command.Parameters.AddWithValue("#Application", escalation.Application);
command.Parameters.AddWithValue("#UpdatedTime", escalation.UpdatedTime);
command.ExecuteNonQuery();
}
using (SqlConnection con2 = new SqlConnection(connStr))
{
con2.Open();
SqlCommand command = new SqlCommand("Select ##Identity", con2);
recID = (int)command.ExecuteScalar();
}
Also you can execute both queries in one command if you want:
int recID = 0;
string connStr = ProcThatGivesYouConnectionString();
using (SqlConnection con = new SqlConnection(connStr))
{
con.Open();
SqlCommand command = new SqlCommand("
EXEC CREATE_RECORD #Application = #Application, #UpdatedTime = #UpdatedTime
SELECT ##Identity", con);
command.Parameters.AddWithValue("#Application", escalation.Application);
command.Parameters.AddWithValue("#UpdatedTime", escalation.UpdatedTime);
recID = (int)command.ExecuteScalar();
}
object r = command.ExecuteScalar();
Convert.ToInt32(r.ToString());
To prevent the ExecuteScalar gets Specified cast is not valid error , use above

insert special character into SQL Server 2008 database from c#

i want to insert special character into sqlserver 2008 database. for example ('/##&*$) etc.
i have tried the following code but it remove these string from the orignal string.
string[] arrtime = postingtime.Split(',');
string sss = arrtime[1];
string sss1 = "EDT";
bool first2 = true;
string s33 = Regex.Replace(sss, sss1, (m) =>
{
if (first2)
{
first2 = false;
return "";
}
return sss1;
});
But i didnt want to remove these string from the orignal string...because i want to insert a franch language data and removal of these special character will change the meaning of sentence.
my insert query is:
cn.Open();
adp.InsertCommand = new SqlCommand("insert into ttt values('r=DE'S''C/pa-ge=1/$#')", cn);
adp.InsertCommand.ExecuteNonQuery();
cn.Close();
when i click on insert button then it gives error(datatype error).
my problem is , to insert string with special characters not to remove these character. i want to pass these characters to our sql server 2008 from c# application.
thanx in advance
Use parameterized queries like this:
using (SqlConnection cn = new SqlConnection(...))
{
cn.Open();
using (SqlCommand cmd = new SqlCommand("insert into ttt values (#testvalue)", cn))
{
cmd.Parameters.AddWithValue("#testValue", "r=DE'S'C#4593§$%");
cmd.ExecuteNonQuery();
}
}
Use parameters
adp.InsertCommand = new SqlCommand("insert into ttt values(#p1)", cn);
adp.InsertCommand.Parameters.Add(new SqlParameter("#p1", SqlDbType.NVarChar)).Value = "r=DE'S''C/pa-ge=1/$#";
Your Insert query vunlerable to SQL injections.. Try using SqlParameters. and in SQLServer User NVarchar datatype.
using (SqlConnection con = new SqlConnection(dc.Con))
{
using (SqlCommand cmd = new SqlCommand("insert into ttt values(#paramValue)", con))
{
cmd.Parameters.AddWithValue("#paramValue", "r=DE'S'C#4593§$%");
con.Open();
cmd.ExecuteNonQuery();
}
}

How to use input from a textbox and use it in a mysql query in C#

Code:
string connString = "SERVER=;UID=;PASSWORD=;DATABASE=;";
MySqlConnection connect = new MySqlConnection(connString);
MySqlCommand myCommand = connect.CreateCommand();
string input = textBox4.Text;
myCommand.CommandText = "SELECT * FROM project WHERE Id = #input";
connect.Open();
MySqlDataReader reader = myCommand.ExecuteReader();
if (reader.Read())
textBox1.Text = reader["Name"].ToString();
connect.Close();
I am trying to use data from a form textbox (textBox4) and pass that input into a mysql query.
The program works by the user inputting their id number and the form outputs their name into another textbox (textBox1).
When I use either the string 'input' or textBox4.Text itself I get an error message which is: "Fatal error encountered during command execution."
However if I manually type in a correct id number in the code itself it returns the correct vaule
New to C# and mysql sorry for any big errors.
Here is what I would do in your case:
string connString = "SERVER=;UID=;PASSWORD=;DATABASE=;";
MySqlConnection connect = new MySqlConnection(connString);
MySqlCommand myCommand = connect.CreateCommand();
string input = textBox4.Text;
myCommand.CommandText = "SELECT * FROM project WHERE Id = #input";
myCommand.Parameters.Add("#input", SqlDbType.Int).Value = Convert.ToInt32(textBox4.Text);
connect.Open();
MySqlDataReader reader = myCommand.ExecuteReader();
if (reader.Read())
textBox1.Text = reader["Name"].ToString();
connect.Close();
As you can see in the example above I am doing two things:
Sanitizing the input by using a SqlParameter and,
Converting the value of "#input" to a number; which is the assumption based on your question.
Best of luck to you, and please continue learning!
You're almost there, actually. You're using a parameter (#input) and not concatenating strings ("select .. " + text + " from ..."), which is wrong for many reasons.
Just tell your command how to replace that parameter. I guess it's something like this (not sure for MySQL):
myCommand.Parameters.Add("#input", SqlDbType.Int).Value = Convert.ToInt32(textBox4.Text);
Note that I'm assuming that Id is of type SqlDbType.Int. You may change it accordingly.
You must do this before calling myCommand.ExecuteReader(). Most likely, you'll put this line after myCommand.CommandText = "...";.

insert in sql using c#

this code is successfully inserting a new value in a SQL db, but only when I insert constant values.
I need help where it says **(?)** in the code below, where I want to insert new values without specifying constants in the code.
What I mean is, I want to be able to type any random value in output window and it gets inserted into the SQL db.
private void InsertInfo()
{
String strConnection = "Data Source=HP\\SQLEXPRESS;database=MK;Integrated Security=true";
SqlConnection con = new SqlConnection(strConnection);
string connetionString = null;
SqlConnection connection ;
SqlDataAdapter adapter = new SqlDataAdapter();
connetionString = #"Data Source=HP\SQLEXPRESS;database=MK;Integrated Security=true";
connection = new SqlConnection(connetionString);
string sql = "insert into record (name,marks) **values( ?))";**
try
{
connection.Open();
adapter.InsertCommand = new SqlCommand(sql, connection);
adapter.InsertCommand.ExecuteNonQuery();
MessageBox.Show ("Row inserted !! ");
}
catch (Exception ex)
{
MessageBox.Show(ex.ToString());
}
}
private void insert_Click(object sender, EventArgs e)
{
InsertInfo();
}
There is no need to use an adapter here; that is not helping you. Just:
var name = ...
var marks = ...
using(var conn = new SqlConnection(connectionString))
using(var cmd = conn.CreateCommand()) {
cmd.CommandText = "insert into record (name, marks) values (#name, #marks)";
cmd.Parameters.AddWithValue("name", name);
cmd.Parameters.AddWithValue("marks", marks);
conn.Open();
cmd.ExecuteNonQuery();
}
or with a tool like "dapper":
var name = ...
var marks = ...
using(var conn = new SqlConnection(connectionString)) {
conn.Open();
conn.Execute("insert into record (name, marks) values (#name, #marks)",
new {name, marks});
}
Those '?' are termed as parameters. From what I understand, you are wanting to use a parametrized query for your insert which is a good approach as they save you from chance of a SQL injection. The '?' sing in your query is used when you are using an
OLEDBConnection & Command object.
Normally, you would use '#' symbol to specify a parameter in your query. There is no need for an adapter. You just
//Bind parameters
// Open your Connection
// Execute your query
// Close connection
// return result
Parametrized queries 4 Guys from Rolla
MSDN: How to Protect from SQL injection in ASP.NET

Categories

Resources