Contact Us

If you still have questions or prefer to get help directly from an agent, please submit a request.
We’ll get back to you as soon as possible.

Please fill out the contact form below and we will reply as soon as possible.

  1. Fotoware Alto
    • 11.14 Schreckhorn
    • Terminology
    • Solutions
    • User Guide - Deutsch
    • User Guide - English
    • API Changelog
  2. Fotoware Veloz
    • Managing users and groups
    • Configuring archives
    • Configuring workflows
    • Configuring site behavior
    • Navigating and searching to find your assets
    • Working with your assets
    • Editing asset metadata
    • Uploading files
    • Version Control in Fotoware
    • Albums - Creating and sharing collections
    • Placing assets in a CMS
    • Working with the Fotoware Pro interface
    • Using the Fotoware plugins
    • Consent management
    • User guide to FotoWeb for iPad (Legacy)
    • Picture conferencing with FotoWeb Screens (Legacy)
    • What's what in Fotoware
    • GDPR
    • Fotoware Veloz releases
    • Activity Exports
    • Fotoware Example Workflows
  3. Fotostation
    • Getting started with Fotostation
    • Viewing, selecting and sorting files
    • Managing your assets with archives
    • Adding metadata to assets
    • Searching for assets
    • Working with your assets
    • Version Control in Fotostation
    • Automating tasks with Actions
    • Configuring metadata fields and editors
    • Configuring Fotostation
    • Configuring Fotostation for multi-user environments
    • Troubleshooting Fotostation
  4. Fotoware Flow
    • What is Flow?
    • Getting started
    • Flow dictionary
  5. Fotoware On-Premises
    • Getting started
    • Index Manager
    • FotoWeb
    • Color Factory
    • Connect
    • Operations Center Guide
  6. Integrations and APIs
    • The Fotoware API
    • Creating integrations using embeddable widgets
    • Authorizing applications using OAuth
    • Auto-tagging
    • FotoWeb Drag and Drop export
    • Integration using webhooks
    • Optimizely and Episerver plugin documentation
    • User Interface Integrations
  7. Fotoware Mobile
    • User guide for Fotoware Mobile for iPhone and Android
    • User guide to FotoWeb for iPad (Legacy)
    • User guide to FotoWeb for iPhone and Android (Legacy)

Contact Us

If you still have questions or prefer to get help directly from an agent, please submit a request.
We’ll get back to you as soon as possible.

Please fill out the contact form below and we will reply as soon as possible.

  • Support

Table of Contents

How it works Examples Key features of the integration Known issues Installation and usage Installing the package Register in Startup.cs Configure appsettings.json Implementing the model interface Configure TinyMCE Apply UIHint and FotowareConfiguration attributes to Optimize properties Disable the plugin in Optimizely Commerce Asset list Logging Multiple site configuration Customization Managing the structure of downloaded assets in Optimizely Customize the TinyMCE HTML template Event handling with Fotoware events How to use in the frontend Using PropertyFor Adding a HTML attribute Adding a query string Adding query parameters Use CDN URL Use CDN URL with the specified width Change log
  • Home
  • Fotoware Alto
  • 11.14 Schreckhorn
  • Appendix
  • Integrations

Optimizely plugin

13. March 2025

Elaine Foley

Table of Contents

How it works Examples Key features of the integration Known issues Installation and usage Installing the package Register in Startup.cs Configure appsettings.json Implementing the model interface Configure TinyMCE Apply UIHint and FotowareConfiguration attributes to Optimize properties Disable the plugin in Optimizely Commerce Asset list Logging Multiple site configuration Customization Managing the structure of downloaded assets in Optimizely Customize the TinyMCE HTML template Event handling with Fotoware events How to use in the frontend Using PropertyFor Adding a HTML attribute Adding a query string Adding query parameters Use CDN URL Use CDN URL with the specified width Change log

How it works

The plugin provides a decorator for the existing content selector or a button in the TinyMCE toolbar, enabling users to choose content from the DAM. Once selected, the content (or a shared embedding) is downloaded and imported into the default Optimizely media management system.

Examples

  1. Example of the decorator on a Video content reference

    Before video selected

    After video selected
  2. Example of the toolbar button in TinyMCE
  3. The Insert Media button in TinyMCE
  4. Example of Fotoware content picker

    Fotoware content picker

Key features of the integration

  • Easy to add to both new and existing Optimizely solutions.
  • The integration can be removed without affecting utilized assets.
  • Automatically synchronize media from the DAM with Optimizely's default asset management system, simplifying the process for developers.
  • It is possible to configure content display to show only local media, media from the DAM CDN, or both.
  • Allow developers to configure custom media models containing metadata synchronized from the DAM.

Known issues

  • When using DXP and Cloudflare, you sometimes need to whitelist the "/EPiServer/Fotoware.ContentPlatform.Plugins.Optimizely/api/picturepark" URL in ALL ENVIRONMENTS. 
    To do this, please contact Optimizely support.
  • To create any WAF bypass rule, you will need a WAF bypass agreement signed by the customer. Additionally, a custom domain must be connected to the site; the generic *.episerver.net domain will not work.

Installation and usage

Installing the package

To get started with the plugin, you need to install it from the Optimizely NuGet feed.

The Nuget package is called Fotoware.ContentPlatform.Plugins.Optimizely, and is available at: https://nuget.optimizely.com/package/?id=Fotoware.ContentPlatform.Plugins.Optimizely

Dependencies:

  • EPiServer.CMS.UI version 12.18.0
  • EPiServer.CMS.TinyMce version 4.2.0

Register in Startup.cs

Navigate to the Startup.cs file and add the following code to the ConfigureServices method to register the plugin with the solution's service collection.

using Fotoware.ContentPlatform.Plugins.Optimizely;
services.AddFotowareContentPlatformPlugin();

Configure appsettings.json

"ContentPlatform": {
 "BaseCdnUrl": "https://yourdomain.preview-picturepark.com",
 "RootFolderId": 102,
 "EnableOnAllMedia": true,
 "DisableDefaultMediaSelector": false,
 "DefaultTinyMceImageWidth": 600,
 "UseImageCdnUrlInTinyMce": false,
 "DisableAssetPane":false,
 "MediaTypes": [
   {
     "Name": "Image",
     "FileExtensions": ".jpg,.jpeg,.jpe,.gif,.bmp,.png,.gif",
     "DownloadContentSelectionName": "Original",
     "PreviewContentSelectionName": "Preview",
     "PreferredDownloadWidth": 1200
   },
   {
     "Name": "Video",
     "FileExtensions": ".mov,.mp4",
     "DownloadContentSelectionName": "VideoSmall",
     "PreviewContentSelectionName": "Preview"
   },
   {
     "Name": "Pdf",
     "FileExtensions": ".pdf",
     "DownloadContentSelectionName": "Original",
     "PreviewContentSelectionName": "Preview"
   }
 ]
}
Value Description
BaseCdnUrl The base URL of the picker.
RootFolderId The Optimizely media folder ID where the media is downloaded and stored.
EnableOnAllMedia When set to true, all media properties will have the DAM picker capability.
DisableDefaultMediaSelector When set to true, the default Optimizely media selector behavior will be disabled.
DefaultTinyMceImageWidth The default width for displaying images selected from the DAM in TinyMCE.
UseImageCdnUrlInTinyMce When enabled, the image URL in TinyMCE will use the CDN URL instead of the Optimizely image URL.
DisableAssetPane When set to true, the right-click on a media folder will be disabled.
MediaTypes Configuration for the supported media types in the plugin.
MediaTypes.Name The name of the media type. The supported media types are Image, Video, and PDF.
MediaTypes.FileExtensions The file extensions of the media type, separated by a comma.
MediaTypes.DownloadContentSelectionName Refers to the content variant name used for downloading and importing into Optimizely media.
MediaTypes.PreviewContentSelectionName Refers to the content variant name used for previewing purposes.
PreferredDownloadWidth Specifies the preferred image width for downloading. This option is supported only for the Image media type.

Implementing the model interface

You must implement the IFotowareMedia interface on a content type that inherits from the Optimizely MediaData class in your solution. This enables additional fields that the add-on uses to maintain synchronization with the original media.

public interface IFotowareMedia : IContentData
{
   string Name { get; set; }
   /// <summary>
   /// Fotoware alternative text
   /// </summary>
   string FotowareAltText { get; set; }
   /// <summary>
   /// Fotoware description
   /// </summary>
   string FotowareDescription { get; set; }
   /// <summary>
   /// Fotoware CDN url
   /// </summary>
   string FotowareUrl { get; set; }
   /// <summary>
   /// Fotoware Preview CDN url
   /// </summary>
   string FotowarePreviewUrl { get; set; }
   /// <summary>
   /// Fotoware JSON metadata
   /// </summary>
   string FotowareJson { get; set; }
   /// <summary>
   /// Fotoware modified date
   /// </summary>
   DateTime? FotowareModifiedDate { get; set; }
}

Example implementation of IFotowareMedia

[ContentType(GUID = "0A89E464-56D4-449F-AEA8-2BF774AB8730")]
[MediaDescriptor(ExtensionString = "jpg,jpeg,jpe,ico,gif,bmp,png")]
public class ImageFile : ImageData, IFotowareMedia
{
   [UIHint(UIHint.Textarea)]
   public virtual string Description { get; set; }
   public virtual string AltText { get; set; }
   // IFotowareMedia properties
   [Display(GroupName = FotowareGroupNames.Fotoware)]
   public virtual string FotowareUrl { get; set; }
   [Editable(false)]
   [Display(GroupName = FotowareGroupNames.Fotoware)]
   public virtual string FotowarePreviewUrl { get; set; }
   [UIHint(UIHint.Textarea)]
   [Editable(false)]
   [Display(GroupName = FotowareGroupNames.Fotoware)]
   public virtual string FotowareJson { get; set; }
   [Editable(false)]
   [Display(GroupName = FotowareGroupNames.Fotoware)]
   public virtual DateTime? FotowareModifiedDate { get; set; }
   [ScaffoldColumn(false)]
   public string FotowareAltText
   {
       get => this.GetPropertyValue(p => p.AltText);
       set => this.SetPropertyValue(p => p.AltText, value);
   }
   [ScaffoldColumn(false)]
   public string FotowareDescription
   {
       get => this.GetPropertyValue(p => p.Description);
       set => this.SetPropertyValue(p => p.Description, value);
   }
}

The ModifiedDate property tracks when the media was last changed in the DAM. The plugin uses it to determine whether to download the media.

Configure TinyMCE

To add a button for inserting media from the DAM, include contentplatform-insert-media in the TinyMCE configuration.

Example of TinyMCE configuration

services.Configure<TinyMceConfiguration>(config =>
{
   config.Default().AddSetting("extended_valid_elements",
           "iframe[src|alt|title|width|height|align|name],picture,source[srcset|media|src],span")
       .AddPlugin(
           "epi-link epi-image-editor epi-dnd-processor epi-personalized-content preview searchreplace autolink directionality visualblocks visualchars fullscreen image link media template codesample table charmap pagebreak nonbreaking anchor insertdatetime advlist lists " +
           "wordcount help code")
       .Toolbar(
           "bold italic strikethrough forecolor | epi-link image media epi-image-editor epi-personalized-content | contentplatform-insert-media | bullist numlist | searchreplace fullscreen ",
           "styleselect blocks | alignleft aligncenter alignright alignjustify | removeformat | table toc | code"
           , "");
});

The button is added to the default TinyMCE by default, but if you have custom tinys for blocks with other configurations, you can apply the following: .AddFotowareContentPlatformToTinyMCE(serviceCollection)

          services.Configure<TinyMceConfiguration>(config =>
                config.For<TextHtmlBlock>(t => t.Text)
               .AddEpiserverSupport()
               .AddFotowareContentPlatformToTinyMCE(serviceCollection) // This registers the plugin and the settings. 
               .Toolbar(AllSettings);
         );

Apply UIHint and FotowareConfiguration attributes to Optimize properties

Decorating the Optimizely property with the UIHint attribute will replace the Optimizely built-in content selector with an extended version that supports selecting content from both DAM and Optimizely content.

Example of using the image UIHint

[Display(Name = "Content Reference (Optimizely)", GroupName = "Content Reference", Order = 10)]
[UIHint(ContentPlatformUiHint.Image)]
public virtual ContentReference ContentReferenceOptimizely { get; set; }
[Display(Name = "Content Reference (Fotoware)", GroupName = "Content Reference", Order = 20)]
[FotowareConfiguration(DisableDefaultMediaSelector = true)]
[UIHint(ContentPlatformUiHint.Image)]
public virtual ContentReference ContentReferenceFotoware { get; set; }
[Display(Name = "Url (Optimizely)", GroupName = "Url", Order = 10)]
[UIHint(ContentPlatformUiHint.ImageUrl)]
public virtual Url ImageAsUrlOptimizely { get; set; }

The UIHint attribute can be applied to ContentReference and Url property types.

Value Description
ContentPlatformUiHint.Image Replaces the Optimize selector with the Fotoware image selector for the ContentReference property.
ContentPlatformUiHint.ImageUrl Replaces the Optimize selector with the Fotoware image selector for the Url property.
ContentPlatformUiHint.Video Replaces the Optimize selector with the Fotoware video selector for the ContentReference property.
ContentPlatformUiHint.VideoUrl Replaces the Optimize selector with the Fotoware video selector for the Url property.
ContentPlatformUiHint.Pdf Replaces the Optimize selector with the Fotoware media selector for the ContentReference property.
ContentPlatformUiHint.PdfUrl Replaces the Optimize selector with the Fotoware media selector for the Url property.

FotowareConfiguration

You can use the FotowareConfiguration attribute to add settings for rendering in the frontend. This should be used together with the UIHint attribute.

  • DisableDefaultMediaSelector - To turn off the default Optimizely Media Selector, set the property to true. The default value is false.
  • QueryParameters - An additional query string appended to the media URL, i.e., format=webp&quality=75.
  • ImageWidth - The default width of the image imported into TinyMCE. This does not apply to video or PDF files.

Disable the plugin in Optimizely Commerce Asset list

To disable the plugin in the Optimizely Commerce Asset list, set the PreventCommerceEditorIntegration setting to true.

"ContentPlatform": {
 ...
 "PreventCommerceEditorIntegration": true
}

Logging

The plugin has a number of logging information that can be used for information and debugging the integration. Update appsettings.json as the following.

"Logging": {
   "LogLevel": {
     "Fotoware.ContentPlatform.Plugins.Optimizely": "Information"
   }
 },

Multiple site configuration

You can configure the plugin to run with Optimizely multi-site scenario by specifying the site ID for each site in the Sites collection in appsettings.json.

"ContentPlatform": {
 "BaseCdnUrl": "https://optimizely.preview-picturepark.com",
 "Sites": [
   {
     "SiteId": "7e9335f8-2f16-44b0-8870-8f2d4bc0160c",
     "RootFolderId": 102,
     "EnableOnAllMedia": true,
     "DisableDefaultMediaSelector": false,
     "DefaultTinyMceImageWidth": 600,
     "UseImageCdnUrlInTinyMce": false,
     "MediaTypes": [
       {
         "Name": "Image",
         "FileExtensions": ".jpg,.jpeg,.jpe,.gif,.bmp,.png,.gif",
         "PreferredDownloadWidth": 1200,
         "DownloadContentSelectionName": "Original",
         "PreviewContentSelectionName": "Preview"
       },
       {
         "Name": "Video",
         "FileExtensions": ".mov,.mp4",
         "DownloadContentSelectionName": "VideoSmall",
         "PreviewContentSelectionName": "Preview"
       },
       {
         "Name": "Pdf",
         "FileExtensions": ".pdf",
         "DownloadContentSelectionName": "Original",
         "PreviewContentSelectionName": "Preview"
       }
     ]
   }
 ]
}

SiteId - The ID of the site, which you can find in Admin > Manage Websites.

Customization

Managing the structure of downloaded assets in Optimizely

Fotoware Media imported into Optimizely are organized into a year-month folder structure to facilitate browsing and prevent issues with large media lists in the same folder, which Optimizely doesn't handle well. By default, folders are created based on the year and month when the media was imported. However, you can customize this structure. For example, you could base it on metadata within your solution.

2024/
└── 06/
├── image01.jpg
└── video02.mp4

This customization is achieved by implementing the IFolderResolver interface.

If you want to save the image to "For this page", register this in startup.

services.AddScoped<IFolderResolver, ForThisPageFolderResolver>();

Customize the TinyMCE HTML template

You can create custom HTML input when inserting media into TinyMCE, such as filling in the alt text or adding CSS classes.

To do so, implement and register an IFotowareTinyMceTemplate where you implement the GetHtml(ContentReference contentReference, InsertTinyMceMedia insertTinyMceMedia) method.

Event handling with Fotoware events

Example of how to register event handlers for the Fotoware events in an InitializationModule

[ModuleDependency(typeof(InitializationModule))]
public class FotowareContentEventsInitializationModule : IInitializableModule
{
   public void Initialize(InitializationEngine context)
   {
       var events = context.Locate.Advanced.GetRequiredService<FotowareEvents>();
       events.OnContentDownloading += OnContentDownloading;
       events.OnContentDownloaded += OnContentDownloaded;
   }
   public void Uninitialize(InitializationEngine context)
   {
       var events = context.Locate.Advanced.GetRequiredService<FotowareEvents>();
       events.OnContentDownloading -= OnContentDownloading;
       events.OnContentDownloaded -= OnContentDownloaded;
   }
   private void OnContentDownloading(object sender, FotowareContentEventArgs e)
   {
       // Handle content downloaded event here
   }
   private void OnContentDownloaded(object sender, FotowareContentEventArgs e)
   {
       // Handle content downloaded event here
   }
}

OnContentDownloading - Raised before downloading a media with the possibility to cancel the action.

OnContentDownloaded - Raised after the media has been downloaded.

How to use in the frontend

Using PropertyFor

@Html.PropertyFor(m => Model.CurrentPage.ImageAsContentReference)

Output

<img alt="image01.jpg" src="/globalassets/fotoware/2024/6/image01.jpg" />

Adding a HTML attribute

@Html.PropertyFor(x => Model.CurrentPage.ContentReferenceOptimizely, new { Attributes = new { @class = "fotoware-image" }

Output

<img alt="image01.jpg" class="fotoware-image" src="/globalassets/fotoware/2024/6/image01.jpg">

Adding a query string

@Html.PropertyFor(x => Model.CurrentPage.ContentReferenceOptimizely, new { QueryStrings = new { format = "webp" } })

Output

<img alt="image01.jpg" src="/globalassets/fotoware/2024/6/image01.jpg?format=webp">

Adding query parameters

@Html.PropertyFor(x => Model.CurrentPage.ContentReferenceOptimizely, new { QueryParameters = "format=webp&quality=80" })

Output

<img alt="image01.jpg" src="/globalassets/fotoware/2024/6/image01.jpg?format=webp&quality=80">

Use CDN URL

@Html.PropertyFor(x => Model.CurrentPage.ContentReferenceOptimizely, new { MediaOptions = new { UseCdnUrl = true } })

Output
<img alt="image01.jpg" src="https://optimizely.preview-picturepark.com/v/TBVACNY3/">

Use CDN URL with the specified width

@Html.PropertyFor(x => Model.CurrentPage.ContentReferenceOptimizely, new { MediaOptions = new { Width = 600, UseCdnUrl = true } })

Output

<img alt="image01.jpg" src="https://optimizely.preview-picturepark.com/v/TBVACNY3/fit-in:600x100000">

Change log

 ## 2.0.0.0 

  •  Target .net 8 and .net 6
  • Save assets to 'for this page'
  • Right-click on asset pane folders to save assets direct to a folder
  • Bug: Change API internal path

## 1.1.0.0 

  •  Fix bugs filesize

## 1.0.0.0 

  •  Initial version

Was this article helpful?

Yes
No
Give feedback about this article

Related Articles

  • Consent management overview
  • Getting started with consent management
  • Collections
eco-lighthouse-miljøfyrtårn

Company

  • About us
  • Resellers
  • Careers
  • Contact us

Help & support

  • Support center
  • Consultancy
  • Tech partners
  • Fotostation
  • System status

Trust Center

  • Legal
  • Security
  • Sustainability & ESG

Locations

Fotoware AS (HQ)
Tollbugata 35
0157 OSLO
Norway
FotoWare Switzerland AG
Industriestrasse 25
5033 Buchs (AG)
Switzerland

Copyright 2025 Fotoware All rights reserved.

  • Terms of service
  • Privacy policy
  • Cookie policy

Knowledge Base Software powered by Helpjuice

Expand