单页应用程序的深度链接与登录页面。

3
我的团队计划为我们未来的项目构建单页应用程序。目前,我在设计包含登录页面的应用程序时遇到了问题。有两种方法:
  1. 将登录页面作为单独的页面创建,其余部分是另一页。
  2. 应用程序只有一个页面,登录页面将是应用程序中的视图,使用 JavaScript 来回切换。
我不知道该采取哪种方法。我已经在网上阅读了一些讨论,似乎创建登录页面作为单独页面更受欢迎,原因是我们可以使用基于 cookie 的身份验证和服务器上的会话,成功登录后将用户重定向到默认页面(主页面)等。因此,我考虑将登录页面创建为单独页面,但我遇到了深层链接的问题。
例如,假设我有两个页面:login.htmlindex.html(主页)。当未经身份验证的用户请求类似这样的页面 index.html#product=1 时,用户将被重定向到 login.html,成功登录后,将用户重新导向到 index.html#product=1。但是此时,#product=1 将丢失。
请指导我如何保留深层链接或是否应采取第二种方法?谢谢。

我想采用方法一,你能指导我吗? - NgaNguyenDuy
正如我在问题中所说,方法1存在问题,我们应该采用我在答案中提到的方法2。 - Khanh TO
@KhanhTO:是的,我也想采用第二种方法,但我在登录页面和主页面的ng-view上遇到了麻烦。登录页面的GUI与主页面完全不同,因此我不能为它们使用相同的ng-view。 - NgaNguyenDuy
@NgaNguyenDuy:你可以创建一个顶级的 ng-view(例如在 <body> 标签上),这个 ng-view 可以容纳你的登录页面或者包含另一个 ng-view 的主页面。如果这不能解答你的问题,请在 SO 上提出另一个带有更多代码示例的问题,这样人们就可以更容易地帮助你了。 - Khanh TO
@KhanhTO:感谢您的解决方案。现在将尝试。 :) - NgaNguyenDuy
显示剩余3条评论
2个回答

0
如果您正在构建单页应用程序,从用户的角度来看,将所有内容放在一个页面上会更好,因此我建议选择选项2。
不确定是否需要JavaScript来切换它,但您可以使用类似以下的代码(PHP代码)
在应用程序开始时保存用户正在查看的视图,并检查用户是否在登录表单上按下了“提交”按钮。
 $selected_menu = $_GET['menu'] ;

 //check to see if they've submitted the login form  
 if(isset($_POST['submit-login'])) {  

如果登录成功,将它们重定向回相同的页面,并将合适的视图作为参数传递。
然后,在应用程序的主页面中,当您要显示数据时,您将检查用户是否经过验证,如果没有,则将登录表单呈现为页面的一部分。
 $usr = CheckLogon(); 
 if ( $usr == "" ) {  // check for correct test to make sure user is logged on
     ShowLoginForm(); 
     ....

1
谢谢您的回答,但这与将登录页面创建为单独页面类似。您正在使用全页刷新和重定向。 - Khanh TO
非常好的观点 - 我这方面有些脑抽了。不过我仍然会选择你的第二个选项,并且像你说的那样,使用JavaScript来捕捉用户登录提示并刷新相应的页面。 - acutesoftware

0
我决定采用第二种方法:应用程序只有一个页面,登录页面将是应用程序中的视图,可以使用JavaScript来切换。我发现这并不难做,我仍然可以使用基于cookie的身份验证和服务器上的会话,成功登录后将用户重定向到默认页面(主页面)等。以下是我使用angularjs的示例代码。
路由:
var App = angular.module('App', ["ui.state"]);

App.config(function ($stateProvider, $routeProvider) {
   $stateProvider.
   .state('login', {
        url: "/login?returnUrl",
        templateUrl: '/Home/Login',
        controller:"LoginController"
    })
    .state('main', {
        url: "/main",
        abstract:true,
        templateUrl: '/Home/Main',
        controller: "MainController"
     })
})
.run(function ($rootScope, $state, $stateParams, $location) {
     $rootScope.$on('$stateChangeError', function(event, toState, toParams, fromState, fromParams, error){ 
        if (error.status == 401) {
            $state.transitionTo("login", { returnUrl: $location.url() });
        }
     })
});

这里的重点是当路由发生错误时,状态码为401(来自服务器),表示用户未登录,我将转换到带有返回URL的登录状态。

用户成功使用ajax登录后,我将状态转换回我的主视图。类似于这样:

$http.post("/Login", JSON.stringify({UserName:username,Password:password}))
     .success(function (data, status, headers, config) {
        var returnUrl = $stateParams.returnUrl ? $stateParams.returnUrl : "mydefaulturl";
        $location.url(returnUrl);
 })

通过这种方法,现在我能够创建深度链接到我的应用程序中的特定状态,包括登录页面和返回URL。

我已经写了一篇关于这个主题的博客文章,可能会对你感兴趣。http://jonsamwell.com/url-route-authorization-and-security-in-angular/ - Jon

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接