How to inject UrlHelper in Web API 2 using StructureMap.WebApi2 nuget package - asp.net-web-api2

I am using StructureMap.WebApi2 nuget package for Web API 2 project for managing the depedency injection.
The Web API controllers use constructor injection to inject a UrlHelper dependency which should be resolved by StructureMap Ioc.
I am trying the following approach to set the UrlHelper for web api controller:
public class FooController : ApiController
{
private UrlHelper _UrlHelper;
public ModelFactory(HttpRequestMessage request)
{
_UrlHelper = new UrlHelper(request);
}
}
But with the above code I am getting the following error:
No default Instance is registered and cannot be automatically determined for type 'System.Net.Http.HttpMethod' There is no configuration specified for System.Net.Http.HttpMethod
Can anyone suggest me the best possible ways to resolve the above issue?

Your problem is that StructureMap tries to resolve the greediest constructor first, in this instance taking a look at the source code for HttpRequestMessage reveals the following constructors:
public HttpRequestMessage(HttpMethod method, string requestUri);
public HttpRequestMessage(HttpMethod method, Uri requestUri);
This is where your HttpMethod issue is coming from. StructureMap tries to create an instance of HttpRequestMessage but has no idea how to resolve the method and requestUri dependencies.
In this instance you need to manually configure your dependency within your StructureMap configuration so it knows how to create an instance of HttpRequestMessage like so:
this.For<HttpRequestMessage>().Use(new HttpRequestMessage());
Alternatively, to create instances of overloaded constructors then you'll need to manually resolve the overloaded dependencies (I would recommend using a factory for this in order to keep your SM configuration nice and clean. Here is an example of how you can do this).

Related

Issue when configuring Hangfire in ASP.NET app

I'm attempting to wire up Hangfire in my ASP.NET application (not Core) using the Global.asax.cs route explained in their documentation. However, none of their extensions methods on GlobalConfiguration.Configuration seem to be working for me. It appears, for one example, that SetDataCompatibiltyLevel() method extends Hangfire.IGlobalConfiguration, which my GlobalConfiguration.Configuration does not inherit from. I even backed off a few versions of Hangfire and it doesn't seem to make a difference. When I attempt to access the extensions method directly, I get this:
Prefix GlobalConfiguration class with the Hangfire namespace – System.Web.Http namespace defines its own GlobalConfiguration class, so you get a conflict. And that another class is referenced, most likely because you have the System.Web.Http namespace included in the beginning of the file.
Hangfire.GlobalConfiguration.Configuration
.SetDataCompatibilityLevel(CompatibiltyLevel.Version_170);
You can also combine all the calls to the GlobalConfiguration class in a single chain:
Hangfire.GlobalConfiguration.Configuration
.SetDataCompatibilityLevel(CompatibiltyLevel.Version_170)
.UseXXX()
.UseYYYStorage();

How do I get a connection string in a .net core standard class library from the configuration file in a .net core 2.0 web app?

I have .net core standard class library which is essentially a DAL with several class methods that return collections and objects from a database. The connection string is in the appsettings.json file of the ASP.net 2 core web app. I also want to access this class library from a console app project where the configuration file with the connection string will be present in that console app project.
This was simple in .net prior to .net core. The DAL class library would just access the web.config from a web project and an app.config from a console application as it the library is referenced in both the web app and console apps. But it doesn't seem like this is at all possible.
I'm looking for the simple solution in .net core to get a connection string from web app or console app as the case may be.
Where you're probably going wrong is that you want to access configuration from your class library, but then you want to leak details specifically about the caller (That it will have a web.config).
But what if you decide in your Web Application you want to use Azure Key Vault or another secrets mechanism? Does your class library need to then change it's entire implementation to use Key Vault? And then does that mean your console application also has no option but to use Key Vault too?
So the solution is to use dependency inversion. Put simply, let's say I have code like the following :
interface IMyRepositoryConfiguration
{
string ConnectionString {get;}
}
class MyRepositoryConfiguration : IMyRepositoryConfiguration
{
public string ConnectionString {get;set;}
}
class MyRepository
{
private readonly IMyRepositoryConfiguration _myRepositoryConfiguration;
public MyRepository(IMyRepositoryConfiguration myRepositoryConfiguration)
{
_myRepositoryConfiguration = myRepositoryConfiguration;
}
}
Now in my startup.cs I can do something like :
services.AddSingleton<IMyRepositoryConfiguration>(new MyRepositoryConfiguration {//Set connection string from app settings etc});
And now my class library doesn't need to know exactly how those configuration strings are stored or how they are fetched. Just that if I request an instance of IMyRepositoryConfiguration, that it will have the value in there.
Alternatively of course, you can use the Options class too, but personally I prefer POCOs. More info here : https://dotnetcoretutorials.com/2016/12/26/custom-configuration-sections-asp-net-core/
It is very much possible to access "connection strings" or other configuration data easily in .Net core without much additional effort.
Just that the configuration system has evolved (into something much better) & we have to make allowances for this as well (& follow recommended practices).
In your case as you are accessing the connection string value in a standard library (intended to be reused), you should not make assumptions as how the configuration values will be "fed" to your class. What this means is you should not write code to read a connection string directly from a config file - instead rely on the dependency injection mechanism to provide you with the required configuration - regardless of how it has been made available to your app.
One way to do this is to "require" an IConfiguration object to be injected into your class constructor & then use the GetValue method to retrieve the value for the appropriate key, like so:
public class IndexModel : PageModel
{
public IndexModel(IConfiguration config)
{
_config = config;
}
public int NumberConfig { get; private set; }
public void OnGet()
{
NumberConfig = _config.GetValue<int>("NumberKey", 99);
}
}
In .net core, before the app is configured and started, a "host" is configured and launched. The host is responsible for app startup and lifetime management. Both the app and the host are configured using various "configuration providers". Host configuration key-value pairs become part of the app's global configuration.
Configuration sources are read in the order that their configuration providers are specified at startup.
.Net core supports various "providers". Read this article for complete information on this topic.

Share a Kernel between WebAPI and MVC

I've got a simple MVC4 site which uses ASP.NET webAPI and also MVC pages.
I'd like to use Ninject DI for both controller types but I'm wondering how this can be done?
I've got Ninject DI working for WebAPI, but now not sure how to share the same Kernel elegantly.
Should I be using some sort of Kernel singleton which both Dependency Resolvers can refer to?
Anyone had any experience with this?
Cheers.
You should use the same IKernel instance for a single application-level composition root, may be WebApi or MVC controllers.
If you are using Ninject.MVC3 package:
When the kernel is initialized in NinjectWebCommon.cs inside your App_Start folder, you already have access to it. For MVC controllers, you don't need to do anything else for Ninject DI to work.
But for WebAPI controllers, you need to use a DependencyResolver to inject dependencies into your controllers. Using this implementation for this resolver, you then set it to be the resolver for all your WebAPI controllers like this:
Bind the NinjectDependencyResolver to self (optional), inside RegisterServices in NinjectWebCommon.cs:
kernel.Bind<NinjectDependencyResolver>().ToSelf();
Set the WepAPI configuration to use your Resolver, usually inside WebApiConfig.cs:
public static void Register(HttpConfiguration config)
{
//Other initialization code
config.DependencyResolver = (new Bootstrapper()).Kernel.Get<NinjectDependencyResolver>();
}
This will fit your scenario for all controllers sharing the same IKernel.
Hope that helps!
Yes, you are right. There should be one kernel/ container for an application, because this will eleminate possible mistakes in the future.In case of multiple kernels, you may register an interface in a kernel, and then try to resolve it using another kernel, and the program crashes.Only After spending time debugging, you find out what was wrong,etc.
In addition, using a single kernel, you wouldn't have to register a same implementation multiple times.

Ninject 3, WCF Service and parameterized constructor

I have a WCF Service hosted in IIS. This solution is composed of 2 projects: Service and Data. Service depends on Data, like so:
Service -> Data
I've been trying to invert the dependency, like so:
Service <- Data
Which is quite a headache using WCF, since the WCF service constructor must be parameter-less (by default).
I hear it's possible to inject the dependency using Ninject and its WCF extension, so I tried to integrate it to my solution, but it's still not clear to me in which project should be the related files and references? What I did is :
Download Ninject using NuGet
Add Ninject to both my Data and Service projects (that created the NinjectWebCommon file in the App_Start folder of the Service Project
Create a IDataProxy interface in my Service project
Implement the interface in my Data project
Add a IDataProxy argument to the WCF service constructor
Added the factory configuration in the .svc file markup
Up to that point, I'm pretty sure I'm doing it right. Now the shaky part :
I created a DataInjectionModule in my data project with this code :
namespace Data
{
public class DataInjectionModule : NinjectModule
{
public override void Load()
{
Bind<IResolutionRoot>().ToConstant(Kernel);
Bind<ServiceHost>().To<NinjectServiceHost>();
Bind<IDataProxy>().To<DataProxy>();
}
}
}
I finally tried to register the service in the NinjectWebCommon files (of both projects to be sure) like that :
/// <summary>
/// Load your modules or register your services here!
/// </summary>
/// <param name="kernel">The kernel.</param>
private static void RegisterServices(IKernel kernel)
{
kernel.Bind<IService>().To<Service>()
.WithConstructorArgument("IDataProxy", context => context.Kernel.Get<IDataProxy>());
}
When I try to start my service, I still get this :
The service type provided could not be loaded as a service because it does not have a default (parameter-less) constructor. To fix the problem, add a default constructor to the type, or pass an instance of the type to the host.
I have a feeling that the problem resides in the fact that I did not bind my DataInjectionModule in the kernel, but if I try to do so, I must add a dependency from Service to Data, which is what I'm trying to avoid.
General expert advice would be greatly appreciated. Thanks.
Please check your point 6: "Added the factory configuration in the .svc file markup."
Have you done it properly?
The *.svc file should have this code:
Factory="Ninject.Extensions.Wcf.NinjectServiceHostFactory"

Jboss 7.1.1 - Jackson ContextResolver<ObjectMapper> works only on one deployment

I have two rest webapps I want to deploy on Jboss 7.1.1. server.
Rest requests in both apps produces and consumes Json. I use jackson provider to serialize and deserialize objects.
Now, I need custom ObjectMapper configurations for each webapp.
So to resolve this problem I added #Provider classes implementing ContextResolver. One for each project. Fe. One of my class looks like that:
#provider
#Produces(MediaType.APPLICATION_JSON)
#Consumes(MediaType.APPLICATION_JSON)
public class JacksonConfig implements ContextResolver<ObjectMapper> {
private final ObjectMapper objectMapper;
public JacksonConfig()
{
objectMapper = new ObjectMapper();
objectMapper.configure(SerializationConfig.Feature.WRAP_ROOT_VALUE, true);
}
#Override
public ObjectMapper getContext(Class<?> objectType) {
return objectMapper;
}
}
It works well when I deploy only one of this projects on jboss. When I try to deploy both, only first initialized project use defined objectMapper. Other one never calls getContext method from ContextResolver class. What could I do wrong?
EDIT!:
After a lot of trials I decided to change method of parsing json from jackson to staxon. I hoped at least this method will work well. But not... Serialization works perfectly on both deployed applications. But again, somehow jboss decided to use jackson instead of staxon in deserialization process. Again always application which I call first after deployment works well. But Second one using jackson (no idea why...) which calls exceptions. Always...
Is there any problem with Jboss? Probably I'm just doing something wrong but I have no idea where. Anybody has idea where should I look?
Looks like I found solution for this problem.
It was known issue of resteasy, that can be removed by build-in option:
To solve this problem I just had to add param to web.xml of my projects:
<context-param>
<param-name>resteasy.use.deployment.sensitive.factory</param-name>
<param-value>false</param-value>
</context-param>
I found this solution in Resteasy jira. It's really strange for me that there is no info in any jboss or resteasy related documentation...