diff --git a/umbraco/presentation/macro.cs b/umbraco/presentation/macro.cs
index ae1d9e5215..89db4fbf33 100644
--- a/umbraco/presentation/macro.cs
+++ b/umbraco/presentation/macro.cs
@@ -368,24 +368,38 @@ namespace umbraco
String macroHtml = null;
Control macroControl = null;
- // zb-00037 #29875 : parse attributes here (and before anything else)
- foreach (var prop in model.Properties)
- prop.Value = helper.parseAttribute(pageElements, prop.Value);
+ // zb-00037 #29875 : parse attributes here (and before anything else)
+ foreach (var prop in model.Properties)
+ prop.Value = helper.parseAttribute(pageElements, prop.Value);
model.CacheIdentifier = getCacheGuid(model, pageElements, pageId);
if (model.CacheDuration > 0)
{
- macroHtml = macroCache["macroHtml_" + model.CacheIdentifier] as String;
-
- if (!String.IsNullOrEmpty(macroHtml))
+ if (cacheMacroAsString(model))
{
macroHtml = macroCache["macroHtml_" + model.CacheIdentifier] as String;
- HttpContext.Current.Trace.Write("renderMacro", "Content loaded from cache ('" + model.CacheIdentifier + "')...");
+
+ if (!String.IsNullOrEmpty(macroHtml))
+ {
+ macroHtml = macroCache["macroHtml_" + model.CacheIdentifier] as String;
+ HttpContext.Current.Trace.Write("renderMacro", "Macro Content loaded from cache ('" + model.CacheIdentifier + "')...");
+ }
+ }
+ else
+ {
+ if (macroCache["macroControl_" + model.CacheIdentifier] != null)
+ {
+ MacroCacheContent cacheContent = (MacroCacheContent)macroCache["macroControl_" + model.CacheIdentifier];
+ macroControl = cacheContent.Content;
+ macroControl.ID = cacheContent.ID;
+ HttpContext.Current.Trace.Write("renderMacro", "Macro Control loaded from cache ('" + model.CacheIdentifier + "')...");
+ }
+
}
}
- if (String.IsNullOrEmpty(macroHtml))
+ if (String.IsNullOrEmpty(macroHtml) && macroControl == null)
{
int macroType = model.MacroType != MacroTypes.Unknown ? (int)model.MacroType : MacroType;
switch (macroType)
@@ -475,29 +489,40 @@ namespace umbraco
{
if (macroControl != null)
{
- using (var sw = new StringWriter())
+ // NH: Scripts and XSLT can be generated as strings, but not controls as page events wouldn't be hit (such as Page_Load, etc)
+ if (cacheMacroAsString(model))
{
- var hw = new HtmlTextWriter(sw);
- macroControl.RenderControl(hw);
+ using (var sw = new StringWriter())
+ {
+ var hw = new HtmlTextWriter(sw);
+ macroControl.RenderControl(hw);
- macroCache.Insert("macroHtml_" + model.CacheIdentifier,
- sw.ToString(),
- null,
- DateTime.Now.AddSeconds(model.CacheDuration),
- TimeSpan.Zero,
- CacheItemPriority.Low,
- null);
+ macroCache.Insert("macroHtml_" + model.CacheIdentifier,
+ sw.ToString(),
+ null,
+ DateTime.Now.AddSeconds(model.CacheDuration),
+ TimeSpan.Zero,
+ CacheItemPriority.Low,
+ null);
+
+ // zb-00003 #29470 : replace by text if not already text
+ // otherwise it is rendered twice
+ if (!(macroControl is LiteralControl))
+ macroControl = new LiteralControl(sw.ToString());
+ }
+ }
+ else
+ {
+ macroCache.Insert("macroControl_" + model.CacheIdentifier, new MacroCacheContent(macroControl, macroControl.ID), null,
+ DateTime.Now.AddSeconds(model.CacheDuration), TimeSpan.Zero, CacheItemPriority.Low,
+ null);
- // zb-00003 #29470 : replace by text if not already text
- // otherwise it is rendered twice
- if (!(macroControl is LiteralControl))
- macroControl = new LiteralControl(sw.ToString());
}
}
}
}
}
- else
+ else if (macroControl == null)
{
macroControl = new LiteralControl(macroHtml);
}
@@ -505,6 +530,11 @@ namespace umbraco
return macroControl;
}
+ private bool cacheMacroAsString(MacroModel model)
+ {
+ return model.MacroType == MacroTypes.XSLT || model.MacroType == MacroTypes.Python;
+ }
+
public static XslCompiledTransform getXslt(string XsltFile)
{
if (HttpRuntime.Cache["macroXslt_" + XsltFile] != null)
@@ -604,7 +634,7 @@ namespace umbraco
foreach (DictionaryEntry macroDef in macro.properties)
{
var prop = model.Properties.Find(m => m.Key == (string)macroDef.Key.ToString().ToLower());
- // zb-00037 #29875 : values have already been parsed + no need to parse ""
+ // zb-00037 #29875 : values have already been parsed + no need to parse ""
string propValue = prop != null ? prop.Value : "";
if (!String.IsNullOrEmpty(propValue))
{
@@ -761,27 +791,27 @@ namespace umbraco
/// Gets a collection of all XSLT extensions for macros, including predefined extensions.
///
/// A dictionary of name/extension instance pairs.
- public static Dictionary GetXsltExtensions()
- {
- // zb-00041 #29966 : cache the extensions
+ public static Dictionary GetXsltExtensions()
+ {
+ // zb-00041 #29966 : cache the extensions
- // We could cache the extensions in a static variable but then the cache
- // would not be refreshed when the .config file is modified. An application
- // restart would be required. Better use the cache and add a dependency.
+ // We could cache the extensions in a static variable but then the cache
+ // would not be refreshed when the .config file is modified. An application
+ // restart would be required. Better use the cache and add a dependency.
- return umbraco.cms.businesslogic.cache.Cache.GetCacheItem(
- _xsltExtensionsCacheKey, _xsltExtensionsSyncLock,
- CacheItemPriority.Normal, // normal priority
- null, // no refresh action
- new CacheDependency(_xsltExtensionsConfig), // depends on the .config file
- TimeSpan.FromDays(1), // expires in 1 day (?)
- () => { return GetXsltExtensionsImpl(); });
- }
+ return umbraco.cms.businesslogic.cache.Cache.GetCacheItem(
+ _xsltExtensionsCacheKey, _xsltExtensionsSyncLock,
+ CacheItemPriority.Normal, // normal priority
+ null, // no refresh action
+ new CacheDependency(_xsltExtensionsConfig), // depends on the .config file
+ TimeSpan.FromDays(1), // expires in 1 day (?)
+ () => { return GetXsltExtensionsImpl(); });
+ }
- // zb-00041 #29966 : cache the extensions
- const string _xsltExtensionsCacheKey = "UmbracoXsltExtensions";
- static string _xsltExtensionsConfig = IOHelper.MapPath(SystemDirectories.Config + "/xsltExtensions.config");
- static object _xsltExtensionsSyncLock = new object();
+ // zb-00041 #29966 : cache the extensions
+ const string _xsltExtensionsCacheKey = "UmbracoXsltExtensions";
+ static string _xsltExtensionsConfig = IOHelper.MapPath(SystemDirectories.Config + "/xsltExtensions.config");
+ static object _xsltExtensionsSyncLock = new object();
static Dictionary GetXsltExtensionsImpl()
{
@@ -790,7 +820,7 @@ namespace umbraco
// Load the XSLT extensions configuration
var xsltExt = new XmlDocument();
- xsltExt.Load(_xsltExtensionsConfig);
+ xsltExt.Load(_xsltExtensionsConfig);
// add all descendants of the XsltExtensions element
foreach (XmlNode xsltEx in xsltExt.SelectSingleNode("/XsltExtensions"))
@@ -834,14 +864,14 @@ namespace umbraco
//also get types marked with XsltExtension attribute
- // zb-00042 #29949 : do not hide errors, refactor
+ // zb-00042 #29949 : do not hide errors, refactor
foreach (Type xsltType in BusinessLogic.Utils.TypeFinder.FindClassesMarkedWithAttribute(typeof(XsltExtensionAttribute)))
{
object[] tpAttributes = xsltType.GetCustomAttributes(typeof(XsltExtensionAttribute), true);
foreach (XsltExtensionAttribute tpAttribute in tpAttributes)
{
- string ns = !string.IsNullOrEmpty(tpAttribute.Namespace) ? tpAttribute.Namespace : xsltType.FullName;
- extensions.Add(ns, Activator.CreateInstance(xsltType));
+ string ns = !string.IsNullOrEmpty(tpAttribute.Namespace) ? tpAttribute.Namespace : xsltType.FullName;
+ extensions.Add(ns, Activator.CreateInstance(xsltType));
}
}
@@ -1112,8 +1142,8 @@ namespace umbraco
}
MacroPropertyModel propModel = model.Properties.Find(m => m.Key == propertyAlias.ToLower());
- // zb-00037 #29875 : values have already been parsed + no need to parse ""
- object propValue = prop != null ? propModel.Value : "";
+ // zb-00037 #29875 : values have already been parsed + no need to parse ""
+ object propValue = prop != null ? propModel.Value : "";
// Special case for types of webControls.unit
if (prop.PropertyType == typeof(Unit))
propValue = Unit.Parse(propValue.ToString());
@@ -1205,8 +1235,8 @@ namespace umbraco
}
MacroPropertyModel propModel = model.Properties.Find(m => m.Key == propertyAlias.ToLower());
- // zb-00037 #29875 : values have already been parsed + no need to parse ""
- object propValue = prop != null ? propModel.Value : "";
+ // zb-00037 #29875 : values have already been parsed + no need to parse ""
+ object propValue = prop != null ? propModel.Value : "";
if (propValue == null)
continue;
@@ -1400,8 +1430,8 @@ namespace umbraco
var myHttpWebRequest = (HttpWebRequest)WebRequest.Create(url);
// propagate the user's context
- // zb-00004 #29956 : refactor cookies names & handling
- HttpCookie inCookie = StateHelper.Cookies.UserContext.RequestCookie;
+ // zb-00004 #29956 : refactor cookies names & handling
+ HttpCookie inCookie = StateHelper.Cookies.UserContext.RequestCookie;
var cookie = new Cookie(inCookie.Name, inCookie.Value, inCookie.Path,
HttpContext.Current.Request.ServerVariables["SERVER_NAME"]);
myHttpWebRequest.CookieContainer = new CookieContainer();