.Net 4.0 is encoding values when using Attributes.Add. In previous versions it didn't. With the new behaviour it is no longer possible to write attributes containing single quotes.
Yes I know that ' is encoded. The point is that it shouldn't be! You have not suggested a workaround that works in general for setting attribute values programmatically from code behind pages. Imagine for example if the string passed to the function
were to be varied between calls depending on what is occuring server-side.
This problem:
1. is a change in behaviour from 2.0 to 4.0, breaking existing applications
2. has no clear workaround to achieve the desired result.
3. reduces the capability of the ASP.Net developer in building web applications.
It's either a bug or a poorly considered design change. Either way, it needs to be addressed.
Yes, but it is a security change, and security changes trump backward compatibility.
Regardless, I am sorry for sounding so terse and not offering a work around. Does your web.config have a value for "controlRenderingCompatibilityVersion" attribute of the pages
element? I haven't tried it, but if you set it to 3.5 - does it correct the issue for you?
As I noted above, this isn't just about backward compatibility, it is also about the capability to do web development. Nailing the doors of your house shut would improve the security of your house but it would make it unreasonably difficult to enter.
No, controlRenderingCompatibilityVersion="3.5" does not resolve the problem. Even if it did it would not be a reasonable long term fix.
We need a way to put single quotes in html attribute values using 4.0.
After reviewing the code with reflector, I cannot find a reasonable way to do this. This appears to be baked into the framework. The only solution that I can offer other than contacting Microsoft directly is to use a
Control Adapter, which would need to be done with every Web Control. Like this:
public class ButtonControlAdapter : WebControlAdapter
{
protected override void RenderBeginTag(HtmlTextWriter writer)
{
writer.WriteBeginTag("input");
var control = Control as Button;
writer.WriteAttribute("type", control.UseSubmitBehavior ? "submit" : "button");
foreach (string attribute in control.Attributes.Keys)
{
writer.WriteAttribute(attribute, control.Attributes[attribute], false);
}
}
protected override void RenderEndTag(HtmlTextWriter writer)
{
writer.WriteEndTag("input");
}
}
And then registering it in your browser definition. Given that the last solution was not acceptable even if it worked, I would assume this is not acceptable either.
Maybe we are looking at this the wrong why. Can you provide a specific example as why you absolutely positively need the legacy behavior?
However, now we must worry that new controls may depend on the new standard 4.0 behaviour and not encode single quotes, so it's still imperfect, nay, worse than imperfect: security is even worse, because we don't know what is going on where, so it's not
a great workaround really.
I think only Microsoft can fix this properly. Others have suggested the need for an HtmlAttributeString class here:
If there were such a class and Attributes.Add could take an object like this for its value parameter then we would have the control that we need again.
Marked as answer by vcsjones on May 07, 2010 10:48 PM
I just wanted to say thank you for this. Man, why does .net suck so much with JavaScript?
It's like Microsoft couldn't imagine a scenario where you'd want to do some client side stuff outside of their framework.
And how does escaping single qutoes that I write out from code behind make this more secure?
I have no clue what the below does, but it works. And that's good enough for me.
I found that I also needed to override the HtmlEncode method to handle script blocks that were being written as part of content in the innerHtml of HtmlGenericControls. Not sure if this is necessary, but I decided to let the default Encoding happen, and
then just override the result replacing the escaped quotes
franzo
0 Points
4 Posts
.Net 4.0 Attributes.Add encoding bug
May 04, 2010 10:20 PM|LINK
.Net 4.0 is encoding values when using Attributes.Add. In previous versions it didn't. With the new behaviour it is no longer possible to write attributes containing single quotes.
Here's an example.
<asp:TextBox ID="txtTest" runat="server" />
txtTest.Attributes.Add("onkeyup", "keyuphandler('hello')");
With the application pool framework version set to 2.0 it produces the desired result:
<input name="txtTest" type="text" id="txtTest" onkeyup="keyuphandler('hello')" />
With it set to 4.0 it produces an undesirable result:
<input name="txtTest" type="text" id="txtTest" onkeyup="keyuphandler('hello')" />
.Net 4.0 needs to be fixed to allow the developer to write attribute values containing single quotes.
encoding attribute .NET 4.0 quote
vcsjones
All-Star
34842 Points
4424 Posts
Moderator
MVP
Re: .Net 4.0 Attributes.Add encoding bug
May 04, 2010 10:48 PM|LINK
' is an escape character for a single quote. The browser will interpret this as single quote. For example, given this HTML:
<html> <body> <input type="button" value="Click Me" onclick="alert('Hello');" /> </body> </html>saving that do disk still works and functions as desired. This is rather a security feature to prevent XSS than a bug.
franzo
0 Points
4 Posts
Re: .Net 4.0 Attributes.Add encoding bug
May 05, 2010 01:29 AM|LINK
Yes I know that ' is encoded. The point is that it shouldn't be! You have not suggested a workaround that works in general for setting attribute values programmatically from code behind pages. Imagine for example if the string passed to the function were to be varied between calls depending on what is occuring server-side.
This problem:
1. is a change in behaviour from 2.0 to 4.0, breaking existing applications
2. has no clear workaround to achieve the desired result.
3. reduces the capability of the ASP.Net developer in building web applications.
It's either a bug or a poorly considered design change. Either way, it needs to be addressed.
vcsjones
All-Star
34842 Points
4424 Posts
Moderator
MVP
Re: .Net 4.0 Attributes.Add encoding bug
May 05, 2010 01:50 AM|LINK
Yes, but it is a security change, and security changes trump backward compatibility.
Regardless, I am sorry for sounding so terse and not offering a work around. Does your web.config have a value for "controlRenderingCompatibilityVersion" attribute of the pages element? I haven't tried it, but if you set it to 3.5 - does it correct the issue for you?
franzo
0 Points
4 Posts
Re: .Net 4.0 Attributes.Add encoding bug
May 05, 2010 03:12 AM|LINK
As I noted above, this isn't just about backward compatibility, it is also about the capability to do web development. Nailing the doors of your house shut would improve the security of your house but it would make it unreasonably difficult to enter.
No, controlRenderingCompatibilityVersion="3.5" does not resolve the problem. Even if it did it would not be a reasonable long term fix.
We need a way to put single quotes in html attribute values using 4.0.
vcsjones
All-Star
34842 Points
4424 Posts
Moderator
MVP
Re: .Net 4.0 Attributes.Add encoding bug
May 05, 2010 04:23 AM|LINK
After reviewing the code with reflector, I cannot find a reasonable way to do this. This appears to be baked into the framework. The only solution that I can offer other than contacting Microsoft directly is to use a Control Adapter, which would need to be done with every Web Control. Like this:
public class ButtonControlAdapter : WebControlAdapter { protected override void RenderBeginTag(HtmlTextWriter writer) { writer.WriteBeginTag("input"); var control = Control as Button; writer.WriteAttribute("type", control.UseSubmitBehavior ? "submit" : "button"); foreach (string attribute in control.Attributes.Keys) { writer.WriteAttribute(attribute, control.Attributes[attribute], false); } } protected override void RenderEndTag(HtmlTextWriter writer) { writer.WriteEndTag("input"); } }And then registering it in your browser definition. Given that the last solution was not acceptable even if it worked, I would assume this is not acceptable either.
Maybe we are looking at this the wrong why. Can you provide a specific example as why you absolutely positively need the legacy behavior?
franzo
0 Points
4 Posts
Re: .Net 4.0 Attributes.Add encoding bug
May 07, 2010 09:18 AM|LINK
http://www.asp.net/learn/whitepapers/aspnet4#0.2__Toc253429247 talks about creating custom encoding routines.
You can turn off attribute encoding by creating a class like this:
public class HtmlAttributeEncodingNot : System.Web.Util.HttpEncoder
{
protected override void HtmlAttributeEncode(string value, System.IO.TextWriter output)
{
output.Write(value);
}
}
and adding this to web.config under <system.web>:
<httpRuntime encoderType="HtmlAttributeEncodingNot"/>
This gives me the control I need.
However, now we must worry that new controls may depend on the new standard 4.0 behaviour and not encode single quotes, so it's still imperfect, nay, worse than imperfect: security is even worse, because we don't know what is going on where, so it's not a great workaround really.
I think only Microsoft can fix this properly. Others have suggested the need for an HtmlAttributeString class here:
http://haacked.com/archive/2009/09/25/html-encoding-code-nuggets.aspx
If there were such a class and Attributes.Add could take an object like this for its value parameter then we would have the control that we need again.
kevinmcc
Member
9 Points
5 Posts
Re: .Net 4.0 Attributes.Add encoding bug
Sep 16, 2010 05:35 PM|LINK
Frazno,
I just wanted to say thank you for this. Man, why does .net suck so much with JavaScript?
It's like Microsoft couldn't imagine a scenario where you'd want to do some client side stuff outside of their framework.
And how does escaping single qutoes that I write out from code behind make this more secure?
I have no clue what the below does, but it works. And that's good enough for me.
;-)
<httpRuntime encoderType="HtmlAttributeEncodingNot"/>
matt_letharg...
Member
4 Points
8 Posts
Re: .Net 4.0 Attributes.Add encoding bug
Oct 20, 2010 03:07 PM|LINK
So what if I wanted to do this for only a few controls and not every control on my site?!?
webst128
Member
6 Points
5 Posts
Re: .Net 4.0 Attributes.Add encoding bug
Dec 07, 2010 06:12 PM|LINK
I found that I also needed to override the HtmlEncode method to handle script blocks that were being written as part of content in the innerHtml of HtmlGenericControls. Not sure if this is necessary, but I decided to let the default Encoding happen, and then just override the result replacing the escaped quotes
protected override void HtmlAttributeEncode(string value, System.IO.TextWriter output) { StringBuilder sb = new StringBuilder(); StringWriter sw = new StringWriter(sb); base.HtmlAttributeEncode(value, sw); output.Write(sw.ToString().Replace("'","'")); } protected override void HtmlEncode(string value, System.IO.TextWriter output) { StringBuilder sb = new StringBuilder(); StringWriter sw = new StringWriter(sb); base.HtmlEncode(value, sw); output.Write(sw.ToString().Replace("'", "'")); }