Hi,
We have started using the new Product catalog with viewmodels and it works great, but we are missing the JSON-feed-feature from the standard Ecom catalog.
Being able to output the content of an APP as JSON is an awesome feature that allows async rendering and it's sad to see it missing from the new ecom with viewmodels.
Are there plans for having this implemented? Currently we making by, by "hacking" the output through an observer, but I'm wondering if you have a better alternative?
[Subscribe(Dynamicweb.Ecommerce.Notifications.Ecommerce.ProductCatalog.OnBeforeContent)]
[Subscribe(Standard.Page.OnOutput)]
public class ProductPageFeedObserver : NotificationSubscriber
{
private const string IsJsonFeedParameter = "json";
private const string ShouldRender = "ShouldRender";
private static readonly HashSet<string> FeedCompatibleModuleSystemNames = new HashSet<string>
{
"eCom_ProductCatalog"
};
public override void OnNotify(string notification, NotificationArgs args)
{
if (!IsJsonFeed())
return;
SkipNormalRenderingForFeed(args);
OverrideOutputWithJsonFeed(args);
}
private void SkipNormalRenderingForFeed(NotificationArgs args)
{
if (args is Dynamicweb.Ecommerce.Notifications.Ecommerce.ProductCatalog.OnBeforeContentArgs beforeContentArgs)
{
beforeContentArgs.StopExecution = !Converter.ToBoolean(Dynamicweb.Context.Current.Items[ShouldRender]);
}
}
private void OverrideOutputWithJsonFeed(NotificationArgs args)
{
if (args is Standard.Page.OnOutputArgs arg)
{
var moduleOutput = RenderEcomCatalogOutput();
if (!string.IsNullOrEmpty(moduleOutput))
{
arg.PageViewTemplate.Html = moduleOutput;
Dynamicweb.Context.Current.Response.ContentType = "application/json";
}
}
}
public static bool IsJsonFeed()
{
return Dynamicweb.Context.Current.Request.GetBoolean(IsJsonFeedParameter);
}
private string RenderEcomCatalogOutput()
{
var paragraphService = ObjectFactory.GetInstance<ParagraphService>();
var paragraphs = paragraphService.GetParagraphsByPageId(PageView.Current().Page.ID);
foreach (var paragraph in paragraphs)
{
if (FeedCompatibleModuleSystemNames.Contains(paragraph.ModuleSystemName))
{
Dynamicweb.Context.Current.Items[ShouldRender] = true;
return Content.GetModuleOutput(paragraph, PageView.Current());
}
}
return null;
}