Windsor WCF Facility factory? - c#

So I currently have a master DAO class ITrackingToolDAO that has all the Service Contracts for each of my business entities.
public partial interface ITrackingToolDAO {
void Open(string connectionString);
void Close();
IBusinessFunctionDAO BusinessFunction { get; }
IBusinessUnitDAO BusinessUnit { get; }
IProgramBudgetDAO ProgramBudget { get; }
IProjectDAO Project { get; }
...
}
My Service Contract looks like so
[ServiceContract(Namespace="http://bmgops.qintra.com/Tracking/v1/BusinessFunction")]
public partial interface IBusinessFunctionDAO {
[OperationContract]
BusinessFunction GetBusinessFunction(Int32 businessFunctionId);
[OperationContract]
IEnumerable<BusinessFunction> Find(string filter);
[OperationContract]
SaveEventArgs<BusinessFunction>Save(BusinessFunction businessFunction);
}
I currently have 2 concrete implementations of my ITrackingToolDAO interface.
The first one is TrackingToolSqlDAO which instantiates a concrete SQL DAO for each entity. i.e) BusinessFunctionSqlDAO, ProjectSqlDAO, etc.
The second one is a TrackingToolWCFDao which creates WCF proxys using ChannelFactory<T> to create an implementation for all my DAO members.
Now, I want to start using the Windsor WCF facility instead of CreateChannel. What would be the best way to accomplish this ?
I was thinking of creating a dummy implementation of ITrackingToolDAO that took in an IKernel parameter in the constructor.
public class DummyDAO: ITrackingToolDAO {
public DummyDAO(IKernel kernel) {
_ProjectDAO = kernel.Resolve<IProject>();
....
}
}
This way i could use the WCF Facility to create all my channels. I just don't like it cuz it's using the container as a service locator which is a code smell. Ideally I would also like it if I could have my SQL DAO and new WCF DAo both registered in the container so I could create either one by just referencing them by name.
Any thoughts ?

If you're using Castle.Facilities.WcfIntegration, you could setup your dao like this:
container.Register(Component.For<IProject>().ImplementedBy<Project>());
You can than use WcfIntegration facility like this:
container.AddFacility<WcfFacility>()
.Register(Castle.MicroKernel.Registration.Component.For<IBusinessFunctionDAO>()
.ImplementedBy<BusinessFunctionDAO>()
.AsWcfService());
Than for BusinessFunctionDAO you can do constructor injection like this:
public class BusinessFunctionDAO : IBusinessFunctionDAO
{
public BusinessFunctionDAO(IProject project)
{
if (project== null) new ArgumentException("project");
_project = project;
}
...
private readonly IProject _project;
}

Related

Nested Interface (empty) Dependency Registration

I have a parent interface that is empty, and its only purpose is to implement 2 other child interfaces. This way I can reduce the number of constructor parameters to an acceptable count. The problem is I dont know how to register this dependency in the container since there is no implementation of the parent Interface. Entries are present for the child services, but the dependent services are unable to find the required service dependencies for both children at this point.
services.AddScoped<IServiceChild1, IServiceChild1>();
services.AddScoped<IServiceChild2, IServiceChild2>();
// how to register IServiceParent
public interface IServiceParent: IServiceChild1, IServiceChild2
{
}
Make it a class instead:
public class ServiceParentServices
{
public IServiceChild1 Service1 { get; }
public IServiceChild2 Service2 { get; }
public class ServiceParentServices(IServiceChild1 service1, IServiceChild2 service2)
{
Service1 = service1;
Service2 = service2;
}
}
Register this class to the ServiceCollection, and when you want to consume it, just inject ServiceParentServices into the constructor
public class ServiceParent
{
private ServiceParentServices _services;
public ServiceParent(ServiceParentServices services)
{
_services = services;
}
}
As an alternative you could also inject IServiceProvider, but this more like the ServiceLocator anti pattern.

Cannot access appsettings.json from class library

I have been following this tutorial in order to get access to my appsettings.json from my MVC project inside my class library.
geek-tutorial
I have a class as such in my class library
using dapper;
public class SqlDataAccess : IConfigManager
{
private readonly IConfiguration _configuration;
public SqlDataAccess(IConfiguration configuration)
{
this._configuration = configuration;
}
public List<T> LoadData<T>(string sql)
{
using (IDbConnection cnn = new SqlConnection(GetConnectionString()))
{
return cnn.Query<T>(sql).ToList();
}
}
public int SaveData<T>(string sql, T data)
{
using (IDbConnection cnn = new SqlConnection(GetConnectionString()))
{
return cnn.Execute(sql, data);
}
}
public string GetConnectionString(string connectionName = "URLShortnerDB")
{
return this._configuration.GetConnectionString(connectionName);
}
}
Interface:
public interface IConfigManager
{
string GetConnectionString(string connectionName);
}
I have added services.AddSingleton<IConfigManager, SqlDataAccess>(); in my mvc startup.cs
However now I would like to use my SqlDataAccess class and call methods from another class e.g:
public static class ShortUrlProcessor
{
public static ShortURLModel GetOriginalURL(string shortUrl)
{
string sql = $#"SELECT * FROM dbo.shorturl WHERE shortUrl = '{ shortUrl }'";
var originalURLEnum = SqlDataAccess.LoadData<ShortURLModel>(sql); //<--- problem
return originalURLEnum.First();
}
}
However SqlDataAccess is not instantiated, and in order to do var _sqldataaccess = SqlDataAccess() I need to pass in a parameter as defined in the constructor of the class. I do not know what to pass in? I do not have any IconfigurationManager in this ShortUrlProcessor class. I understand the reason of doing this is dependancy injection, however I am still not grasping how this all works?
You're very close, but you need to fix a few things. SqlDataAccess implements IConfigManager. Why? What's that providing? Instead, you should have it implement an interface that allows it to expose the functionality other classes depend on.
public interface ISqlDataAccess
{
List<T> LoadData<T>(string sql);
int SaveData<T>(string sql, T data);
}
Change your SqlDataAccess class to implement this interface...
public class SqlDataAccess : ISqlDataAccess
And of course, wire this up with your DI container.
services.AddTransient<ISqlDataAccess, SqlDataAccess>();
Now, any class that needs to run SQL can take a dependency on the ISqlDataAccess interface, utilizing constructor injection to get an instance of ISqlDataAccess. Since we've told the DI container to provide a SqlDataAccess instance when the ISqlDataAccess dependency is present, it will all wire up nicely in your app.
Then we have the issue with ShortUrlProcessor. You declared that class as static. That's bad, because it makes it difficult for it to use constructor injection to get its dependencies, and any other class that needs to invoke its methods has to do so directly, rather than via an abstraction. That violates the Dependency Inversion Principle of SOLID. And since we should always strive to write SOLID code because of the maintainability and testability, we need to fix that.
public class ShortUrlProcessor : IShortUrlProcessor
{
readonly ISqlDataAccess _dataAccess;
public ShortUrlProcessor(ISqlDataAccess dataAccess)
{
_dataAccess = dataAccess;
}
public ShortURLModel GetOriginalURL(string shortUrl)
{
string sql = $#"SELECT * FROM dbo.shorturl WHERE shortUrl = '{ shortUrl }'";
var originalURLEnum = _dataAccess.LoadData<ShortURLModel>(sql); //<--- problem
return originalURLEnum.First();
}
}
And we'll need an interface so other classes don't have to depend directly on ShortUrlProcessor...
public interface IShortUrlProcessor
{
ShortURLModel GetOriginalURL(string shortUrl);
}
And of course, we need to register it with our DI container.
services.AddTransient<IShortUrlProcessor, ShortUrlProcessor>();
Then any class that needs to access the functionality of ShortUrlProcessor can do so via the abstraction IShortUrlProcessor. You mentioned you have a controller calling this, so let's wire that up too.
public class MyController()
{
readonly IShortUrlProcessor _shortUrlProcessor;
public MyController(IShortUrlProcessor shortUrlProcessor)
{
_shortUrlProcessor = shortUrlProcessor;
}
public ActionResult SomeActionMethod()
{
var model = _shortUrlProcessor.GetOriginalURL("asdf");
return View(model);
}
}
We don't have to create an interface for the controller, because the controller will be called by the framework. And we don't have to wire up the controller with the DI container, because the framework handles that for us.
By doing all this, we can easily test individual methods in isolation. There's still some improvements to be made (the SQL Injection attack I mentioned in the comments needs to be fixed), but it's a good step in the right direction.

Unity: configure container to resolve to same type in mutliple ways

Consider these interfaces and classes
interface IWorkflowService
{
void FillContext(WFContext context, IWorkflowableEntity entity);
}
interface IDataService<Entity>
{
}
abstract class DataService<TEntity>
{
}
class EmployeeDataService : IWorkflowService, DataService<Employee>
{
}
class WorkflowHandler
{
private IUnityContainer _container;
public bool Handle(IWorklfowableEntity entity)
{
// now I want to resolve the correct IWorkflowService
// suppose entity is an employee Entity
// EmployeeDataService should be resolved
}
}
//container definition:
container.RegisterType<IDataService<employee>, EmployeeDataService>();
In the Workflhandler I want to resolve the correct IWorkflowService, which is dependent on the type of the given entity.
How should I define my unity container to be able get the EmployeeDataService, based on IWorkflowService and the Employee type of my entity?
How should I call this from my Handle method in Workflowhandler?
By the way: Perhaps I am misusing Unity as a service locator. If that is the case should I create my own service locator to get the correct service?
Thanks in advance for any thoughts and answers.
As I was suspecting, it is considered a malpractice to use the unity container as a service locator.
Instead, the workflowhandler class should be dependent on a factory. This is often needed when you are writing cross cutting features and use Dependecy Injection.
So instead WorkflowHandler looks like this:
class WorkflowHandler
{
private IWorkflowServiceFactory _wfsfactory
public WorkflowHandler(IWorkflowServiceFactory workflowservicefactory)
{
_wfsfactory = workflowservicefactory;
}
public bool Handle(IWorklfowableEntity entity)
{
var svc = _wfsfactory.GetServiceByEntity(entity);
var context = new WfContext();
svc.FillContext(context, entity);
//handle evaluate etc.
}
}
And the service factory would look like this:
class WorkflowServiceFactory : IWorkflowServiceFactory
{
private IUnityContainer _container;
public GetServiceByEntity(IWorkflowableEntity entity)
{
Type t = typeof(IDataService<>);
Type fulltype = t.MakeGenericType(new [] { entity.GetType() });
return _container.Resolve(fulltype);
}
}

IUnitOfWork to DomainService constructor using Unity container

I created Silverlight application and I want to realise it via WCF RIA Services. There are 3 projects in my solution:
Data access layer library which contains all db logic and entities. I will use IUnitOfWork interface to communicate with it:
public interface IUnitOfWork : IDisposable
{
IRepository<Customer> Customers { get; }
IRepository<Product> Products { get; }
IRepository<Order> Orders { get; }
void Save();
}
WCF RIA Services project where I created custom DomainService class. Its constructor takes IUnitOfWork interface parameter:
[EnableClientAccess()]
public void StoreService : DomainService
{
private IUnitOfWork _repository;
public StoreService(IUnitOfWork repository)
{
_repository = repository;
}
// ... some methods to query _repository
}
Client project (its written in WPF).
So, I want to use Unity IoC container to path interface implementation into service. I can't understand where need to create custom service factory or something like that and where to register it to be used by system. For example, I know that in ASP.NET MVC there is DefaultControllerFactory class which I need to derive. Then put my IoC bindings in it and then register it in Global.asax.cs file. Can you help me, please. Thanks.
The DomainService exposes a static property called DomainService.DomainServiceFactory.
You'll need a custom class that implements IDomainServiceFactory
interface IDomainServiceFactory
{
DomainService CreateDomainService(Type domainServiceType, DomainServiceContext context);
void ReleaseDomainService(DomainService domainService)
}
I've copied and pasted a blog post from Fredrik Normen how to wire up Unity to DomainService.
public class MyDomainServiceFactory : IDomainServiceFactory
{
public DomainService CreateDomainService(Type domainServiceType, DomainServiceContext context)
{
var service = Global.UnityContainer.Resolve(domainServiceType) as DomainService;
service.Initialize(context);
return service;
}
public void ReleaseDomainService(DomainService domainService)
{
domainService.Dispose();
}
}
In your Global.asax
protected void Application_Start(object sender, EventArgs e)
{
DomainService.Factory = new MyDomainServiceFactory();
UnityContainer.RegisterType<StoreService>();
UnityContainer.RegisterType<IUnitOfWork, UnitOfWorkImpl>();
}

Dependency Injection in C# Web API [duplicate]

This question already has an answer here:
Dependency Injection with ASP.NET Web API
(1 answer)
Closed 6 years ago.
I am trying to create a rest service in C# Web API.
At the moment I'm not considering any DB decisions, hence I'm adding a mock class library.
I'm creating a model interface and implementing the model in the mock class library.
public interface IUser
{
int userId { get; set; }
string firstName { get; set; }
string lastName { get; set; }
string email { get; set; }
List<IUser> getAllUsers();
IUser getUser(int ID);
bool updateUser(IUser user);
bool deleteUser(int ID);
}
and implementing this in the mock class library
public class User : IUser
{
public string email { get; set; }
public string firstName { get; set; }
public string lastName { get; set; }
public int userId { get; set; }
public bool deleteUser(int ID)
{
throw new NotImplementedException();
}
public List<IUser> getAllUsers()
{
throw new NotImplementedException();
}
public IUser getUser(int ID)
{
throw new NotImplementedException();
}
public bool updateUser(IUser user)
{
throw new NotImplementedException();
}
}
Now the mock library references the service application to implement the interface.
Now I need to call the mock implementation from the controller class in the service application.
How do I do that without creating a cyclic dependency. I did some research and came up with a solution that DI is the way to go.
Can someone help me to implement this with code samples?
Many thanks.
If you don't mind which IoC container you might use, I would recommend Ninject.
You need to install the next packages via Nuget:
Ninject
Ninject integration for Web Api 2
Ninject Web Host for WebApi 2
Ninject Web Common
Ninject Web Common Web Host
Then in the Ninject configuration file NinjectWebCommon.cs in the end of RegisterServices() method add the following code:
kernel.Bind<IUser>().To<User>();
And now just add IUser as a parameter to the controller class and Ninject will automatically inject it.
public class MyController : Controller
{
private IUser _user;
// Ninject will automatically inject a User instance here
// on controller creation
public MyController(IUser user)
{
_user = user;
}
}
There are different approaches for using Ninject so you can search for other that will fit your needs better.
"Now I need to call the mock implementation from the controller class in the service application."
This doesn't sound right. I think you have a design issue here; why do you need to reference a mock implementation of IUser from your service application?
One thing to bear in mind is that clients own the interface, so the IUser interface does not belong in the Mock class library at all; it should ideally be defined in a totally separate assembly so that both your mock class library and your service class library can reference it (and provide their own implementations for it if required).
This is the Dependency Inversion Principle and whilst I agree that a DI library of some kind can help you to manage the implementation of such Inversion of Control, I don't believe that it will help you here in the long run. You will probably still run into the same cyclic reference issues in the container itself.
Right now I think you first need to look at using the Stairway Pattern to get your Dependencies correctly inverted before you look at using any DI libraries
Now the mock library references the service application to implement the interface.
This is the source of your problem. I would recommend moving the interfaces for your data access layer out into a separate project. Then you can create a project with mock/in memory implementations, and later on add another project with the real implementations.
Another thing is that your IUser is the contract for your DTO (data transfer object), but it contains DAO (data access object) methods. Typically you would want to separate these concerns with something like the repository pattern.
public interface IUserRepository
{
IEnumerable<IUser> GetAllUsers();
IUser GetUser(int id);
...
}
This repository is what you would inject into your API controller.

Categories