From 3edcfe2edce6e7691733b0f328fad46f101f39c5 Mon Sep 17 00:00:00 2001 From: Enrico Risa Date: Mon, 16 Oct 2023 18:01:11 +0200 Subject: [PATCH] feat: STS API spec --- .../identity-trust-sts-api/build.gradle.kts | 33 ++++++++++++++ .../api/sts/SecureTokenServiceApi.java | 42 +++++++++++++++++ .../SecureTokenServiceApiController.java | 38 ++++++++++++++++ .../api/sts/model/StsTokenErrorResponse.java | 31 +++++++++++++ .../api/sts/model/StsTokenRequest.java | 33 ++++++++++++++ .../api/sts/model/StsTokenResponse.java | 34 ++++++++++++++ .../sts/model/StsTokenErrorResponseTest.java | 41 +++++++++++++++++ .../api/sts/model/StsTokenResponseTest.java | 45 +++++++++++++++++++ settings.gradle.kts | 2 +- 9 files changed, 298 insertions(+), 1 deletion(-) create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/build.gradle.kts create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/SecureTokenServiceApi.java create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/controller/SecureTokenServiceApiController.java create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponse.java create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenRequest.java create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponse.java create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponseTest.java create mode 100644 extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponseTest.java diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/build.gradle.kts b/extensions/common/iam/identity-trust/identity-trust-sts-api/build.gradle.kts new file mode 100644 index 00000000000..a49ffed4fbb --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/build.gradle.kts @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2023 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +plugins { + `java-library` + `maven-publish` + id("io.swagger.core.v3.swagger-gradle-plugin") +} + +dependencies { + api(project(":spi:common:web-spi")) + + implementation(libs.jakarta.rsApi) + implementation(libs.swagger.annotations.jakarta) + + testImplementation(libs.jersey.common) + testImplementation(libs.jersey.server) + + testImplementation(project(":core:common:junit")) + testImplementation(testFixtures(project(":extensions:common:http:jersey-core"))) +} + diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/SecureTokenServiceApi.java b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/SecureTokenServiceApi.java new file mode 100644 index 00000000000..c3fc0c5c7f7 --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/SecureTokenServiceApi.java @@ -0,0 +1,42 @@ +/* + * Copyright (c) 2023 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +package org.eclipse.edc.connector.api.sts; + +import io.swagger.v3.oas.annotations.OpenAPIDefinition; +import io.swagger.v3.oas.annotations.Operation; +import io.swagger.v3.oas.annotations.media.ArraySchema; +import io.swagger.v3.oas.annotations.media.Content; +import io.swagger.v3.oas.annotations.media.Schema; +import io.swagger.v3.oas.annotations.responses.ApiResponse; +import io.swagger.v3.oas.annotations.tags.Tag; +import jakarta.ws.rs.BeanParam; +import org.eclipse.edc.connector.api.sts.model.StsTokenErrorResponse; +import org.eclipse.edc.connector.api.sts.model.StsTokenRequest; +import org.eclipse.edc.connector.api.sts.model.StsTokenResponse; + +@OpenAPIDefinition +@Tag(name = "Secure Token Service Api") +public interface SecureTokenServiceApi { + + + @Operation(description = "", + responses = { + @ApiResponse(responseCode = "200", description = "The Self-Issued ID token", + content = @Content(schema = @Schema(implementation = StsTokenResponse.class))), + @ApiResponse(responseCode = "400", description = "Invalid Request", + content = @Content(array = @ArraySchema(schema = @Schema(implementation = StsTokenErrorResponse.class)))) + }) + StsTokenResponse token(@BeanParam StsTokenRequest request); +} diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/controller/SecureTokenServiceApiController.java b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/controller/SecureTokenServiceApiController.java new file mode 100644 index 00000000000..5d2b5d14082 --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/controller/SecureTokenServiceApiController.java @@ -0,0 +1,38 @@ +/* + * Copyright (c) 2023 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +package org.eclipse.edc.connector.api.sts.controller; + +import jakarta.ws.rs.BeanParam; +import jakarta.ws.rs.Consumes; +import jakarta.ws.rs.POST; +import jakarta.ws.rs.Path; +import jakarta.ws.rs.Produces; +import jakarta.ws.rs.core.MediaType; +import org.eclipse.edc.connector.api.sts.SecureTokenServiceApi; +import org.eclipse.edc.connector.api.sts.model.StsTokenRequest; +import org.eclipse.edc.connector.api.sts.model.StsTokenResponse; + +@Path("/") +public class SecureTokenServiceApiController implements SecureTokenServiceApi { + + @Consumes({ MediaType.APPLICATION_FORM_URLENCODED }) + @Produces({ MediaType.APPLICATION_JSON }) + @Path("token") + @POST + @Override + public StsTokenResponse token(@BeanParam StsTokenRequest request) { + return null; + } +} diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponse.java b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponse.java new file mode 100644 index 00000000000..96fe422bda3 --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponse.java @@ -0,0 +1,31 @@ +/* + * Copyright (c) 2022 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +package org.eclipse.edc.connector.api.sts.model; + +import com.fasterxml.jackson.annotation.JsonProperty; + + +/** + * OAuth2 Error Response + * + * @param error Error code. + * @param errorDescription Human-readable description. + * @param errorUri URI of the error page. + */ +public record StsTokenErrorResponse(@JsonProperty String error, + @JsonProperty("error_description") String errorDescription, + @JsonProperty("error_uri") String errorUri) { + +} diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenRequest.java b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenRequest.java new file mode 100644 index 00000000000..fcda01293dd --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenRequest.java @@ -0,0 +1,33 @@ +/* + * Copyright (c) 2023 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +package org.eclipse.edc.connector.api.sts.model; + +import jakarta.ws.rs.FormParam; + +/** + * OAuth2 Client Credentials Access Token Request + * + * @param grantType Type of grant. Must be client_credentials. + * @param clientId Client ID identifier. + * @param clientSecret Authorization secret for the client. + * @param bearerAccessScope Space-delimited scopes to be included in the access_token claim. + * @param accessToken VP/VC Access Token to be included as access_token claim. + */ +public record StsTokenRequest(@FormParam("grant_type") String grantType, + @FormParam("client_id") String clientId, + @FormParam("client_secret") String clientSecret, + @FormParam("bearer_access_scope") String bearerAccessScope, + @FormParam("access_token") String accessToken) { +} diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponse.java b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponse.java new file mode 100644 index 00000000000..9514a4d887c --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/main/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponse.java @@ -0,0 +1,34 @@ +/* + * Copyright (c) 2023 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +package org.eclipse.edc.connector.api.sts.model; + +import com.fasterxml.jackson.annotation.JsonProperty; + +/** + * OAuth2 Client Credential Access Token Response + * + * @param accessToken Self-Issued ID token. + * @param expiresIn Duration of the token. + * @param tokenType Token type. + */ +public record StsTokenResponse(@JsonProperty("access_token") String accessToken, + @JsonProperty("expires_in") long expiresIn, + @JsonProperty("token_type") String tokenType) { + + public StsTokenResponse(String accessToken, long expiresIn) { + this(accessToken, expiresIn, "Bearer"); + } + +} diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponseTest.java b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponseTest.java new file mode 100644 index 00000000000..46b21083f74 --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenErrorResponseTest.java @@ -0,0 +1,41 @@ +/* + * Copyright (c) 2023 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +package org.eclipse.edc.connector.api.sts.model; + +import org.eclipse.edc.spi.types.TypeManager; +import org.junit.jupiter.api.Test; + +import java.io.IOException; +import java.io.StringWriter; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.assertNotNull; + +public class StsTokenErrorResponseTest { + + @Test + void verifyDeserialize() throws IOException { + var mapper = new TypeManager().getMapper(); + + var response = new StsTokenErrorResponse("error", "description", "uri"); + StringWriter writer = new StringWriter(); + mapper.writeValue(writer, response); + + var deserialized = mapper.readValue(writer.toString(), StsTokenErrorResponse.class); + + assertNotNull(deserialized); + assertThat(deserialized).isEqualTo(response); + } +} diff --git a/extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponseTest.java b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponseTest.java new file mode 100644 index 00000000000..74062933378 --- /dev/null +++ b/extensions/common/iam/identity-trust/identity-trust-sts-api/src/test/java/org/eclipse/edc/connector/api/sts/model/StsTokenResponseTest.java @@ -0,0 +1,45 @@ +/* + * Copyright (c) 2023 Bayerische Motoren Werke Aktiengesellschaft (BMW AG) + * + * This program and the accompanying materials are made available under the + * terms of the Apache License, Version 2.0 which is available at + * https://www.apache.org/licenses/LICENSE-2.0 + * + * SPDX-License-Identifier: Apache-2.0 + * + * Contributors: + * Bayerische Motoren Werke Aktiengesellschaft (BMW AG) - initial API and implementation + * + */ + +package org.eclipse.edc.connector.api.sts.model; + +import org.eclipse.edc.spi.types.TypeManager; +import org.junit.jupiter.api.Test; + +import java.io.IOException; +import java.io.StringWriter; +import java.time.Clock; + +import static org.assertj.core.api.Assertions.assertThat; +import static org.junit.jupiter.api.Assertions.assertNotNull; + +public class StsTokenResponseTest { + + @Test + void verifyDeserialize() throws IOException { + var mapper = new TypeManager().getMapper(); + + var accessToken = "token"; + var expiration = Clock.systemUTC().millis(); + var tokenResponse = new StsTokenResponse(accessToken, expiration); + StringWriter writer = new StringWriter(); + mapper.writeValue(writer, tokenResponse); + + var deserialized = mapper.readValue(writer.toString(), StsTokenResponse.class); + + assertNotNull(deserialized); + assertThat(deserialized).isEqualTo(tokenResponse); + assertThat(deserialized.tokenType()).isEqualTo("Bearer"); + } +} diff --git a/settings.gradle.kts b/settings.gradle.kts index eecce4e27b5..34bc9c56b54 100644 --- a/settings.gradle.kts +++ b/settings.gradle.kts @@ -115,6 +115,7 @@ include(":extensions:common:iam:identity-trust:identity-trust-transform") include(":extensions:common:iam:identity-trust:identity-trust-service") include(":extensions:common:iam:identity-trust:identity-trust-core") include(":extensions:common:iam:identity-trust:identity-trust-sts-embedded") +include(":extensions:common:iam:identity-trust:identity-trust-sts-api") include(":extensions:common:json-ld") include(":extensions:common:metrics:micrometer-core") include(":extensions:common:monitor:monitor-jdk-logger") @@ -226,4 +227,3 @@ include(":system-tests:telemetry:telemetry-test-runner") include(":system-tests:telemetry:telemetry-test-runtime") include(":version-catalog") -