Prevent caching of stylesheet and javascript files

First something about caching

The numerous caching options you have in ASP.NET (MVC) are mainly focused on data and page output caching. But caching also occurs at the webserver, network and browser level.  These you can’t always control from within your code.

When your content leaves your application, it is processed by the webserver, depending on the server and version it has numerous options to control how and when it is cached. When your content is processed by the webserver and sent to the browser, there is also the network that can control the caching, namely proxy and web acceleration servers. Finally the content arrives in the browser and the browser itself has also numerous options related to caching. Generally spoken, they all use the same parameters, or at least some of them, to determine when, what and how long the content should be cached.

How does this caching work? Generally spoken, following rules apply:

  1. If the response header says not to cache, it doesn’t cache
  2. If we use a secure or authenticated transfer, like HTTPS, it doesn’t cache either
  3. If the cache expiring time or any other age-controlling header says it’s still ‘fresh’, it doesn’t cache
  4. If there’s an old version in the cache, the server will be asked to validate the version.  If the version is still good, it is served from the cache.
  5. Sometimes when the server cannot be reached due to network failure or disconnectivity, the content is also directly served from the cache.

Then what parameters are used, and how are they used?

  • HTTP Headers: these are sent in the request, but are not visible in the content
    • Expires: tells the cache how long the content stays fresh. After that time, the cache will always check back with the server. It uses an HTTP date in Greenwich Mean Time (GMT), any other or invalid format will be interpreted as in the pas and makes the content uncachable.  For static data you can set a time in the very far future, for highly dynamic content, you can set a time much closer, or even in the past to have the cache refresh the content more often or at every request.
    • Cache-Control: In response to some of the drawbacks of the Expired header, the Cache-Control header class was introduced. It includes (some, not all):
      • max-age=[seconds]
      • public / private
      • no-cache / no-store
      • must-revalidate
    • Pragma: no-cache: the HTTP specifications aren’t clear of what it means, so don’t rely on it, use the ones above
  • HTML meta tags: Unlike HTTP Headers, HTML meta tags are present in the visible content, more precisely in the <HEAD> section of your HTML page. A huge drawback of the us of HTML meta tags is, is that they can only be interpreted by browsers, and not all of them use them like you would expect. So prefer HTTP headers over HTML meta tags

A great Caching Tutorial can be found here: http://www.mnot.net/cache_docs/, and another one here: Save Some Cash: Optimize Your Browser Cache

An easy solution

Now, all of the caching systems rely in some way on the full request string to identify the content that is being cached.

So, the easiest solution would be to request a new unique URL every time the resource has changed, with a new version number.

How we do it in ASP.NET MVC

ASP.NET MVC (and ASP.NET Webforms also) doesn’t generate a new version number automatically.  You need to tell it to do so in the AssemblyInfo.cs file.  After a default project setup it contains a line like:

[assembly: AssemblyVersion("1.0.0.0")]

The version number is a four-part string with the following format: <major version>.<minor version>.<build number>.<revision>.  You usually set the major and minor version manually, as they are used as the type library version number when the assembly is exported, and don’t (need to) care of the build and revision number.  Well, now we do.

When you change this line to (or add it if it doesn’t exist):

[assembly: AssemblyVersion("1.0.*")]

We tell the compiler to generate a build and revision number for us. The generated build number is the number of days since 1-01-2000 (so 9-08-2010 gives 3873) and the revision number is the number of two second intervals since midnight local time (so a build at 11:59:12 gives 19776).

Now we have instructed our application to generate a new unique build number for us with every build, and every (possible) change of a resource, we can use this number as a unique parameter value in the URL of the the resource.

First we need to pass this version number from controller to view.  In the constructor of the (base)controller we put the version number in the ViewData Dictionary. With the ViewData you easily can pass data from the controller to the view using a key-value pattern.

protected BaseController(){
ViewData["version"] = Assembly.GetExecutingAssembly().GetName().Version;
}

And finally in the view, all you need to do is append this version number to the URL of the files you want to be prevented from caching:

<script type="text/javascript" language="javascript" src="<%: Url.Content("~/Scripts/commonFunctions.js?" + ViewData["version"]) %>"></script>

This makes sure we have a unique URL for our resources and they are not cached by the browser or a proxy.

Of course, like stated above, there are other ways of preventing files from being cached anywhere between the server and the browser, but the advantage of this method is that you don’t need to poke around in IIS settings (in case when you don’t have access to it) and you can define when and which version of the file you want to be cached.  And you can of course use any other method to generate a unique URL.

One more remark: When building a multi-tier application, make sure you set the version number in the AssemblyInfo.cs of the project where you use it, meaning, that if you put your base controller in a shared assembly, you need to specify the version number in the shared assembly project.

21 Stimulating Color Palette Tools For Designers

I’m always excited about the possibilities of a new design. At the very beginning, I never really know where it will end up, and I love that feeling. The whole process of choosing colors and creating a color palette for a site is usually one of my first (and favorite) steps. Even if I have the chosen colors from the client, I still use a series of color scheme tools to put together the final palette. It’s one of my design inspiration triggers.

SitePoint21 Stimulating Color Palette Tools For Designers

50 Useful Design Tools For Beautiful Web Typography | CSS, Fonts | Smashing Magazine

Typography is elegant when it is attractive and communicates the designer’s ideas. When chosen wisely and used carefully, it can be very effective in supporting the overall design. Designers are always exploring different techniques with type: some use images or sIFR to produce very beautiful typography, while others prefer CSS alone to get the typography just right.

Today, we will look at 50 most useful typographic tools, techniques and resources for creating effective and expressive designs. We will also look at some hands-on typography tools that help designers and developers learn how to style their Web content, test it interactively and see the changes instantly. These tools are great for experimenting with different font types for your website.

Below we cover typographic tools, useful typographic references, font browsers, typographic CSS- and JavaScript-techniques, hyphenation techniques, sIFR tools and resources, grids and related tools, free and commercial fonts, a guide to Web typography, examples of great Web typography.

Smashing Magazine50 Useful Design Tools For Beautiful Web Typography

Design for Developers

A few years ago I had the opportunity to sit down with a designer possessed of a rare talent. We were both part of the same team and he was creating some UI elements that I was to wire up. As I sat there (in awe) watching him work I realized that much of his considerable skill was rooted in fundamentals not unlike the art of programming. Of course, there are design skills that are intuitive that can’t be "learned." But, that can also be said of the logical clarity found in a really elegant data model or a brilliant inheritance tree. I am certainly no designer, but I have observed the more creative among us for several years and have gained some insight into their world. In this article I’ll share some basic principles that can help raise your design acumen and improve the experience of your users.

SYS-CON MEDIADesign for Developers

10 Useful Techniques To Improve Your User Interface Designs

Web design consists, for the most part, of interface design. There are many techniques involved in crafting beautiful and functional interfaces. Here’s my collection of 10 that I think you’ll find useful in your work. They’re not related to any particular theme, but are rather a collection of techniques I use in my own projects. Without further ado, let’s get started.

Smashing Magazine10 Useful Techniques To Improve Your User Interface Designs

50 Extremely Useful And Powerful CSS Tools

We love useful stuff. For months, we have been bookmarking interesting, useful and creative CSS tools and related resources. We have been contacting developers, encouraging them to improve their tools and release their handy little apps to the public. Last year we prepared and published some of them in a series of smashing posts about CSS. Now again is the time to give these tools the attention they deserve. Big thanks to all designers and developers who contributed to the design community over the last months and years. We — our community and the design community — truly appreciate your efforts.

Below, we present 50 extremely useful CSS tools, generators, templates and resources. We did not include “traditional” CSS tools, such as Firebug or the Web Developer extension, but tried to focus on rather unknown tools that are definitely worth a look. Some tools are new and some are old, but hopefully everybody will find a couple of new useful or at least inspiring tools.

We strongly encourage you to develop these tools further, build on the ideas presented here, release new tools for the public and let us know about them. We would love to feature your handy tool in our next review.

Smashing Magazine50 Extremely Useful And Powerful CSS Tools

Opera: Web Standards Curriculum

As the most standards-compliant Web browser, Opera is dedicated to promoting Web standards across the globe. Web standards make the Web available to anyone, on any device, anywhere in the world.

Opera has created the Web Standards Curriculum (WSC) in association with the Yahoo! Developer Network. This tutorial course takes students from complete beginner to having a solid grounding in standards-based Web design, including HTML, CSS, and JavaScript development. The course is supported by top companies and organizations such as the Web Standards Project (WaSP) and Yahoo!.

Split into more than 50 focused articles, students can follow the curriculum from start to finish or simply read articles that interest them the most. Each article contains essential theory, practical examples, and exercise questions. The first 41 articles are now published, and roughly ten ones covering JavaScript basics will follow ASAP, to complete the course.

Why should you incorporate the Opera WSC into your curriculum? Web standards in a Web site promote efficiency, ease of maintenance, accessibility, device compatibility, and search optimization. The Opera WSC features the most up-to-date practices in Web standards. Best of all, the course is free, requiring no expensive textbooks.

OperaWeb Standards Curriculum

Migrate apps from Internet Explorer to Mozilla

When Netscape started the Mozilla browser, it made the conscious decision to support W3C standards. As a result, Mozilla is not fully backwards-compatible with Netscape Navigator 4.x and Microsoft Internet Explorer legacy code; for example, Mozilla does not support as I will discuss later. Browsers, like Internet Explorer 4, that were built before the conception of W3C standards inherited many quirks. In this article, I will describe Mozilla’s quirks mode, which provides strong backwards HTML compatibility with Internet Explorer and other legacy browsers.

MDCMigrate apps from Internet Explorer to Mozilla

CSS Sprites2 – It’s JavaScript Time

A sense of movement is often the differentiator between Flash-heavy web sites and standards-based sites. Flash interfaces have always seemed more alive—responding to the user’s interactions in a dynamic way that standards-based web sites haven’t been able to replicate.

Lately that’s been changing, of course, with a resurgence in dynamic interface effects, helped along by JavaScript libraries that make it easy—libraries such as Prototype, Scriptaculous, Moo, YUI, MochiKit (and I could go on). It’s high time to revisit the CSS Sprites technique from four years ago, and see if we can’t interject a little bit of movement of our own.

A List Apart: Articles: CSS Sprites2CSS Sprites2 – It’s JavaScript Time

URL Rewriting in IIS 7

I started to use URL Rewriting on a Windows 2008 Server running Internet Information Server 7.  At the time of writing, a technical preview of the module is available here: Using URL Rewrite Module.

After installing the module, I was able to configure a first rule that rewrote an incoming URL in the form of http://server/en/catalogue/123/abc123 to http://server/Catalogue.aspx?l=en&cat=123&sub=abc123, exactly the way I wanted it.

But when opening the page, I saw my layout and styles were gone.  Not difficult to know where the problem is, because stylesheets and images are loaded from the client with their path relative to the requested page.  In this case a reference to "style.css" will be loaded from http://server/en/catalogue/123/style.css instead of http://server/style.css, as the client doesn’t know we’re using URL rewriting on the server.

To get around this problem, several options are possible.  I’ll list few of them here, some good, some even worse.  Of course, these are not the only ones, but these were the ones I looked at to solve my problem.  Other solutions might be even better, so any input and feedback is welcome. My solution is much easier and fits my needs.  It’s posted below the other options.

  1. Override the Render() method of your base page or masterpage: URL rewriting breaks ASP.NET 2’s themes
  2. Use RewritePath Method (String, Boolean) with the second parameter (rebaseClientPath) set to false. (Huh? custom code?)
  3. Move your images and stylesheets out of the App_Themes folder (WTF?): URL Rewriting and folders with dashcommerce
  4. Hardcode your links to stylesheets and images (OMG!)
  5. I’m not going to list any more options as it’s getting worse and worse…

But why don’t you use the power when you’re using the force?

I wrote a rule that is processed before any other rule, and which takes any url pointing to file in an App_Themes folder (or just a stylesheet, which is also possible in the same way):

  • Pattern: ^(.+)/App_Themes/(.+)
  • Rewrite URL: App_Themes/{R:2}
  • and check "Stop processing of subsequent rules"

If you make sure that this rule is processed before the other regular rules by moving it to the top in the ordered list, than all references to theme files (stylesheets, images,…) are correctly served and your layout remains correct.

Testing IE Versions Just Got a Little Easier

Testing your sites on different versions of Internet Explorer has always been notoriously difficult mainly due to the fact that Microsoft prevents you from running to different versions of the browser in Windows. Sure there have been solutions to get around this limitation but in my experience, they’ve always caused unexpected results and instability for the operating system or required you to run a VM. Not ideal.

AjaxianTesting IE Versions Just Got a Little Easier