Checksum Dependencies In Surf

cancel
Showing results for 
Search instead for 
Did you mean: 

Checksum Dependencies In Surf

ddraper
Intermediate II
0 13 9,396
Please note: The following features are at the time of writing only available in the Alfresco Community source code and have not as yet been included in any release.

Introduction



One of the problems that has affected upgrades of Alfresco in the past is that the end-users’ browsers may end up using cached copies of JavaScript and  CSS files that have been updated during the upgrade.  Spring Surf now has introduced a new service called the “DependencyHandler” which has been created to solve this specific problem. It does this by appending a unique checksum to the end of each requested JavaScript and CSS dependency where the checksum is generated from the contents of the file and so will change whenever the file content is changed. The checksum associated with the file is cached for the lifecycle of the web server meaning that it does not need to be generated for each request and Surf performance has actually been enhanced by this mechanism because Surf also caches the location from which the dependency is retrieved (Surf can retrieve dependencies from a number of different locations, e.g. JAR files, class path, file system, remote location, etc.).

Configuration and Usage



By default the capability is disabled in Surf but will be enabled in future releases of Alfresco Share. To enable is you simply need to set the following line within the Surf configuration (this can be found in the “webapps/share/WEB-INF/surf.xml”):

<web-framework>

   …

   <use-checksum-dependencies>true</use-checksum-dependencies>

   …

</web-framework>


In order to make use of the dependency handler you will need to use  the <@script>, <@link> and <@checksumResource> FreeMarker directives in your  TemplateInstance and WebScript files, e.g.

<@script src='${url.context}/res/yui/yahoo/yahoo.js'></@script>

<@link rel='stylesheet' type='text/css' href='${url.context}/res/css/base.css' />

<@checksumResource src='${url.context}/res/css/ipad.css'/>


(Those examples are taken from the resources.get.html.ftl file  where the ${url.context} is a FreeMarker variable set to the application  context, e.g. “share”)



  • <@script> generates JavaScript script import declarations.


  • <@link> rolls up multiple CSS requests into a style declaration using a separate '@import' statement for each usage of <@link>.


  • <@checksumResource> generates just the URL (i.e. without being specific to CSS or JavaScript and can therefore be used with images or even WebScript requests. One additional feature of the <@checksumResource> directive is that you can specify the attribute 'parameter' which makes the checksum appear as the value of a request parameter of the supplied name (rather than as part of the file name itself).


Debug and Production Suffices



The DependencyHandler is capable of dealing with production (minified) and debug versions of files and actually handles these better than before. The Spring application context configuration for the bean allows you to specify the different file suffices that can be used for both production and debug versions and the DependencyHandler will work through the options until it finds a file. This means that Surf will always be able to fall back to the debug version of the code if a minified version does not exist. By default the debug suffices are:



  • “” (i.e. no suffix)


  • “_src”


  • “-debug”


And the production suffices are:



  • “-min”


  • “-minified”


  • “” (i.e. no suffix)


You can change these suffices by overriding the definition for the “dependency.handler” bean in the Spring application context in case you want to add, remove or re-order the default entries.

Example



The following screenshot shows the Chrome Developer Tools window displaying the JavaScript resources loaded for a page in Alfresco Share - note that each request is appended with a checksum value (apart from 'tiny_mce.js' which handles its dynamic dependencies in its own way).





Current Limitations



The current limitation of this solution is that it only works with static requests from the page and not dynamic requests made from a script – although many JavaScript libraries provide their own solution to this problem (e.g. TinyMCE) however it is something to be aware of.
13 Comments
blog_commenter
Active Member
This is a great addition for ressources. I would also love to see checksum support for repository contents to be able to cache content like avatar and preview images in the browser without having to look up modification dates in every request. This would also improve performance as each avatar image takes 30-50ms until a '304 not modified' is returned. Have you looked into that as well?
ddraper
Intermediate II
@Florian Thanks for the feedback. We're aware of this problem and something that we'd really like to solve. I'm going to find some time to look into this, but haven't had a chance yet. I'll be sure to post any updates if we come up with something.
blog_commenter
Active Member
This really will ease upgrades and deploying addons. The email from IT department 'We have upgraded Alfresco, oh and by the way refresh your browser cache (again)' is no more Smiley Happy
Ran into one little issue that I just filed ALF-13209 that css links have media='screen' hardcoded, that is not always so that you want to just use css for screen layout. I need it for print for example, see links in the case. I think since you are working on this it may be a good time to maybe add media as an optional parameter for @link to override media type.
blog_commenter
Active Member
[...] David Draper's Blog A Blog From Alfresco Engineering      « Checksum Dependencies In Surf [...]
ddraper
Intermediate II
@Peter, thanks - you're right, the hard-coded media setting is an oversight on my part. Thanks for raising the JIRA issue -  I'll make sure that it gets fixed.
ddraper
Intermediate II
@Peter I've started looking at the ALF-13209 but I've realised that there's actually much simpler solution - you can just use the <@checksumResource> which just outputs the URL and you can then place this inside a <style> element and set your own media attribute. Although we're changing the URL of the existing <@link> directive we're not changing how it's used or how it rolls up CSS files into a <style> element to workaround an old IE bug. I'll also update the JIRA issue with this information.
ddraper
Intermediate II
@Florian I've done some work on the 304 issue and have a fix for the web-preview and document library thumbnails but not the avatar images yet - these will make their way into the community source in due course (can't say for certain when yet though). I'll also look at addressing the avatar image requests too.
ddraper
Intermediate II
@Florian I've just committed some updates to the Community Source to fix the majority of the unnecessary 304 revalidation requests for avatars and thumbnails.
blog_commenter
Active Member
[...] use-checksum-dependencies (see blog by David Draper) [...]
blog_commenter
Active Member
[...] my last blog post I described the new DependencyHandler service that has recently been added to Spring Surf.  Whilst [...]
blog_commenter
Active Member
[...] Using MD5 checksums to allow browsers so safely cache resources indefinitely [...]
blog_commenter
Active Member
Where can I find the implementation of the these freemarker's macro: @link, @script and @checksumResource. Thanks a lot for the tuto and your answer.
ddraper
Intermediate II
The directives are all in the org.springframework.extensions.directives package in the spring-surf project, 'ChecksumResourceDirective.java', 'LinkFreeMarkerDirective.java' ... I think  is actually a FreeMarker macro and isn't backed by Java.