It seems like you're using an older browser. Things might not work as expected.

In the default configuration of Avensia Storefront you can sell both Product Master with variants and Products (variants) depending on your setup in Dynamics 365 FO. In some cases you might only want product-variation setup in Episerver but in your ERP you have some sellable Products. Here is an example for how your can modify your product pipeline to change the product to a variant and create a "fake" product it belongs to. There are a few ways of solving this issue, we recommend that you create a new implementation of our interface ITransformer<TSource, TTarget>.

The ITransformer is an interface we are using when we are importing data from our Staging into Episerver. The implementation is responsible for transforming the dto into a domain object. The provided implementation that comes with Storefront works for cases where there are always variations on a product. What we need to do it to create a new class that derives from our original storefront ProductTransformer to be able to reuse the main logic. But to make it resolve correct method in our pipeline we also need to specifically add the ITransformer interface.

Things our transformer has to be responsible for: 

  • Find all products without any variation.
  • Loop through the found products.
  • Add a new Variation to the product, with DistinctProductVariantId same as the product's recordId.
  • Assign the productNumber to the variant, it's an entry in the product's properties property keyed ItemNumber.
  • Prefix the product's recordId with something.

Code idea for the new Transformer class.

public class VariationMediaTransformer:
    ProductTransformer<ProductDto, WebProduct, WebVariant>,
    ITransformer<ProductDto, ProductToSave<WebProduct, WebVariant>>
{
    public MyProductTransformer(
        ReferenceConverter referenceConverter,
        IContentRepository contentRepository,
        IProductCodeResolver productResolver,
        IVariationCodeResolver variationResolver,
        ICategoryCodeResolver categoryCodeResolver,
        LanguageSelectorFactory languageSelectorFactory,
        IPipelineSettings pipelineSettings,
        ILanguageInformation languageInformation,
        IVariationNameFormatter variationNameFormatter)
        : base(
            referenceConverter,
            contentRepository,
            productResolver,
            variationResolver,
            categoryCodeResolver,
            languageSelectorFactory,
            pipelineSettings,
            languageInformation,
            variationNameFormatter)
    {}
    public new IEnumerable<TransformedItem<ProductDto, ProductToSave<WebProduct, WebVariant>>> Transform(
        ImportContext context,
        IEnumerable<ProductDto> items,
        IRuntimeProfilingItem profilingItem)
    {
        return base.Transform(context, items.Select(x => TransformProduct(x, context)), profilingItem);
    }

    private static ProductDto TransformProduct(ProductDto productDto, ImportContext context)
    {
        if (productDto.Variations != null && productDto.Variations.Any())
        {
            return productDto;
        }
        productDto.RecordId = $"fake_{productDto.RecordId}";         productDto.Variations = new[] {CreateVariation(productDto, context)}; return productDto;
}

private static VariationDto CreateVariation(ProductDto productDto, ImportContext context)
{
return new VariationDto(productDto.Properties.Cast<PropertyDto>().ToArray())
{
DistinctProductVariantId = productDto.RecordId,
ProductNumber = productDto.Properties.First(x => x.KeyName == "ItemNumber").Value
.Values[context.Language].ToString()
        };
    }
}

With this code we will get a varaiation that we can buy through Episerver site. But there is one more thing to do and that is to make sure we can import images for this special cased variations. So what we need to do is to create a new pipelinetask where reuse all the steps from "Variation Media" but exchange the VariationMediaReader with a ProductMediaReader.

m.AddPipelineTask<EntryMediaDto, EntryMediaToSave<WebVariant, ImageFile>>(
t =>
{
t.Name("Product without variation Media");
t.UseReader<ProductMediaReader<EntryMediaDto>>();
t.UseTransformer<VariationMediaTransformer<EntryMediaDto, WebVariant, ImageFile>>();
t.AddPatcher<MediaNamePatcher<EntryMediaDto, WebVariant, ImageFile>>();
t.UseWriter<MediaWriter<EntryMediaDto, WebVariant, ImageFile>>();
t.AddReporter<StagingReporter<EntryMediaDto, EntryMediaToSave<WebVariant, ImageFile>>>();
});

In the end we have one pipelinetask for "Product Media", one for "Variation Media" and one for "Product without varaiation Media".
Deleteing the product in ERP will delete the product and it's variation in Episerver without any changes requried.