I am having trubble to get the stored values from my mdf. I can see they are there and all is working as suposed to untill i a want to get hold of them, I just cant. I have been trying for almost 48h and I just cant get it to work. I read tons of guides and other threads here but nothing seems to work for me. I guess I just have get my head around this way of accessing and mdf SQL database. I just want it to give up the secrets stored on specified row.
I am trying to access the three values stored on a numbered row(specified as int row) in a mdf file called Table1 and return them to the caller.
My code I have been fighting the last hours is this:
public static void loadAnimalData(int row, out string stringId, out string name, out double age)
{
int antal = AnimalsDBCount();
String connString = "Data Source=.\\SQLEXPRESS;AttachDbFilename=|path.to.db|DBList.mdf;Integrated Security=True;Connect Timeout=30;User Instance=True";
SqlConnection con = new SqlConnection(connString);
con.Open();
using (SqlCommand command = new SqlCommand("SELECT ID WHERE ID = " + row, con))
{
SqlDataReader reader = command.ExecuteReader();
while (reader.Read())
{
m_stringId = reader.GetString(0);
m_name = reader.GetString(1);
m_age = reader.GetDouble(2);
}
}
con.Close();
stringId = m_stringId;
name = m_name;
age = m_age;
}
I am lost here, I can't seem to get access to specied row or values, Where am I going wrong?
Might you want is;
m_stringId = reader[0].ToString();
m_name = reader[1].ToString();
m_age = reader[2].ToString();
SqlDataReader read rows, since you select one, you can't access others.
Provides a way of reading a forward-only stream of rows from a SQL
Server database.
You shoudl select other columns also like;
using (SqlCommand command = new SqlCommand("SELECT ID, NAME, AGE WHERE ID = " + row, con))
{
SqlDataReader reader = command.ExecuteReader();
while (reader.Read())
{
m_stringId = reader.GetInt32(0);
m_name = reader.GetString(1);
m_age = reader.GetString(2);
}
}
You are only selecting the ID (which is already known), not any other columns.
Try changing:
"SELECT ID WHERE ID = " + row
to
"SELECT ID, NAME, AGE WHERE ID = " + row
You may wish to select your columns in your select statement
using (SqlCommand command = new SqlCommand("SELECT ID, name, age from TableOfInterest WHERE ID = " + row, con))
Then you can use them in your Reader
Related
This is my code, and I want to be able to search for a name, and then pull from the database the name, status, member_id into the textboxes in my form.
I got the name to work but how do I get the other columns and parse the output into the textboxes with the additional columns (member_id, status)? Let's say the other textboxes have the standard name such as textbox2, 3, 4...
string connetionString = null;
SqlConnection connection;
SqlCommand command;
string sql = null;
string sql1 = null;
SqlDataReader dataReader;
connetionString = "Data Source=......"
sql = "SELECT NAME FROM Test_Employee WHERE Name LIKE '" + textBox1.Text.ToString() + "%'";
connection = new SqlConnection(connetionString);
{
connection.Open();
command = new SqlCommand(sql, connection);
dataReader = command.ExecuteReader();
while (dataReader.Read())
{
textBox9.Text = dataReader[0].ToString();
textBox7.Text = dataReader[0].ToString();
}
connection.Close();
}
Are the fields Member_Id and Status also in the table Test_Employee? You can add them in your Select statement and get them from your SqlReader, like the code below (assuming you are using c#7 and below). You may copy and paste this code.
var connectionString = "";
var sql = #"SELECT TOP 1 Name, Member_Id, Status
FROM Test_Employee
WHERE Name LIKE #name + '%'";
using (var connection = new SqlConnection(connectionString))
using (var command = new SqlCommand(sql, connection))
{
command.Parameters.Add("name", SqlDbType.NVarChar, 100).Value = textBox1.Text.ToString();
connection.Open();
var reader = command.ExecuteReader();
if (reader.Read())
{
textBox9.Text = dataReader["Name"].ToString();
textBox7.Text = dataReader["Name"].ToString();
textBox2.Text = dataReader["Member_Id"].ToString();
textBox3.Text = dataReader["Status"].ToString();
}
}
You will notice that instead of including the Textbox1.Text's value in your Select statement, it is added as a parameter in the SQLCommand object's Parameters. In this way your query is protected from SQL Injection. If you want to learn more, you can search c# sqlcommand parameters and why it is very important to build data access code this way.
Also, notice that I added Top 1 in your Select statement, and instead of using while, I am using if. This is because a textbox can only hold 1 result at a time in a comprehensible way. If you meant to show multiple results clearly, you need to use a different control other than a TextBox.
The using statements allow you to dispose the connection, so you don't have to call connection.Close().
I am trying to first create a new row in my SQL Compact Edition database via C# and then I want to update the same row with information in my radiobuttons. I have an "ID" column in the database which is auto incremental.
So I tried to assign its value to a variable using ##Identity and call it in the update query but it doesn't work. I've tried MAX to find the max value in ID column which will be the latest row but it still didn't work. Here's my code.
con.Open();
string sqlAdd = "Insert into MembersTable ([First Name],Surname,[Middle Name])
Values('"+txtFirstName.Text+"','"+txtSurname.Text+"','"+ txtMiddleName.Text+"')";
string IDIdentifier = "Select ##Identity AS TempID";
string sqlgenderM = "Update MembersTable set Gender='M' where ID='" + DC.ID + "'";
string sqlgenderF = "Update MembersTable set Gender='F' where ID='" + DC.ID + "'";
com = new SqlCeCommand(sqlAdd, con);
com.ExecuteNonQuery();
SqlCeCommand com1 = new SqlCeCommand(IDIdentifier, con);
SqlCeDataReader dr1 = com1.ExecuteReader();
if (dr1.Read())
{
DC.ID = dr1["TempID"].ToString();
}
{
if (rbGenderMale.Checked == true)
{
SqlCeCommand gendercom = new SqlCeCommand(sqlgenderM, con);
gendercom.ExecuteNonQuery();
}
else if (rbGenderFemale.Checked == true)
{
SqlCeCommand gendercom = new SqlCeCommand(sqlgenderF, con);
gendercom.ExecuteNonQuery();
}
}
The fields (First Name, Middle Name, Surname) get updated but the Gender columns don't. What am I doing wrong?
Thanks to #Soner I used:
int.TryParse(dr1["TempID"].ToString(), out Identity);
string IdentityS = Identity.ToString();
and replaced DC.ID with IdentityS
Now it works perfectly.
I need to know what order number has been written to the database. To achieve this I use the SQL expression EXECUTESCALAR.
I debugged the program and monitored the database. The record is written once into the Database when I execute the 2nd Command it writes the same record a 2nd time. Can you help me out what I need to change so it does not write 2 records and I get my Order number back?
This is my code:
public static int CreateDocumentNumber(string userId, string todaysDate, decimal docprice, decimal docpaid, int packageId, int orderstatus)
{
int orderId = 0; //return value order Id
//create order
string connectionString = ConfigurationManager.ConnectionStrings["conString"].ConnectionString;
string insertSql = "INSERT INTO [dbo].[LD_Orders](TD_OrdUserID, TD_OrdDate, TD_OrdCost, TD_OrdPaid, TD_OrdPackage, TD_OrdStatus)" +
" VALUES (#UserId, #Date, #Cost, #Paid, #Package, #Status);SELECT SCOPE_IDENTITY()";
using (SqlConnection myConnection = new SqlConnection(connectionString))
{
myConnection.Open();
SqlCommand myCommand = new SqlCommand(insertSql, myConnection);
myCommand.Parameters.Add("#UserId", SqlDbType.VarChar).Value = userId;
myCommand.Parameters.Add("#Date", SqlDbType.Date).Value = todaysDate;
myCommand.Parameters.Add("#Cost", SqlDbType.Decimal).Value = docprice;
myCommand.Parameters.Add("#Paid", SqlDbType.Decimal).Value = docpaid;
myCommand.Parameters.Add("#Package", SqlDbType.Int).Value = packageId;
myCommand.Parameters.Add("#Status", SqlDbType.Int).Value = orderstatus;
myCommand.ExecuteNonQuery(); <---- FIRST RECORD WRITTEN
// time to collect the last order id
orderId = Convert.ToInt32(myCommand.ExecuteScalar()); <---- SECOND RECORD WRITTEN
myConnection.Close();
}
return orderId;
}
Your code should work if you remove the line myCommand.ExecuteNonQuery();
Both ExecuteNonQuery() and ExecuteScalar() send the command to SQL server, the only difference is how they treat the result. Basically, you are executing two INSERT statements, which you don't need.
On a side note, it is very seldom justified to do hardcore ADO.NET coding nowadays. You typically save a lot of time if you use some ORM, like Entity Framework or my personal favorite, Dapper.NET.
Here's how you could rewrite your entire function using Dapper:
public static int CreateDocumentNumber(string userId, string todaysDate, decimal docprice, decimal docpaid, int packageId, int orderstatus)
{
//create order
string connectionString = ConfigurationManager.ConnectionStrings["conString"].ConnectionString;
string insertSql = "INSERT INTO [dbo].[LD_Orders](TD_OrdUserID, TD_OrdDate, TD_OrdCost, TD_OrdPaid, TD_OrdPackage, TD_OrdStatus)" +
" VALUES (#UserId, #Date, #Cost, #Paid, #Package, #Status);SELECT SCOPE_IDENTITY()";
using (SqlConnection myConnection = new SqlConnection(connectionString))
{
myConnection.Open();
int orderId = myConnection.Query<int>(
insertSql,
new {
UserId = userId,
Date = todaysDate,
Cost = docprice,
Paid = docpaid,
Package = packageId,
Status = orderstatus
}).Single();
}
return orderId;
}
I have a MYSQL database and I am trying to get the first name and last name of every student I put in the database and dynamically show them as a label in my WPF form, here is what I got so far
string connstr = "Server=localhost; Database=login; UID=root; Pwd=password";
MySqlConnection connc = new MySqlConnection(connstr);
MySqlCommand command;
connc.Open();
// Label[] labels = new Label[n];
try
{
command = connc.CreateCommand();
command.CommandText = "SELECT First_name, Last_name FROM Students";
command.ExecuteReader();
MessageBox.Show("S");
}
catch (Exception ex)
{
MessageBox.Show("something went wrong: " + ex.ToString());
}
finally
{
connc.Close();
}
So how could I add all my entry's in the database to a label?
ExecuteNonQuery method just executes your query. You can't get your values with it.
You need to use ExecuteReader at least to get your values. You can read your column values in a while statement with MySqlDataReader.Read() method. This method reads your query row by row.
Also use using statement to dispose your MySqlConnection, MySqlCommand and MySqlDataReader.
using(MySqlConnection connc = new MySqlConnection(connstr))
using(MySqlCommand command = new MySqlCommand("SELECT First_name, Last_name FROM Students", connc))
{
using(MySqlDataReader reader = command.ExecuteReader())
{
while (reader.Read())
{
// reader[0] gets you first column which is First_name
// reader[1] gets you second column which is Last_name
// Do your label assingments..
}
}
}
First , ExecuteNonQuery() method is used for DML statements INSERT ,UPDATE , DELETE .
Use ExecuteReader() method.
command = connc.CreateCommand();
command.CommandText = "SELECT First_name, Last_name FROM Students";
SqlDataReader dr = command.ExecuteReader();
string result=string.Empty;
while(dr.Read())
{
result += dr["First_name"].ToString() + " " + dr["Last_name"].ToString();
}
lableId.Content=result;
I have problem with my code specifically on the update code.
private void updatebtn_Click(object sender, EventArgs e)
{
String Fname = fnametb.Text;
String Lname = lnametb.Text;
String Age = agetb.Text;
String Address = addresstb.Text;
String Course = coursetb.Text;
{
connection.Open();
OleDbCommand select = new OleDbCommand();
select.Connection = connection;
select.CommandText = "Select * From Accounts";
OleDbDataReader reader = select.ExecuteReader();
while (reader.Read())
{
OleDbCommand insert = new OleDbCommand("UPDATE Accounts SET Firstname=#Fname, Lastname=#Lname, Age=#Age, Address=#Address, Course=#Course WHERE Lastname='"+ reader[2].ToString()+"'", connection);
insert.Parameters.Add("#Fname", OleDbType.VarChar).Value = Fname;
insert.Parameters.Add("#Lname", OleDbType.VarChar).Value = Lname;
insert.Parameters.Add("#Age", OleDbType.VarChar).Value = Age;
insert.Parameters.Add("#Address", OleDbType.VarChar).Value = Address;
insert.Parameters.Add("#Course", OleDbType.VarChar).Value = Course;
insert.ExecuteNonQuery();
fnametb.Clear();
lnametb.Clear();
agetb.Clear();
addresstb.Clear();
coursetb.Clear();
listBox1.Items.Clear();
searchtb.Clear();
}
connection.Close();
}
}
above is my code. Whenever I update one record, all the records in the table are affected.I think there's something wrong with the reader.
Please help, thanks.
You are selecting all records,
select.CommandText = "Select * From Accounts";
then you loop the result with the reader.
while (reader.Read())
Then you update each record.
String sql = "UPDATE Accounts SET Firstname=#Fname, Lastname=#Lname, Age=#Age, Address=#Address, Course=#Course WHERE Lastname='"+ reader[2].ToString()+"'";
OleDbCommand insert = new OleDbCommand(sql, connection);
So why are you surprised?
I'm not sure what you actually want. Maybe you have forgotten to add a WHERE clause to your first select and you want to use lnametb.Text. But then the first select is simply redundant and you could use the WHERE for the update-command:
String sql = "UPDATE Accounts SET Firstname=#Fname, Lastname=#Lname, Age=#Age, Address=#Address, Course=#Course WHERE Lastname=#LastName";
insert.Parameters.Add("#LastName", OleDbType.VarChar).Value = lnametb.Text;
Btw, why have you named your update-command insert?
The problem is that for some reason you execute the update in a loop for every record that the reader finds. Naturally, the reader would find every single last name that you have in the table, so the update is going to change every single record!
You need to remove the loop, remove the reader, and change the update command to use the last name from one of the entry boxes on the screen:
connection.Open();
OleDbCommand update = new OleDbCommand("UPDATE Accounts SET Firstname=#Fname, Age=#Age, Address=#Address, Course=#Course WHERE Lastname=#Lname", connection);
update.Parameters.Add("#Fname", OleDbType.VarChar).Value = Fname;
update.Parameters.Add("#Lname", OleDbType.VarChar).Value = Lname;
update.Parameters.Add("#Age", OleDbType.VarChar).Value = Age;
update.Parameters.Add("#Address", OleDbType.VarChar).Value = Address;
update.Parameters.Add("#Course", OleDbType.VarChar).Value = Course;
update.ExecuteNonQuery();
connection.Close();
Of course this does not let you update the last name: for that you need to supply some sort of an independent student ID, and use it in the WHERE clause of your UPDATE instead of the last name.
You are iterating all records from the table and setting to one value..
it is wrong access only the matching record and update it