How to use logger and notifier in html helper

Topics: Writing modules
Nov 22, 2012 at 3:34 PM
Edited Nov 22, 2012 at 3:39 PM

Hi.

I wrote custom HtmlHelper and i'm trying to handle exceptions to ILogger (like in controllers)

Unfortunetly class (and extension method) are static so i can't initlialize ILogger by 

public ILogger Logger { get; set; }

 

Neither i can't initialize Notifier in class constructor.

I would like to use notifier and logger like in controllers. My code is similar to below.

 

public static class ReportInputHelpers
    {
        public static MvcHtmlString CompanyId(this HtmlHelper htmlHelper, IUser user, string name)
        {
            
            try
            {
                // some code
            }
            catch (Exception ex)
            {
                // how to do logging and notifying like this?
                Logger.Error(ex, "Some error.");
                _notifier.Error(T("Exception happend."));
            }
            
           return MvcHtmlString.Create("some html");
        }
}

Anyone have any idea to solve my problem?

 

 

 

Developer
Nov 22, 2012 at 5:48 PM

var logger = htmlHelper.ViewContext.RequestContext.GetWorkContext().Resolve<ILogger>()

var notifier = htmlHelper.ViewContext.RequestContext.GetWorkContext().Resolve<INotifier>()

Nov 22, 2012 at 9:11 PM
Edited Nov 22, 2012 at 9:15 PM

var logger = htmlHelper.ViewContext.RequestContext.GetWorkContext().Resolve<ILogger>()

is throwing following error

 

Sequence contains no elements

Description: An unhandled exception occurred during the execution of the current web request. Please review the stack trace for more information about the error and where it originated in the code.

Exception Details: System.InvalidOperationException: Sequence contains no elements

Source Error:

private static ILogger CreateLogger(IComponentContext context, IEnumerable<Parameter> parameters) {

Line 72:             // return an ILogger in response to Resolve<ILogger>(componentTypeParameter)

Line 73:             var loggerFactory = context.Resolve<ILoggerFactory>();

Line 74:             var containingType = parameters.TypedAs<Type>();

Line 75:             return loggerFactory.CreateLogger(containingType);

Line 76:         }


Source File: c:\{…}\Orchard\src\Orchard\Logging\LoggingModule.cs Line: 74

And parameters variable is an empty array of {Autofac.Core.Parameter[0]}. When Logger works in controller array contain 1 element.

 

Notifier doesn't throw any exceptions but is not showing any notifications :/

Developer
Nov 22, 2012 at 11:20 PM

ILogger is actually being registered in a way that it's not possible to get it through WorkContext, as the WorkContext.Resolve<T>() method won't allow you to pass additional parameters, required to get an instance of ILogger.

What you have to do is to resolve IComponentContext first and then resolve ILogger through it, passing appropriate parameters:

var componentContext = htmlHelper.ViewContext.RequestContext.GetWorkContext().Resolve<IComponentContext>();
var logger = componentContext.Resolve<ILogger>(new TypedParameter(typeof(Type), typeof(ReportInputHelpers));
Nov 23, 2012 at 1:08 AM

Your solution works. Thanks!