【问题标题】:MapMvcAttributeRoutes in Referenced/External Assembly引用/外部程序集中的 MapMvcAttributeRoutes
【发布时间】:2017-12-18 03:37:52
【问题描述】:

我使用动态加载的程序集作为 MVC 控制器(插件/附加框架)的源。我无法在引用的程序集中映射控制器的属性路由。

我尝试从引用的程序集中调用 MapMvcAttributeRoutes(如文章中建议的将在 Web API 中工作),但没有成功。

如何在引用的程序集中映射控制器的属性路由?

编辑:

我有一个从文件加载程序集的主 MVC 应用程序。这些程序集的结构如下:

我扩展了用于创建控制器和查找视图的代码,但我找不到有关如何处理(映射)外部程序集中指定的RouteAttributes 的说明,如下所示:

[RoutePrefix("test-addon")]
public class MyTestController : Controller
{
    [Route]
    public ActionResult Page()
    {
        return View(new TestModel { Message = "This is a model test." });
    }
}

【问题讨论】:

  • 是自定义框架还是任何 CMS?最好显示一些代码以更好地理解它。
  • 请用一些代码更详细地叙述问题。

标签: c# .net asp.net-mvc attributerouting


【解决方案1】:

我设法找到了解决方案:手动将 Route Attributes 解析到 Route Dictionary 中。可能没有做到 100% 正确,但这似乎到目前为止有效:

public static void MapMvcRouteAttributes(RouteCollection routes)
{
    IRouteHandler routeHandler = new System.Web.Mvc.MvcRouteHandler();

    Type[] addOnMvcControllers =
        AddOnManager.Default.AddOnAssemblies
            .SelectMany(x => x.GetTypes())
            .Where(x => typeof(AddOnWebController).IsAssignableFrom(x) && x.Name.EndsWith("Controller"))
            .ToArray();

    foreach (Type controller in addOnMvcControllers)
    {
        string controllerName = controller.Name.Substring(0, controller.Name.Length - 10);
        System.Web.Mvc.RoutePrefixAttribute routePrefix = controller.GetCustomAttribute<System.Web.Mvc.RoutePrefixAttribute>();
        MethodInfo[] actionMethods = controller.GetMethods();
        string prefixUrl = routePrefix != null ? routePrefix.Prefix.TrimEnd('/') + "/" : string.Empty;

        foreach (MethodInfo method in actionMethods)
        {
            System.Web.Mvc.RouteAttribute route = method.GetCustomAttribute<System.Web.Mvc.RouteAttribute>();

            if (route != null)
            {
                routes.Add(
                    new Route(
                        (prefixUrl + route.Template.TrimStart('/')).TrimEnd('/'),
                        new RouteValueDictionary { { "controller", controllerName }, { "action", method.Name } },
                        routeHandler));
            }
        }
    }
}

看似过多的修剪,其实只是为了确保在任何情况下,开头、中间或结尾都没有多余的'/'。

【讨论】:

    猜你喜欢
    • 2011-01-08
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2010-12-05
    • 1970-01-01
    • 2015-11-18
    • 1970-01-01
    • 1970-01-01
    相关资源
    最近更新 更多