How to Simplify C# query Execution? - c#

I am programmer in asp.net. I am using C#. I have written very lengthy code for query execution in each time. How to re-factor and organize the following code?
MySqlConnection connection = new MySqlConnection(connstring);
string query = "Select fo_region_Name from fo_region where fo_region_DeleteStatus=0";
MySqlCommand command = new MySqlCommand(query, connection);
MySqlDataReader reader;
connection.Open();
reader = command.ExecuteReader();
while (reader.Read())
{
ddl_Country.Items.Add(UppercaseFirst(reader[0].ToString()));
}
connection.Close();
query = "Select Fo_Nationality_Name from fo_Nationality a, Fo_region b where a.Fo_Nationality_Type=1 and "
+ "LEFT(a.Fo_Nationality_Code,2)=LEFT(b.fo_region_Name,2) and a.Fo_Nationality_DeleteStatus=0 and "
+ "b.fo_region_DeleteStatus=0 Union Select Fo_Nationality_Name from fo_nationality where Fo_Nationality_DeleteStatus=0";
command = new MySqlCommand(query, connection);
connection.Open();
reader = command.ExecuteReader();
while (reader.Read())
{
ddl_Nationality.Items.Add(UppercaseFirst(reader[0].ToString()));
}
connection.Close();
query = "select mcs_CreditCard_CardName from mcs_creditcard where mcs_CreditCard_DeleteStatus=0";
command = new MySqlCommand(query, connection);
connection.Open();
reader = command.ExecuteReader();
while (reader.Read())
{
ddl_CreditCard.Items.Add(UppercaseFirst(reader[0].ToString()));
}
connection.Close();

Some thoughts:
Use multiline strings to format your SQL statements.
There is no need to close and reopen the connection betwween each command execution.
There is also no need to create new connection and command objects (in this case)
If you have parameters on the command objects, it is easier to create new command objects, rather than clearing out the old parameters
Use var statements to have the C# compiler automatically determine the variable type for you.
Wrap objects that need to be disposed, in a using block.
using (var connection = new MySqlConnection(connstring)) {
connection.Open();
using (var command = new MySqlCommand()) {
MySqlDataReader reader;
command.CommandText = #"
SELECT fo_region_Name
FROM fo_region
WHERE fo_region_DeleteStatus=0
";
using (reader = command.ExecuteReader()) {
while (reader.Read()) {
ddl_Country.Items.Add(UppercaseFirst(reader[0].ToString()));
}
}
command.CommandText = #"
SELECT Fo_Nationality_Name
FROM fo_Nationality a,
Fo_region b
WHERE a.Fo_Nationality_Type = 1
AND LEFT(a.Fo_Nationality_Code,2) = LEFT(b.fo_region_Name,2)
AND b.fo_region_DeleteStatus=0
UNION SELECT Fo_Nationality_Name
FROM fo_nationality
WHERE Fo_Nationality_DeleteStatus=0
";
using (reader = command.ExecuteReader()) {
while (reader.Read()) {
ddl_Nationality.Items.Add(UppercaseFirst(reader[0].ToString()));
}
}
command.CommandText = #"
SELECT mcs_CreditCard_CardName
FROM mcs_creditcard
WHERE mcs_CreditCard_DeleteStatus = 0
";
using (reader = command.ExecuteReader()) {
while (reader.Read()) {
ddl_Nationality.Items.Add(UppercaseFirst(reader[0].ToString()));
}
}
}
}
With LINQ (add a using System.Data.Common statement):
using (reader = command.ExecuteReader()) {
/*while (reader.Read()) {
ddl_Country.Items.Add(UppercaseFirst(reader[0].ToString()));
}*/
ddl_Country.Items.AddRange((
from DbDataRecord row in reader
select new ListItem(
UppercaseFirst(reader.GetString(0))
)
).ToArray());
}

Maybe use can use EnterpriseLibrary, to reduce amount of code that deals with database.

Related

C# SQL Server database queries

I have written the following code to query stuff from a SQL Server database. The query in the first reader works, but not in the second. I just can't seem to figure out why as the approach is exactly the same in both readers. Any help is much appreciated.
The parameters for the commands are given in the function above which isn't in the code btw.
using (SqlConnection conn = new SqlConnection())
{
conn.ConnectionString = "...";
conn.Open();
SqlCommand command = new SqlCommand("SELECT stuff FROM table WHERE Belegnummer= #n and Belegjahr=#j", conn);
command.Parameters.Add(new SqlParameter("n", nr));
command.Parameters.Add(new SqlParameter("j", jahr));
using (SqlDataReader reader = command.ExecuteReader())
{
while (reader.Read())
{
r = reader.GetInt32(0);
}
}
command.Dispose();
SqlCommand command2 = new SqlCommand("SELECT stuff1, stuff2, stuff3 FROM sameTable WHERE BelID = #rnr", conn);
command2.Parameters.Add(new SqlParameter("rnr", r));
using (SqlDataReader reader2 = command2.ExecuteReader())
{
while (reader2.Read())
{
// variables are defined somewhere above
b = reader2.GetInt32(0);
j = reader2.GetInt32(1);
m = reader2.GetInt32(2);
}
}
}
Please post the error messages as well.
You may run into trouble with DbNull values. Check for DbNull before you parse the values with:
SqlReader.IsDBNull(column)
Or load the Data into a DataTable:
DataTable dt = new DataTable();
using (SqlDataReader reader = cmd1.ExecuteReader())
{
dt.Load(reader);
}

get common id numbers from sqldatabase table c#

I need to know how to get all the clientID that are #2 so i could get the programs they are assigned to...so far my code only gets the first clientID with #2 in it...
int progs;
string Command = #"select * from clientprogram where clientProgClientID = #clientID;";
using (MySqlConnection mConnection = new MySqlConnection(mycon))
{
mConnection.Open();
using (MySqlCommand cmd2 = new MySqlCommand(Command, mConnection))
{
cmd2.Parameters.Add(new MySqlParameter("#clientID", lblcID.Text));
using (MySqlDataReader reader = cmd2.ExecuteReader())
{
if (reader.Read())
{
progs = (int)reader["clientProgramID"];
cmbProgram.Items.Add(progs);
}
}
}
mConnection.Close();
}
Change
if (reader.Read())
to
while (reader.Read())
It seems it should be in a loop to add records recursively rather than just the first one
of course it only get the first result because you are reading it only once.
use while(reader.Read()) instead of if(reader.Read()).
while(reader.Read())
{
progs = (int)reader["clientProgramID"];
cmbProgram.Items.Add(progs);
}
change
if (reader.Read())
to
while(reader.Read())
side note; don't use select * when you only need single column data, use select Coumnname from yourtable
int progs;
string Command = #"select * from clientprogram where clientProgClientID = #clientID;";
using (MySqlConnection mConnection = new MySqlConnection(mycon))
{
mConnection.Open();
using (MySqlCommand cmd2 = new MySqlCommand(Command, mConnection))
{
cmd2.Parameters.Add(new MySqlParameter("#clientID", lblcID.Text));
using (MySqlDataReader reader = cmd2.ExecuteReader())
{
while (reader.Read()) // CHANGE TO THIS
{
progs = (int)reader["clientProgramID"];
cmbProgram.Items.Add(progs);
}
}
}
mConnection.Close();
}

Parameter SQL in C# doesn't work

I have this code and it does not work. Does anyone know why?
It did not return any data, but if run the query in SQL Server it returns the data.
using (SqlConnection connection = new SqlConnection(_dbContext.GetConnectionString()))
{
using (SqlCommand command = new SqlCommand())
{
StringBuilder stringQuery = new StringBuilder();
stringQuery.Append(" SELECT cd_material, ds_material");
stringQuery.Append(" FROM tbl_materiais");
stringQuery.Append(" WHERE ds_material like #Name");
command.Parameters.AddWithValue("#Name", "%" + name + "%");
command.CommandText = stringQuery.ToString();
command.CommandType = System.Data.CommandType.Text;
command.Connection = connection;
connection.Open();
using (SqlDataReader reader = command.ExecuteReader())
{
while (reader.Read())
{
_product = new ProductSell();
((IProduct)_product).ID = reader.GetFieldValue<int>(0);
((IProduct)_product).Name = reader.GetFieldValue<string>(1);
listProduct.ToList<IProduct>().Add(_product);
}
}
}
}
What is listProduct and why do you call its ToList<>()?
listProduct.ToList<IProduct>() returns a new instance of List<IProduct> that is forgotten after this line executes. Calling .Add(_product) on this returned list does not affect listProduct.
My problem stay here
while (reader.Read())
{
DoSomething();
}
reader.Read() never is read, my table is simple, have only attributes: cd_material(int), ds_material(varchar). And Exception not are triggered.
This query :
SELECT cd_material, ds_material FROM tbl_materiais WHERE ds_material = '%produto%'
Many rows are returned if in owner database ( sql management)

C# use a reader in another reader solution?

I need to get some mysql data into another mysql reader request anyway to workaround that I apparently can't have 2 readers open at the same time it will all end up in a datagrid
public void DBSelectPraktikanter(object sender)
{
string Command = "SELECT * FROM forlob WHERE firmaid = N'" + firmaid + "'";
MySqlConnection sqlConnection1 = new MySqlConnection(connectionString);
MySqlCommand command = new MySqlCommand(Command, sqlConnection1);
sqlConnection1.Open();
MySqlDataReader reader = command.ExecuteReader();
var items = new List<praktikanter>();
if (reader.HasRows)
{
while (reader.Read())
{
string praktikantid = String.Format("{0}", reader["praktikantid"]);
string Command2 = "SELECT * FROM praktikanter WHERE id = N'" + praktikantid + "'";
MySqlCommand command2 = new MySqlCommand(Command, sqlConnection1);
MySqlDataReader reader2 = command.ExecuteReader();
if (reader.HasRows)
{
while (reader2.Read())
{
Praktikant = String.Format("{0}", reader["Navn"]);
}
}
string Fra = String.Format("{0}", reader["fra"]);
string Til = String.Format("{0}", reader["til"]);
items.Add(new praktikanter(Praktikant, Fra, Til));
}
}
sqlConnection1.Close();
var grid = sender as DataGrid;
grid.ItemsSource = items;
}
Instead of nesting MySqlCommands and looping the first resultset to query again the database to collect all of your data you should really use one query. Also use the using-statement to ensure that the connection gets closed even on error and use sql-parameters to avoid sql-injection issues:
var items = new List<praktikanter>();
string sql = #"SELECT p.*, f. Navn
FROM praktikanter p INNER JOIN forlob f ON p.id = f.praktikantid
WHERE f.firmaid = #firmaid";
using (var con = new MySqlConnection(connectionString))
using (var command = new MySqlCommand(sql, con))
{
command.Parameters.Add(new MySqlParameter("#firmaid", MySqlDbType.VarChar).Value = firmaid);
con.Open();
using (var rd = command.ExecuteReader())
{
while (rd.Read())
{
string praktikant = rd.GetString("Navn");
string fra = rd.GetString("Fra");
string til = rd.GetString("Til");
items.Add(new praktikanter(praktikant, fra, til));
}
}
}

C# ASP.NET error: There is already an open datareader associated with this command which must be closed first

I keep getting this error
There is already an open datareader associated with this command which must be closed first.
at this line of code:
using (SqlDataReader rd = command.ExecuteReader())
I have tried to close all other SqlDataReader's in class but it didn't work.
public int SifreGetir(string pEmail) {
SqlCommand command = con.CreateCommand();
command.CommandText = #"SELECT Sifre FROM Kullanici WITH (NOLOCK) WHERE email=#email";
command.Parameters.Add("#email", SqlDbType.VarChar);
command.Parameters["#email"].Value = pEmail;
using (SqlDataReader rd = command.ExecuteReader())
{
rd.Read();
string pass = rd["Sifre"].ToString();
int p = Convert.ToInt32(pass);
return p;
}
}
Try implementing your code in the below format
using(SqlConnection connection = new SqlConnection("connection string"))
{
connection.Open();
using(SqlCommand cmd = new SqlCommand("your sql command", connection))
{
using (SqlDataReader reader = cmd.ExecuteReader())
{
if (reader != null)
{
while (reader.Read())
{
//do something
}
}
}
}
}
The using statement will ensure disposal of the objects at the end of the using block
try this:
public int SifreGetir(string pEmail) {
SqlConnection con = new SqlConnection("Your connection string here");
con.Open();
SqlDataAdapter da = new SqlDataAdapter();
DataSet ds = new DataSet();
SqlCommand command = new SqlCommand(#"SELECT Sifre FROM Kullanici WITH (NOLOCK) WHERE email=#email",con);
command.CommandType = CommandType.Text;
command.Parameters.Add("#email", SqlDbType.VarChar).Value = pEmail;
da.Fill(ds);
foreach(DataRow dr in ds.Tables[0].Rows)
{
string pass = dr["Sifre"].ToString();
int p = Convert.ToInt32(pass);
return p;
}
con.Close();
}
You have used Using Keyword for SQL Reader but There is nothing to take care of your command and connection object to dispose them properly. I would suggest to try disposing your Connection and command both objects by Using keyword.
string connString = "Data Source=localhost;Integrated " + "Security=SSPI;Initial Catalog=Northwind;";
using (SqlConnection conn = new SqlConnection(connString))
{
SqlCommand cmd = new;
cmd.CommandText = "SELECT ID, Name FROM Customers";
conn.Open();
using (SqlDataReader rd = command.ExecuteReader())
{
rd.Read();
string pass = rd["Sifre"].ToString();
int p = Convert.ToInt32(pass);
return p;
}
}

Categories

Resources