Orchard CMS. IAutofacActionFilter - asp.net-web-api

I need to inject services into WebApi Action Filter (or into DelegatingHandler).
With Autofac I can use IAutofacActionFilter (https://code.google.com/p/autofac/wiki/WebApiIntegration). But there isn't Autofac's WebApi Dependecy Resolver in the Orchard. There is Orchard's resolver implementation.
Also I tried this:
var service = (IMyService)GlobalConfiguration.Configuration.DependencyResolver.GetService(typeof(IMyService));
or
var service = (IMyService)request.GetDependencyScope().GetService(typeof(IMyService));
But it doesn't work too.

Related

NServiceBus and ApiController

i try to configure my NServiceBus for a WebApi. I've tried this one: https://coderkarl.wordpress.com/2012/03/16/injecting-nservicebus-into-asp-net-webapi/
The Problem is the Syntax has been changed in the newest NServiceBus-Versin. I can't use the Functions for the Configure-Class because they will be removed in further Versions. The new way to configure the Bus is using the BusConfiguration-Class but i have no idea how.
Here is the older Code:
public static Configure ForWebApi(this Configure configure)
{
// Register our http controller activator with NSB
configure.Configurer.RegisterSingleton(typeof(IHttpControllerActivator),
new NSBHttpControllerActivator());
// Find every http controller class so that we can register it
var controllers = Configure.TypesToScan
.Where(t => typeof(IHttpController).IsAssignableFrom(t));
// Register each http controller class with the NServiceBus container
foreach (Type type in controllers)
configure.Configurer.ConfigureComponent(type, ComponentCallModelEnum.Singlecall);
// Set the WebApi dependency resolver to use our resolver
GlobalConfiguration.Configuration.ServiceResolver.SetResolver(new NServiceBusResolverAdapter(configure.Builder));
// Required by the fluent configuration semantics
return configure;
}
And Application_Start():
AreaRegistration.RegisterAllAreas();
// Use LocalDB for Entity Framework by default
Database.DefaultConnectionFactory = new SqlConnectionFactory("Data Source=(localdb)\v11.0; Integrated Security=True; MultipleActiveResultSets=True");
RegisterGlobalFilters(GlobalFilters.Filters);
RegisterRoutes(RouteTable.Routes);
BundleTable.Bundles.RegisterTemplateBundles();
Configure.WithWeb()
.DefaultBuilder()
.ForWebApi() // <------ here is the line that registers it
.Log4Net()
.XmlSerializer()
.MsmqTransport()
.IsTransactional(false)
.PurgeOnStartup(false)
.UnicastBus()
.ImpersonateSender(false)
.CreateBus()
.Start();
Does someone has managed it for the NServiceBus Version 5?
As wlabaj says, the documentation on the particular website says it all. Almost.
We use AutoFac so we don't need any direct reference to IBus or ISendOnlyBus and therefor we do this
ContainerBuilder builder = new ContainerBuilder();
var container = builder.Build();
configuration.UseContainer<AutofacBuilder>(x => x.ExistingLifetimeScope(container));
What we do in WebAPI and ASP.NET applications is this
NServiceBus.Bus.CreateSendOnly(configuration);
Because it's not a good practice to expect reply messages to come back after sending them.
Here you can see 3.0 vs 4.0 vs 5.0 configuration syntax. At the top of the page you have a link to download code samples.
The examples are for ASP .NET though, so you'll need to tweak it slightly for WebAPI. Let me know if you need further help with that.
ForWebApi was never a part of NServiceBus, this was an extension method from the sample that was used to configure NServiceBus dependency resolver to instantiate controllers. The way how it was done is shown here.
There is no need to use NServiceBus resolver since it is just a wrapper around another container. By default it uses Autofac, so you can just use Autofac to work for you in the whole application.
Autofac WebAPI integration is properly described in the documentation.
NServiceBus documentation has a page about using your own container.
This is a very well known setup that you can easily implement.

AutofacWebApiDependencyResolver usage

What is the usage of the AutofacWebApiDependencyResolver?
I set it like this:
GlobalConfiguration.Configuration.DependencyResolver =
new AutofacWebApiDependencyResolver(container);
But how can I access it in my ApiControllers?
DependencyResolver.Current is not the AutofacWebApiDependencyResolver, its the MVC version.
.Current is available under AutofacDependencyResolver but not under AutofacWebApiDependencyResolver. How can I access the web api version in the web api?
As you showed yourself... use GlobalConfiguration.Configuration.DependencyResolver to access this resolver, same way as you did when you set it initially (it's a static object can be accessed from anywhere in Web API).
Or, use the request dependency scope - wherever you have access to current request (i.e. in MessageHandler):
var myservice = request.GetDependencyScope().GetService(typeof(IMyService)) as IMyService
this will resolve IMyService using the currently set AutofacWebApiDependencyResolver
Try the straightforward way: this.Configuration.DependencyResolver, where this is an ApiController instance.

MVC Web API not working with Autofac Integration

I used the MVC integration from autofac like this:
...
var container = builder.Build();
DependencyResolver.SetResolver(new AutofacDependencyResolver(container));
But now I want to recreate the solution with the new Web Api RTM.
And I want to use the new AutofacWebApiDependencyResolver class.
But if I do this with AutofacWebApiDependencyResolver i got this error:
The type Autofac.Integration.WebApi.AutofacWebApiDependencyResolver
does not appear to implement
Microsoft.Practices.ServiceLocation.IServiceLocator.
I read that i have to do this now for setting the resolver:
GlobalConfiguration.Configuration.DependencyResolver = new AutofacWebApiDependencyResolver(container);
But if I set it with '=', it is not set. Its still the DefaultResolver...
If I use the MVC AutofacDependencyResolver class again, it works.
Are were still problems with autofac and web api rtm? (the current integration is RC version)
ASP.Net Wep.API and ASP.NET MVC uses two different IDependencyResolver (because they designed the Wep.API to not depend on ASP.NET MVC) so you need to setup both:
var container = builder.Build();
DependencyResolver.SetResolver(new AutofacDependencyResolver(container));
GlobalConfiguration.Configuration.DependencyResolver =
new AutofacWebApiDependencyResolver(container);
So the AutofacDependencyResolver is needed to inject decencies to regular MVC Controller derived controllers.
And the AutofacWebApiDependencyResolver is needed to inject dependencies to the Web.API ApiController derived controllers.
And don't forget to register your Api controllers in your container builder with the call (it differs from usual builder.RegisterControllers method):
builder.RegisterApiControllers(Assembly.GetExecutingAssembly());
Following is a very good example
Using Autofac with Web Api

ASP .Net 4 Web Api RC + Autofac manual resolving

I'm trying to use depedency resolver inside a Web Api method. This worked fine and works fine with classic ASP.NET MVC with the DepedencyResolver.GetService()
But I can't get this to work inside WepApi methods.
My registration register all instances as InstancePerApiRequest and if I add any of all the types I have registred in my bootstrapper on the constructor of my WebAPiConroller thay inject fine but not anymore when calling them inside.
Like this in my say Get Method
var userRepository = (IUserRepositoryu)GlobalConfiguration
.Configuration.DependencyResolver.GetService(typeof(IUserRepository));
I got the no scope WebRequest error. The strange thing is that it worked fine in Beta before they change it all to the GlobalConfiguration.
So my question is, how can I activate my Autofac registered assemblies in the lifetime scope of my webAPi as before?
My error:
"No scope with a Tag matching 'AutofacWebRequest' is visible from the scope in which the instance was requested. This generally indicates that a component registered as per-HTTP request is being reqested by a SingleInstance() component (or a similar scenario.) Under the web integration always request dependencies from the DependencyResolver.Current or ILifetimeScopeProvider.RequestLifetime, never from the container itself."
var resolver = new AutofacWebApiDependencyResolver(container);
configuration.DependencyResolver = resolver;
In Web API the global dependency resolver is used to access global instances. Per-request services come from a dependency scope that Web API creates to handle the request. I'm not sure that there is any way in Web API to access the current dependency scope - it would be interesting to know.
The best option here is to just use dependency injection rather than calling the resolver directly like this. Which part of your code needs to make this call?
AutoFac has integration with ASP.NET WebAPI consider to use it.
Also dependecy resolver for WebAPi is slightly different to ASP.NET MVC, so make shure, that you have implemented resolver suitable for WebAPI and added it to WebAPI configuration.
http://www.asp.net/web-api/overview/extensibility/using-the-web-api-dependency-resolver
As the error indicated, you must always request dependencies from the DependencyResolver.Current or ILifetimeScopeProvider.RequestLifetime. The correct way is getting the dependency from current web api request:
// Get the request lifetime scope so you can resolve services.
var requestScope = Request.GetDependencyScope();
// Resolve the service you want to use.
var userRepository = requestScope.GetService(typeof(IUserRepository)) as IUserRepository;
See more from Autofac offical documentations:
http://docs.autofac.org/en/latest/integration/webapi.html#standard-web-api-filter-attributes-are-singletons

How to enable Dependency Injection for ServiceRoute in MVC3 and WCF Web API

I am creating a MVC3 website that will expose a REST API using WCF Web API.
To register routes to the REST API I add code to the Global.asax similar to the code below.
routes.MapServiceRoute<RelationsService>("relations");
This works well enough but i need to use a DI approach to inject the dependencies that the Service depends on.
As you can see in the code above the MVC framework is creating the instance of the RelationsService but this should be done by the DI container.
Does anyone know how to configure MVC3 so that my own DI container is used for creating the instances of the Services?
You have to extend your current service registration call with an IHttpHostConfigurationBuilder that has been created with an IResourceFactory.
var configurationBuilder = HttpHostConfiguration.Create()
.SetResourceFactory(new ResourceFactory());
routes.MapServiceRoute<RelationsService>("relations", configurationBuilder);
Then if you for instance use StructureMap as preferred IoC/DI tool you can just ask for the service in the GetInstance method.
public class ResourceFactory : IResourceFactory
{
public object GetInstance(Type serviceType, InstanceContext instanceContext, HttpRequestMessage request)
{
return ObjectFactory.GetInstance(serviceType);
}
}

Resources