2

Sitecore 9.3 with SXA

I am getting the below exception while accessing the Event Queue Statistics page in Sitecore.

URL: <cm_domain>/sitecore/admin/EventQueueStats.aspx

    22180 05:16:57 ERROR Application error.
Exception: System.Web.HttpUnhandledException
Message: Exception of type 'System.Web.HttpUnhandledException' was thrown.
Source: System.Web
   at System.Web.UI.Page.HandleError(Exception e)
   at System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
   at System.Web.UI.Page.ProcessRequest(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)
   at System.Web.UI.Page.ProcessRequest()
   at System.Web.UI.Page.ProcessRequest(HttpContext context)
   at ASP.sitecore_admin_eventqueuestats_aspx.ProcessRequest(HttpContext context)
   at System.Web.HttpApplication.CallHandlerExecutionStep.System.Web.HttpApplication.IExecutionStep.Execute()
   at System.Web.HttpApplication.ExecuteStepImpl(IExecutionStep step)
   at System.Web.HttpApplication.ExecuteStep(IExecutionStep step, Boolean& completedSynchronously)

Nested Exception

Exception: System.InvalidOperationException
Message: getTimestampForLastProcessingMI is null
Source: Sitecore.Kernel
   at Sitecore.Diagnostics.Assert.IsNotNull(Object value, String message)
   at Sitecore.ExperienceContentManagement.Administration.EventQueueStats.ReloadStatistics()
   at System.Web.UI.Control.LoadRecursive()
   at System.Web.UI.Page.ProcessRequestMain(Boolean includeStagesBeforeAsyncPoint, Boolean includeStagesAfterAsyncPoint)

Checked I'm able to access and query the [EventQueue] table in <InstanceName>_Master DB.

Any help will be much appreciated?

3

It looks like there is a bug in Sitecore 9.3.

It tries to get a method using reflection on interface IEventQueue instead of on EventQueue abstract class, like it was in earlier version.

You can either contact Sitecore Support or do the following changes:

  • Add a reference to Sitecore.ExperienceContentManagement.Administration library to your project
  • Create own EventQueueStats class and override ReloadStatistics method:
using System;
using System.Collections.Generic;
using System.Reflection;
using Sitecore.Configuration;
using Sitecore.Data;
using Sitecore.Diagnostics;
using Sitecore.Eventing;

namespace MyAssembly.MyNamespace
{
    public class EventQueueStats : Sitecore.ExperienceContentManagement.Administration.EventQueueStats
    {
        protected override void ReloadStatistics()
        {
            List<Database> databases = Factory.GetDatabases();
            List<EQStats> eqStatsList = new List<EQStats>();
            foreach (Database database in databases)
            {
                EQStats eqStats = new EQStats();
                EventQueue eventQueue = database.RemoteEvents.EventQueue as EventQueue;
                if (eventQueue != null)
                {
                    eqStats.DatabaseName = database.Name;
                    eqStats.NumberOfRecords = eventQueue.GetQueuedEventCount();

                    MethodInfo method = typeof(EventQueue).GetMethod("GetTimestampForLastProcessing",
                        BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);

                    Assert.IsNotNull(method, "getTimestampForLastProcessingMI is null");
                    object obj = method.Invoke(eventQueue, null);
                    Assert.IsNotNull(obj, "timestampObject is null");

                    PropertyInfo sequenceProperty = obj.GetType().GetProperty("Sequence",
                        BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);

                    Assert.IsNotNull(sequenceProperty, "sequencePI is null");
                    eqStats.LastProcessedTimestamp = (long) sequenceProperty.GetValue(obj);
                    eqStats.LastTimestamp = GetLastEventTimestamp(eventQueue, database.ConnectionStringName);

                    PropertyInfo dateProperty = obj.GetType().GetProperty("Date",
                        BindingFlags.Instance | BindingFlags.Public | BindingFlags.NonPublic);

                    Assert.IsNotNull(sequenceProperty, "datePI is null");

                    eqStats.RecordsToBeProcessed = GetNumberOfRecordsToProcess(database.ConnectionStringName,
                        eqStats.LastProcessedTimestamp, (DateTime) dateProperty.GetValue(obj));

                    eqStatsList.Add(eqStats);
                }
            }
            EQStatsRepeater.DataSource = eqStatsList;
            EQStatsRepeater.DataBind();
        }
    }
}
  • Edit /sitecore/admin/EventQueueStats.aspx page and change the type of Inherits to your assembly and namespace:
<%@ Page Language="C#" AutoEventWireup="true" CodeBehind="EventQueueStats.aspx.cs" Inherits="MyAssembly.MyNamespace.EventQueueStats" %>

Be aware that I haven't tested this solution so it's possible that you will have to adapt some of the bits, but general idea should work.

0

As Marek suggested above, We reached out to Sitecore support for this issue and they confirmed that this is a bug in Sitecore 9.3. This bug has reference number 420812 and it was fixed in Sitecore 10.

You can find the Hotfix package for this bug in this KB article:
https://support.sitecore.com/kb?id=kb_article_view&sysparm_article=KB0997904

This hotix provide fixes for for page EventQueueStats.aspx that might fail with error getTimestampForLastProcessingMI is null, also for administration pages like Logs.aspx and SqlShell.aspx.

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service, privacy policy and cookie policy

Not the answer you're looking for? Browse other questions tagged or ask your own question.