Udostępnij za pośrednictwem


Instrukcje: Tworzenie usługi tokenów zabezpieczeń

Usługa tokenu zabezpieczającego implementuje protokół zdefiniowany w specyfikacji WS-Trust. Ten protokół definiuje formaty komunikatów i wzorce wymiany komunikatów na potrzeby wystawiania, odnawiania, anulowania i weryfikowania tokenów zabezpieczających. Dana usługa tokenu zabezpieczającego zapewnia co najmniej jedną z tych funkcji. W tym temacie przedstawiono najbardziej typowy scenariusz: implementowanie wystawiania tokenów.

Tokeny wystawiające

WS-Trust definiuje formaty komunikatów na RequestSecurityToken podstawie elementu schematu XML schema language (XSD) i RequestSecurityTokenResponse elementu schematu XSD do wystawiania tokenów. Ponadto definiuje skojarzone identyfikatory URI (Action Uniform Resource Identifiers). Identyfikator URI akcji skojarzony z komunikatem RequestSecurityToken to http://schemas.xmlsoap.org/ws/2005/02/trust/RST/Issue. Identyfikator URI akcji skojarzony z komunikatem RequestSecurityTokenResponse to http://schemas.xmlsoap.org/ws/2005/02/trust/RSTR/Issue.

Struktura komunikatów żądania

Struktura komunikatów żądania problemu zwykle składa się z następujących elementów:

  • Identyfikator URI typu żądania z wartością http://schemas.xmlsoap.org/ws/2005/02/trust/Issue.

  • Identyfikator URI typu tokenu. W przypadku tokenów SAML (Security Assertions Markup Language) 1.1 wartość tego identyfikatora URI to http://docs.oasis-open.org/wss/oasis-wss-saml-token-profile-1.1#SAMLV1.1.

  • Wartość rozmiaru klucza wskazująca liczbę bitów w kluczu do skojarzenia z wystawionym tokenem.

  • Identyfikator URI typu klucza. W przypadku kluczy symetrycznych wartość tego identyfikatora URI to http://schemas.xmlsoap.org/ws/2005/02/trust/SymmetricKey.

Ponadto może istnieć kilka innych elementów:

  • Kluczowy materiał dostarczony przez klienta.

  • Informacje o zakresie wskazujące usługę docelową, z którą będzie używany wystawiony token.

Usługa tokenu zabezpieczającego używa informacji w komunikacie żądania problemu podczas konstruowania komunikatu odpowiedzi na problem.

Struktura komunikatów odpowiedzi

Struktura komunikatów odpowiedzi na problem zwykle składa się z następujących elementów;

  • Wystawiony token zabezpieczający, na przykład asercji SAML 1.1.

  • Token dowodowy skojarzony z tokenem zabezpieczającym. W przypadku kluczy symetrycznych jest to często zaszyfrowana forma materiału klucza.

  • Odwołania do wystawionego tokenu zabezpieczającego. Zazwyczaj usługa tokenu zabezpieczającego zwraca odwołanie, które może być używane, gdy wystawiony token pojawia się w kolejnym komunikacie wysłanym przez klienta i innym, który może być używany, gdy token nie jest obecny w kolejnych komunikatach.

Ponadto może istnieć kilka innych elementów:

  • Materiał klucza udostępniany przez usługę tokenu zabezpieczającego.

  • Algorytm potrzebny do obliczenia klucza współużytkowanego.

  • Informacje o okresie istnienia wystawionego tokenu.

Przetwarzanie komunikatów żądań

Usługa tokenu zabezpieczającego przetwarza żądanie problemu, sprawdzając różne elementy komunikatu żądania i upewniając się, że może wystawiać token spełniający żądanie. Usługa tokenu zabezpieczającego musi określić następujące elementy, zanim skonstruuje token do wystawienia:

  • Żądanie jest naprawdę żądaniem wystawienia tokenu.

  • Usługa tokenu zabezpieczającego obsługuje żądany typ tokenu.

  • Osoba żądający ma autoryzację do wykonania żądania.

  • Usługa tokenu zabezpieczającego może spełniać oczekiwania żądającego w odniesieniu do kluczowych materiałów.

Dwie istotne części konstruowania tokenu określają klucz do podpisania tokenu za pomocą i klucz do zaszyfrowania klucza współużytkowanego. Token musi być podpisany, aby gdy klient przedstawi token usłudze docelowej, usługa może określić, że token został wystawiony przez usługę tokenu zabezpieczającego, któremu ufa. Materiał klucza musi być zaszyfrowany w taki sposób, aby usługa docelowa mogła odszyfrować ten materiał klucza.

Podpisywanie asercji SAML obejmuje utworzenie SigningCredentials wystąpienia. Konstruktor dla tej klasy przyjmuje następujące elementy:

  • Wartość SecurityKey dla klucza używanego do podpisywania asercji SAML.

  • Ciąg identyfikujący algorytm podpisu do użycia.

  • Ciąg identyfikujący algorytm mieszania do użycia.

  • Opcjonalnie element SecurityKeyIdentifier identyfikujący klucz używany do podpisywania asercji.

void AddSigningCredentials(SamlAssertion assertion, SecurityKey signingKey)
{
    SigningCredentials sc = new SigningCredentials(signingKey,
        SecurityAlgorithms.RsaSha1Signature, SecurityAlgorithms.Sha1Digest);
    assertion.SigningCredentials = sc;
}
Sub AddSigningCredentials(ByVal assertion As SamlAssertion, _
    ByVal signingKey As SecurityKey)
    Dim sc As New SigningCredentials(signingKey, _
    SecurityAlgorithms.RsaSha1Signature, SecurityAlgorithms.Sha1Digest)
    assertion.SigningCredentials = sc

End Sub

Szyfrowanie klucza wspólnego obejmuje pobranie materiału klucza i zaszyfrowanie go za pomocą klucza, którego usługa docelowa może użyć do odszyfrowania klucza wspólnego. Zazwyczaj jest używany klucz publiczny usługi docelowej.

byte[] EncryptKey(byte[] plainTextKey, SecurityKey encryptingKey)
{
    return encryptingKey.EncryptKey(SecurityAlgorithms.RsaOaepKeyWrap, plainTextKey);
}
Function EncryptKey(ByVal plainTextKey() As Byte, _
        ByVal encryptingKey As SecurityKey) As Byte()
    Return encryptingKey.EncryptKey(SecurityAlgorithms.RsaOaepKeyWrap, plainTextKey)
End Function

Ponadto SecurityKeyIdentifier potrzebny jest element dla zaszyfrowanego klucza.

SecurityKeyIdentifier GetKeyIdentifierForEncryptedKey(byte[] encryptedKey,
    SecurityToken encryptingToken)
{
    SecurityKeyIdentifier encryptingKeyIdentifier = new SecurityKeyIdentifier(encryptingToken.CreateKeyIdentifierClause<X509ThumbprintKeyIdentifierClause>());
    return new SecurityKeyIdentifier(new EncryptedKeyIdentifierClause(encryptedKey, SecurityAlgorithms.RsaOaepKeyWrap, encryptingKeyIdentifier));
}
Function GetKeyIdentifierForEncryptedKey(ByVal encryptedKey() _
 As Byte, ByVal encryptingToken As SecurityToken) _
    As SecurityKeyIdentifier
    Dim encryptingKeyIdentifier As New SecurityKeyIdentifier( _
        encryptingToken.CreateKeyIdentifierClause(Of X509ThumbprintKeyIdentifierClause)())
    Return New SecurityKeyIdentifier(New EncryptedKeyIdentifierClause( _
        encryptedKey, SecurityAlgorithms.RsaOaepKeyWrap, encryptingKeyIdentifier))
End Function

Następnie SecurityKeyIdentifier jest on używany do utworzenia SamlSubject elementu w ramach elementu SamlToken.

SamlSubject CreateSamlSubjectForProofKey(SecurityKeyIdentifier proofKeyIdentifier)
{
    List<string> confirmations = new List<string>();

    confirmations.Add("urn:oasis:names:tc:SAML:1.0:cm:holder-of-key");

    return new SamlSubject(null, null, "IssuerName", confirmations, null, proofKeyIdentifier);
}
Function CreateSamlSubjectForProofKey( _
    ByVal proofKeyIdentifier As SecurityKeyIdentifier) As SamlSubject
    Dim confirmations As List(Of String) = New List(Of String)()
    confirmations.Add("urn:oasis:names:tc:SAML:1.0:cm:holder-of-key")
    Return New SamlSubject(Nothing, Nothing, "IssuerName", _
        confirmations, Nothing, proofKeyIdentifier)
End Function

Aby uzyskać więcej informacji, zobacz Przykład federacji.

Tworzenie komunikatów odpowiedzi

Gdy usługa tokenu zabezpieczającego przetworzy żądanie problemu i skonstruuje token, który ma zostać wystawiony wraz z kluczem dowodowym, należy skonstruować komunikat odpowiedzi, w tym co najmniej żądany token, token dowodowy i wystawione odwołania do tokenu. Wystawiony token jest zazwyczaj tworzony na SamlSecurityToken podstawie SamlAssertionelementu , jak pokazano w poniższym przykładzie.

SecurityToken CreateIssuedToken(SamlAssertion assertion)
{
    return new SamlSecurityToken(assertion);
}
Function CreateIssuedToken(ByVal assertion As SamlAssertion) As SecurityToken
    Return New SamlSecurityToken(assertion)
End Function

W przypadku, gdy usługa tokenu zabezpieczającego udostępnia materiał klucza współużytkowanego, token dowodowy jest konstruowany przez utworzenie elementu BinarySecretSecurityToken.

BinarySecretSecurityToken CreateProofToken(byte[] proofKey)
{
    return new BinarySecretSecurityToken(proofKey);
}
Function CreateProofToken(ByVal proofKey() As Byte) As BinarySecretSecurityToken
    Return New BinarySecretSecurityToken(proofKey)

End Function

Aby uzyskać więcej informacji na temat konstruowania tokenu dowodowego, gdy klient i usługa tokenu zabezpieczającego zapewniają materiał klucza dla klucza współużytkowanego, zobacz Przykład federacji.

Wystawione odwołania do tokenu są tworzone przez utworzenie wystąpień SecurityKeyIdentifierClause klasy.

SecurityKeyIdentifierClause CreateTokenReference(SamlSecurityToken token)
{
    return token.CreateKeyIdentifierClause<SamlAssertionKeyIdentifierClause>();
}
Function CreateTokenReference(ByVal token As SamlSecurityToken) _
    As SecurityKeyIdentifierClause
    Return token.CreateKeyIdentifierClause( _
    Of SamlAssertionKeyIdentifierClause)()
End Function

Te różne wartości są następnie serializowane w komunikacie odpowiedzi zwróconym do klienta.

Przykład

Pełny kod usługi tokenu zabezpieczającego można znaleźć w temacie Federation Sample (Przykład federacji).

Zobacz też