Identity Server 4 Выход из системы с несколькими арендаторами - PullRequest
0 голосов
/ 16 июня 2020

В настоящее время я разрабатываю сервер идентификации. Это мультитенантный с несколькими пользовательскими репозиториями.

Я могу передать (используя Services.OpenIDConnect.Options) мои данные клиента из моего MVC в IDS, чтобы выбрать соответствующий пользовательский репозиторий при входе в систему

options.Events.OnRedirectToIdentityProvider = context =>
{                        
    context.ProtocolMessage.SetParameter("Tenant", "TenantDetail");
    return Task.CompletedTask;
};

Я пытаюсь получить ту же информацию для выхода, однако при первоначальном вызове выхода из системы есть некоторый внутренний процесс, который вызывает CustomProfileService.IsActiveAsyn c (контекст IsActiveContext).

Я не могу получить информацию о клиенте из IsActiveContext, и я не могу прочитать какую-либо строку запроса (как я использовал для входа в систему).

Любые предложения или даже альтернативные методы, которые могут быть более правильными чем то, что я пытаюсь сделать, буду очень признателен.

1 Ответ

1 голос
/ 20 июня 2020

OnRedirectToIdentityProvider не будет нажата при выходе. Вместо этого вам нужно будет передать информацию о клиенте в событии OnRedirectToIdentityProviderForSignOut в вашем клиенте.

Вот фрагмент, который далеко не полный:

services
    .AddOpenIdConnect("oidc", options =>
    {
        options.Events = new OpenIdConnectEvents
        {
            OnRedirectToIdentityProviderForSignOut = context =>
            {
                context.ProtocolMessage.AcrValues = "tenant:TenantDetail";
                return Task.CompletedTask;
            },
        }
    }

В IdentityServer вам понадобится для поиска acr_values ​​в параметрах запроса из запроса. Введите IHttpContextAccessor для доступа к контексту:

public class ProfileService : IProfileService
{
    private readonly IHttpContextAccessor _httpContextAccessor;

    public ProfileService(IHttpContextAccessor httpContextAccessor)
    {
        _httpContextAccessor = httpContextAccessor;
    }

    public async Task GetProfileDataAsync(ProfileDataRequestContext context)
    {
        // ...
    }

    public async Task IsActiveAsync(IsActiveContext context)
    {
        // Please note that this method is called on many occasions. Check context.Caller
        // This means that you'll have to make sure that the acr_valus are present on all
        // ocassions, hence the question in my comment.

        var request = _httpContextAccessor.HttpContext.Request;
        if (request.Method == HttpMethods.Get)
        {
            // acr_values should be present on all ocassions.
            var values = (string)request.Query["acr_values"];

            // This is just a sample, you'll need to parse the values.
            var tenant = values.Split(':')[1];
        }

        // Your code where you link the repository ...

        var sub = context.Subject.GetSubjectId();
        var user = await userManager.FindByIdAsync(sub);
        context.IsActive = user != null;
    }
}

Сообщите мне, решит ли это проблему для вас.

...