I need to write a .NET 4.5 component which potentially can be used by .EXE or Web applications. This component has a number of configuration parameters to be provided - in main app.config or web.config accordingly.
Is there an universal API to read config or at least a way to determine the mode?
The System.Configuration.Abstractions library from David Whitney works across both desktop and web applications. You can install it with nuget:
install-package System.Configuration.Abstractions
There's documentation on the Github site, but in a nutshell where you'd use ConfigurationManager or WebConfigurationManager, you can instead use System.Configuration.Abstractions.ConfigurationManager.Instance (or use IConfigurationManager and inject an instance)
For App.config (desktop applications, foo.exe.config) use:
https://msdn.microsoft.com/en-us/library/system.configuration.configurationmanager(v=vs.110).aspx
For Web.config, you need to use:
https://msdn.microsoft.com/en-us/library/system.web.configuration.webconfigurationmanager(v=vs.110).aspx
Abstract both of these and you're covered.
To determine whether or not you're in an ASP.NET environment, I have used System.Web.Hosting.HostingEnvironment.IsHosted in the past.
Related
Is there a configuration provider already pre-configured in .net core that I can just use without having to add in boilerplate code? In the same way that app.config files just work in full .net.
I'm writing a console app in .net core 2 and it needs some settings, a connection string and a few app settings that I would have previously just tossed into the app.config file.
I've started googling about configuration in .net core and found a whole heap of documentation about how flexible it is - you just add a file, make sure it gets copied to the correct location and then spin up a configuration builder add it the correct provider build it etc. etc.
As nice and flexible as it is I don't want to clutter up my tiny console apps with this config boilerplate - it feels like we have to roll our own config for each app.
Ideally, in a .NET Core application, one would choose JSON setting files over XML configuration files, but it is still possible to use legacy XML configuration files if needed.
There is an API to access application setting files; just check out the following NuGet packages: Microsoft.Extensions.Configuration and Microsoft.Extensions.Configuration.Xml, and this article might be a good reading: http://benfoster.io/blog/net-core-configuration-legacy-projects since it also covers the integration of app.config or web.config files, as well as how to create a custom configuration provider.
Since the ConfigurationManager doesn't exist in .NET Standard, what is the best way to retrieve application settings for the executing assembly, whether it be a web.config or an appSettings.{env}.json, within a .NET standard class library?
We have three projects:
ASP.NET Core Web App (1.1)
ASP.NET Web App (4.6.1 )
.NET Standard Class Library (1.4) -> Referenced by both projects
In the .NET Standard class lib, we have a URL which needs to change based on the environment it's deployed to.
This is fine for the .NET Core app, we simply add the URLs to the appropriate appSettings.{env}.json file, add the appropriate values to the DI container, then use the Microsoft.Extensions.Options library to retrieve the configuration.
However, we also need to call the library from our .NET Framework 4.6.1 application, but since there is no method (at least none that I could find) to retrieve the values from a web.config file, we don't have a good way to set the URL within the class library.
We've gotten around this for now by making the URL variable static and setting its value from within the Application_Start() method of each .NET Framework project we reference it from, we determine which environment it is via an appSetting key we added to each web.config, then manually set the URL based on the environment.
Is there a more robust way to handle retrieving appSettings values from both a .NET Core and .NET Framework application within a .NET Standard class library?
Preferably where we can set the value solely within the class library.
You should read the value from configuration before calling your library, and pass it by parameter, either into a method or constructor.
In general, library code shouldn't depend on side effects from the configuration of its host environment. Doing so makes it very difficult to reuse code, or to test effectively.
Is it possible to deploy ;
1- a web-api project
2- a website written in Asp.net
3- a WCF service as windows service
in one msi file using/in Windows Web Installer Project (preferably) or in Wix ?
Yes, it is possible using WiX. I maintain an open source project called IsWiX that even makes it somewhat easy. See:
Create and Package a Windows Service using IsWiX
IsWiX Web Site Demo
The concept behind IsWiX is project templates (scaffolding) and graphical designers that give you a project structure and most heavy lifting for your WiX MSI project. The template already contains examples of IIS configuration that merely need to be uncommented out. If you need a Web API and a Web Site you'll have to clone that part of the code and make a few adjustments. For example a static website typically won't be a web application where a web-api will be. Then you'll use the services designer to define the windows service. The fact that the service hosts a WCF endpoint really doesn't matter.
For that matter, one of the really cool things about WCF is it's possible to eliminate your dependencies on IIS. I've seen solutions using this with no dependency on IIS and this really makes creating installers a lot simpler.
I have a web application that contains a bunch of classes in the App_Code folder. I compile the project and publish it to the IIS server.
I want to share some of the code in the app_code folder with another application on the server and therefore I think I need to register an assembly in the GAC.
What is the best way to do this? I have read this article: http://msdn.microsoft.com/en-us/library/Aa479044, which suggests a number of options?
Put the code in a class library, and add the library as a project reference to both applications.
Side Note:
If you need to access the request or response, etc. import the Sysyem.Web library and use the HttpContext object. This will give you most, if not all the information available to the page.
You'll have to move the code into a separate project, which will output a library.
If you have any references to dlls related to the ASP .Net or web in general, you can reference them from that library.
The code might not compile in the first, but you can refactor it, it really depends on how tight is with what is in App_Code.
You can then reference that library on the Web Site (you'll have to refactor here too some things). The library, once is signed, can be added to GAC also.
The solution for me was to expose the shared functionality in a web service.
I have a fully functional wcf service where I can perform CRUD operations using jQuery on the client. I want this small service application to be portable so I am trying to avoid any app or web.config settings (e.g. Specific address endpoints). I have compiled my service application into a small dll file and have tried it in several different projects hosted at various web addresses. Everything works fine.
The only setting I put in the web.config file was for aspNetCompatibilityEnabled because I am using forms authentication. I did not define a name or a namespace for my service contract and my app.config file is empty sans a connectionstring. When I type in the address to my .svc file I get the 'endpoint not found error'. However my service is fully functional when I use the UriTemplates I defined in my operation contracts. What are the ramifications of this?
I don't care about exposing my data objects or methods on the .svc file. I just need this service to be portable and not blow up due to some unforeseen error.
Cautiously optimistic.
UPDATE
After further investigation it appears my example above is the default behavior for WCF. There is a good article from MS that explains it here.
I'm not sure what do you mean by portable. Your service is in dll, which can be used in any web application. Then it depends on your version of .NET Framework.
In .NET 3.5 you have to host the service in .svc file and configure it (service, endpoints, behaviors, AspNetCompatibility) in configuration file or in code.
In .NET 4.0 you can take advantage of simplyfied configuration model which can create endpoints for you based on other provided information. You can host the service in .svc file, by configuration based activation or by service route. In all cases it is important to use WebServiceHostFactory to allow automatic creation of endpoint using WebHttpBinding. You only need to configure AspNetCompatibility. If you need to futher specify webHttp behavior you can place it also in configuration without specifying behavior's name. Such behavior will be taken as default for all services (also not possible in .NET 3.5).
In neither case you don't need to configure base address because it is always taken from hosting web application.