ServiceStack 记住我不能在使用 AngularJS 的 Azure 上工作 - 会话超时太快



我们在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 正常工作?

会话

超时

您担心的是您的会话过早过期。这是你应该独立于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 进行回复,前提是您的凭据是有效的。此会话 cookie 将由 Angular 针对随后的任何请求发送。

// 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值。请参阅我之前关于此问题的回答,其中讨论了如何跟踪会话。

应用程序池回收

如果在测试后发现会话提前过期,并且您在 ServiceStack 中使用In-Memory缓存(默认),请注意,如果 IIS 主机回收了服务的应用程序池,则缓存数据也将销毁。但这种情况经常发生是不寻常的。

您可以在global.aspxApplication_Start活动中注销,以记录回收的频率。

我的这个答案涉及应用程序池的回收。

我希望这有所帮助。

最新更新