2017-02-08 22 views
0

У меня возникли проблемы с получением JWT из ADFS (Windows Server 2012R2) с помощью ClientAssertionCertificate.Как получить JWT из ADFS (сервер Windows 2012R2) с помощью ClientAssertionCertificate в C#

Все работает нормально, когда я позволяю пользователю аутентифицироваться с его именем пользователя и паролем непосредственно в окне входа в adfs - login, но я не хочу, чтобы мое приложение отображало окно входа в систему ADFS, потому что пользователи моего приложения выиграли Не знаю верительные грамоты. Мое приложение фактически является пользователем (из api), поэтому я хочу выполнить аутентификацию с помощью сертификата. Когда я пытаюсь сделать это, я получаю сообщение «Сервер авторизации не поддерживает запрашиваемый grant_type. Сервер авторизации поддерживает только authorization_code или refresh_token как тип гранта.

Кто-нибудь знает какой-либо обходной путь или другой метод получения JWT ? от ADFS с использованием сертификата Thx много

мое приложение является приложением .Net 4.6.1 консоль

Это мой код прямо сейчас:.

var certPath = Path.Combine(GetCurrentDirectoryFromExecutingAssembly(), "mycertificate.pfx"); 
     var certfile = File.OpenRead(certPath); 
     var certificateBytes = new byte[certfile.Length]; 
     certfile.Read(certificateBytes, 0, (int)certfile.Length); 
     var cert = new X509Certificate2(
      certificateBytes, 
      "mypassword", 
      X509KeyStorageFlags.Exportable | 
      X509KeyStorageFlags.MachineKeySet | 
      X509KeyStorageFlags.PersistKeySet); 

     var certificate = new ClientAssertionCertificate("myclientid", cert); 

     AuthenticationContext context = new AuthenticationContext("https://sts.example.com/adfs",false); 
     AuthenticationResult authenticationResult = await context.AcquireTokenAsync("http://example.com/api", certificate); 
     var token = authenticationResult.AccessToken; 

ответ

2

Вы пытались использовать WSTrustChannelFactory с помощью CertificateWSTrustBinding? В RequestSecurityToken вы можете указать в TokenType, что вы хотите JWT. Получаемая вами JWT будет строкой base64, которую необходимо декодировать.

public static async Task<string> GetAccessToken(string authority, string resource, string clientId) 
    { 


     var certPath = Path.Combine(GetCurrentDirectoryFromExecutingAssembly(), "mycertificate.pfx"); 
     var certfile = File.OpenRead(certPath); 
     var certificateBytes = new byte[certfile.Length]; 
     certfile.Read(certificateBytes, 0, (int)certfile.Length); 
     var cert = new X509Certificate2(
      certificateBytes, 
      "PASSWORD", 
      X509KeyStorageFlags.Exportable | 
      X509KeyStorageFlags.MachineKeySet | 
      X509KeyStorageFlags.PersistKeySet); 



     var factory = new WSTrustChannelFactory(
      new CertificateWSTrustBinding(
       SecurityMode.TransportWithMessageCredential), 
      "https://example.com/adfs/services/trust/13/certificatemixed") {TrustVersion = TrustVersion.WSTrust13}; 


     if (factory.Credentials != null) 
      factory.Credentials.ClientCertificate.Certificate = cert; 

     // create token request 
     var rst = new RequestSecurityToken 
     { 
      RequestType = RequestTypes.Issue, 
      KeyType = KeyTypes.Bearer, 
      AppliesTo = new EndpointReference("http://example.com/api"), 
      KeySizeInBits = 0, 
      TokenType = "urn:ietf:params:oauth:token-type:jwt" 
     }; 

     // request token and return 
     var genericXmlSecurityToken = factory.CreateChannel().Issue(rst) as GenericXmlSecurityToken; 
     return genericXmlSecurityToken != null 
      ? Encoding.UTF8.GetString(Convert.FromBase64String(genericXmlSecurityToken.TokenXml.InnerXml)) 
      : string.Empty; 
    } 
+0

Thx Tommy! Оно работает! Я искал это в течение последних 5 дней! –

 Смежные вопросы

  • Нет связанных вопросов^_^