Use Value of ASP.NET TextBox in SQL SELECT Query - c#

Im looking at ASP.NET and I want to be able to use a value that a user types in a TextBox in a SELECT query to get that record.
For example, user types "1234" in the TextBox, and the SQL SELECT query gets the record with primary key value "1234" from the database and displays it on the page. Is this possible (programmatically or not)? Im using C# for my ASP.NET site as well. If you could point me in the right direction I'd really appreciate it.

Here is a sample code snippet to get you started. Basically, you establish the connection and supply the textbox.Text value into the command's Parameters collection.
using (SqlConnection thisConnection = new SqlConnection(ConfigurationManager.ConnectionStrings["YourSQLConnectionString"].ConnectionString))
{
SqlCommand queryCommand = thisConnection.CreateCommand();
try
{
// Open Connection
thisConnection.Open();
queryCommand.CommandText = #"select * from [YourTable] where id = #id";
queryCommand.Parameters.AddWithValue("#id", this.ID.Text);
SqlDataReader dr = queryCommand.ExecuteReader();
if (dr.Read())
this.message.Text = dr["id"].ToString();
else
this.message.Text = "ID not found";
}
catch (Exception ex)
{
this.message.Text = ex.Message;
}
}
}

You need an ORM (Object Relational Mapper) like Entity Framework, Dapper ..etc. To map your objects (in your application) with the database objects (tables, views, sp ..etc.). Then, you can (from your application) query your database, update, delete, insert operation.
Then, from your code behind, you can get the selected value, and use ORM to process that value on the database.
This is basically what you need. The rest is a learning curve !

Related

Connecting different tables to different items in combo box in C#

Good afternoon all,
I was hoping someone can point me in the right direction with this. I am currently working on a project and I am using an Access file as a database. I am trying to figure out how to populate items in my combobox from the different tables I have inside of my access database. I am using C# and Access 2016. I have tried to use some other examples and found that I am not looking in the right direction.
Edit:
I may have been a bit vague in this question. I have around 7 tables all with different names "ESC,AJJH,etc." in a Access file and I need to have the table names populate my combobox so when the user selects the combo box they can manipulate the data that's within the selected table. I hope this is more clear, I apologize if not.
Thank you!
private void Form1_Load(object sender, EventArgs e)
{
using (var connection = new OleDbConnection())
{
connection.ConnectionString =
#"Provider=Microsoft.ACE.OLEDB.12.0;Data Source=C:\Users\grosales\Documents\rhg\RHG\Used.accdb;Jet OLEDB:Database Password = MyDbPassword;";
try
{
connection.Open();
OleDbCommand command = new OleDbCommand();
command.Connection = connection;
string query = "select * from Tables";
command.CommandText = query;
OleDbDataReader reader = command.ExecuteReader();
while(reader.Read())
{
schoolcombo.Items.Add(reader);
}
}
catch (Exception ex)
{
MessageBox.Show("Connection Failed\r\n\r\n" + ex.Message);
}
}
You can use DbConnection. GetSchema to get the list of tables.
display the list of tables in access database using c#
It is not so clear what you want. But supposing that your tables have the same kind of columns. You could make use of UNION statement:
string query = "select field1, field2 from Table1 UNION select field1, field2 from Table2"; //AND SO ON

Creating Registration form in c# with mysql

Hello so i m creating a registration form in C# with MySql so it connects to the database and everything but i get this error Napaka pri registraciji Unknown column " in 'field list' the translation of Napaka pri registraciji means Error at registering i just have it in my language. I get this error when i insert data in textboxes and press Register..
the code:
private void btn_Reg_Click(object sender, EventArgs e)
{
MySqlConnection dataConnection = new MySqlConnection();
dataConnection.ConnectionString = "datasource=localhost;port=3306;username=root;password=";
dataConnection.Open();
MySqlTransaction transakcija = dataConnection.BeginTransaction();
MySqlCommand dataCommand = new MySqlCommand();
dataCommand.Connection = dataConnection;
dataCommand.Transaction = transakcija;
try
{
dataCommand.CommandText = "Insert INTO lr.users (upIme,geslo) VALUES (`"+this.tB_upIme.Text+"`,`"+this.tB_geslo.Text+"`)";
dataCommand.CommandType = CommandType.Text;
dataCommand.ExecuteNonQuery();
transakcija.Commit();
MessageBox.Show("Registracija uspešna!");
}
catch (Exception eks)
{
transakcija.Rollback();
MessageBox.Show("Napaka pri registraciji\n" + eks.Message);
}
finally
{
dataCommand.Connection.Close();
}
}
There are two things I immediately see wrong here...
First, you're using back ticks to wrap your values. In MySQL Back ticks represent database objects, so the query is looking for objects named by those values instead of using the values themselves. So instead of this:
`"+this.tB_upIme.Text+"`
You'd want this:
'"+this.tB_upIme.Text+"'
Second, and vastly more importantly, your code is wide open to SQL injection attacks. You'll want to use query parameters, not direct string concatenation. While it may look like you're just putting values into the query string, you're actually taking user input and treating it as executable code in your query string, which means users can run any arbitrary code they want on your database.
First, add parameters to your query:
"Insert INTO lr.users (upIme,geslo) VALUES (#upIme, #geslo)"
(You'll notice this also makes the query a heck of a lot cleaner and easier to read.) Then add your parameters to the command:
dataCommand.Parameters.AddWithValue("#upIme", this.tB_upIme.Text);
dataCommand.Parameters.AddWithValue("#geslo", this.tB_geslo.Text);
Then when you execute that command it will treat the user-input values as values instead of as executable code.
Change to single quotes ' in the values.
dataCommand.CommandText =
"Insert INTO lr.users (upIme,geslo)
VALUES ('"+this.tB_upIme.Text+"','"+this.tB_geslo.Text+"');";

.NET MySQL Data Reader Select Function?

It has been a long time since I have used .NET, but thankfully have almost finished writing a tool to compare an sqlite and mysql database. I am running into an issue though when trying to write a function for my wrapper that will handle SELECT calls as I cannot entirely figure out the Data Reader.
My understanding is that each iteration of a loop on the reader is the next row, and GetString(x) returns the column value for "x" as the index. All the examples I found though went into it knowing the row/column names they needed. How can I do this with a "SELECT * FROM" call and save the column names/values for later access? Microsoft seems to have a "FieldCount" function but I am coming up empty on the MySQL Connector.
Thanks!
public void Query(string query, string tableName)
{
//Open connection
if (this.OpenConnection() == true)
{
//Create Command
MySqlCommand cmd = new MySqlCommand(query, connection);
MySqlDataReader dataReader = cmd.ExecuteReader();
//Read the data and store them in the list
while (dataReader.Read())
{
int count = Count(tableName);
for (int x = 0; x < count; x++)
{
Console.WriteLine(dataReader.GetString(count));
}
}
//close Data Reader
dataReader.Close();
//close Connection
this.CloseConnection();
}
}
You can use DbDataReader.GetName to get the name of a column given its ordinal x.
use the "mysql connector" to access data in MySql it is more simple then to write the queries by your self:
http://dev.mysql.com/downloads/connector/net/
Then use the EntityFramework to access the data through this connector. Also you can automaticly generate *.edmx model from your existing DB in mysql, this will let you to fastly access and work with the Data in your database. Here is information about adding *.edmx model from existing DB:
http://msdn.microsoft.com/en-us/library/vstudio/cc716703(v=vs.100).aspx
The query which will select all data from the table, for example - "Products" will look like that:
List products = dbContext.Products.Where(e=>e.ProductId!=-1).ToList();
this will return the whole list of products in your data base in table Products.
then you can work with products as you want. for example taking the "Name" column for the first product in 'products' will look like that:
String firstProductName = products[0].name;
I hope it helps.

How do I use Multiple controls using the same ObjectDataSource, but with different filters

I'm playing with optimization in ASP.Net WebForms.
in my case I have 2 dropdowns and a grid.
I want the dropdowns to act as a filter for the grid, each containing a distinct list of the data in one column of the grid (to use as a filter)
That's fine.. I got it working, but I can't use the same datasource as the grid for the dropdowns anymore because I'm applying a filterexpression to the datasource to filter whats in the grid.
since its the same datasource as the dropdowns, I get a smaller distinct list in the dropdown.
now I can use multiple datasources, each consuming the same data object, but I see in Sql Profiler that 2 data calls are made, but I'd really like to use the same one so I can have a single data call.
is it even possible to have a single ObjectDataSource be filtered for the grid, and at the same time and provide unfiltered data for another control?
If you're focused on not having to make multiple SQL calls, one option would be to use LINQ to query your DataSet in your SelectMethod. There may be a more elegant way to do this syntactically (I couldn't figure one out) but this should provide your desired functionality using a single ObjectDataSource.
If your ObjectDataSource declaration looks like:
<asp:ObjectDataSource ID="myObjectDataSource" runat="server" SelectMethod="myObjectDataSource_Select" OnFiltering="myObjectDataSource_Filtering">
In your SelectMethod you could do something like:
public DataSet myObjectDataSource_Select()
{
string sqlQuery = "SELECT col1, col2, col3 FROM foo";
SqlDataAdapter da = new SqlDataAdapter(sqlQuery, myConnectionString);
DataSet ds = new DataSet();
using (da) {
da.Fill(ds);
}
//Perform your secondary filtering here
object [] unfilteredQuery= (from r in ds.Tables[0].AsEnumerable()
select r.Field<string>(“col1”)).ToArray();
myUnfilteredComboBox.Items.Clear();
myUnfilteredComboBox.Items.AddRange(unfilteredQuery);
return ds;
}
Are you using Linq? If yes, that should be possible:
// Loading complete data into object
var myCompleteDataSource = (from c in ctx select c).ToList();
// Filtering the already loaded data
var myFilteredDataSource = myCompleteDataSource.Where(o=>o.MyField=="abc").ToList();
And then just set the datasources to your objects.
That will load your data only one time (the first .ToList() method) from the db and filter just the object list into the second object without accessing the db again.
As you said "since its the same datasource as the dropdowns, I get a
smaller distinct list in the dropdown."
You can keep the Database Information in the ViewState. In this way, you can prevent the Request to Database for your client request. Thus Reducing the Access time.
Example
public DataTable Employees
{
get
{
if (ViewState["Employees"] == null)
{
return FollowsDAL.GetAllEmployees();
}
return (DataTable)ViewState["Employees"];
}
set
{
ViewState["Employees"] = value;
}
}
How can I make the ViewState Data filtering fast ?
Answer is - Please don't use Update Panel. I will use Page Method.
Please check the example below. I used Update Panel with Script Manager.
Output
To display the 22 character string you can check how much data is being received and sent to server. Just imagine following
If you would consider send each request to Database using Update Panel and your GridView is in Update Panel!!!!!!
If you would use ViewState data for each request and with GridView Inside the Update Panel.
Both the above techniques are worst as per my understanding.
Now I will describe you Page Methods
Page Method over Update panel
Page methods allow ASP.NET AJAX pages to directly execute a Page’s Static Methods, using JSON (JavaScript Object Notation). Instead of posting back and then receiving HTML markup to completely replace our UpdatePanel’s contents, we can use a web method to request only the information that we’re interested.
Sample Code
Output
So conclusion is that I will definitely use ViewState BUT with Page Methods.
Filtering Technique for on the ViewState Data.
public static class GetFilteredData
{
public static DataTable FilterDataTable(this DataTable Dt,
string FilterExpression)
{
using (DataView Dv = new DataView(Dt))
{
Dv.RowFilter = FilterExpression;
return Dv.ToTable();
}
}
}
Example
DataTableObject.FilterDataTable("Search Expression")
Hi vpiTriumph... I found a bit improvement in the code. Below is the suggested approach.
Sample code in C Sharp
private void DsataBaseInteraction()
{
using (SqlConnection con = new SqlConnection("Your Connection String"))
{
using (SqlCommand cmd = new SqlCommand())
{
cmd.Connection = con;
cmd.CommandType = System.Data.CommandType.StoredProcedure;
cmd.CommandText = "Your Stored Procedure name";
using (SqlDataReader DR = cmd.ExecuteReader())
{
}
}
}
}
#KevinDeus - I am assuming that the Database being used is SQL Server. So below mentioned is my suggestion for Stored Procedure in Database.
Create Proc ProcedureName
#UserName Varchar(50),
#Password Varchar(50),
#Email Varchar(50)
As
SET NOCOUNT ON
SET XACT_ABORT ON
Begin Try
Begin Tran
Insert into Account (Username,Password, Email)
Values(#UserName, #Password, #Email)
Commit Tran
End Try
Begin Catch
Rollback Tran
End Catch
Reference is Here and Here

How to update a large table using ADO.NET

Ok, so here's the problem I have to solve. I need to write a method in C# that will modify a table in SQL Server 2008. The table could potentially contain millions of records. The modifications include altering the table by adding a new column and then calculating and setting the value of the new field for every row in the table.
Adding the column is not a problem. It's setting the values efficiently that is the issue. I don't want to read in the whole table into a DataTable and then update and commit for obvious reasons. I'm thinking that I would like to use a cursor to iterate over the rows in the table and update them one by one. I haven't done a whole lot of ADO.NET development, but it is my understanding that only read-only server side (firehose) cursors are supported.
So what is the correct way to go about doing something like this (preferably with some sample code in C#)? Stored procedures or other such modifications to the DB are not allowed.
jpgoody,
Here is an example to chew on using the NerdDinner database and some SQLConnection, SQLCommand, and SQLDataReader objects. It adds one day to each of the Event Dates in the Dinners table.
using System;
using System.Data.SqlClient;
namespace NerdDinner
{
public class Class1
{
public void Execute()
{
SqlConnection readerConnection = new SqlConnection(Properties.Settings.Default.ConnectionString);
readerConnection.Open();
SqlCommand cmd = new SqlCommand("SELECT DinnerID, EventDate FROM Dinners", readerConnection);
SqlDataReader reader = cmd.ExecuteReader();
SqlConnection writerConnection = new SqlConnection(Properties.Settings.Default.ConnectionString);
writerConnection.Open();
SqlCommand writerCommand = new SqlCommand("", writerConnection);
while (reader.Read())
{
int DinnerID = reader.GetInt32(0);
DateTime EventDate = reader.GetDateTime(1);
writerCommand.CommandText = "UPDATE Dinners SET EventDate = '" + EventDate.AddDays(1).ToString() + "' WHERE DinnerID = " + DinnerID.ToString();
writerCommand.ExecuteNonQuery();
}
}
}
}
Your problem looks like something that you should be solving using T-SQL and not C#, unless there is some business rule that you are picking up dynamically and calculating the column values T-SQL should be the way to go. Just write a stored procedure or just open up Management studio and write the code to make your changes.
If this does not help then please elaborate on what exactly you want to do to the table, then we can help you figure out if this can be done via T-SQL or not.
[EDIT] you can do something like this
string sql = " USE " + paramDbName;
sql+= " ALTER TABLE XYZ ADD COLUMN " + param1 + " datatype etc, then put semicolon to separate the commands as well"
sql+= " UPDATE XYZ SET Columnx = " + some logic here
cmd.CommandText = sql;
cmd.ExecuteNonQuery();
get this executed on the required instance of Sql Server 2008.
If you have too many lines of text then use StringBuilder.
Here's a suggestion:
You can read data using a DataReader , create a update command for current row and add it to a list of commands.Then run update commands in a transaction.
something like this:
var commands=new List<SqlCommand>();
while(dr.Read())
{
var cmd=new SqlCommand();
cmd.CommandText="Add your command text here";
commands.Add(cmd);
}
using(var cnn=new SqlConnection("Connection String"))
{
IDbTransaction transaction;
try
{
cnn.Open();
transaction=cnn.BeginTransaction();
foreach(var cmd in commands)
{
cmd.Transaction=transaction;
cmd.ExecuteNonQuery();
cmd.Dispose();
}
transaction.Commit();
}
catch(SqlException)
{
if(transaction!=null)
transaction.Rollback();
throw;
}
}

Categories