Mocking System.Web.TraceContext with Moq - c#

I've got some code that's accessing the HttpContextBase.Trace object and doing some things with it (checking IsEnabled, writing some messages). The problem is that it's a System.Web.TraceContext object. TraceContext is a sealed class with only one constructor: that takes an HttpContext object. Moq is unable to mock either TraceContext or HttpContext. Can I do anything here to test this code with Moq?
Or will I need to factor this code out and stop referring to HttpContextBase.Trace?

I sort of hate answers that say "don't do that" because there might be value in the answer, regardless of the approach, however, here we go:
Don't do that.
Let's assume you have this class:
public class MyCode
{
public void Do()
{
HttpContext.Current.Trace.WriteLine("WOO!");
}
}
This kind of thing isn't very testable. If you wanted to refactor for testability, you could use more of an "inversion of control" type of method. Here I'll use "dependency injection" (there are other options, like "service location" and "abstract factories", but this is easiest to understand):
public class MyCode
{
private IMyLogger _logger = null;
public MyCode(IMyLogger logger)
{
_logger = logger;
}
public void Do()
{
_logger.TraceWriteLine("WOO!");
}
}
Now you can see that this code is very testable and you don't have to jump through hoops to mock anything.
//Confirms "Do" method calls "TraceWriteLine"
public void Do_Called_CallsTraceWriteLine()
{
//Arrange
var loggerMock = new Mock<IMyLogger>();
loggerMock.Setup(l => l.TraceWriteLine(It.IsAny<string.());
var target = new MyCode(loggerMock.Object);
//Act
target.Do();
//Assert
loggerMock.VerifyAll();
}
Now your implementation of IMyLogger might call out to HttpContext, but it keeps your target class testable.
public DefaultLogger : IMyLogger
{
public void TraceWriteLine(string message)
{
HttpContext.Current.Trace.WriteLine(message);
}
}
To implement such a thing, many people choose to use an Inversion of Control container. You don't have to do this, but it makes things a little simpler and doesn't decrease maintainability as you add more dependencies. You can imagine if you had an interface for each part of the .NET framework that was untestable, your "new MyCode" constructor calls would start to get quite long. IoC containers help you avoid this.
Popular IoC containers for .NET:
Ninject
Unity
MEF (builtin to .NET 4.0)
Autofac
Castle Windsor
StructureMap
Your post is tagged "ASP.NET". Hopefully you are using MVC. If so, it has new support for dependency injection, examples here:
http://weblogs.asp.net/shijuvarghese/archive/2011/01/21/dependency-injection-in-asp-net-mvc-3-using-dependencyresolver-and-controlleractivator.aspx
Hopefully this helps. Sorry it doesn't directly answer your question.

Related

Inject IServiceProvider into an API controller or Individual Services

I've just come from a place where an API controller would have just the Services it needed injected in to it...
[ApiController]
public class SomeController : ControllerBase
{
private IFirstService firstService
private ISecondService secondService
public SomeController(IFirstService firstService, ISecondService secondService)
{
this.firstService = firstService;
this.secondService = secondService;
}
[HttpGet]
public IActionResult SomeMethod()
{
var data = firstService.GetSomething();
return OkObjectResult(data);
}
}
Now I find myself in a shop that does this...
[ApiController]
public class SomeController : ControllerBase
{
private IServiceProvider services;
public SomeController(IServiceProvider services)
{
this.services = services;
}
[HttpGet]
public IActionResult SomeMethod()
{
var service = servies.Get<IFirstService>();
if(service is null)
{
//...
}
var data = firstService.GetSomething();
return OkObjectResult(data);
}
}
Now, I can't really explain why, but this just seems wrong.
Am I just experiencing StuckInMyWaysitis or is this really the bad practice my bones tells me it is? Or, is there, in fact, a more widely accepted way of doing the "right" thing?
Injecting IServiceProvider implements the Service Locator pattern, which is generally considered to be an anti-pattern.
In your first example two services are injected. You can easily tell what the controller depends on. It's easier to tell if a class begins to depend on too many things when we see five, 10, or 20 dependencies injected. When that happens we usually refactor because the number of dependencies indicates that the class is doing too many things.
In the second example we can't tell from the injected dependency (IServiceProvider) what the class depends on. The only way to tell is to look at every use of services throughout the class and see what gets resolved from it. A class could end up depending on many other classes even though we only see one dependency in the constructor.
This also makes unit testing more difficult. In the first example we might have to create fakes or mocks for one or both services. In the second example we have to either mock IServiceProvider to return mocks or create an IServiceCollection, register the mocks with it as service implementations, and then build a ServiceProvider from it. Both make tests more complex.
Some have reasoned that API controllers are an exception, and that it's okay to have them depend on something like a service locator. (MediatR is a common example.) This is an opinion: It's not bad as long as the controller has little or no logic and is only used to route HTTP requests to some higher-level code.
If we use MediatR or some similar abstraction like ICommandHandler<TCommand> then at least we've constrained the class to submitting queries or commands to handlers. It's not as bad as injecting IServiceProvider which allows the class to resolve any registered service.
It's wrong because it means that every time you need a service you have to explicitly request it and then check the instance for null. This is unnecessary code duplication for no benefit.
It also violates the explicit dependencies principle, which Microsoft recommends you use to architect your code.
Almost certainly this was done because somebody couldn't figure out how DI works, or they forgot to register a service and couldn't be a***d to fix it properly, so they just chucked in IServiceProvider instead and that ended up working, and then they cargo-culted it everywhere. In other words, laziness and/or ignorance.
Likely you will come up against resistance when you try to fix this by using explicit dependencies. The trick is to make the person(s) advocating for this mess explain why the mess is better than following good architectural practices, particularly those from Microsoft.
When you've been programming long enough, you learn to trust your gut. If it feels bad, it almost always is.
First, Let us refactor the second code to get rid of some code smells,
[ApiController]
public class SomeController : ControllerBase
{
private IFirstService firstService
private ISecondService secondService
private IServiceProvider services;
public SomeController(IServiceProvider services)
{
this.services = services;
this.firstService= servies.Get<IFirstService>();
this.secondService= servies.Get<ISecondService>();
}
[HttpGet]
public IActionResult SomeMethod()
{
var data = firstService.GetSomething();
return OkObjectResult(data);
}
}
Why?
you automatically get rid of all the checks, and now you can do that in your constructor if needed.
If many methods needed instances all might have duplicate codes like this.
It violates SRP as the methods are doing more than they should be.
Now if we look it is closer to your First code. With one difference, Instantiating service vs Injecting service. There are a few problems with this IMO,
DI Containers are tools, they are not part of our domain. By taking IServiceProvider, we are trying our services to them. Which implies we always need some DI provider.
Secondly this also hides our dependencies, which makes integration
difficult. Constructors are like messengers that clearly tell us
what we need to keep ready beforehand, before we instantiate a
Class. If we hide this information, you may not know if certain
dependency was configured or not without running the application.
With clearly defined dependencies in constructor, we cannot skip
this part.
Also, just like we had duplicate code in our methods, now we have duplicate code in constructor of different services. Each service will be calling these Get methods. So why not do them in one place. And if you consider this and refactor, you automatically reach to your first example.
[ApiController]
public class SomeController : ControllerBase
{
private IFirstService firstService
private ISecondService secondService
public SomeController(IFirstService firstService, ISecondService secondService)
{
this.firstService = firstService;
this.secondService = secondService;
}
}
public class Startup()
{
public void Start()
{
//....
//....
var service1 = servies.Get<IFirstService>();
var service2 = servies.Get<IFirstService>();
SomeController= new Controller(service1,service2);
//or just servies.Get<SomeController>();
}
}
This is how instantiation happen if you use Containers like AutoFac.

MVVM Light SimpleIoc

I'm using WPF with MVVM Light in my project. I have some small question about SimpleIoC containter and DI. Which is the better way to use it or tell me if I don't need to use DI there.
There is my VM constructor:
public MainViewModel(IDialogService dialogService, IChannelObserverService channelObserverService, IInternalBroadcastService internalBroadcastService,
IUserDataAccessService userDataAccessService, IUserService userService)
And SimpleIoC register:
SimpleIoc.Default.Register<MainViewModel>(() => {
return new MainViewModel(SimpleIoc.Default.GetInstance<IDialogService>(),
SimpleIoc.Default.GetInstance<IChannelObserverService>(),
SimpleIoc.Default.GetInstance<IInternalBroadcastService>(),
SimpleIoc.Default.GetInstance<IUserDataAccessService>(),
SimpleIoc.Default.GetInstance<IUserService>()); });
Please tell me, do I need to use DI there?
First I had using all services like this:
public MainViewModel(){...}
User user = SimpleIoc.Default.GetInstance<IUserService>().GetCurrentLoggedUser();
or this:
private IDialogService dialogService;
public MainViewModel()
{
dialogService = = SimpleIoc.Default.GetInstance<IUserService>();
}
private void MyMethod()
{
dialogService.ShowQuestionDialog(abc,abc,abc);
}
So I didn't use DI when I was creating my View-Models.
I'd recommend you to use the DI as it enables the development of loosely coupled code. Through DI, you can decrease tight coupling between software components. Also, it makes unit testing convenient.
I would suggest to have constructor like this (as you have mentioned in your post)
public MainViewModel(IDialogService dialogService, IChannelObserverService channelObserverService, IInternalBroadcastService internalBroadcastService,
IUserDataAccessService userDataAccessService, IUserService userService)
But registration can be simplified as
SimpleIoc.Default.Register<IDialogService, DialogService>();
//// Other service registrations.
SimpleIoc.Default.Register<MainViewModel>(); // without injecting the other dependent types.
With this DI will take to inject the right dependencies while creating an instance of MainViewModel.
So with this above approach, you don't need to Resolve the instance inside your code as it is already inject in constructor, so service code can be simplified as
private void MyMethod()
{
dialogService.ShowQuestionDialog(abc,abc,abc);
}

IoC and binding to interfaces

Forgive a genuine but n00b level query, please. I'm doing a new project and starting to bake in the IoC aspect of it. It's the first I've worked on where I was in charge of building up the framework so I'm cutting my teeth with IoC somewhat. I'm taking a hearty recommendation to use Ninject. Cool.
But as I sit down to create my first class that will rely on constructor injection, it strikes me - I still need to use all of these quite custom/3rd party interfaces in the constructors. So How is it that my code is less coupled to log4net if my classes all take a log4net ILog instance in their constructor? I still need a using statement for log4net in each file that wants to log anything.
I thought that was the point - abstraction and de-coupling of your multitudes of classes, and pushing all of the dependencies into one class. It seems to me that every class that wants to log anything is still quite bound to log4net, and to change log4net out for another logger would be tedious all the same. how is this a win?
I'm sure I'm missing something, so help me out? Am I meant to create my own interfaces everywhere I wanted to be truly decoupled and then add adapters for the implementations or something? Only then would it seem to be we've pushed all the dependencies to one area.
If you use IOC, you inject the interfaces into your class, not the implementation, so that is ok. To get around your specific problem, try looking at the common logging framework (http://netcommon.sourceforge.net/) which itself is a wrapper for log4net or a multitude of other logging frameworks.
This couples you to the common logging framework, but it is very widely used, stable and abstracts the specific of logging without you having to do any of that yourself.
When I have used this in the past, I use a post build script to bring the log4net assemblies into the output directory, so the binding happens at runtime only. For testing purposes and as far as your code is concerned, you are talking to the common logging framework via the public interface provided.
I know what are you talking about! you are going to make a kind of generalization to reduce code duplication(I'm hopping). as you are using .net framework, I have to say that it does not support for aspect oriented programming by default to let you behave different in every situation. for example take a look at this piece of code:
public class BlogService : IBlogService
{
private readonly IBlogRepository _blogRepository;
private readonly IUnitOfWork _unitOfWork;
private readonly ILogger _logger;
public BlogService(
IBlogRepository blogRepository,
IUnitOfWork unitOfWork,
ILogger logger)
{
_blogRepository = blogRepository;
_unitOfWork = unitOfWork;
_logger = logger;
}
public GetAllBlogPostResponse GetAllBlogPost(GetAllBlogPostRequest request)
{
var response = new GetAllBlogPostResponse();
try
{
var blogPosts = _blogRepository.GetAll();
if (blogPosts != null)
{
response.BlogPostViewModel = blogPosts.ConvertToPostListViewModel();
response.Success = true;
response.MessageType = MessageType.Success;
response.Message = ServiceMessages.GeneralServiceSuccessMessageOnRetrieveInformation;
_logger.Log(string.Format(response.Message));
}
else
{
response.MessageType = MessageType.Info;
response.Message = ServiceMessages.GeneralServiceAlarmMessageOnRetrieveInformation;
_logger.Log(string.Format(response.Message));
}
}
catch (Exception exception)
{
response.Success = false;
response.Message = ServiceMessages.GeneralServiceAlarmMessageOnRetrieveInformation;
_logger.Log(string.Format(response.Message));
_logger.Log(exception.Message);
}
return response;
}
I have injected IBlogRepository, IUnitOfWrork and ILogger(Log4net) in every service class of my application. rather than that I have similar response and generic message in every catch statement. once I wanted to make a kinds of generalization and not to re-implement the similar code in every service class but you making generalization in such a condition will be more cost effective and difficult. although it's so important to not duplicate the code in some situations, for example I have this BaseController and derive all of my controller from that:
public class BaseController : Controller
{
private readonly ICookieStorageService _cookieStorageService;
private readonly ILanguageService _languageService;
public BaseController(ICookieStorageService cookieStorageService,ILanguageService languageService)
{
_cookieStorageService = cookieStorageService;
_languageService = languageService;
}
}
so I don't need to create the cookieStorageService and languageService in my controllers each time as I have implemented it in for once.

Achieving DI without 3rd party framework

I am writing a plugin as part of a plugin architecture. The way plugins are created is via reflection and CreateInstance. Therefore the default constructor is called. This code I cannot touch and I am trying to find a sensible way to use DI without the ability to use a framework.
I believe I have 3 options:
i) Poor Man's DI (PMDI)
ii) Factory Pattern
iii) TinyIOC or similar (one cs file that handles DI)
I started looking at PMDI but then a dependency needed another dependency so I ended up with something similar to this which is ugly and could get worse:
public MyMainPluginClass() : this(new Repo(new Logger()))
{
}
public MyMainPluginClass(IRepo repo)
{
}
I then moved onto the idea of a Factory Pattern but could not find any decent demo code. I assume I would have something like this:
public static FactoryUtility
{
public static IRepo GetRepo()
{
return new Repo(GetLogger());
}
public static ILogger GetLogger()
{
return new Logger();
}
}
public MyMainPluginClass() : this(FactoryUtility.GetRepo())
{
}
public MyMainPluginClass(IRepo repo)
{
}
Is that how it would look?
I then came across TinyIOC which is one class that does all the dependency registering but I believe it requires to be setup in a Program.cs which I don't have in a class library. If someone has any experience using this could it be used like so:
public MyMainPluginClass()
{
var container = TinyIoCContainer.Current;
container.AutoRegister();
var implementation = container.Resolve<IRepo>();
MyMainPluginClass(implementation);
}
public MyMainPluginClass(IRepo repo)
{
}
Are there any alternative approaches to achieve DI without using a 3rd party library and if not which approach would choose from above?
NOTE: The code above has not been compiled and is just an idea of what I think would work. Please post corrections if they are valid approaches.
Since you're using .NET 4, you might want to consider using MEF, as it's built into the framework itself. This looks like fairly straightforward DI, which MEF handles well, as it's intended mainly for extensibility.
For details, see the Learn More page on the MEF CodePlex site.
I went with TinyIOC in the end. Unfortunately the plugin's constructor gets called several times before its actually up and running. I simply set a boolean to prevent registration being called several times and therefore it allows me to simply auto-register dependencies and off we go.
public MyMainPluginClass() : this(FactoryUtility.SetupIOC())
{
}
public MyMainPluginClass(IRepo repo)
{
}
public static class FactoryUtility
{
private static bool Initialized = false;
public static IRepo SetupIOC()
{
var container = TinyIoCContainer.Current;
if (!Initialized)
{
container.AutoRegister(new[] { Assembly.GetExecutingAssembly() });
Initialized = true;
}
var result = container.Resolve<IRepo>();
return result;
}
}
If I absolutely don't want to add a dependency to a DI container, I like to use my own TinyIOC (sorry about the name, didn't know it was taken), which for small projects gives me the same semantics as using a container, but clocks in at below 200 LOC.
If you are interested, here is the code: https://gist.github.com/ad7608e2ae10b0f04229

Autofac test all registered types can be resolved

I have a bunch of types registered with Autofac and some of the dependencies are rather deep. Is there a built in way to test that I can resolve all registered types? I want to fail fast at application startup, and not several minutes later part way in.
This is what I'm currently doing, and it seems to work, but I still wonder if there isn't a better way.
public void VerifyAllRegistrations()
{
foreach (IComponentRegistration registration in _container.ComponentRegistrations)
{
bool isNewInstance;
registration.ResolveInstance(_container, new Parameter[0], new Disposer(), out isNewInstance);
}
}
private class Disposer : IDisposer
{
public void Dispose()
{
// no-op
}
public void AddInstanceForDisposal(IDisposable instance)
{
instance.Dispose();
}
}
Autofac doesn't offer anything to that effect - because Autofac creates components in response to ResolveInstance, you're going to be faced with constructor side-effects etc.
Integration testing is the best way to address this.

Categories

Resources