ASP.NET Web.Api plugin architecture - asp.net

Can you suggest me some articles or code samples about plugin architecture in web api?
Currently I'm thinking about this scenario: to have 1, centralized api gateway, where every client sends request, and have different applications controllers in Plugins folder. If someone wants to add new service, writes it's own controllers and puts dll files in Plugin folder.

For locating controller classes at run time, you can write an assembly resolver, like this.
public class MyAssembliesResolver : DefaultAssembliesResolver
{
public override ICollection<Assembly> GetAssemblies()
{
List<Assembly> assemblies = new List<Assembly>(base.GetAssemblies());
// Add all plugin assemblies containing the controller classes
assemblies.Add(Assembly.LoadFrom(#"C:\Plugins\MyAssembly.dll"));
return assemblies;
}
}
Then, add this line to the Register method in WebApiConfig.
config.Services.Replace(typeof(IAssembliesResolver), new MyAssembliesResolver());
With this, the request will still need to be sent to the individual controller even though the controller classes can come from assemblies in the plugin folder. For example, if MyAssembly.dll in the plugins folder contains CarsController, the URI to hit this controller will be /api/cars.

Related

Routing for Single Page Application in ASP.NET Core

I have a Single Page Application written in JavaScript, and I use HTML5 history API to handle URLs on the client side. This means any URLs sent to the server should cause the server to render the same page.
In the ASP.NET MVC 5 I wrote this code to do this:
public class RouteConfig
{
public static void RegisterRoutes(RouteCollection routes)
{
// ...
routes.Add(new Route("{*path}", new MyRouteHandler()));
}
}
public class MyRouteHandler : IRouteHandler
{
public IHttpHandler GetHttpHandler(RequestContext requestContext)
{
return WebPageHttpHandler.CreateFromVirtualPath("~/index.cshtml");
}
}
This worked really well. No matter what URL the server gets, it renders index.cshtml. Note that I am able to use a .cshtml file (as opposed to an .html file) which means I can have some C# code to dynamically change what .js scripts are included, append version numbers to .css files, and so on. What's more, I didn't have to implement controllers and views and so on just to render this .cshtml file.
Now we come to the question: How do you do this in ASP.NET Core? I have been reading the documentation, but I don't see how to render a .cshtml file without adding controller classes, view folders and other rigmarole.
Anyone know the equivalent code in ASP.NET Core?
Currently to run a CSHTML page "the normal way" in ASP.NET Core requires using ASP.NET Core MVC.
However, there is a planned feature that is being worked on that is somewhat similar to ASP.NET (non-Core) Web Pages, where you can have standalone CSHTML files. That feature is being tracked here: https://github.com/aspnet/Mvc/issues/494 (and as far as naming for the new feature, that is being tracked here: https://github.com/aspnet/Mvc/issues/5208).
There's also a sample of how to render an MVC view to a string (e.g. to generate an email, report, etc.), and that sample is available here: https://github.com/aspnet/Entropy/tree/dev/samples/Mvc.RenderViewToString
But to use this sample in the scenario you describe, you'd have to do some extra plumbing to wire it up as its own middleware (not a lot of plumbing; just a little!).
It's also worth noting that in your scenario you probably don't want all URLs going to this one view, because you still need the static files middleware running first to handle the CSS, JS, images, and other static content. Presumably you just want all other URLs to go to this dynamic view.

How to localize urls with routing in ASP.NET WebForms application - not MVC

I have a webforms application (VB.net, .NET 4.0) which is translated in three languages and I managed to localize everything except the URLs. My preference is to use routing, so I'd like to find a solution in this direction (not URL rewriting or IIS rewrites, etc.)
Out of many read articles I stumbled into this one as well: http://blog.maartenballiauw.be/post/2010/01/26/Translating-routes-%28ASPNET-MVC-and-Webforms%29.aspx, but this example is for MVC application. (As are the most of the questions here as well)
Any comments and ideas are very much welcome!
I could implement Maarten's solution in a WebForms ASP.NET application as described below.
I downloaded his sample and opened with Visual Studio. As you see it the essential part of translated routing can be found in Routing folder.
I created a new Class Library project in my web application, and copied these 5 files. This project missed some assembly references, so I added System.Web and System.Web.Routing to it.
After this there was only one problem in TranslatedRouteCollectionExtensions class. The two extension methods used MvcRouteHandler. This is the only piece of code which depends on MVC. To eliminate this dependency modify both extension methods like this:
public static TranslatedRoute MapTranslatedRoute(
this RouteCollection routes,
string name,
string url,
object defaults,
object routeValueTranslationProviders,
IRouteHandler routeHandler,
bool setDetectedCulture)
{
TranslatedRoute route = new TranslatedRoute(
url,
new RouteValueDictionary(defaults),
new RouteValueDictionary(routeValueTranslationProviders),
setDetectedCulture,
routeHandler);
routes.Add(name, route);
return route;
}
I added a reference in my Web Application to this Class Library project.
With this modification Maarten's example of register a translated route changes as follows:
routes.MapTranslatedRoute(
"TranslatedRoute",
"{controller}/{action}/{id}",
new { controller = "Home", action = "Index", id = "" },
new { controller = translationProvider, action = translationProvider },
new GeneralRouteHandler(),
true
);
Implementing a custom route handler is not a complicated process. You can find many good articles about it.

How do I redirect to the cshtml page created inside shared folder in ASP.NET MVC3

Please help me out how do I redirect to a .cshtml page which is created inside a shared folder.
I want something like this
href="#Url.Content("Shared/UnderConstruction")"
Here it's not getting redirecting to the UnderConstruction page, which I created.
You cannot redirect to anything that's stored inside the ~/Views folder including the ~/Views/Shared. This folder is simply not served by ASP.NET MVC and cannot be accessed directly. Also notice that in ASP.NET MVC you are not serving .cshtml pages directly. You are always passing through controller action that return views and those views might represent .cshtml pages.
Now if you have some Shared folder directly under the site root ~/Shared, then you can do this:
construction
In ASP.NET MVC3 you can't render views directly by calling the files directly. They can only be served via controllers.
In order to call the view in your shared folder you woul have to do something similar to the following:
public class HomeController : Controller
{
public ActionResult About()
{
return View("Construction");
}
}
If you want to display a page at url "shared/underconstruction" as per the other posts:
Create controller SharedController.
Define action "UnderConstruction"
Create "UnderConstruction.cshtml" in Views/Shared/ folder.
Map URL "Shared/{action}" , new { Controller = "Shared" } if you want to be explicit.
Give that a shot... to be honest even I don't know if this will work, and you will pollute your "Shared" folder. You could rename existing Shared folder to something else, maybe, and modify ViewStart.cshtml to point to new folder, maybe.
In ASP.NET MVC you can only redirect to controllers, and the controllers return a view. You can access views in Shared the same way as your normal controller views, by their name. ASP.NET MVC first looks in your controller view folder then in your shared view folder when resolving view names.

Why are ASP.Net MVC2 area controller actions callable without including the area in the url path?

I've just installed Visual Studio 2010 and have created a new MVC2 project so that I can learn about the changes and updates and have discovered an issue with areas that I'm not sure what to make of.
I created a new EMPTY MVC2 project
I right clicked the project and, from the context menu, added a new area called "Test"
In the new test area, I added a controller called "Data".
The code is:
public class DataController : Controller
{
//
// GET: /Test/Data/
public ActionResult Index()
{
Response.Write("Hi");
return new EmptyResult();
}
}
Now, I compile and call this address:
http://localhost/mytest/test/data and get the output:
Hi
All good. Now I call this: http://localhost/mytest/data and get the same response! I thought routing was supposed to take care of this? Am I overlooking something? Or has the default project setup for MVC2 overlooked something?
This is intentional. The default route in Global.asax does not limit its search to a particular area or set of namespaces. There are overloads of MapRoute (see one example on MSDN) which take a namespaces parameter, which can be used to disambiguate which controller was meant by this request. But even so, the namespaces parameter is just a hint about which namespaces to search in first; it's not a restriction.
In short, in MVC, you have to be prepared for any of your controllers to be hit by any route. This is why all of the MVC documentation states that security and other logic should be done at the controller level, never at the route level.

How to add a reference to my Web Service Proxy from a Custom Class

I'm creating a custom class to abstract out some of the repeated SOAP header work. I want to reference a Web Service Reference I just created in my custom class so I can create an instance of it. How do I reference it?
Notice I said I am trying to reference a Web Service "reference" (right click in VS and I added a "Web Service Reference" not a "Web Service"). So I'm trying to create an instance of that Proxy class that was created in MyCustomClass.cs
Once you have the reference created you need to add an import(vb) or using(c#) statement in the code file you want to use it. After that you simply need to instantiate an instance of the web service class.
// add the service reference
using ServiceReference1;
public partial class _Default : System.Web.UI.Page
{
protected void Page_Load(object sender, EventArgs e)
{
//create the instance of the web sevice of the class
SomeWebService sweb = new SomeWebService();
//call the web services HelloWorld Method
sweb.HelloWorld();
}
}
Hopefully this was what you were asking for
This is more Web Site weirdness. I recommend that web sites be used only for pages, images, css, js, etc, Anything else should be done in a separate project, and the web site can reference the other project.
I avoid web sites like the plague, so I've never had to make this work, but consider that web sites don't build. Instead, various things are built on the fly, when the site is used. There will be no Reference.cs file in a web site.
In more recent versions of Visual Studio the using statement for these web service references also has had to include the project name.
Using cptScarlet's original code example, change the first line to look like this:
// add the service reference
using MyProject.ServiceReference1;
When you type in your project name, the class and/or namespace of the objects created in the web reference should show up in the intellisense.

Resources