Posts tagged ‘webforms’

November 4, 2013

Continuous deploy of multiple Azure Cloud Services within a single solution using TFS Online

Team Foundation Server is a fantastic configuration management system that integrates with the full Microsoft development stack.

With Windows Azure and its TFS online integration, continuous deploy can easily be set up and customized. However, one frustration I came across, is that I have a solution that has a worker role and a web role. I want these deployed to separate Cloud Services within my Azure Subscription, but the AzureContinuousDeployment build process only supports targeting the first project to be deployed.

In order to get around this, we can modify the AzureContinuousDeployment process to allow the developer to dictate which Cloud Service project to deploy. The first step to do this is to duplicate the AzureContinuousDeployment.11.xaml workflow. You can do this by opening the Source Control Explorer in Visual Studio, and navigating to the BuildProcessTemplates folder.

You will see, in the right hand pane, a list of the Build Process Templates that are available to you.

Build Process Templates

You can copy AzureContinuousDeployment.11.xaml and use the copied Build Process Template to create the alternate template that will allow you to dictate which Cloud Service is deployed.

When you open the copied xaml file you will see the, hopefully familiar, Windows Workflow designer. What we are going to do is modify the process flow to allow the definition of the Cloud Service to deploy.

When you open the xaml file, find the block that defines the Cloud Service to deploy, it will look like this:

Find the Azure Project

You’ll notice that the action that finds the Azure Project in the solution has no inputs to it, this is because it simply looks for the first Azure Project in the solution. In order to look for others, we need to define the MSBuild target name of the Azure Project.

To do this we first need to add an argument to the build process template that can then be configured in the build definition.

Open the argument editor by clicking “Arguments” at the bottom of the content pane and add a new argument.

Next, we can change the block that defines the Azure Project to check if the Alternate MS Build Target has been set and if it is, set ccProjName, the variable that captures the Azure project name, to that value.

We can now save this build process template, and select it in the build definition.

Finally, we need to choose the project that we want to deploy from the build definition.

We do this by setting the AlternateMSBuildTarget argument to the target name that we want to deploy. This is usually the name of the project with _ (underscore) replacing . (period). So, for example, if your project name was “Ebenezer.Web.Azure”, you would use “Ebenezer_Web_Azure”.

September 21, 2010

Writing JavaScript based Web Apps that degrade well using Web Forms

A trait I’ve observed in programmers who have learnt their trade using Web Forms, rather than programmers who have been involved with another language such as PHP or Python, which forces a slightly higher regard for the output that the browser sees, is a slight disregard for browser settings, and a reluctance to write apps which degrade well; preferring the argument that JavaScript, Java, Flash or another technology must be enabled for the function of the particular web application.

Now, more than ever, with the increased push within Microsoft of jQuery as a Javascript platform, an understanding of writing JavaScript that degrades well is important.

Here I will outline a few techniques that are useful in ensuring that JavaScript content will degrade in a useful way for users with browsers which do not support JavaScript. While some of these techniques apply to all web applications, I write particularly with Web Forms in mind.

1) Do not hide elements that are essential to page context, and can only be shown using JavaScript

A common use of jQuery, Scriptaculous and other JavaScript libraries, is the ability to lay related information into tabs which are switchable without changing the page context, and without a postback to the server. As such the page is often laid out with the first tab visible, and the others hidden by CSS, waiting for the JavaScript event which triggers other tabs being shown and hidden. However, this alienates people without JavaScript support, in that they are stuck with just the first tab visible. There are two ways in which we can deal with this problem. Firstly, we could implement this functionality using PostBacks (asp:MultiView, with asp:Buttons styled correctly, to switch tabs), getting data from a library which is also presented as an HttpModule. The front end can then, in the document.ready method override the asp:Buttons functionality to call off to the HttpModule directly using an AJAX call and format the tabs accordingly. Secondly, and more simply, we could allow the tabs to degrade as a simple list at the top of the page, with anchor named links allowing the user to jump to areas of the page. This method is preferable since the anchor named links (denoted by a #name on the end of the URI), enable the developer to ensure that history is maintained when the jumps are captured with JavaScript, allowing the user to switch tabs and use the back button on their browser to switch back a tab.

2) Be cautious in use of LinkButton and AutoPostback

Both LinkButton and AutoPostback require JavaScript in order to function correctly. Of course clients sometimes want this functionality, but this can be mitigated in both cases. Firstly, with LinkButtons, use a simple anchor tag, which links to a page which parses QueryString arguments. If a PostBack is absolutely required use an asp:Button and use CSS to style it to appear as a link. Secondly, with AutoPostback, this is a piece of functionality oft requested. We can enable AutoPostback, but in addition add an asp:Button which points to the same method as the, for example, asp:DropDown change handler. This button can then be hidden using JavaScript on the page load. Therefore, if the user has JavaScript enabled, the functionality is as expected, if not, the AutoPostback will not work, but the Button will appear.

3) Where Flash is used, use swfobject and insist on a functional alternative

swfobject is a great library which allows injection of Flash based on the browsers capability to display it. As part of the arguments to inject the Flash object into the page, swfobject accepts a div in which the Flash sits. As part of the design of the site, always insist that a reasonable, even with low functionality, alternative is designed. This can then be positioned in the div that the Flash replaces. If the user does not have the correct version of Flash, the alternative is presented and does not disrupt the user’s experience of the site. As an example, I did this with a Flash file that presented a “Coverflow” style interface to the user; the non JavaScript alternative was simply the current focussed image with left and right arrows, which triggered PostBacks to jump to the next image. Though not as highly functional as the Flash object, this presented users without a JavaScript/Flash capable browser/machine, with an alternative that served the purpose, and put across the message adequately.