Creating macro namespaces
Macro namespaces serve as containers for static macro methods and fields. Users can access the members of namespaces when writing macro expressions, for example {% Math.Pi %} or {% Math.Log(x)* %}. Namespaces also appear in the macro autocomplete help. The system uses several default namespaces such as Math, String* or Util, and you can create your own namespaces for custom macros.
To add a custom macro namespace:
- Create a class inheriting from MacroNamespace<Namespace type>. In web site projects, you can either add the class into the App_Code folder or as part of a custom assembly.
- Register macro fields or methods into the namespace — add Extension attributes to the class, with the types of the appropriate container classes as parameters.
using CMS.Base;
using CMS.MacroEngine;
[Extension(typeof(CustomMacroFields))]
[Extension(typeof(CustomMacroMethods))]
public class CustomMacroNamespace : MacroNamespace<CustomMacroNamespace>
{
}
See Registering custom macro methods and Adding custom macro fields to learn about creating container classes for macro fields and methods.
Registering macro namespaces
Once you have defined the macro namespace class, you need to register the namespace as a source into a macro resolver (typically the global resolver).
We recommend registering your macro namespaces at the beginning of the application’s life cycle. Choose one of the following options:
- During the initialization process of the application itself — use the CMSModuleLoader partial class in the App_Code folder.
- When initializing custom modules — override the OnInit method of the module class.
The following steps describe how to register a macro namespace into the global resolver using the App_Code folder:
Create a class file in the App_Code folder (or CMSApp_AppCode -> Old_App_Code on web application projects).
Extend the CMSModuleLoader partial class.
Create a new class inside CMSModuleLoader that inherits from CMSLoaderAttribute.
Add the attribute defined by the internal class before the definition of the CMSModuleLoader partial class.
Override the Init method inside the attribute class.
Call the SetNamedSourceData method for the global resolver with the following parameters:
- A string that sets the visible name of the namespace (used in macro syntax).
- An instance of your macro namespace class.
- (Optional) By default, the registered namespace appears in the high priority section of the autocomplete help and macro tree. To add namespaces with normal priority, add false as the third parameter.
using CMS.Base;
using CMS.MacroEngine;
[MacroNamespaceLoader]
public partial class CMSModuleLoader
{
/// <summary>
/// Attribute class that ensures the registration of custom macro namespaces.
/// </summary>
private class MacroNamespaceLoaderAttribute : CMSLoaderAttribute
{
/// <summary>
/// Called automatically when the application starts.
/// </summary>
public override void Init()
{
// Registers "CustomNamespace" into the macro engine
MacroContext.GlobalResolver.SetNamedSourceData("CustomNamespace", CustomMacroNamespace.Instance);
}
}
}
The system registers your custom macro namespace when the application starts. Users can access the namespace’s members when writing macro expressions.
Registering namespaces as anonymous sources
By registering a macro namespace as an anonymous source, you can allow users to access the namespace’s members directly without writing the namespace as a prefix. For example, {% Field %} instead of {% Namespace.Field %}.
// Registers "CustomNamespace" as an anonymous macro source
MacroContext.GlobalResolver.AddAnonymousSourceData(CustomMacroNamespace.Instance);
You can register the same namespace as both a named and anonymous source. If you only register a namespace as an anonymous source, users cannot access the members using the prefix notation, and the namespace does not appear in the macro autocomplete help.
Note: Data items registered through anonymous macro sources do NOT appear in the macro autocomplete help. As a result, the autocomplete help only displays namespace members when using the prefix notation, even when the namespace is registered as both a named and anonymous source.