【问题标题】:ServiceStack RememberMe not working on Azure with AngularJS - Sessions Time Out Too QuicklyServiceStack RememberMe 无法使用 AngularJS 在 Azure 上工作 - 会话超时太快
【发布时间】:2014-04-03 17:23:16
【问题描述】:

我们在 Azure VM 上建立了一个 Angular 管理站点。 API 是使用 ServiceStack 构建的,我们遇到了一个问题,当我们登录并说“记住我”时,我们的用户没有被记住。

这是我们的 AppHost 插件位。

Plugins.Add(new AuthFeature(() => new AuthUserSession(), new IAuthProvider[]
    {
        // it seems as though order matters here. If these are reversed, CredentialsAuth doesn't work.
        new CustomCredentialsAuthProvider(container),
        new CustomBasicAuthProvider(container)
    })
    {
        HtmlRedirect = "~/login.html"
    });

在 Angular 中,我们初始化我们的凭据

    $scope.credentials = {
        userName: '',
        password: '',
        rememberMe: false
    };
    $scope.login = function (credentials) {

        if (!$scope.signinForm.$valid) {
            $scope.submitted = true;
            toaster.pop(nullFieldAlert);
            return;
        }

        authService.save(credentials,

            // Success
            function (data) {
                $rootScope.authenticated = true;
                history.back();
            },

            // Failure
            function (e) {
                handleErrors(e);
            });
    };

然后当用户登录时,他们可以选择更改rememberMe = true;

很遗憾,无论是否设置了 rememberMe,我们的会话都会在几分钟(有时是几秒钟)内到期。

为了让会话在 Azure 上持续 > 3 分钟并让 RememberMe 正常工作,我们需要做些什么?

【问题讨论】:

    标签: azure servicestack session-timeout


    【解决方案1】:

    会话超时

    您担心会话提前到期。这是你应该独立于 AngularJS 进行测试的东西,因为正如我在下面提到的,我怀疑问题与 AngularJS 相关。

    您应该从浏览器直接使用您的 ServiceStack Api 进行身份验证: 您可以通过导航至:

    <your-api-url>/Auth?UserName=username&Password=password&x-http-method-override=POST
    

    酌情替换usernamepassword。这应该会让你获得一个有效的会话。

    然后您应该通过在浏览器开发者控制台中检查 ss-id cookie 来确认您有一个有效的会话。

    通过此会话向您的安全服务提出一些数据请求,确定在会话到期之前您可以访问此数据的时间。我怀疑以这种方式直接交互不会失败,而是您的问题是在您使用 AngularJS 时引起的。

    失去$rootScope.authenticated 状态

    我可能在这里吐槽,因为人们以许多不同且令人兴奋的方式构建他们的 AngularJS 应用程序,这是我对您提供的部分代码的解释。

    我认为这个问题可能与您使用 AngularJS 记录客户端身份验证状态的方式有关,而不是 ServiceStack 问题。

    当您的 AuthService 将凭据发送到 ServiceStack 进行身份验证时,它将使用 Angular 的 $http 服务来执行此操作。假设您的凭据有效,ServiceStack 将使用有效的会话 cookie 进行回复。 Angular 将为随后的任何请求发送此会话 cookie。

    // Success
    function (data) {
        $rootScope.authenticated = true;
        history.back(); // $rootScope on the other page won't be set when you go back
    }
    

    但是,您似乎正在根据 $rootScope 中的变量 authenticated 确定身份验证状态。因此,一旦您成功进行身份验证,您就可以设置该变量。但问题是你正在失去这个状态,通过使用history.back() 导航到上一页,因为这不在login.html 的范围内,你设置的$rootScope 值不再存在。所以如果你依靠这个来判断你是否登录,它是行不通的。

    您需要做的是在应用程序启动时恢复您的$rootScope.authenticated 值。 See my previous answer on this issue,讨论如何跟踪会话。

    应用程序池回收

    如果您的会话在测试后过早到期,并且您在 ServiceStack 中使用 In-Memory 缓存(默认),请注意如果您的服务的 ApplicationPool 被 IIS 主机回收,那么缓存数据也会被摧毁。但这种情况经常发生是不寻常的。

    您可以在global.aspx 中退出您的Application_Start 事件以记录回收频率。

    This answer of mine here涉及到应用程序池的回收。

    我希望这会有所帮助。

    【讨论】:

    • history.back(); 之前调用$rootScope.$apply(); 是否有效?我们的登录页面是应用程序大范围内的部分模板。
    • 那么您向用户展示的登录视图的 url 是什么,即它是应用程序的状态 #/Login 还是 /login.html?当您使用history.back() 时,您是否保持在同一页面上而只是转换状态?您是否通过直接访问服务确认会话没有提前到期?
    • 我也肯定会在控制台中获得 401。
    • 我也一样 - 你是怎么解决这个问题的?我的会话肯定会提前到期。这有点像一两个小时,而不是默认的 14 天。
    • @t316 如果您已按照我的回答中的建议进行操作,但仍有问题,请创建您自己的问题,详细说明您的问题和设置的具体问题,也许可以解决你的问题。
    猜你喜欢
    • 2011-03-29
    • 1970-01-01
    • 2013-09-10
    • 1970-01-01
    • 2012-03-05
    • 1970-01-01
    • 1970-01-01
    • 1970-01-01
    • 2020-12-21
    相关资源
    最近更新 更多