Reading up alot on how to implement the Dispose pattern in a typical layered MVC architecture, I have come across alot of answers and even contradictions, which has now confused me.
I'm using the Domain Model pattern, and Repository pattern. Note, not using UoW, or Dependency Injection. I may use DI soon (not sure yet), which means the architecture would change and the Dispose technique also.
Anyway, here is the code.
Controller
protected override void Dispose(bool disposing)
{
_myService.Dispose();
// Call base class implementation
base.Dispose(disposing);
}
Service
public void Dispose()
{
_myRepository.Dispose();
}
Domain
public interface IMyRepository : IDisposable
Repository
Extra question: Is the IDisposable required here?
public class MyRepository : IMyRepository, IDisposable
// Flag, has Dispose already been called?
private bool disposed = false;
// Protected implementation of Dispose pattern
protected virtual void Dispose(bool disposing)
{
if (!this.disposed)
{
if (disposing)
{
// Free any other managed objects here
_context.Dispose();
}
}
// Free any unmanaged objects here
this.disposed = true;
}
// Public implementation of Dispose pattern callable by consumers
public void Dispose()
{
// Dispose of unmanaged resources
Dispose(true);
// Suppress finalization
GC.SuppressFinalize(this);
}
I have put together (below) what I believe is correct, but not entirely sure.
Question. Will the above code cleanup all unmanaged resources, e.g. database connections? (i.e. is what I've done correct)
no, not on MyRepository as you've already inherited it though IMyRepository
Related
tldr: Is there any way I can choose which constructor to use when I register a type?
I have followed the instructions to create a platform specific inversion of control as outlined in Inversion of control.
In your core project, you can declare an interface and you can use
that interface in your classes there ...
In each UI project, you can then declare the platform-specific
implementation ...
You can then register these implementations in each of the
platform-specific Setup files - e.g. you could override
MvxSetup.InitializeFirstChance
So in my core project I have defined the following interface
public interface IJob
{
void AddAction(Action action);
}
In my Android project I have implemented the interface as follows
public class CustomJob: Job, IJob
{
private Action _action;
public CustomJob(IntPtr javaReference, JniHandleOwnership transfer) : base(javaReference, transfer)
{
}
public CustomJob() : base(new Params
(Jobs.Priority.MID
).RequireNetwork().Persist())
{
//_action = action;
}
public override void OnAdded()
{
}
protected override void OnCancel(int p0, Throwable p1)
{
}
public override void OnRun()
{
_action.Invoke();
}
protected override RetryConstraint ShouldReRunOnThrowable(Throwable p0, int p1, int p2)
{
return RetryConstraint.Cancel;
}
public void AddAction(Action action)
{
_action = action;
}
}
And I overrode the implementation of InitializeFirstChance in Setup.cs
protected override void InitializeFirstChance()
{
Mvx.IoCProvider.RegisterType<IJob, CustomJob>();
base.InitializeFirstChance();
}
However, I get the following stacktrace at runtime
{MvvmCross.Exceptions.MvxIoCResolveException: Failed to resolve
parameter for parameter javaReference of type IntPtr when creating
CustomJob. You may pass it as an argument at
MvvmCross.IoC.MvxIoCContainer.GetIoCParameterValues (System.Type type,
System.Reflection.ConstructorInfo firstConstructor,
System.Collections.Generic.IDictionary2[TKey,TValue] arguments)
[0x0005a] in
C:\projects\mvvmcross\MvvmCross\IoC\MvxIoCContainer.cs:648 at
MvvmCross.IoC.MvxIoCContainer.IoCConstruct (System.Type type,
System.Collections.Generic.IDictionary2[TKey,TValue] arguments)
[0x00031] in
C:\projects\mvvmcross\MvvmCross\IoC\MvxIoCContainer.cs:413
Is there any way I can choose which constructor to use when I register a type? Thank you.
AFAIK you can't choose which constructor the Mvx's IoC engine will choose.
So one way is to make another class that implements your IJob that has a reference to Job internally and in the implementation of the class you pass the action to the Job implementation.
public class JobHandler : IJob
{
private Job _customJob;
public JobHandler()
{
this._customJob = new CustomJob();
}
public void AddAction(Action action)
{
this._customJob.AddAction(action);
}
}
If you want you can do an IJobHandler that inherits IJob so that you can use that interface for the JobHandler implementations and the IJob for you actual Job
Another way is to add stub parameters to the parameterless constructor so that it takes more parameters than the other and gets elected by the IoC engine (I'm not entirely sure that it would work, but I think so). But it is a bit messy.
Another way is you to tell the IoC engine how you want to construct your IJob:
Mvx.IoCProvider.RegisterType<IJob>(() => new CustomJob());
HIH
I have built a API service using ASP.NET Core. Just like any other API, this one has to retrieve some data from database, apply some business logic and then send data back to the client.
To start with, I have EmployeeDataContext class that is scaffolded using Entity Framework.Core. This class is derived from Microsoft.EntityFrameworkCore.DbContext as shown below.
public partial class EmployeeDataContext : DataContext
{
protected override void OnModelCreating(ModelBuilder modelBuilder)
{
......
}
}
This data context class is used in a data provider class as follows.
public class EmployeeDataProvider : IEmployeeDataProvider, IDisposable
{
private EmployeeDataContext dataContext;
public EmployeeDataProvider(EmployeeDataContext context)
{
this.dataContext = context;
}
// Various CRUD methods
// Dispose
public void Dispose()
{
if ( this.dataContext != null )
{
this.dataContext.Dispose();
}
}
}
The service layer holds a reference to data provider as follows.
public class EmployeeService : IEmployeeService
{
private IEmployeeDataProvider dataProvider;
public EmployeeService(IEmployeeDataProvider dataProvider)
{
DataProvider = dataProvider;
}
// Add/Delete/Update Employee related calls
}
All the dependencies are injected in Startup class as follows.
public class Startup
{
public void ConfigureServices(IServiceCollection services)
{
services.AddScoped<IEmployeeDataProvider, EmployeeDataProvider>();
services.AddScoped<IEmployeeService, EmployeeService>();
}
}
According to Microsoft doc
The container will call Dispose for IDisposable types it creates.
This mean that EmployeeDataProvider.Dispose() method will be called by container at the end of request lifecycle.
The question I have is about how to implement IDisposable for EmployeeDataProvider class. The link provides best practices for implementing IDisposable for various scenarios which may require you to implement Disposable(bool) also. However, for this scenario, I am not sure if
all that is needed and my current (simple) implementation of Dispose is good enough because (since there is no call via finalizer is involved here). Is my understanding and IDisposable look correct for this situation?
Implementing IDisposable is trivial in the case where your class is sealed:
public sealed class Foo : IDisposable {
private readonly FileStream stream;
public Foo() {
this.stream = new FileStream( ... );
}
public void Dispose() {
this.stream.Dispose();
}
}
You only need the protected virtual void Dispose(Boolean disposing) method, and the recommended implementation of IDisposable if your class will be subclassed.
This is described in the documentation for FxCop rule CA1063 "Implement IDisposable correctly": https://msdn.microsoft.com/en-us/library/ms244737.aspx
Dispose() is not public, sealed, or named Dispose.
Dispose(bool) is not protected, virtual, or unsealed.
In unsealed types, Dispose() must call Dispose(true).
For unsealed types, the Finalize implementation does not call either or both Dispose(bool) or the case class finalizer.
[...]
How to Fix Violations
[...]
Ensure that $className is declared as public and sealed.
Another tip: if your fields are only ever assigned in the type initializer or in the constructor - and should never be assigned a null value - then you should use the readonly modifier (or use read-only auto-properties - which have a readonly backing field) and that way you don't need to do a null-check in your Dispose method.
Note that Dispose() methods are generally idempotent:
https://msdn.microsoft.com/en-us/library/fs2xkftw.aspx
To help ensure that resources are always cleaned up appropriately, a Dispose method should be callable multiple times without throwing an exception.
Historically there were a few classes in .NET 1.x and 2.x that did throw ObjectDisposesException if they were Disposed twice, but I haven't personally observed non-idempotent behaviour since upgrading to .NET 4.x - though it's possible that some poorly-written third-party libraries and components might implement it incorrectly, however.
In my application I've noticed that if I mark a class in the SM registry as a Singleton type it gets disposed of, however if don't specify any Singleton it doesn't get disposed of.
What and why are the reasons for this?
public class IoC
{
public static IContainer Init()
{
var container = new Container(x =>
{
x.Scan(s => {
s.TheCallingAssembly();
s.AssembliesFromApplicationBaseDirectory();
s.WithDefaultConventions();
});
// disposed is called on this class but not if .Singleton() is removed
x.For<IMyService>().Singleton();
});
return container;
}
}
class Program
{
static void Main(string[] args)
{
using (var container = IoC.Init())
{
var theStory1 = container.GetInstance<MyService>();
theStory1.TheMethod();
}
}
}
Singleton lifecycle is bound to the container's scope thus when disposing the container it takes care to dispose all singletons implementing IDisposable. With transients and other lifecycles like HttpContextScoped it is up to developer to dispose them manually when no longer need them.
Transient disposables are tricky a little bit in terms of how it should be handled. Imagine case like this one below:
public class ClassWithDisposableTypeDependency
{
private readonly ISampleDisposable disposableType;
public ClassWithDisposableTypeDependency(ISampleDisposable disposableType)
{
this.disposableType = disposableType;
}
public void SomeAction()
{
using (this.disposableType)
{
this.disposableType.DoSomething();
}
}
}
What will happend when SomAction() won't be executed? Dispose won't be called on disposableType field. In fact in this case ClassWithDisposableTypeDependency should also implement IDisposable and dispose its disposable dependencies.
But there is a better way to handle such cases. In mentioned case the main issue is to defer creation of a dependency to a moment when we really need that objects. We can achieve that in many ways: func, lazy, factory, etc. Here is possible solution with usage of func.
public class ClassWithDisposableTypeFuncDependency
{
private readonly Func<ISampleDisposable> disposableTypeFactory;
public ClassWithDisposableTypeFuncDependency(Func<ISampleDisposable> disposableTypeFactory)
{
this.disposableTypeFactory = disposableTypeFactory;
}
public void SomeAction()
{
var disposable = this.disposableTypeFactory();
using (disposable)
{
disposable.DoSomething();
}
}
}
This is how we need to setup it in StructureMap:
var container = new Container(c => c.For<ISampleDisposable>().Use<SampleDisposable>());
var clazz = container.GetInstance<ClassWithDisposableTypeFuncDependency>();
clazz.SomeAction(); // dependency is created and disposed
Hope this helps!
Preliminaries
I'm using Ninject.MVC3 2.2.2.0 Nuget Package for injecting into my controller an implementation of a IDomain Interface that separates my Business Logic (BL) using an Factory approach.
I'm registering my Ninject Modules in the preconfigured NinjectMVC3.cs using:
private static void RegisterServices(IKernel kernel)
{
var modules = new INinjectModule[]
{
new DomainBLModule(),
new ADOModule()
};
kernel.Load(modules);
}
I'm trying to avoid the fatal curse of the diabolic Service Locator anti-pattern.
The Domain Class uses a DBContext that i'm trying to inject an interface implementation too, via an IDBContext, with the following scenario:
IDomainBLFactory:
public interface IDomainBLFactory
{
DomainBL CreateNew();
}
DomainBLFactory:
public class DomainBLFactory : IDomainBLFactory
{
public DomainBL CreateNew()
{
return new DomainBL();
}
}
In the controller's namespace:
public class DomainBLModule : NinjectModule
{
public override void Load()
{
Bind<IDomainBLFactory>().To<DomainBLFactory>().InRequestScope();
}
}
At this point i can inject the IDomainBLFactory implementation into my controller using Ninject Constructor Injection without any problem:
public class MyController : Controller
{
private readonly IDomainBLFactory DomainBLFactory;
// Default Injected Constructor
public MyController(IDomainBLFactory DomainBLFactory)
{
this.DomainBLFactory = DomainBLFactory;
}
... (use the Domain for performing tasks/commands with the Database Context)
}
Now my central problem.
In the DomainBL implementation, i will inject the dependency to a particular DBContext, in this case ADO DBContext from Entity Framework, again, using a IDBContextFactory:
IDbDataContextFactory
public interface IDbDataContextFactory
{
myADOEntities CreateNew();
}
DbDataContextFactory
public class DbDataContextFactory : IDbDataContextFactory
{
public myADOEntities CreateNew()
{
return new myADOEntities ();
}
}
ADOModule
public class ADOModule : NinjectModule
{
public override void Load()
{
Bind<IDbDataContextFactory>().To<DbDataContextFactory>().InRequestScope();
}
}
Now in the DomainBL implementation I faced the problem of injecting the necessary interface for the DBContext Object Factory:
public class DomainBL
{
private readonly IDbDataContextFactory contextFactory;
**** OPS, i tried to understand about 10+ Stackoverflow articles ***
...
}
What have I tried?
To Use the constructor Injection. But I don't know what to inject in the call for the Factory CreateNew() in the IDBContextFactory. For clear:
public class DomainBLFactory: IDomainBLFactory
{
// Here the constructor requires one argument for passing the factory impl.
public DomainBL CreateNew()
{
return new DomainBL(?????) // I need a IDBContextFactory impl to resolve.
//It's not like in the MVC Controller where injection takes place internally
//for the controller constructor. I'm outside a controller
}
}
In this Useful Post, our unique true friend Remo Gloor describes in a comment a possible solution for me, citing: "Create an interface that has a CreateSomething method that takes everything you need to create the instance and have it return the instance. Then in your configuration you implement this interface and add an IResolutionRoot to its constructor and use this instace to Get the required object."
Questions: How do I implement this in a proper way using Ninject.MVC3 and my modest Domain Class approach? How do I Resolve the IResolutionRoot without be punished for relaying in the Service Locator anti-pattern?
To Use the property injection for an IDBContexFactory. In the course of learning and reading all the contradictory points of view plus the theoretical explanations about it, I can deduce it's not a proper way of doing the injection for my DBContexFactory class code. Nevermind. It doesn't work anyway.
public class DomainBL
{
[Inject]
public IDbDataContextFactory contextFactory
{
get;
set;
}
//Doesn't works, contextFactory is null with or without parameterless constructor
.... (methods that uses contextFactory.CreateNew()....
}
Question: What am I missing? Even if this approach is wrong the property is not injecting.
Be cursed. Use a DependencyResolver and live with the stigmata. This works and I will remain in this approach until a proper solution appears for me. And this is really frustrating because the lack of knowledge in my last 10 days effort trying to understand and do things right.
public class DomainBL
{
private readonly IDbDataContextFactory contextFactory;
this.contextFactory = DependencyResolver.Current.GetService<IDbDataContextFactory>();
//So sweet, it works.. but i'm a sinner.
}
Question: Is there a big mistake in my understanding of the Factory Approach for the injection of interfaced implementations and using a Domain Driven Approach for taking apart the Business Logic? In the case I'm wrong, what stack of patterns should I implement with confidence?
I saw before a really big quantity of articles and blogs that does not ask this important question in a open a clear way.
Remo Gloor introduces the Ninject.Extensions.Factory for the Ninject 3.0.0 RC in www.planetgeek.ch/2011/12/31/ninject-extensions-factory-introduction.
Question: Will this extension work coupled with Ninject.MVC3 for general porpouse?. In such case it should be my hope for the near future.
Thank you all in advance for your guidance and remember we appreciate your kind help. I think a lot of people will find this scenario useful too.
I don't really get the purpose of your factories. Normally, you have exactly one ObjectContext instance for one request. This means you don't need the factory and can simply bind myADOEntities in Request scope and inject it into your DomainBL without adding the factories:
Bind<myADOEntities>().ToSelf().InRequestScope();
Bind<DomainBL>().ToSelf().InRequestScope();
And Yes the factory and mvc extrensions work together.
Here's an implementation of a generic IFactory to solve the problem without resorting to the ServiceLocator anti-pattern.
First you define a nice generic factory interface
public interface IFactory<T>
{
T CreateNew();
}
And define the implementation which uses ninject kernel to create the objects requested
class NinjectFactory<T> : IFactory<T>
{
private IKernel Kernel;
public NinjectFactory( IKernel Kernel )
{
this.Kernel = Kernel;
}
public T CreateNew()
{
return Kernel.Get<T>();
}
}
Binding to your factory using the following
private static void RegisterServices(IKernel kernel)
{
kernel.Bind<myADOEntities>().ToSelf();
kernel.Bind<DomainBL>().ToSelf();
kernel.Bind(typeof(IFactory<>)).To(typeof(NinjectFactory<>));
}
You can now do the following in your controller.
public class MyController : Controller
{
private readonly IFactory<DomainBL> DomainBLFactory;
public MyController( IFactory<DomainBL> DomainBLFactory )
{
this.DomainBLFactory = DomainBLFactory;
}
// ... (use the Domain for performing tasks/commands with the Database Context)
}
And in your DomainBL
public class DomainBL
{
IFactory<myADOEntities> EntitiesFactory;
public DomainBL( IFactory<myADOEntities> EntitiesFactory )
{
this.EntitiesFactory = EntitiesFactory;
}
// ... (use the Entities factory whenever you need to create a Domain Context)
}
How do I handle classes with static methods with Ninject?
That is, in C# one can not have static methods in an interface, and Ninject works on the basis of using interfaces?
My use case is a class that I would like it to have a static method to create an
unpopulated instance of itself.
EDIT 1
Just to add an example in the TopologyImp class, in the GetRootNodes() method, how would I create some iNode classes to return? Would I construct these with normal code practice or would I somehow use Ninject? But if I use the container to create then haven't I given this library knowledge of the IOC then?
public interface ITopology
{
List<INode> GetRootNodes();
}
public class TopologyImp : ITopology
{
public List<INode> GetRootNodes()
{
List<INode> result = new List<INode>();
// Need code here to create some instances, but how to without knowledge of the container?
// e.g. want to create a few INode instances and add them to the list and then return the list
}
}
public interface INode
{
// Parameters
long Id { get; set; }
string Name { get; set; }
}
class NodeImp : INode
{
public long Id
{
get { throw new NotImplementedException(); }
set { throw new NotImplementedException(); }
}
public string Name
{
get { throw new NotImplementedException(); }
set { throw new NotImplementedException(); }
}
}
// Just background to highlight the fact I'm using Ninject fine to inject ITopology
public partial class Form1 : Form
{
private ITopology _top;
public Form1()
{
IKernel kernal = new StandardKernel(new TopologyModule());
_top = kernal.Get<ITopology>();
InitializeComponent();
}
}
If you're building a singleton or something of that nature and trying to inject dependencies, typically you instead write your code as a normal class, without trying to put in lots of (probably incorrect) code managing the singleton and instead register the object InSingletonScope (v2 - you didnt mention your Ninject version). Each time you do that, you have one less class that doesnt surface its dependencies.
If you're feeling especially bloody-minded and are certain that you want to go against that general flow, the main tools Ninject gives you is Kernel.Inject, which one can use after you (or someone else) has newd up an instance to inject the dependencies. But then to locate one's Kernelm you're typically going to be using a Service Locator, which is likely to cause as much of a mess as it is likely to solve.
EDIT: Thanks for following up - I see what you're after. Here's a hacky way to approximate the autofac automatic factory mechanism :-
/// <summary>
/// Ugly example of a not-very-automatic factory in Ninject
/// </summary>
class AutomaticFactoriesInNinject
{
class Node
{
}
class NodeFactory
{
public NodeFactory( Func<Node> createNode )
{
_createNode = createNode;
}
Func<Node> _createNode;
public Node GenerateTree()
{
return _createNode();
}
}
internal class Module : NinjectModule
{
public override void Load()
{
Bind<Func<Node>>().ToMethod( context => () => Kernel.Get<Node>() );
}
}
[Fact]
public void CanGenerate()
{
var kernel = new StandardKernel( new Module() );
var result = kernel.Get<NodeFactory>().GenerateTree();
Assert.IsType<Node>( result );
}
}
The ToMethod stuff is a specific application of the ToProvider pattern -- here's how you'd do the same thing via that route:-
...
class NodeProvider : IProvider
{
public Type Type
{
get { return typeof(Node); }
}
public object Create( IContext context )
{
return context.Kernel.Get<Node>();
}
}
internal class Module : NinjectModule
{
public override void Load()
{
Bind<Func<Node>>().ToProvider<NodeProvider>();
}
}
...
I have not thought this through though and am not recommending this as A Good Idea - there may be far better ways of structuring something like this. #Mark Seemann? :P
I believe Unity and MEF also support things in this direction (keywords: automatic factory, Func)
EDIT 2: Shorter syntax if you're willing to use container-specific attributes and drop to property injection (even if Ninject allows you to override the specific attributes, I much prefer constructor injection):
class NodeFactory
{
[Inject]
public Func<Node> NodeFactory { private get; set; }
public Node GenerateTree()
{
return NodeFactory();
}
}
EDIT 3: You also need to be aware of this Ninject Module by #Remo Gloor which is slated to be in the 2.4 release
EDIT 4: Also overlapping, but not directly relevant is the fact that in Ninject, you can request an IKernel in your ctor/properties and have that injected (but that doesn't work directly in a static method).