views:

78

answers:

3

I have a web application that works in our stage/test environment fine but once we moved it to our production environment something weird happens. All the control ids change. For example a label went from ctl00_cphMainContent_lblPetName to _ctl0_cphMainContent_lblPetName. Why would this happen? What could cause something like this to happen. The only two differences I know of are the production environment has HTTPS and I've disabled debugging.

+4  A: 

As the way the client id is generated may change between different versions of the framework, you should not rely on a specific pattern.

The ClientID and UniqueID properties should be used to determine the id and name that are generated for the html code.

The ClientID property contains the generated id, which you for example can use with the document.getElementById method in Javascript.

The UniqueID property contains the generated name, which you for example can use if you read a value posted with a form from the Request.Form collection.

Guffa
This change was between 1.1 and 2.0 and probably will be in 4.0. I do not think that environments differ so much...
Mike Chaliy
I don't think that this specific behavior will change in 4.0, as all versions of the framework since 2.0 are incremental.
Paulo Santos
A: 

Your web.configs differ. Behaviour of the client ID generation depends on EnableLegacyRendering. Please review xhtmlConformance element of your web.config. If it Legacy you will get "_ctl", if not - "ctl".

Mike Chaliy
Thanks this was exactly what the problem was. The root web.config had this set to legacy and this was inherited by our application that was in a sub folder.
Andre
A: 

The trick is to have the server, which knows the control id, send it to the client-side JavaScript, which will use it.

The usual way to do this is something like this:

var btn1 = document.getElementById(" <%= button1.ClientID %>");

I've always hated this, as, in effect, you're writing all of your JavaScript at runtime. Instead, what I like is to have a page (or control) emit a class containing all the control ids (or other server-side values) that it needs.

I'd post an example, but I haven't done this for a while, and don't have one with me. Basically, create a JavaScript class with members for every control ID you need, and register that with the page. Then register a startup script that does something like this:

myPage_Instance.btn1 = <%= button1.ClientID %>; // Better - do it in the codebehind
// more of the same

Your code can now be:

var btn1 = document.getElementById(myPage_Instance.btn1);

John Saunders