MVC2 Routing with WCF ServiceRoute: Html.ActionLink отображает неверные ссылки! - PullRequest
25 голосов
/ 26 августа 2010

У меня есть служба WCF, которая работает бок о бок с веб-сайтом MVC2.Я хотел бы, чтобы мой URL-адрес службы выглядел следующим образом:

http://localhost/projdir/Service

Сайт MVC находится в зачаточном состоянии, поэтому на нем все еще имеются стандартные контроллеры и т. Д.

Следующий код работает на первый взгляд в global.asax:

public static void RegisterRoutes(RouteCollection routes)
{
    routes.IgnoreRoute("{resource}.axd/{*pathInfo}");

    routes.Add(new ServiceRoute("Service", new ServiceHostFactory(), 
               typeof(MyService)));

    routes.MapRoute(
        "Default", // Route name
        "{controller}/{action}/{id}", // URL with parameters
        new { controller = "Home", action = "Index", 
              id = UrlParameter.Optional } // Parameter defaults
    );
}

Служба появляется именно там, где я описал, и работает как рекламируется.Отлично.

Однако я только что заметил, что порядок моего кода таким образом меняет все мои ActionLink.Например, вкладка «О программе» на сайте MVC теперь выглядит следующим образом:

http://localhost/projdir/Service?action=About&controller=Home

Это, очевидно, неверно (должно быть http://localhost/projdir/Home/About/).

Если переместить добавление ServiceRoute ниже значения по умолчанию MapRoute(), то я получу ошибку пропавшего контроллера.(На самом деле я получаю сообщение «StructureMapControllerFactory не возвратил экземпляр контроллера», потому что я подключен к StructureMap, да, это не контроллер с самого начала.)

Интересно, что это только кажетсяповлиять на вывод Html.ActionLink().Я могу вручную ввести http://localhost/projdir/Home/About/ и перейти на нужную страницу.

Какую ужасно очевидную ошибку новичка я делаю?

Ответы [ 3 ]

18 голосов
/ 26 августа 2010

Попробуйте переместить Сервисный маршрут после маршрута MVC. Но чтобы избежать ошибки «отсутствует контроллер», которую вы получили ранее, добавьте MVC-маршрут с a Route Constraint . Этими ограничениями маршрута может быть Regex - в основном вы хотите, чтобы в качестве ограничения маршрута использовался любой контроллер, который не"Служба". Когда запрашивается запрос «Служба», он заставляет его провалиться и его маршрут службы WCF.

8 голосов
/ 03 июня 2012

Я решил с этим:

     routes.MapRoute(
             "Default", // Route name
             "{controller}/{action}/{id}", // URL with parameters
             new { controller = "Home", action = "Index", id = UrlParameter.Optional },
             new { controller = "^(?!api).*" }
        );
        routes.Add(new ServiceRoute("api", new DataServiceHostFactory(), typeof(dwService)));

Я надеюсь, что это хорошо для вас

3 голосов
/ 29 июня 2011

Другим решением является наследование ServiceRoute и переопределение метода GetVirtualPath для возврата null, как описано здесь

public class AppServiceRoute : ServiceRoute
{
    public AppServiceRoute(string routePrefix, ServiceHostFactoryBase serviceHostFactory, Type serviceType)
        : base(routePrefix, serviceHostFactory, serviceType)
    {
    }

    public override VirtualPathData GetVirtualPath(RequestContext requestContext, RouteValueDictionary values)
    {
        return null;
    }
}

Таким образом, обратное сопоставление маршрутов никогда не выбирает этот маршрутдля любого действия.Работает как шарм

...