From 107c9b0ea6d0191110cccfbbbf6ad95442032c94 Mon Sep 17 00:00:00 2001 From: Paul Millar Date: Fri, 12 Apr 2024 09:09:59 +0200 Subject: [PATCH] common: add issuer URI to OAuthProviderPrincipal Motivation: The OAuthProviderPrincipal carries information about which issuer issued the OIDC token. Currently, it carries only the dCache alias for that issuer. Downstream gPlazma plugins may wish to know the corresponding issuer URI; i.e., the value of the 'iss' claim. Modification: Update the OAuthProviderPrincipal to carry the issuer URI. Update places where the principal is created to include the issuer URI. Some unit-tests need to be updated. Result: No user- or admin observable changes; however, downstream gPlazma plugins can now learn the issuer URI after a successful 'oidc' plugin invocation. Target: master Requires-notes: no Requires-book: no Request: 10.1 Request: 10.0 Request: 9.2 --- .../java/org/dcache/auth/OAuthProviderPrincipal.java | 9 ++++++++- .../java/org/dcache/gplazma/oidc/OidcAuthPlugin.java | 2 +- .../dcache/gplazma/oidc/MockIdentityProviderBuilder.java | 5 +++++ .../main/java/org/dcache/gplazma/scitoken/Issuer.java | 2 +- .../org/dcache/gplazma/scitoken/SciTokenPluginTest.java | 2 +- 5 files changed, 16 insertions(+), 4 deletions(-) diff --git a/modules/common/src/main/java/org/dcache/auth/OAuthProviderPrincipal.java b/modules/common/src/main/java/org/dcache/auth/OAuthProviderPrincipal.java index 540ab821944..936324604c3 100644 --- a/modules/common/src/main/java/org/dcache/auth/OAuthProviderPrincipal.java +++ b/modules/common/src/main/java/org/dcache/auth/OAuthProviderPrincipal.java @@ -18,6 +18,7 @@ */ package org.dcache.auth; +import java.net.URI; import static java.util.Objects.requireNonNull; import java.security.Principal; @@ -29,9 +30,11 @@ public class OAuthProviderPrincipal implements Principal { private final String name; + private final URI issuer; - public OAuthProviderPrincipal(String name) { + public OAuthProviderPrincipal(String name, URI issuer) { this.name = requireNonNull(name); + this.issuer = requireNonNull(issuer); } @Override @@ -39,6 +42,10 @@ public String getName() { return name; } + public URI getIssuer() { + return issuer; + } + @Override public boolean equals(Object other) { return other instanceof OAuthProviderPrincipal diff --git a/modules/gplazma2-oidc/src/main/java/org/dcache/gplazma/oidc/OidcAuthPlugin.java b/modules/gplazma2-oidc/src/main/java/org/dcache/gplazma/oidc/OidcAuthPlugin.java index a241bdd59cb..3397de527a6 100644 --- a/modules/gplazma2-oidc/src/main/java/org/dcache/gplazma/oidc/OidcAuthPlugin.java +++ b/modules/gplazma2-oidc/src/main/java/org/dcache/gplazma/oidc/OidcAuthPlugin.java @@ -199,7 +199,7 @@ public void authenticate(Set publicCredentials, Set privateCrede checkAudience(result, identifiedPrincipals); var idp = result.idp(); - identifiedPrincipals.add(new OAuthProviderPrincipal(idp.getName())); + identifiedPrincipals.add(new OAuthProviderPrincipal(idp.getName(), idp.getIssuerEndpoint())); Profile profile = idp.getProfile(); var profileResult = profile.processClaims(idp, result.claims()); diff --git a/modules/gplazma2-oidc/src/test/java/org/dcache/gplazma/oidc/MockIdentityProviderBuilder.java b/modules/gplazma2-oidc/src/test/java/org/dcache/gplazma/oidc/MockIdentityProviderBuilder.java index 39366b5805e..30b50a2c859 100644 --- a/modules/gplazma2-oidc/src/test/java/org/dcache/gplazma/oidc/MockIdentityProviderBuilder.java +++ b/modules/gplazma2-oidc/src/test/java/org/dcache/gplazma/oidc/MockIdentityProviderBuilder.java @@ -30,6 +30,7 @@ */ public class MockIdentityProviderBuilder { private final IdentityProvider provider = mock(IdentityProvider.class); + private boolean hasEndpoint; static public MockIdentityProviderBuilder anIp(String name) { return new MockIdentityProviderBuilder(name); @@ -42,6 +43,7 @@ public MockIdentityProviderBuilder(String name) { public MockIdentityProviderBuilder withEndpoint(String endpoint) { URI url = URI.create(endpoint); BDDMockito.given(provider.getIssuerEndpoint()).willReturn(url); + hasEndpoint = true; return this; } @@ -72,6 +74,9 @@ public MockIdentityProviderBuilder withSuppress(String keyword) { } public IdentityProvider build() { + if (!hasEndpoint) { + withEndpoint("https://example.org/"); + } return provider; } } diff --git a/modules/gplazma2-scitoken/src/main/java/org/dcache/gplazma/scitoken/Issuer.java b/modules/gplazma2-scitoken/src/main/java/org/dcache/gplazma/scitoken/Issuer.java index 9573b6bb82b..f76760973f1 100644 --- a/modules/gplazma2-scitoken/src/main/java/org/dcache/gplazma/scitoken/Issuer.java +++ b/modules/gplazma2-scitoken/src/main/java/org/dcache/gplazma/scitoken/Issuer.java @@ -88,7 +88,7 @@ public Issuer(HttpClient client, String id, String endpoint, FsPath prefix, String configEndpoint = sb.toString(); userIdentity = Set.copyOf(identity); - opIdentity = new OAuthProviderPrincipal(id); + opIdentity = new OAuthProviderPrincipal(id, URI.create(endpoint)); this.configuration = new HttpJsonNode(client, configEndpoint, Duration.ofHours(1), Duration.ofSeconds(10)); diff --git a/modules/gplazma2-scitoken/src/test/java/org/dcache/gplazma/scitoken/SciTokenPluginTest.java b/modules/gplazma2-scitoken/src/test/java/org/dcache/gplazma/scitoken/SciTokenPluginTest.java index 48208a3c74c..c9f158423bf 100644 --- a/modules/gplazma2-scitoken/src/test/java/org/dcache/gplazma/scitoken/SciTokenPluginTest.java +++ b/modules/gplazma2-scitoken/src/test/java/org/dcache/gplazma/scitoken/SciTokenPluginTest.java @@ -1481,7 +1481,7 @@ public void shouldAcceptWlcgProfileWithoutScope() throws Exception { .issuedBy("OP1").usingKey("key1")); assertThat(identifiedPrincipals, hasItems(new JwtSubPrincipal("EXAMPLE", sub), - new OidcSubjectPrincipal(sub, "EXAMPLE"), new OAuthProviderPrincipal("EXAMPLE"), + new OidcSubjectPrincipal(sub, "EXAMPLE"), new OAuthProviderPrincipal("EXAMPLE", URI.create("https://example.org")), new JwtJtiPrincipal("EXAMPLE", jti))); assertThat(identifiedPrincipals, not(hasItems(new UidPrincipal(1000), new GidPrincipal(1000, true)))); }