I am relatively new to the entire NuGet ecosystem. What I expected is for things to just work. You know... Microsoft. However the web of interdepencies seems to be too much even for them. The problems that appear when updating MVC versions, .NET Framework versions, etc, are as annoying as they are unclear. One example: I was trying to publish a project that worked perfectly on my system. I moved it to the server machine, and weird things began to happen. The most annoying of them all is that the errors that occur do that at runtime instead of at compile time. Such an error was "Could not load file or assembly System.Web.WebPages, Version=188.8.131.52...". The project reference for WebPages was 184.108.40.206. If I removed it and tried to add a reference, only versions 220.127.116.11 and 18.104.22.168 were available. Meanwhile Razor was complaining that it didn't find the 22.214.171.124 version of WebPages. Long story short: don't try to resolve only the library dependencies, but also the framework dependencies. In this case, System.Web.WebPages 126.96.36.199 is only available for the .NET framework 4.5.1. The project was configured as 4.5. Updating the MVC framework after the change to .NET 4.5.1 solved it.
- Change the project version to 4.5.1 (or whatever the newest usable .NET framework version)
- go to the NuGet Package Manager Console in Visual Studio
- Run command Update-Package -reinstall Microsoft.AspNet.Mvc
This, of course, is not a panacea for all problems, but just remember that the .NET framework is important in these scenarios.
I had this memory problem that I could not understand. OK, the design of the application was not the best in the world, but why would it always give me a damn OutOfMemoryException when I have a super duper computer with a lot of memory and I have solved issues like heap memory allocation? And the reason is that IISExpress, the default Windows7 ASP.Net web server is running in 32bit mode, meaning it has a maximum of 4GB of memory no matter what you do. Well, you can make IISExpress run in 64bit mode by simply switching it on in the Windows registry. I don't want to copy the content of the article from someone else, so here is a link towards how to do it: Debugging VS2013 Websites Using 64-bit IIS Express
Just in case you want the ultra fast version, copy this into a file with the .reg
extension and execute it:
Windows Registry Editor Version 5.00
An attempt was made but it didn't work. All the scripts were loaded and executed at once. The user would still see an empty page, then a progress bar that immediately gets to 100%. Strange, that, since we knew that in certain circumstances, the scripts are executed as they are loaded. The answer was that browsers are caching a minimum bit of the page before they are interpreting it, about 1024 characters. The solution, then, was to send 1024 empty spaces before we start sending in the progress.
This value of 1024 is not really documented or standard; it is a browser implementation thing.
Our design had the page loaded in an iframe, which allowed for scripts and html to not be loaded in the import page (thus making us stumble upon this behavior), and allowed for them to be loaded in the parent page. The scripts that we sent through the ASP.Net pipeline (using Response.Write and Response.Flush) accessed the resources from the parent page and showed a nice progress bar.
In case the page would have been a simple ASP.Net page, then the html and the CSS would have had to be sent first, perhaps instead of the 1024 spaces. There would have been problems when the page would have finished the import and the output of the page would have followed the one sent via the pipeline, but for our specific scenario it seems mere spaces and script blocks did not change the way browsers interpreted the rest of the page output. A secondary side effect of this change was that we prevented the closing of the connection by some types of routers that need HTTP connections to have some traffic sent through them in an interval of time, providing a sort of "keep-alive"
. Before we made this change, these routers would simply cut the connection, leaving the user hanging.
I had a pretty strange bug to fix. It involved a class used in a web page that provided localized strings, only it didn't seem to work for Japanese, while French or English or German worked OK. The resource class was used like this: AdminUIString.SomeStringKey, where AdminUIString was a resx file in the App_GlobalResources folder. Other similar global resource resx classes were used in the class and they worked! The only difference between them was the custom tool that was configured for them. My problem class was using PublicResXFileCodeGenerator
from namespace Resources
, while the other classes used the GlobalResourceProxyGenerator
, without any namespace.
Now, changing the custom tool did solve the issue there, but it didn't solve it in some integration tests where it failed. The workaround for this was to use HttpContext.GetGlobalResourceObject("AdminUIString", "SomeStringKey").ToString()
, which is pretty ugly. Since our project was pretty complex, using bits of ASP.Net MVC and (very) old school ASP.Net, no one actually understood where the difference stood. Here is an article that partially explains it: Resource Files and ASP.NET MVC Projects
. I say partially, because it doesn't really solve my problem in a satisfactory way. All it says is that I should not use global resources in ASP.Net MVC, it doesn't explain why it fails so miserable for Japanese, nor does it find a magical fix for the problem without refactoring the convoluted resource mess we have in this legacy project. It will have to do, though, as no one is budgeting refactoring time right now.
I've pinpointed the issue after a few other investigations. The https:// site was returning a security certificate that was issued for another domain. Why it worked in FireFox anyway and why it didn't work in Chrome, but then it worked after an unauthorized call first, I still don't know, but it is already in the domain of browser internals.
I was trying to access an API on https://
from a page that was hosted on http://
. Since the scheme of the call was different from the scheme of the hosted URL, it is interpreted as a cross domain call. You might want to research this concept, called CORS
, in order to understand the rest of the post.
The thing is that it didn't work. The server was correctly configured to allow cross domain access, but my jQuery calls did not succeed. In order to access the API I needed to send an Authorization header, as well as request the information as JSON. Investigations on the actual browser calls showed the correct OPTIONS request method, as well as the expected headers, only they appeared as 'Aborted
'. It took me a few hours of taking things apart, debugging jQuery, adding and removing options to suddenly see it work! The problem was that after resetting IIS, the problem appeared again! What was going on? In the end I've identified a way to consistently reproduce the problem, even if at the moment I have no explanation for it. The calls succeed after making a call with no headers (including the Content-Type one). So make a bogus, unauthorized call and the next correct calls will work. Somehow that depends on IIS as well as the Chrome browser. In Firefox it works directly and in Chrome it seems to be consistently reproducible.
I had to investigate a situation where a message of "Object moved to here", where "here" was a link, appeared in our ASP.Net application. First of all, we don't have that message in the app, it appears it is an internal message in ASP.Net, more exactly in HttpResponse.Redirect
. It is a hardcoded HTML that is displayed as the response status code is set to 302 and the redirect location is set to the given URL. The browser is expected to move to the redirect location anyway, and the displayed message should be only a temporary thing. However, if the URL is empty, the browser does not go anywhere.
In conclusion, if you get to a webpage that has the following content:
<h2>Object moved to <a href="[url]">here</a>.</h2>
then you are probably trying to Response.Redirect to an empty URL.
A Microsoft patch for ASP.Net released on the 29th of December 2011 adds a new functionality that rejects POST http requests with more than 1000 keys and any JSON http request with more than 1000 members.
That is pretty huge, and if you have encountered this exception:Operation is not valid due to the current state of the object.
Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code.
Exception Details: System.InvalidOperationException: Operation is not valid due to the current state of the object.
An unhandled exception was generated during the execution of the current web request. Information regarding the origin and location of the exception can be identified using the exception stack trace below.
[InvalidOperationException: Operation is not valid due to the current state of the object.]
System.Web.HttpValueCollection.FillFromEncodedBytes(Byte bytes, Encoding encoding) +61
[HttpException (0x80004005): The URL-encoded form data is not valid.]
System.Web.UI.Page.GetCollectionBasedOnMethod(Boolean dontReturnNull) +97
System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint) +133
then your site has been affected by this patch.
Well, you probably know that something is wrong with the design of a page that sends 1000 POST values, but still, let's assume you are in a situation where you cannot change the design of the application and you just want the site to work. Never fear, use this:
<add key="aspnet:MaxHttpCollectionKeys" value="5000" />
<add key="aspnet:MaxJsonDeserializerMembers" value="5000" />
More details:Knowledge base article about itThe security advisor for the vulnerability fixedThe entire MS11-100 security update bulletin
I was trying to access http://localhost/Reports/Page.aspx
, in other words an ASP.Net page in the Reports path of the local site. Instead, I was getting a Windows authentication prompt that had no business being there. At first I thought to debug the page, but it wouldn't even get there before I got the authentication prompt. I googled for it, but I didn't get far because I was looking for weird Windows authentication prompts, not for the specific location of my page: the Reports folder. It was stranger yet, as I stopped IIS and the authentication dialog was still appearing!In the end, a colleague told me the solution: SQL Reporting Services is answering on the local Reports path! I stopped the service and voila! no more authentication prompt. Instead, a Service unavailable 503 error. This article explained things quite clearly. Even if you stop the service, you have to delete the access control list entry for /Reports with the command netsh http delete urlacl url=http://+:80/Reports
or, I guess, restart the system after you set the Reporting Services service to Manual or Disabled.Update:
It is even easier to go to Sql Server Configuration Tools (in the Start Menu), run the Reporting Service Configuration Manager, then change the URL for the Report Manager URL to something other than Reports.
But what is this strange Access Control List? You can get a clue by reading about Http.sys API in Windows Vista and above
and about Namespace Reservation
. Apparently, one can do similar things on Windows Server 2003 and maybe even XP with the Httpcfg utility
I've finally finished reading Pro ASP.Net MVC Framework
by Steven Sanderson
. The book is slightly dated, since it discusses the technology used in Visual Studio 2008 and without any mention of the new Razor engine, but these are details that are not important to the content of the book anyway. I can say that it is a very nice book and it was worth reading, especially the first part.
There are two parts to this, the first being a TDD ASP.Net MVC web shop application built step by step and explained line by line. It goes through some Domain Driven Design concepts as well, it does unit testing and mocking, even shows off a little dependency injection via Castle Windsor. What I liked most, though, is how painstakingly thorough Sanderson was explaining every single detail. He didn't assume anything as he documented every step of the way, down to what lambda expressions are and what .Net features he was using.
The second part of the book is a little less readable, as it goes through the classes and features of ASP.Net MVC, complete with methods, properties and small samples. I highly recommend reading this part while actually experimenting with the framework on the computer. Even if you do not, this part of the book remains a very valuable reference for when you do. In this section of the book you can learn about data entry, Ajax and partial updates, application security and deployment, even how to mix classic ASP.Net with MVC, though not really recommended.
The bottom line is that Pro ASP.Net MVC Framework is a must read for a developer learning ASP.Net MVC. There is an updated version of the book for VS2010 and .Net 4 that I think that I will also read (the book was so good). Here is the link for Pro ASP.NET MVC 2 Framework
Well, I have been kind of absent from the blog lately and that is for several reasons. One is that I have been waiting for some news that would determine my direction as a professional developer. The other is that I have re-acquired a passion for chess. So, between work at the office, watching chess videos, playing chess with my PDA and watching all seven seasons of Star Trek Deep Space 9, I haven't had much time for blogging.
Also, when you think about it, the last period of my programming life has been in some sort of a limbo: switched from ASP.Net to WPF, then to ASP.Net again (while being promised it would be temporary), then back to WPF (but in a mere executive position). Meanwhile, Microsoft didn't do much to help me, and thus saw their profits plummet. Well, maybe it was a coincidence, but what if it wasn't?
All of this, plus the mysterious news I have been waiting for that I won't detail (don't want to jinx it :-S), but which could throw me back into the web world, plus the insanity with the mobile everything that has only one common point: web. Add to it the not too enthusiastic reaction of my blog readers when starting talking about WPF. So the world either wants web or I just have been spouting one stupid thing after another and blew my readers away.
I restarted my computer and afterwards I could not access any of the local sites via IIS. The error message in the Application logs of the EventViewer was
Event Type: Error
Event Source: ASP.NET 4.0.30319.0
aspnet_wp.exe could not be started. The error code for the failure is C0000142. This error can be caused when the worker process account has insufficient rights to read the .NET Framework files. Please ensure that the .NET Framework is correctly installed and that the ACLs on the installation directory allow access to the configured account.
I did the classic
to no avail. I was about to curse and restart the computer again when I found this pretty little link: IIS doesn't start. Error code: C0000142
. A solution is at the bottom, as the least voted answer: Go to Task Manager, kill explorer.exe, Run another explorer.exe. This starts IIS (aspnet_wp.exe under inetinfo.exe) correctly. Update
: It bugged me that I had to kill explorer.exe. First of all it is a manual solution, then it always messed with my system tray icons. So I searched a little more. Short story shorter, you need to edit machine.conf and replace <processModel autoConfig="true" /> with <processModel userName="system" password="AutoGenerate" />
. That effectively makes ASP.Net work under the System account, not the default machine. It does indicate the issue is permission related, but I don't get exactly where and why it should work if I restart explorer.exe. As long as you don't mind running ASP.Net under the System account, this solution seems to solve it. Here is the long version
Note: you can find the machine.config file in %windir%\Microsoft.NET\Framework\[framework version]\Config\machine.config
Well, there are a lot of good reasons why that could happen because of your bad code, but this time it is a plain ugly Microsoft bug
. You see, the code in the RaisePostBackEvent
method in the TreeView control first checks if the control has an Adapter
and if not, it just does its thing. If there is an Adapter, it tries to cast it to a IPostBackEventHandler and then fires the RaisePostBackEvent event there. However, if the TreeView control has an adapter and it is not a RaisePostBackEvent, nothing happends!
Here is the offending code:
Bottom line, you need to either not use an adapter for the TreeView, or use one that knows how to handle the postback. And given the complexity of the code in the method, it is better to just not use an adapter.
protected virtual void RaisePostBackEvent(string eventArgument)
if (base._adapter != null)
IPostBackEventHandler handler =
base._adapter as IPostBackEventHandler;
if (handler != null)
The solution I have adopted is to recreate the functionality in an override of the RaisePostBackEvent method and add some more (like TreeNodeClicked and SelectedNodeClicked). Hint: you need to also get in LoadPostData
and remember which nodes are selected in order to check if the selected node has changed.
Here is a post
from Phil Haack
about extra extensibility options in ASP.NET 4.0. I would like to emphasize the third "gem
", the one that lets you add an assembly programatically to the list of loaded assemblies (equivalent to adding it in the assemblies tag in web.config). I wanted this from .Net 1.0 ! Unfortunately it must be called during the Application_PreStartInit stage of the application, but maybe the first gem
can help with that.
Of course, I haven't been using these things yet, so I may be saying stupid things. It is a distinct possibility... Quite distinctive... Oh, shut up!
I was minding my own business doing this ridiculous ASP.Net project and suddenly I am hit with: "Multiple controls with the same ID 'lbTitle' were found. FindControl requires that controls have unique IDs.
". I was using this web control that contained two others, each of them having a lbTitle
If you think about it, it does make sense to throw this exception when the FindControl method is used in the parent control. Which control did I mean? But the error appears even if the FindControl is used inside one of the child controls, what is up with that? Update
As a secondary thought, I wasn't using any FindControl. It seems that what does is the AssociatedControlID property of the Label control. Therefore I will set the HtmlTextWriterAttribute.For attribute manually to resolve this. Pretty damn ugly, if you ask me!
: My fault! The controls needed to implement the INamingContainer interface
. It's not that the ClientID was not different, but FindControl works by going to the NamingContainer
control and finding then children by ID. Too bad that you can't just specify the ClientID and be done with it, but that's that.
I don't want you to think that I started working on ASP.Net MVC, but this article
about a 36 year trek through backward compatibility hell was really funny and needed to be linked. What is so funny, I guess, is that it is factual and the humour is in the situation more than in the article itself.
On a separate note, ASP.Net 4.0 fixed this issue
with a web.config setting.