diff --git a/src/Umbraco.Web/Mvc/AreaRegistrationExtensions.cs b/src/Umbraco.Web/Mvc/AreaRegistrationExtensions.cs
index cb905c3569..b67d73880e 100644
--- a/src/Umbraco.Web/Mvc/AreaRegistrationExtensions.cs
+++ b/src/Umbraco.Web/Mvc/AreaRegistrationExtensions.cs
@@ -1,5 +1,6 @@
using System;
using System.Collections.Generic;
+using System.Web.Http;
using System.Web.Mvc;
using System.Web.Routing;
using Umbraco.Core;
@@ -8,73 +9,96 @@ using Umbraco.Core.Configuration;
namespace Umbraco.Web.Mvc
{
internal static class AreaRegistrationExtensions
- {
- ///
- /// Creates a custom individual route for the specified controller plugin. Individual routes
- /// are required by controller plugins to map to a unique URL based on ID.
- ///
- ///
- ///
- /// An existing route collection
- ///
- /// The suffix name that the controller name must end in before the "Controller" string for example:
- /// ContentTreeController has a controllerSuffixName of "Tree", this is used for route constraints.
- ///
- ///
- ///
- ///
- /// The DataToken value to set for the 'umbraco' key, this defaults to 'backoffice'
+ {
+ ///
+ /// Creates a custom individual route for the specified controller plugin. Individual routes
+ /// are required by controller plugins to map to a unique URL based on ID.
+ ///
+ ///
+ ///
+ /// An existing route collection
+ ///
+ /// The suffix name that the controller name must end in before the "Controller" string for example:
+ /// ContentTreeController has a controllerSuffixName of "Tree", this is used for route constraints.
+ ///
+ ///
+ ///
+ ///
+ /// The DataToken value to set for the 'umbraco' key, this defaults to 'backoffice'
/// By default this value is just {action}/{id} but can be modified for things like web api routes
- ///
- ///
- internal static Route RouteControllerPlugin(this AreaRegistration area, string controllerName, Type controllerType, RouteCollection routes,
- string controllerSuffixName, string defaultAction, object defaultId,
- string umbracoTokenValue = "backoffice",
- string routeTokens = "{action}/{id}")
- {
- Mandate.ParameterNotNullOrEmpty(controllerName, "controllerName");
- Mandate.ParameterNotNullOrEmpty(controllerSuffixName, "controllerSuffixName");
- Mandate.ParameterNotNullOrEmpty(defaultAction, "defaultAction");
- Mandate.ParameterNotNull(controllerType, "controllerType");
- Mandate.ParameterNotNull(routes, "routes");
- Mandate.ParameterNotNull(defaultId, "defaultId");
+ /// Default is true for MVC, otherwise false for WebAPI
+ ///
+ ///
+ internal static Route RouteControllerPlugin(this AreaRegistration area, string controllerName, Type controllerType, RouteCollection routes,
+ string controllerSuffixName, string defaultAction, object defaultId,
+ string umbracoTokenValue = "backoffice",
+ string routeTokens = "{action}/{id}",
+ bool isMvc = true)
+ {
+ Mandate.ParameterNotNullOrEmpty(controllerName, "controllerName");
+ Mandate.ParameterNotNullOrEmpty(controllerSuffixName, "controllerSuffixName");
+
+ Mandate.ParameterNotNull(controllerType, "controllerType");
+ Mandate.ParameterNotNull(routes, "routes");
+ Mandate.ParameterNotNull(defaultId, "defaultId");
- var umbracoArea = GlobalSettings.UmbracoMvcArea;
+ var umbracoArea = GlobalSettings.UmbracoMvcArea;
- //routes are explicitly name with controller names and IDs
- var url = umbracoArea + "/" + area.AreaName + "/" + controllerName + "/" + routeTokens;
+ //routes are explicitly name with controller names and IDs
+ var url = umbracoArea + "/" + area.AreaName + "/" + controllerName + "/" + routeTokens;
- //create a new route with custom name, specified url, and the namespace of the controller plugin
- var controllerPluginRoute = routes.MapRoute(
- //name
- string.Format("umbraco-{0}", controllerType.FullName),
- //url format
- url,
- //set the namespace of the controller to match
- new[] { controllerType.Namespace });
-
- //set defaults
- controllerPluginRoute.Defaults = new RouteValueDictionary(
- new Dictionary
- {
- { "controller", controllerName },
- { "action", defaultAction },
- { "id", defaultId }
- });
+ Route controllerPluginRoute;
+ //var meta = PluginController.GetMetadata(controllerType);
+ if (isMvc)
+ {
+ //create a new route with custom name, specified url, and the namespace of the controller plugin
+ controllerPluginRoute = routes.MapRoute(
+ //name
+ string.Format("umbraco-{0}", controllerType.FullName),
+ //url format
+ url,
+ //set the namespace of the controller to match
+ new[] {controllerType.Namespace});
- //constraints: only match controllers ending with 'controllerSuffixName' and only match this controller's ID for this route
- controllerPluginRoute.Constraints = new RouteValueDictionary(
- new Dictionary
- {
- { "controller", @"(\w+)" + controllerSuffixName }
- });
-
-
- //match this area
- controllerPluginRoute.DataTokens.Add("area", area.AreaName);
- controllerPluginRoute.DataTokens.Add("umbraco", umbracoTokenValue); //ensure the umbraco token is set
+ //set defaults
+ controllerPluginRoute.Defaults = new RouteValueDictionary(
+ new Dictionary
+ {
+ {"controller", controllerName},
+ {"action", defaultAction},
+ {"id", defaultId}
+ });
+ }
+ else
+ {
+ controllerPluginRoute = routes.MapHttpRoute(
+ //name
+ string.Format("umbraco-{0}-{1}", "api", controllerType.FullName),
+ //url format
+ url,
+ new { controller = controllerName, id = defaultId });
+ //web api routes don't set the data tokens object
+ if (controllerPluginRoute.DataTokens == null)
+ {
+ controllerPluginRoute.DataTokens = new RouteValueDictionary();
+ }
+ //look in this namespace to create the controller
+ controllerPluginRoute.DataTokens.Add("Namespaces", controllerType.Namespace);
+ }
- return controllerPluginRoute;
- }
- }
+ //constraints: only match controllers ending with 'controllerSuffixName' and only match this controller's ID for this route
+ controllerPluginRoute.Constraints = new RouteValueDictionary(
+ new Dictionary
+ {
+ {"controller", @"(\w+)" + controllerSuffixName}
+ });
+
+
+ //match this area
+ controllerPluginRoute.DataTokens.Add("area", area.AreaName);
+ controllerPluginRoute.DataTokens.Add("umbraco", umbracoTokenValue); //ensure the umbraco token is set
+
+ return controllerPluginRoute;
+ }
+ }
}
\ No newline at end of file
diff --git a/src/Umbraco.Web/Mvc/ControllerExtensions.cs b/src/Umbraco.Web/Mvc/ControllerExtensions.cs
index 0e383add83..d17b1f2afe 100644
--- a/src/Umbraco.Web/Mvc/ControllerExtensions.cs
+++ b/src/Umbraco.Web/Mvc/ControllerExtensions.cs
@@ -14,6 +14,10 @@ namespace Umbraco.Web.Mvc
///
internal static string GetControllerName(Type controllerType)
{
+ if (!controllerType.Name.EndsWith("Controller"))
+ {
+ throw new InvalidOperationException("The controller type " + controllerType + " does not follow conventions, MVC Controller class names must be suffixed with the term 'Controller'");
+ }
return controllerType.Name.Substring(0, controllerType.Name.LastIndexOf("Controller"));
}
diff --git a/src/Umbraco.Web/Mvc/PluginControllerArea.cs b/src/Umbraco.Web/Mvc/PluginControllerArea.cs
index 25472a2ffa..0e34e2cdef 100644
--- a/src/Umbraco.Web/Mvc/PluginControllerArea.cs
+++ b/src/Umbraco.Web/Mvc/PluginControllerArea.cs
@@ -85,7 +85,7 @@ namespace Umbraco.Web.Mvc
{
foreach (var s in apiControllers)
{
- this.RouteControllerPlugin(s.ControllerName, s.ControllerType, routes, "Api", "Index", UrlParameter.Optional, "api");
+ this.RouteControllerPlugin(s.ControllerName, s.ControllerType, routes, "Api", "", UrlParameter.Optional, "api", isMvc: false);
}
}
}