November Happy Hour will be moved to Thursday December 5th.

Loading...
Area: Optimizely CMS
ARCHIVED This content is retired and no longer maintained. See the latest version here.

Recommended reading 

There is persisting and rendering support built in for the most common property types. In some rare cases however it can be needed to implement a custom property. When doing so you select a proper base type to inherit from depending on the type of your data. Optionally you can create a template for the data type (if the property should be visible on templates).

Implementing a custom property

When implementing a custom property you should first select a suitable basetype (e.g. PropertyString, PropertyNumber) depending on your data. Below is an example of a property that holds an enumerable of ContentReference and stores it as a serialized string.

C#
[PropertyDefinitionTypePlugIn] 
public class LinkingProperty : PropertyLongString 
{ 
    public IEnumerable<ContentReference> LinkedReferences 
    { 
        get 
        { 
            if (!String.IsNullOrEmpty(String)) 
            { 
                var entries = String.Split(';'); 
                return entries.Select(e => ContentReference.Parse(e)); 
            } 
            return null; 
        } 
        set 
        { 
            base.String = String.Join(";", value.Select(r => r.ToString())); 
        } 
    } 

    public override object Value 
    { 
        get { return LinkedReferences; } 
        set { 
                IEnumerable<ContentReference> links = value as IEnumerable<ContentReference>; 
                if (links != null) 
                { 
                    LinkedReferences = links; 
                } 
                else 
                { 
                    base.Value = value; 
                } 
            } 
    } 

    public override Type PropertyValueType 
    { 
        get { return typeof(IEnumerable<ContentReference>); } 
    } 

    public override object SaveData(PropertyDataCollection properties) 
    { return base.String; } 
}

Indexing references to other content from a custom property

If the custom property stores references to other content instances, it is a recommendation to have a soft link indexer for the type as well. Then when an editor tries to delete a content item he/she will get a warning if a property on another content item holds a reference to the item to be deleted. In case the custom property is inheriting PropertyContentReferece, PropertyUrl or PropertyXhtml then the soft indexing will likely be handled by the base type indexer. Below is an example of a soft link indexer for the custom property above:

C#
[ServiceConfiguration(typeof(IPropertySoftLinkIndexer))] 
public class LinkingPropertyIndexer : IPropertySoftLinkIndexer<IEnumerable<ContentReference>> 
{ 
    public IEnumerable<SoftLink> ResolveReferences(IEnumerable<ContentReference> propertyValue, IContent owner) 
    { 
        var softLinks = new List<SoftLink>(); 
        foreach (var link in propertyValue) 
        { 
            var softLink = ContentSoftLinkIndexer.CreateSoftLinkForContent(owner); 
            softLink.ReferencedContentLink = link; 
            softLink.SoftLinkType = ReferenceType.PageLinkReference; 
            softLinks.Add(softLink); 
        } 
        return softLinks; 
    } 
 }

The indexer is registered with the IOC container for interface IPropertySoftLinkIndexer. It should implement the generic interface IPropertySoftLinkIndexer<T> where the generic argument should be the PropertyValueType for the property implementation.

Do you find this information helpful? Please log in to provide feedback.

Last updated: Jul 09, 2014

Recommended reading