May I know what's wrong with my statement? I receive a syntax error. Been trying to find out what's wrong all day. :(
cmd.CommandText = "INSERT INTO LogIn(Username,Password) VALUES('" + AddUsernameTextBox.Text + "','" + AddPasswordTextBox.Text + "')";
cmd.CommandText = "INSERT INTO LogIn([Username],[Password]) VALUES('" + AddUsernameTextBox.Text + "','" + AddPasswordTextBox.Text + "')";
This code will help if the error is due to reserved keywords :- username and password. Please quote the error if this is not the case .
command.CommandText = "INSERT INTO Login([Username],[Password]) VALUES(#Username, #Password)";
//Not sure how you create your commands in your project
//here I'm using the ProviderFactory to create instances of provider specific DbCommands.
var parameter = dbProviderFactory.CreateParameter();
parameter.DbType = System.Data.DbType.String;
parameter.ParameterName = "#Username";
parameter.Value = AddUsernameTextBox.Text;
command.Parameters.Add(parameter);
parameter = dbProviderFactory.CreateParameter();
parameter.DbType = System.Data.DbType.String;
parameter.ParameterName = "#Password";
parameter.Value = AddPasswordTextBox.Text;
command.Parameters.Add(parameter);
Below is a more complete code sample of using ConnectionStringSettings and DbProviderFactory etc. This is not going to solve your problem, but this is the way to do data access if you're using ADO.NET core as you seem to be doing in your sample.
ConnectionStringSettings connectionStringSettings = ConfigurationManager.ConnectionStrings["SomeConnectionName"];
if (connectionStringSettings == null)
throw new Exception("Application config file does not contain a connectionStrings section with a connection called \"SomeConnectionName\"");
DbProviderFactory dbProviderFactory = DbProviderFactories.GetFactory(connectionStringSettings.ProviderName);
using (var dbConnection = dbProviderFactory.CreateConnection())
{
dbConnection.ConnectionString = connectionStringSettings.ConnectionString;
dbConnection.Open();
using (var command = dbConnection.CreateCommand())
{
command.CommandText = "INSERT INTO Login([Username],[Password]) VALUES(#Username, #Password)";
var parameter = dbProviderFactory.CreateParameter();
parameter.DbType = System.Data.DbType.String;
parameter.ParameterName = "#Username";
parameter.Value = AddUsernameTextBox.Text;
command.Parameters.Add(parameter);
parameter = dbProviderFactory.CreateParameter();
parameter.DbType = System.Data.DbType.String;
parameter.ParameterName = "#Password";
parameter.Value = AddPasswordTextBox.Text;
command.Parameters.Add(parameter);
var dbTransaction = dbConnection.BeginTransaction();
try
{
command.ExecuteNonQuery();
dbTransaction.Commit();
}
catch (Exception)
{
dbTransaction.Rollback();
throw;
}
}
}
the app.Config file that the code above relies on would look like this the following. Of course only the connectionStrings section in the config file is important in this context
<?xml version="1.0" encoding="utf-8" ?>
<configuration>
<connectionStrings>
<add name="SomeConnectionName" providerName="System.Data.OleDb" connectionString="Your Provider Specific Connection String" />
</connectionStrings>
</configuration>
The Best way is to use Parameters: '#'
By this your code will look much more clearer and easy to understand. And makes your Application more secure.
try this code:
using (var con = new OleDbConnection(_constring))
{
con.Open();
using (
var cmd =
new OleDbCommand(
"UPDATE LogIn SET Username=#Username, Password=#Password WHERE (ID = #Id)",
con))
{
try
{
cmd.Parameters.AddWithValue("#Username",EditUsernameTextBox.Text);
cmd.Parameters.AddWithValue("#Password",EditPasswordTextBox.Text);
cmd.Parameters.AddWithValue("#Id",IDTextBox.Text);
cmd.ExecuteNonQuery();
}
catch (Exception ex)
{
throw;
}
finally
{
con.Close();
}
}
Regards!
Please protect the single quotes. Also, you may need a closing semicolon in the Access SQL string.
cmd.CommandText = "INSERT INTO LogIn(Username,Password) VALUES('" + AddUsernameTextBox.Text.Replace("'","''") + "','" + AddPasswordTextBox.Text.Replace("'","''") + "');";
It is of course only 100% better to use parameterized queries; from you other questions is this C#/Visual Studio against MS Access through OLE/Jet?
Is ID column an integer? If not you need to wrap values in single quotes, too.
Also, try removing the parentheses.
Most likely, the value in IDTextBox.text is not numeric...
But like Daniel points out, this is very vulnerable to SQL inject..
What would happen if I typed:
' ; DROP TABLE login
in the EditUserNameTextBox field
Check if this works. You were missing single quotes for the value in your WHERE statement:
"UPDATE
LogIn
SET
Username = '" + EditUsernameTextBox.Text + "'
,Password = '" + EditPasswordTextBox.Text + "'
WHERE
(ID = '" + IDTextBox.Text + "')";
Plus, make sure, as Daniel White mentioned, you take care of any SQL Injection.
You missed a pair of apostrophes, if your ID is non-numeric:
WHERE (ID ='" + IDTextBox.Text + "')";
Do the values of EditUsernameTextBox.Text or EditPasswordTextBox.Text themselves have quotes? This will bollix up the SQL.
If so, you'll need to escape them. or don't use string concatenation as pointed out already...
And have you printed the statement out to see what it looks like as requested...?
Related
I know plenty of people have these issues, and I've actually tried to implement some of the suggestions to my code, however I'm getting errors that just don't make sense to me. This is my first time implementing database calls to my code. Can someone please tell me what I'm doing wrong? The following error pops up: ERROR: Invalid object name 'Main'. This is actually triggered by my exception so at least something is working. Otherwise, I don't know what the issue is. On the DB end, I have (username VARCHAR, email VARCHAR and number NCHAR) Please see the code below
static string path = Path.GetFullPath(Environment.CurrentDirectory);
static string databaseName = "u_DB.mdf";
string connectionString = #"Data Source=(localdb)\MSSQLLocalDB;AttachDbFilename=" + path + #"\" + databaseName + "; Integrated Security=True;";
private void button1_Click(object sender, EventArgs e)
{
// string query = "INSERT INTO UserInfo '" + textBox1.Text + "' and password = '" + textBox2.Text + "'";
string query = "insert into Main ([username], [email], [number]) values(#username,#email,#number)";
using (SqlConnection con = new SqlConnection(connectionString))
{
try
{
con.Open();
using (SqlCommand cmd = new SqlCommand(query, con))
{
cmd.Parameters.Add("#username", SqlDbType.VarChar).Value = textBox3.Text;
cmd.Parameters.Add("#email", SqlDbType.VarChar).Value = textBox2.Text;
cmd.Parameters.AddWithValue("#number", SqlDbType.VarChar).Value = textBox1.Text;
int rowsAdded = cmd.ExecuteNonQuery();
if (rowsAdded > 0)
MessageBox.Show("Added to Database");
else
MessageBox.Show("Nothing was added");
}
}
catch (Exception ex)
{
MessageBox.Show("ERROR: " + ex.Message);
}
con.Close();
}
}
Firstly, as Chetan assumed, do you have a main table?
The syntax of the query you are using is :
INSERT INTO table_name (column1, column2, column3, ...)
VALUES (value1, value2, value3, ...);
Furthermore,
AddWithValue(string parameterName, object value (<== The actual value to insert!));
in your case
AddWithValue("#number", textBox1.Text);
is enough.
Here are some simple codes that search for the value in TargetColumn where SourceColumn = SourceValue.
Here are these codes:
string cmdText = "select * from " + TableName + " where " + SourceColumn + " = '" + SourceValue + "'";
SqlCommand dbCommand = new SqlCommand(cmdText, dbConnection);
SqlParameter sqlParam = new SqlParameter("#" + SourceColumn, SourceValue);
dbCommand.Parameters.Add(sqlParam);
SqlDataReader dbReader = dbCommand.ExecuteReader();
dbReader.Read();
string _targetValue = dbReader[TargetColumn].ToString();
dbReader.Close();
dbCommand.Dispose();
return _targetValue;
And my questions are:
I passed SourceColumn and SourceValue to SqlCommand using SqlParameter, will this make it SQL injection proof?
Do I need to use TargetColumn together with SqlParameter too for SQL safety purpose? (but it is for SqlDataReader)
If I use SqlParameter for SqlCommand, do I still need to compose a command text in a string and pass it to SqlCommand before SqlParameter is used?
Why do I need to add an "#" for SourceColumn? (I just followed the tutorial and added it) And why SourceValue doesn't need an "#"?
The above codes works well to return the expected value, but I'm so not sure about the above questions.
Thanks very much!
string Update = "UPDATE VehicleReport" +
"SET VehicleReg ='"+textBox1.Text+"',CurrentOdometer ='"+textBox5.Text+"',NextService ='"+textBox6.Text+"'" +
"WHERE Vehiclenum ='"+comboBox1.Text+"' ;";
try
{
SqlConnection conn = new SqlConnection("Data Source=(local);Initial Catalog=FleetTrackingDatabase;Integrated Security=SSPI");
conn.Open();
SqlCommand cmd = new SqlCommand(Update, conn);
cmd.ExecuteNonQuery();
conn.Close();
MessageBox.Show("Updated");
conn.Close();
}
catch (System.Exception f)
{
MessageBox.Show(f.Message, "ERROR");
}
At least this is not correct:
string Update = "UPDATE VehicleReport" + "SET ...
you need to add a space between VehicleReport and Set
string Update = "UPDATE VehicleReport " + "SET....
Add spaces
"UPDATE VehicleReport" +
" SET VehicleReg ='"+textBox1.Text+"',CurrentOdometer ='"+textBox5.Text+"',NextService='"+textBox6.Text+"'" +
" WHERE Vehiclenum ='"+comboBox1.Text+"' ;";
There is missing space after table name :
string Update = "UPDATE VehicleReport"
string Update = "UPDATE VehicleReport "
and the same before WHERE
Can you try this,
string Update = "UPDATE VehicleReport SET VehicleReg ='"+textBox1.Text+"',CurrentOdometer ='"+textBox5.Text+"',NextService ='"+textBox6.Text+"'" + " WHERE Vehiclenum ='"+comboBox1.Text+"' ;";
I'm really shocked there are 4 answers but nobody mentioned about parameterized sql and SQL Injection attacks but anyway..
As others mentioned, you need spaces before your SET and WHERE words.
But more more more important is, DON'T USE THIS WAY. When you use string concatenations in your queries, your code will be open for SQL Injection. Instead of this, you should always use parameterizezd queries.
For example;
string Update = "UPDATE VehicleReport SET VehicleReg = #vehiclereg, CurrentOdometer = #current, NextService = #next WHERE Vehiclenum = #vehiclenum;";
SqlCommand cmd = new SqlCommand(Update, conn);
cmd.Parameters.AddWithValue("#vehiclereg", textBox1.Text);
cmd.Parameters.AddWithValue("#current", textBox5.Text);
cmd.Parameters.AddWithValue("#next", textBox6.Text);
cmd.Parameters.AddWithValue("#vehiclenum", comboBox1.Text);
I am having some trouble with my update() method. The idea is that the user Provides a recipe name, ingredients, instructions and then selects an image using Filestream.
Once the user clicks 'Add Recipe' this will call the update method, however as things stand I am getting an error which is mentioning the contents of the text box:
Here is the update() method code:
private void updatedata()
{
// filesteam object to read the image
// full length of image to a byte array
try
{
// try to see if the image has a valid path
if (imagename != "")
{
FileStream fs;
fs = new FileStream(#imagename, FileMode.Open, FileAccess.Read);
// a byte array to read the image
byte[] picbyte = new byte[fs.Length];
fs.Read(picbyte, 0, System.Convert.ToInt32(fs.Length));
fs.Close();
//open the database using odp.net and insert the lines
string connstr = #"Server=mypcname\SQLEXPRESS;Database=RecipeOrganiser;Trusted_Connection=True";
SqlConnection conn = new SqlConnection(connstr);
conn.Open();
string query;
query = "insert into Recipes(RecipeName,RecipeImage,RecipeIngredients,RecipeInstructions) values (" + textBox1.Text + "," + " #pic" + "," + textBox2.Text + "," + textBox3.Text + ")";
SqlParameter picparameter = new SqlParameter();
picparameter.SqlDbType = SqlDbType.Image;
picparameter.ParameterName = "pic";
picparameter.Value = picbyte;
SqlCommand cmd = new SqlCommand(query, conn);
cmd.Parameters.Add(picparameter);
cmd.ExecuteNonQuery();
MessageBox.Show("Image successfully saved");
cmd.Dispose();
conn.Close();
conn.Dispose();
Connection();
}
}
catch (Exception ex)
{
MessageBox.Show(ex.Message);
}
}
Can anyone see where I have gone wrong with the insert into Recipes query or suggest an alternative approach to this part of the code?
Your code is open to SQL Injection, but probably your error comes from some text that contains a single quote (the instructions fields for example) and this break your command string build using concatenating the user input.
EDIT
As someone pointed in comment the error is caused by the missing quotes around your textboxes. But while easy to fix that's not the way to go because it is wrong to fix the error adding the missing quotes. It is just postponig the problem leaving a big security hole waiting to be exploited.
A parameterized query could avoid all this mess.
string connstr = "....";
string query = "insert into Recipes(RecipeName,RecipeImage,RecipeIngredients,RecipeInstructions) " +
"values (#name, #pic, #ing, #instr)";
using(SqlConnection conn = new SqlConnection(connstr))
using(SqlCommand cmd = new SqlCommand(query, conn))
{
conn.Open();
SqlParameter picparameter = new SqlParameter();
picparameter.SqlDbType = SqlDbType.Image;
picparameter.ParameterName = "#pic";
picparameter.Value = picbyte;
cmd.Parameters.Add(picparameter);
cmd.Parameters.AddWithValue("#name", textbox1.Text);
cmd.Parameters.AddWithValue("#ing", textbox2.Text);
cmd.Parameters.AddWithValue("#instr", textbox3.Text);
cmd.ExecuteNonQuery();
MessageBox.Show("Image successfully saved");
}
Since you using string concatenations, you probably missed a quote or you put an extra quote or missed a comma or put extra comma etc etc....
Don't use this way!
Your error doesn't look obviously but you should always use parameterized queries. This kind of string concatenations are open for SQL Injection attacks.
query = "insert into Recipes(RecipeName,RecipeImage,RecipeIngredients,RecipeInstructions) values (#p1, #pic, #p3, #p4)";
SqlCommand cmd = new SqlCommand(query, conn);
cmd.Parameters.AddWithValue(#p1, textBox1.Text);
cmd.Parameters.AddWithValue(#pic, textBox1.Text);
cmd.Parameters.AddWithValue(#p3, textBox1.Text);
cmd.Parameters.AddWithValue(#p4, picparameter);
try this
query = "insert into Recipes(RecipeName,RecipeImage,RecipeIngredients,RecipeInstructions) values ('" + textBox1.Text + "'," + " #pic" + ",'" + textBox2.Text + "','" + textBox3.Text + "')";
I have some trouble with the SqlDataReader:
public string GetVareNavn(string streg)
{
string navn = "";
SqlConnection myCon = DBcon.getInstance().conn();
string query =
"SELECT Navn FROM Vare WHERE Stregkode = ) Values('" + streg + "')";
myCon.Open();
SqlCommand com = new SqlCommand(query, myCon);
Console.WriteLine("navn: "+navn);
SqlDataReader dr = com.ExecuteReader();
if (dr.Read())
{
navn = dr.GetString(1);
}
myCon.Close();
return navn;
}
It throws an exception at com.ExecutiveReader(); and the exception is:
Incorrect syntax near ')'.
I don't know why this one doesn't work right now, because I've used it in another project.
Your query looks like it was copied from something that used to be an INSERT statement; you don't need the VALUES... clause at the end of the statement. Try changing your query to:
string query =
"SELECT Navn FROM Vare WHERE Stregkode = #streg";
Then modify this code to use the parameter:
SqlCommand com = new SqlCommand(query, myCon);
com.Parameters.AddWithValue("#streg", streg);
It doesn't work because your SQL is broken:
SELECT Navn FROM Vare WHERE Stregkode = ) Values('" + streg + "')"
What did you expect that WHERE clause to do, and what values are you trying to use? It looks like you've got a broken copy/paste from an update command.
Additionally, you shouldn't put values into your SQL like that anyway - you should use parameterized queries to avoid SQL injection attacks (and to avoid formatting issues etc).
Ya, surely it will give. Why you put the Values in your select query? which is wrong syntax, Try Now.
string query = "SELECT Navn FROM Vare WHERE Stregkode = '" + streg + "'";