ASP.NET HTML encoding attributes in server controls

Did you know that asp.net will html encode your server control attributes as from .NET 4.0? This is done for security reasons and prevent cross site scripting attacks. Going forward, you will need to work around this if the need arises as a security enhancement is more likely not to be backwards compatible.

I came across this “problem” when I was trying to build a degradable web app. When javascript is turned off, everything would work as it’s supposed to (through postbacks) but is JS is enabled, then JQuery will kick in. For this to work, I needed to provide an OnClientClick function to the asp.net buttons. It works fine until you try to insert parameters (arguments) in the javascript function. Since javascript parameters are enclosed with apostrophes, you will find the rendered html quite different from what you entered in the code behind. Take for example the following:


btnSubmit.OnClientClick = String.Format("PostContent('{0}', '{1}', '{2}');", "6", _question.Id, "0");

This will be rendered as:

<input type="submit" name="btnSubmit" value="Submit" onclick="PostContent(&#39;6&#39;, &#39;10112&#39;, &#39;0&#39;);" id="btnSubmit" />

The attribute value has been html encoded. If you view the html source code, you will see that the apostrophe has been converted to ‘&#39;’ Now that’s not really a problem as your javascript functions will still work as normal. However it just looks a bit weird! If you want to change that behaviour of asp.net to html encode server control properties, then you will need to create a class as follows:

public class HtmlAttributeNoEncoding : System.Web.Util.HttpEncoder
 {
 protected override void HtmlAttributeEncode(string value, System.IO.TextWriter output)
 {
 output.Write(value);
 }
 }

And in your web.config file:

<httpRuntime encoderType="HtmlAttributeNoEncoding"/>

It’s probably worth doing that if you need backwards compatibility with the previous .net frameworks (prior to .net 4.0).

HttpHandlers and Sessions in ASP.NET

After struggling for a little while with sessions in an http handler, I found that you need to implement either the IRequiresSessionState (if you need read/write access to sessions) or IReadOnlySessionState (for read only access) to be able to work with session in the asp.net httphandler. You will also need to add the System.Web.SessionState namespace to get it working.

I was trying to read a cookie and restore a particular session from an httphandler but without implementing the IRequiresSessionState, it did not work. So this is a nice little reminder for me!

Connecting to MySQL database using ASP.NET

I decided to use MySQL instead of SQL Server because of the costs involved in getting a licence for Microsoft SQL Server. So although the programming language I’ve decided to stick to remains C# (asp.net), I’m moving away from SQL Server. I’m also using nHibernate which will make it easier if I need to switch to another data store.

Ways to connect to MySQL in .net

There are 3 ways to connect to MySQL database from a .net web application and they are Odbc, MySQL native .net providers or OLEDB.net. The first two are most common and there are advantages and disadvantages to both.

Using ODBC.NET

You need to download the MySQL ODBC driver – MyODBC 3.51 from here. Once this is installed, you can set up a DSN (Data Source Name) if you want.

You can now start using the odbc driver by editing your web.config file and adding a connection string for your MySQL database as follows:


string connectiongString = "DRIVER={MySQL ODBC 3.51 Driver};SERVER=localhost;DATABASE=mydatabase;UID=myusername;PASSWORD=mypassword;OPTION=3";
 OdbcConnection con = new OdbcConnection(connectiongString);

 con.Open();

 OdbcCommand cmd = new OdbcCommand("SELECT * FROM tblCustomers", con);
 OdbcDataReader dr = cmd.ExecuteReader();

 while (dr.Read())
 {
 // read the data here
 }

 cmd.Dispose();
 con.Close();
 con.Dispose();

You may need to add a reference to the System.Data.dll and import the System.Data namespace to get this to work.

The advantage of using ODBC is that it is the standard way of connecting to databases, it is not database specific, which means that if you change from MySQL to Oracle or PosgreSQL, your code will still work. The main drawback of this approach is that it is rather slow because of the many layers involved and performance suffers.

Using MySQL native .Net Providers

You will need to download the MySQL .NET provider from here. Once this is installed, you can write sample code as follows:


string connectionString = "Database=mydatabase;Data Source=localhost;User Id=myusername;Password=mypassword;"
string commandString = "DELETE FROM Session WHERE Expires < ?Expires";
MySqlConnection conn = new MySqlConnection(connectionString);
MySqlCommand cmd = new MySqlCommand(commandString, conn);
cmd.Parameters.Add("?Expires", MySqlDbType.DateTime).Value = DateTime.Now;
conn.Open();
cmd.ExecuteNonQuery();
conn.Close();

You will need to import the MySql.Data.MySqlClient namespace to get the code to compile. The MySQL .net connector is the same as the ByteFX connector for MySQL. MySQL bought ByteFX and renamed it to MySQL .NET connector. You can also use CoreLab.MySql available from CoreLabs but that connector is not free.

There are many benefits to using a native .net connector instead of ODBC and the main reason is performance gain. There’s the speed, garbage collection and security as well as database specific things that you can use. The only drawback is that if you later decide to change from MySQL to something else, you might need to rework your code.

Using OLEDB.NET

You can use OLEDB in the same way as ODBC. You need to download MyOLEDB provider (MyOleDB 3.0) and install it on your machine first. Then you should edit your connection string as follows:

Provider=MySQLProv;location=localhost;Data Source=mydatabase;User ID=myusername;Password=mypassword;

I prefer to use a native .net connector and I’ve installed MySQL Server 5.1 on my Windows 7 machine to get it working.

MySql Error Code 1050 – Table ‘tablename’ already exists

I was playing around with some table creation and deletion and I noticed that after issuing a DROP command for a particular table, I was not able to recreate the table. I’ve installed MySQL on my Windows 7 laptop and by default tables are created with the InnoDB engine. This is how the problem occurs – you create a table (testtable) and immediately after that you issue the following command:

DROP TABLE testtable;

You will get a command executed successfully but when you try to create a table with the same name, you will get the following error:

MySql Error Code 1050 – Table ‘testtable’ already exists

Now if you look at your database schema, you will not find the table name and the same applies if you issue a “SHOW TABLES” command. If you look at the directory where MySQL data are stored, you will not find the .frm file for that specific table. The location is C:\ProgramData\MySQL\MySQL Server 5.1\data (not that it’s not Program Files or Program Files (x86) but ProgramData on Windows 7.

To solve the problem, you will need to restart the MySQL service. Once MySQL is restarted, you can create a table with the same name as the table you dropped earlier. If you drop another table and want to recreate a table with the same name, you will have to stop/start MySQL service again. I think MySQL stores a dictionary of the tables created and only checks whether they are still valid at a regular interval or when the service is restarted.