2

Annoyingly, the MediaData class in Episerver doesn't have any basic properties like source URL, alt text, etc. I'm trying to implement a class to inherit from MediaData and provide specific properties for a certain type of media asset (PDF in this example).

I've tried manually setting the property values and also overriding the SetDefaultValues event, to no avail. Although, I do see either a textbox or a URL picker based on the type I use for "SrcUrl", however it is blank and never populates the uploaded PDF's URL.

[ContentType(
    DisplayName = "PDF File",
    GUID = "xxxxxxx-xxxx-xxxxxx-xxxx-xxxxxxxxxxx")]
[MediaDescriptor(ExtensionString = "pdf")]
public class PdfFile : MediaData
{
    [UIHint(UIHint.MediaFile)]
    [Display(Name = "PDF URL",
        Description = "Link to view or reference PDF",
        GroupName = SystemTabNames.Content,
        Order = 10)]
    public virtual string SrcUrl
    {
        get { return UrlResolver.Current.GetUrl(this.ContentLink); }
        set { value = UrlResolver.Current.GetUrl(this.ContentLink); }
    }

    // Sets the default property values
    public override void SetDefaultValues(ContentType contentType)
    {
        base.SetDefaultValues(contentType); 

        this.SrcUrl = UrlResolver.Current.GetUrl(this.ContentLink) ?? "Default";
    }
}

PDF URL property rendering blank in Episerver editor interface when viewing a PDF

****Disclaimer: I'm new to the Episerver CMS and may be missing something stupidly simple (ok with being shamed if appropriate).*

  • Not sure where you got `.SrcUrl` from, looked at their [documentation](https://world.episerver.com/documentation/Class-library/?product=cms&version=11) under `EpiServer.Core.MediaData` and it's inherited class and interface implementation, I do not see `SrcUrl` – penleychan Feb 26 '18 at 17:50
  • @12seconds, SrcUrl is a new property I am attempting to add to the class, not an existing property of it (so it wouldn't be in the documentation). In that documentation, there is the content GUID, which can used in a roundabout way to get the link to the content... however nothing in the base class provides an actual reference to the URL where the content lives. – webDevAndEverythingElse Feb 26 '18 at 21:06

2 Answers2

3

I'm not exactly sure what you need to accomplish, but it should probably be noted that while editing MediaData content, its URL is available by clicking the Publish button (note the Download this file link):

Episerver publish button

Edit: Another suggestion is to create a custom editor dijit (using Dojo) for the MediaFile UI hint. That would allow you to display the URL without having to add an additional property.

Ted Nyberg
  • 7,001
  • 7
  • 41
  • 72
  • 1
    Much appreciated, I was unaware the link was hidden in there. I essentially would like to render that exact same link, but as a read-only property that's more obvious and accessible to our editors. I have a ticket open with Epi support, so I'll be sure to update the question here once I have a resolution. If I end up using one of your solutions, I'll be sure to mark this as the correct answer. Thanks Ted! – webDevAndEverythingElse Mar 01 '18 at 19:43
0

I was able to resolve this with the help of Epi support, essentially I needed to create an Initializable Module - this then allowed me to hook into the needed life cycle events of content creation.

[InitializableModule]
[ModuleDependency(typeof(InitializationModule))]
public class ModelDefaultValuesInitialization : IInitializableModule
{
    public void Initialize(InitializationEngine context)
    {
        var contentEvents = ServiceLocator.Current.GetInstance<IContentEvents>();
        contentEvents.CreatedContent += MediaBlocksDefaultValues;
    }

    private void MediaBlocksDefaultValues(object sender, ContentEventArgs e)
    {
        PopulateAssetURL(e);
    }

    /// <summary>
    /// Get the URL path of the uploaded asset and set it to the SrcUrl field which is easily visible to editors
    /// </summary>
    /// <param name="e"></param>
    private void PopulateAssetURL(ContentEventArgs e)
    {
        var mediaTypeBlock = e.Content as PdfFile;
        if (mediaTypeBlock != null)
        {
            string result = ServiceLocator.Current.GetInstance<UrlResolver>().GetUrl(mediaTypeBlock.ContentLink);
            if (!string.IsNullOrEmpty(result))
            {
                var srvcLoc = ServiceLocator.Current.GetInstance<IContentRepository>();
                var contentClone = mediaTypeBlock.CreateWritableClone() as PdfFile;
                contentClone.SrcUrl = result;
                srvcLoc.Save(contentClone, SaveAction.Publish, EPiServer.Security.AccessLevel.Administer);
            }
        }            
    }

    public void Uninitialize(InitializationEngine context)
    {
        var contentEvents = ServiceLocator.Current.GetInstance<IContentEvents>();
        contentEvents.CreatedContent -= MediaBlocksDefaultValues;
    }
}
  • Note: I posted the above to be consistent, but in reality I refactored the code to set the SrcUrl property on a class called BaseMediaData, which inherits from the MediaData class. In this way, all files types (powerpoints, pdfs, etc.) can have this property, since it is relevant to all of them. Images inherit from a different base class (ImageData), so I also had to make a new class called ImageFile which inherits from ImageData and applies the same property. I was lazy but it would probably be a good idea to use an interface to standardize this implementation across the two classes.