繁体   English   中英

Blazor:在没有会话/JWT 令牌时重定向到登录页面?

[英]Blazor: Redirect to Login page when there is no session / JWT token?

我正在尝试在 Blazor 中创建一个新应用程序并且正在处理身份验证。 我正在使用存储在本地存储中的 JWT 令牌。 当应用程序加载时,我需要检查存储中是否有令牌。 如果是这样,请将其添加到所有 API 请求的 HTTP 标头中,如果没有,则在页面加载之前重定向到登录页面......我在哪里做? 有多个页面需要进行此检查,因此需要在一个位置完成以覆盖所有页面。 这应该在启动中完成吗?

搜索没有提供解决方案,因为我是 Blazor 的新手,找到正确的搜索词有点困难:)

创建一个组件并将其命名为RedirectToLogin.razor

@inject NavigationManager Navigation
@code {
    [CascadingParameter]
    private Task<AuthenticationState> AuthenticationStateTask { get; set; }

    protected override async Task OnInitializedAsync()
    {
        var authenticationState = await AuthenticationStateTask;

        if (authenticationState?.User?.Identity is null || !authenticationState.User.Identity.IsAuthenticated)
        {
            var returnUrl = Navigation.ToBaseRelativePath(Navigation.Uri);

            if (string.IsNullOrWhiteSpace(returnUrl))
                Navigation.NavigateTo("YourLoginPath", true);
            else
                Navigation.NavigateTo($"{YourLoginPath}?returnUrl={returnUrl}", true);
        }
    }
}

修改App.razor

<Found Context="routeData">
    <AuthorizeRouteView RouteData="@routeData" DefaultLayout="@typeof(HostLayout)">
        <NotAuthorized>
            <RedirectToLogin></RedirectToLogin>
        </NotAuthorized>
    </AuthorizeRouteView>
</Found>

学分转到:这篇文章

我所做的是编写自己的 http 服务来做到这一点。

它被称为 Backend 并且具有这样的令牌属性:

    public string ApiToken
    {
        get
        {
            if (!string.IsNullOrEmpty(apitoken))
                return apitoken;

            apitoken = Browser.ReadStorage("apitoken");
            return apitoken;
        }

        set
        {
            Browser.WriteStorage("apitoken", value);
        }
    }

然后在这个类中实现 http 类具有的所有方法,同时注入您的令牌。 例如:

    public async Task<T> GetJsonAsync<T>(string uri)
    {
            this.InProgress = true;
            var result = await http.GetJsonAsync<ServerResult<T>>(uri, this.ApiToken);
            this.InProgress = false;

            if (!result.Success)
            {
                BlazorExtensions.Browser.Alert($"Error: {result.ErrorMessage}");
                return default(T);
            }

            return result.ValueObject;

    }

并且到处使用后端服务来处理您的请求。 对于您的 api 网址也很方便。

编辑对于重定向部分:为简洁起见,我省略了这一部分,但这是完整的方法:

    public async Task<T> GetJsonAsync<T>(string uri)
    {
        try
        {
            this.InProgress = true;
            var result = await http.GetJsonAsync<ServerResult<T>>(uri, this.ApiToken);
            this.InProgress = false;

            if (!result.Success)
            {
                BlazorExtensions.Browser.Alert($"Error: {result.ErrorMessage}");
                return default(T);
            }

            return result.ValueObject;
        }
        catch (UnauthorizedAccessException)
        {
            this.InProgress = false;
            uriHelper.NavigateTo("/bzr/Logon");
            return default(T);
        }
        catch (Exception e)
        {
            BlazorExtensions.Browser.Alert($"Fout bij http fetch: {e.Message}");
            this.InProgress = false;
            return default(T);
        }
    }

uriHelper只是简单地注入到构造函数中:

    public IUriHelper uriHelper { get; private set; }

    public Backend(HttpClient httpInstance, IUriHelper uriHelper)
    {
        http = httpInstance;
        this.uriHelper = uriHelper;

猜猜这就是你需要的?

你是什​​么意思Startup 创业班,对吧?

现在 Razor 组件框架没有应用程序事件循环。 耐心点......它即将到来......同时,为了学习,使用组件事件循环。 通常,您应该将您的 JWT 存储在本地存储中,包括有关用户的数据、他是否已通过身份验证等,以及检索此数据以确定用户是否已通过身份验证的服务。 您可以在需要身份验证(或授权)时调用此服务。

顺便说一句,您并不是要通过说“ before the page loads ”来停止...的过程。 您只是说您不希望显示“新个人资料页面”,例如在在线约会网站中,如果用户未通过身份验证,对吗? 那么,在这种情况下,从页面(组件)的 OnInit 或 OnInitAsync 方法调用身份验证本地服务(从本地存储检索数据)。

希望这可以帮助...

一个解决方案(目前,我认为不是最好的?)是为所有组件页面创建一个基类,以继承和覆盖 OnInit 方法来执行检查和重定向。 在应用程序加载后导航到链接时,这也适用。

app.cshtml 组件中的检查仅适用于初始启动,而不适用于在应用程序中导航时。 这对其他检查很好,但不能保护路由。

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM