Denne omveksling kan modtage et JSON Web Token og omveksle det til en NSP OIO IDWS sikkerhedsbillet.
Et JSON Web Token
I det følgende vises nogle stykker kode der viser hvordan man som anvender skal bruge Seal.Java til denne omveksling.
Der findes et komplet eksempel (incl. STS omveksling) sidst på siden der virker uden at det kræver tilretning.
Et JWT Token der stammer fra en Identity Provider kan Seal.Java parse til en Jwt struktur indeholdende alle oplysninger fra JWT Token:
JWTToIdentityTokenRequest request = ...; String jwt = request.getJsonWebToken(); Jws<Claims> claimsJws = jwtParser.parseClaimsJws(jwt); |
Seal.Java kan anvendes til at opbygge et JWT Token. Dette vil typisk ske i forbindelse med test.
Først skal CredentialVaults sættes op og der skal lave en instans af den factory der kan håndtere JWT Tokens:
// CredentialVault og Factory CredentialVault signingVault = new ClasspathCredentialVault(null, "Filnavn på PKCS#12 Medarbejdercertifikat", "Kodeord til Medarbejdercertifikat"); CredentialVault holderOfKeyVault = new ClasspathCredentialVault(null, "Filnavn på PKCS#12 Holder of key certifikat", "Kodeord til Holder of key certifikat"); OIOSAMLFactory factory = new OIOSAMLFactory(); |
Et signeret JWT Token opbygges vha. Seal.Java på denne måde:
public class TestFactoryFlow extends AbstractUserIDCardTest {
@Test
public void testJWT2Idws() {
/**
* Consumer sender request
*/
// CredentialVault og Factory
CredentialVault signingVault = CredentialVaultTestUtil.getFoces3CredentialVault();
CredentialVault holderOfKeyVault = CredentialVaultTestUtil.getVocesHolderOfKeyCredentialVault();
OIOSAMLFactory factory = new OIOSAMLFactory();
// Byg Jwt token (JTP-H profil)
String audience = "http://audience/clear";
String sub = "urn:dk:healthcare:eid:uuid:global:person:594f7fc0-30cf-4b83-8521-4d3f810b3107";
String acr = "https://data.gov.dk/concept/core/nsis/loa/Substantial";
String cpr = "1111901113";
JwtBuilder builder = Jwts.builder();
String jtph = builder.header()
.keyId("test_foces3_2027")
.and().claims()
.issuer("http://sts-tester")
.id(UUID.randomUUID().toString())
.audience().add(audience).and()
.issuedAt(notBefore)
.expiration(notOnOrAfter)
.subject(sub)
.add("scope", "clear sosi-sts ignoredScope")
.add("system_name", "MyTestSystem")
.add("auth_time", String.valueOf(notBefore))
.add("acr", acr)
.add("iss-policy", "urn:dk:sundhed:oidc:policy_strict")
.add("cpr", cpr)
.add("cpr_uuid", "594f7fc0-30cf-4b83-8521-4d3f810b3107")
.add("over_15", "true")
.and().signWith(SignatureAlgorithm.RS256, signingVault.getSystemCredentialPair().getPrivateKey())
.compact();
// Byg STS request
JWTToIdentityTokenRequestDOMBuilder requestBuilder = factory.createJWTToIdentityTokenRequestDOMBuilder();
requestBuilder.setCPRNumberClaim(cpr);
requestBuilder.setJWTToken(jtph);
requestBuilder.setSigningVault(signingVault);
requestBuilder.setAudience(audience);
Document consumerStsRequestDocument = requestBuilder.build();
/**
* Send request over netværk
*/
String consumerStsRequestXml = XmlUtil.node2String(consumerStsRequestDocument, false, false);
consumerStsRequestDocument = readXml(System.getProperties(), consumerStsRequestXml, false);
/**
* STS modtager request
*/
JWTToIdentityTokenRequest stsRequest = factory.createJWTToIdentityTokenRequestModelBuilder().build(consumerStsRequestDocument);
// Her vil STS'en verificere JSon Web Token. I dette eksempel verificeres følgende tre attributter:
final Jws<Claims> claimsJws = JwtParser(signingVault).parseClaimsJws(stsRequest.getJsonWebToken());
Assert.assertEquals(sub, claimsJws.getBody().get("sub", String.class));
Assert.assertEquals(acr, claimsJws.getBody().get("acr", String.class));
Assert.assertEquals(cpr, claimsJws.getBody().get("cpr", String.class));
/**
* STS bygger response
*/
// Byg IdentityToken
CitizenIdentityTokenBuilder identityTokenBuilder = factory.createCitizenIdentityTokenBuilder();
identityTokenBuilder.setAudienceRestriction("http://fmk-online.dk");
identityTokenBuilder.setRecipientURL("https://fmk");
identityTokenBuilder.setIssuer("Issuer");
identityTokenBuilder.setNotBefore(notBefore);
identityTokenBuilder.setNotOnOrAfter(notOnOrAfter);
identityTokenBuilder.setDeliveryNotOnOrAfter(notOnOrAfter);
identityTokenBuilder.setCprNumberAttribute(cpr);
identityTokenBuilder.setSubjectNameID("SubjectNameID");
identityTokenBuilder.setSubjectNameIDFormat("SubjectNameIDFormat");
identityTokenBuilder.setHolderOfKeyCertificate(holderOfKeyVault.getSystemCredentialPair().getCertificate());
identityTokenBuilder.setSigningVault(signingVault);
IdentityToken identityToken = identityTokenBuilder.build();
// Byg STS response
OIOBootstrapToIdentityTokenResponseDOMBuilder responseBuilder = factory.createOIOBootstrapToIdentityTokenResponseDOMBuilder();
responseBuilder.setIdentityToken(identityToken);
responseBuilder.setSigningVault(holderOfKeyVault);
responseBuilder.setRelatesTo("relatesTo");
responseBuilder.setContext("context");
Document consumerStsResponseDocument = responseBuilder.build();
/**
* Send response over netværk
*/
String consumerStsResponseXml = XmlUtil.node2String(consumerStsResponseDocument, false, false);
consumerStsResponseDocument = readXml(System.getProperties(), consumerStsResponseXml, false);
/**
* Consumer modtager response
*/
OIOBootstrapToIdentityTokenResponse consumerStsResponse = factory.createOIOBootstrapToIdentityTokenResponseModelBuilder().build(consumerStsResponseDocument);
IdentityToken identityTokenResponse = consumerStsResponse.getIdentityToken();
Assert.assertEquals("DK-SAML-2.0", identityTokenResponse.getSpecVersion());
Assert.assertEquals("http://fmk-online.dk", identityTokenResponse.getAudienceRestriction());
Assert.assertEquals(cpr, identityTokenResponse.getCpr());
}
private static JwtParser JwtParser(CredentialVault signingVault) {
return Jwts.parser()
.setSigningKeyResolver(new SigningKeyResolver() {
@Override
public Key resolveSigningKey(JwsHeader jwsHeader, Claims claims) {
return signingVault.getSystemCredentialPair().getCertificate().getPublicKey();
}
@Override
public Key resolveSigningKey(JwsHeader jwsHeader, byte[] bytes) {
throw new UnsupportedOperationException("Method not implemented");
}
})
.build();
}
} |