使用MVC区域的多个SPA - 在SPA路由器路由之外导航

时间:2016-11-18 16:37:09

标签: asp.net-mvc single-page-application durandal asp.net-mvc-areas durandal-navigation

如果想要在路由器中设置的路由设置列表之外导航,我如何逃避客户端路由?

我使用Durandal.js创建了一个项目,并在不同区域内创建了SPA。我遇到的问题是,当我想在当前SPA之外导航到另一个SPA或者说回到整个应用程序的主页时,该主页根本不是SPA,而只是一个cshtml页面。

我尝试做的是使用Durandal的mapUnknownRoutes处理程序拦截然后使用window.location.href导航。这有效,但是当我想要进入应用程序的主页(" /")时,路由器匹配" root" SPA并没有导航到主页,而是导航到SPA的根路线。

此示例中的区域路线是" / spaHome"其MVC路线如下:

context.MapRoute(
           "spaHome_default",
           "spaHome/{*catchall}",
           new { controller = "Home", action = "Index", id = UrlParameter.Optional }
       );

以下是我为设置Durandal路由器所做的工作:

var routes = [
    { route: ['spaHome', ''], moduleId: 'spaHome', title: "spaHome", hash: "#spaHome"},
    { route: 'one/anotherPage', moduleId: 'one/anotherPage', title: "one/anotherPage", hash: "#one/anotherPage"}
];

router.makeRelative({ moduleId: 'viewmodels' });

router.map(routes)
      .mapUnknownRoutes(function (instruction) {
          utils.navigateToPath(instruction.fragment);
          return false;
      })
      .activate({ pushState: true, root: "/spaHome" });

任何针对此方向的指针或引导都将非常感激!

1 个答案:

答案 0 :(得分:0)

经过一些反复试验后,我能够找到解决方案来解决我想要完成的事情。它看起来像一个可靠的解决方案,所以希望它不会导致任何问题。

我更改了路线数组并删除了''''从第一条路线。这让我有一个未知的路线,想要打到正常的MVC主页。我还必须删除" root"来自路由器激活功能的属性。这反过来意味着我必须使用额外的区域部分或URL(" spaHome /")显式声明路径数组中的路由。

然后在我的mapUnknownRoutes处理程序中,我检查了URL的区域部分的路由,如果存在,我使用SPA路由器显示该SPA的未发现页面。另外我假设路线存在于区域之外,我需要使用window.location.href来硬导航到URL。

var routes = [
    { route: ['spaHome'], moduleId: 'spaHome', title: "spaHome", hash: "#spaHome"},
    { route: 'spaHome/one/anotherPage', moduleId: 'one/anotherPage', title: "one/anotherPage", hash: "#spaHome/one/anotherPage"}
];

router.makeRelative({ moduleId: 'viewmodels' });

router.map(routes)
  .mapUnknownRoutes(function (instruction) {
      if (instruction.fragment.toLowerCase().indexOf("spaHome/", 0) === -1) {
            utils.navigateToPath(instruction.fragment);
      } else {
            var notfoundRoute = "notfound";
            instruction.config.moduleId = notfoundRoute;
            history.navigate(notfoundRoute, { trigger: false, replace: true });
      }
  })
  .activate({ pushState: true });

如果有人有更好的解决方案,请告诉我们!

修改

好的,我这样做时遇到了历史问题。我不得不在Durandal router.js文件中添加一行来阻止以前的路由被添加到历史队列中。

 if (!instruction.cancelQueue) {
                router.trigger('router:route:before-config', instruction.config, router);
                router.trigger('router:route:after-config', instruction.config, router);
                queueInstruction(instruction);
            }

修改2

我也遇到过这种方法的问题,导航对于IE9及以下版本来说并不适用。