Friday, 20 February 2009

Copying entire folder content (with subfolders) using standard MsBuild is not as straightforward as I'd imagine this to be. The only solution I've found uses recursion. Following example copies all files from source to dest folder:

Thursday, 19 February 2009

Sometimes, when buidling/deploying your projects standard MsBuild tasks are not enough. I've found a very handy SDC tasks library which allows you to do much more from your build script.

The following example demonstrates creation of application pool and website using this AppPool on IIS. Normally this would need to be done manually. Thanks to SDC we can automate the whole process to eliminate possible errors that can occure during manual deployment.

Wednesday, 11 February 2009

I had a problem with asp.net app losing session data. The same app was working like a charm on my local machine but after deploying to dev server it was throwing exceptions from time to time caused by missing session variables.

My webapp was using default sessionState settings with mode set to 'InProc' and it was configured to use default application pool. The problem was caused by the application pool using Web Garden with 5 worker processes. When using InProc mode the worker processes DO NOT share session data!

Monday, 9 February 2009

Sometimes you want to ensure that your settings (e.g. connection strings) in web.config file are encrypted so nobody except the app iteslf can read/understand them. ASP.Net offers tool called aspnet_regiis which allows that. It can be found in the %WINDOWSDIR%\Microsoft.Net\Framework\version directory.

Solution:Let's say we have a web app deployed on IIS called 'MyApp'. The app uses connection string defined in web.config:

The encrypted information in the web.config can still be accessed by your app without any explicit decoding. Aspnet_regiis tool can be also used to descrypt information, encrypt different sections etc. You can learn more about it here.

WarningIf the encoding succeeds but tha app cannot read the encrypted section because of following error: "Failed to decrypt using provider 'RsaProtectedConfigurationProvider'. Error message from the provider: The RSA key container could not be opened."

If the code executed during update causes an error the browser may warn you about JS error (caused by actual server side error) but the panel will remain faded out. Browser's warning is usually hard to notice or even not displayed at all.

Solution:The following JS code allows you handling update errors on client side. It assumes that there is a span element defined on that page for displaying error messages (with ID=ErrorMsg).

Monday, 2 February 2009

I have an aspx page using standard FileUpload control. When I tried to upload a file bigger than 4MB the page was not displayed or the following error message appeared: "Maximum request length exceeded". This is caused by maximal allowed size of request accepted by the server. Since the uploaded file is sent in request's body the whole request is even bigger than the file itself.

I've seen some solutions using Application_Error handler defined in Global.asax. This approach is quite straightforward and seems to be a way to go but unfortunately it didn't work for me - the page was still not displayed and the error was not handled.

Solution:First, set the size of request accepted by the server to maximum (1GB) in web.config. Then, define a custom HttpModule that would check request's length (also in web.config):

I've found this piece of code here. It works perfect. The only thing I don't understand is why the whole request needs to be read for this to work? I've tried to make the redirection right after wr.GetTotalEntityBodyLength(); but it didn't work. Anybody knows why?

Sometimes you want to disable all page elements at one time. There are many ways to achieve that. I'm using an additional div displayed on the top layer of the page. It covers the whole page content and makes clicking elements on lower layers impossible. The div can be totally transparent so the user still sees the content of the lower layers.

First, you need to place the additional div on your page, right behind the <body> tag:

...</head><body> <div id="disablingDiv" ></div>...

Then, you need to create appropriate style for that div. This element needs to be displayed on the top layer:

#disablingDiv{ /* Do not display it on entry */ display: none;

/* Display it on the layer with index 1001. Make sure this is the highest z-index value used by layers on that page */ z-index:1001;

Now it is ready to use but not displayed. If you want to enable the div (to disable all underlaying page elements) just invoke the following JS code:

document.getElementById('disablingDiv').style.display='block';

To disable it again:

document.getElementById('disablingDiv').style.display='none';

You can also play with background color and opacity to create different effects. The div itself can contain some additional elements e.g. button allowing enabling, pictures, etc. I've created this simple style basing on more complex example of lightbox described here.