Мысли вслух…

Avoiding bugs from cached js and css files in SharePoint (layout folder)

Автор: Июл.18.2012 Категория: SharePoint

Last two days I looked for solution — «How to append param to js and css files which included in masterpage», it needs to avoid bugs with Browser caching after new version deployment.

I found these solutions:

  1. If you using Style Library enable Blob caching and SharePoint will use params to each item from Style Library (more here);
  2. Try to inherit from CssLink (for css only) and override Render method, it hasn’t work for me, Fiddler and others Web-Debuggers shown me a few instances of each files;
  3. Try to change collection in RunTime via Reflection (my choice).

I’ve already used my own User Control which pre-configured end-user data. This control has been included in masterpage. What I did:

  1. Modified HttpContext.Current.Items[«sp-scriptlinks»];
  2. Modified private field «m_css» in SPContext.Current.

As result, my resources (css and js) loaded with param (is version of assembly), it means that after each one system update I will avoid problem with browser caching.

CSS:

var cssListFieldInfo = SPContext.Current.GetType().GetField("m_css", BindingFlags.Instance | BindingFlags.NonPublic);
if (cssListFieldInfo != null)
{
var cssListObj = (IList) cssListFieldInfo.GetValue(SPContext.Current);
if (cssListObj == null)
{
return;
}

foreach (var cssItem in cssListObj)
{
var cssRefFieldInfo = cssItem.GetType().GetField("CssReference");
if (cssRefFieldInfo == null)
{
continue;
}
var cssRef = cssRefFieldInfo.GetValue(cssItem).ToString();

if (cssRef.IndexOf("/_layouts/USPS/styles/", StringComparison.InvariantCultureIgnoreCase) == -1)
{
continue;
}

cssRef += "?rev=" + version;
cssRefFieldInfo.SetValue(cssItem, cssRef);

var cssCanonicalFieldInfo = cssItem.GetType().GetField("m_CanonicalRef", BindingFlags.Instance | BindingFlags.NonPublic);
if (cssCanonicalFieldInfo == null)
{
continue;
}
cssCanonicalFieldInfo.SetValue(cssItem, cssRef);
}

cssListFieldInfo.SetValue(SPContext.Current, cssListObj);
}

JS:

// solution to change names for js for avoiding js caching. Original - http://www.sharepointnutsandbolts.com/2011/01/eliminating-large-js-files-to-optimize.html
// get list of registered script files which will be loaded..
object oFiles = HttpContext.Current.Items[HTTPCONTEXT_SCRIPTLINKS];
var registeredFiles = (IList) oFiles;
var version = typeof(DataPreLoader).Assembly.GetName().Version;

foreach (var file in registeredFiles)
{
//file type of - ScriptLinkInfo (internal class)
// use reflection to get the ScriptLinkInfo.Filename property, then check if in FilesToSuppress list and remove from collection if so..
Type t = file.GetType();
FieldInfo fieldInfo = t.GetField("m_filename", BindingFlags.Instance | BindingFlags.NonPublic);
if (fieldInfo != null)
{
string fullfilename = fieldInfo.GetValue(file).ToString();
if (fullfilename.IndexOf("/_layouts/USPS/scripts/", StringComparison.InvariantCultureIgnoreCase) != -1)
{
fullfilename += "?rev=" + version;
fieldInfo.SetValue(file, fullfilename);
}
}
}

// overwrite cached value with amended collection..
HttpContext.Current.Items[HTTPCONTEXT_SCRIPTLINKS] = registeredFiles;
:,

Leave a Reply

:bad: :beer: :biggrin: :blink: :blush: :bomb: :confused: :cool: :crazy: :cry: :dont_know: :eek: :evil: :dance: :heart: :idea: :joke: :kiss: :lol: :mad: :music: :rose: :sad: :smile: :surprised: :tongue: :yahoo: :wall: :wink:
 

Поиск

Список друзей