API IdentityServer4 не имеет права вызывать конечную точку самоанализа

#c# #identityserver4 #identityserver3

#c# #identityserver4 #identityserver3

Вопрос:

Я пытаюсь настроить и идентифицировать server4, но я застрял на авторизации: вызов конечной точки / connect / introspect выдает ошибку

IdentityServer4.Проверка.ApiSecretValidator: Ошибка: ресурс API с таким именем не найден. прерывание IdentityServer4.Endpoints.Конечная точка самоанализа: Ошибка: API не имеет права вызывать конечную точку самоанализа. прерывание. Клиент представляет собой net framework 4.7 MVc и использует IdentityServer3.Пакет проверки доступа

Вот моя конфигурация сервера идентификации

 internal class Resources
{
    public static IEnumerable<IdentityResource> GetIdentityResources()
    {
        return new[]
        {
        new IdentityResources.OpenId(),
        new IdentityResources.Profile(),
        new IdentityResources.Email(),
        new IdentityResource
        {
            Name = "role",
            UserClaims = new List<string> {"role"}
        }
    };
    }

    public static IEnumerable<ApiResource> GetApiResources()
    {
        return new[]
        {
            new ApiResource
        {
            Name = "electronicinvoice",
            DisplayName = "electronicinvoice",
            Description = "electronicinvoice",
            Scopes = new List<string> { "electronicinvoice" },
            ApiSecrets = new List<Secret> {new Secret("XXXXX".Sha256())},
            UserClaims = new List<string> {"role"}
        }
    };
    }

    public static IEnumerable<ApiScope> GetApiScopes()
    {
        return new[]
        {
            new ApiScope("electronicinvoice", "Access to electronicinvoiceactive api"),
        };
    }
}
  

Клиент:

 internal class Clients
{
    public static IEnumerable<Client> Get()
    {

         ICollection<string> allowed = GrantTypes.ClientCredentials.Union(GrantTypes.ResourceOwnerPassword).ToList();
        return new List<Client>
    {
        new Client
        {
            ClientId = "SolutionUpdate",
            ClientName = "Legal SolutionDOC client",
            AllowedGrantTypes =allowed ,
            ClientSecrets = new List<Secret> {new Secret("XXXXX".Sha256())}, 
            AllowedScopes = new List<string> {"email","openid","profile","electronicinvoice" },
           

        }
    };
    }
}
  

метод запуска

  public void ConfigureServices(IServiceCollection services)
    {



        services.AddIdentityServer()
        .AddInMemoryClients(Clients.Get())

        .AddInMemoryIdentityResources(Resources.GetIdentityResources())
        .AddInMemoryApiResources(Resources.GetApiResources())
        .AddInMemoryApiScopes(Resources.GetApiScopes())
      
         .AddDeveloperSigningCredential()
         .AddProfileService<ProfileService>()
        .AddCustomTokenRequestValidator<TokenRequestValidator>();
     
        services.AddTransient<IResourceOwnerPasswordValidator, ResourceOwnerPasswordValidator>();
        services.AddTransient<IProfileService, ProfileService>();

    }
  

И, конечно, конфигурация клиента

   public void Configuration(IAppBuilder app)
    {
       
        JwtSecurityTokenHandler.InboundClaimTypeMap.Clear();
        app.UseIdentityServerBearerTokenAuthentication(new IdentityServerBearerTokenAuthenticationOptions()
        {
            Authority = "https://localhost:44389",
            ClientId = "SolutionUpdate",
            ClientSecret = "XXXXXX",  
          
            ValidationMode = ValidationMode.ValidationEndpoint
        });
     
       
    }
  

Теперь я могу успешно получить действительный токен, используя этот метод

    var client = new TokenClient("https://localhost:44389/connect/token", "SolutionUpdate", "XXXXX");
            
                var extra = new Dictionary<string, string> { { nameof(paramAuth.CustomerCode), paramAuth.ToJson() } };
                var response = client.RequestClientCredentialsAsync("electronicinvoice" , extra).Resu<
                var token = response.AccessToken;
                return Content(new DTO.GetTokenResponse { Token = token }.ToJson(), "application/json");
  

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

 var introspectionClient = new IntrospectionClient("https://localhost:44389/connect/introspect", "SolutionUpdate", "XXXXXX");

        var response = introspectionClient.SendAsync(new IntrospectionRequest { Token = accessToken }).Resu<

        var isActive = response.IsActive;
        var claims = response.Claims;
  

или от postman,

Авторизация POST / connect / introspect: базовая (с именем пользователя и паролем) и токеном тела = myaccesstoken

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

Ответ №1:

Хорошо, я понял это: конечная точка самоанализа хочет базовую аутентификацию с учетными данными Apiscope. Это поведение, вероятно, отличалось в identityserver3, или мне где-то не хватает конфигурации.

Итак, у меня есть 2 обходных пути: -Измените имя и пароль Apiscope, чтобы они совпадали с идентификатором клиента и паролем -Внедрите мой собственный атрибут AuthorizeAttribute, в котором я вызову конечную точку самоанализа и проанализирую ответ. Я, вероятно, пойду со вторым, он кажется менее «хакерским», и я боюсь, что первое обходное решение вызовет у меня проблемы, когда я настрою шифрование токена

Комментарии:

1. можете ли вы поделиться реализацией атрибута?