bootstrap openapi documentation

This commit is contained in:
Eduard Heimbuch
2020-02-17 13:42:48 +01:00
parent d513ebcd83
commit 7243f3d5a5
5 changed files with 128 additions and 11 deletions

View File

@@ -426,6 +426,13 @@
<scope>provided</scope> <scope>provided</scope>
</dependency> </dependency>
<dependency>
<groupId>io.swagger.core.v3</groupId>
<artifactId>swagger-annotations</artifactId>
<version>2.1.1</version>
<scope>provided</scope>
</dependency>
</dependencies> </dependencies>
<build> <build>
@@ -471,6 +478,50 @@
</executions> </executions>
</plugin> </plugin>
<plugin>
<groupId>io.openapitools.swagger</groupId>
<artifactId>swagger-maven-plugin</artifactId>
<version>2.1.2</version>
<configuration>
<resourcePackages>
<resourcePackage>sonia.scm.api.v2.resources</resourcePackage>
</resourcePackages>
<outputDirectory>${basedir}/target/openapi/META-INF/scm</outputDirectory>
<outputFilename>openapi</outputFilename>
<outputFormats>JSON,YAML</outputFormats>
<prettyPrint>true</prettyPrint>
<swaggerConfig>
<servers>
<server>
<url>http://localhost:8081/scm/api</url>
<description>local endpoint url</description>
</server>
</servers>
<info>
<title>SCM-Manager REST-API</title>
<version>${project.version}</version>
<contact>
<email>scmmanager@googlegroups.com</email>
<name>SCM-Manager</name>
<url>https://scm-manager.org</url>
</contact>
<license>
<url>http://www.opensource.org/licenses/bsd-license.php</url>
<name>BSD</name>
</license>
</info>
<descriptionFile>src/main/doc/openapi.md</descriptionFile>
</swaggerConfig>
</configuration>
<executions>
<execution>
<goals>
<goal>generate</goal>
</goals>
</execution>
</executions>
</plugin>
<plugin> <plugin>
<groupId>sonia.scm.maven</groupId> <groupId>sonia.scm.maven</groupId>
<artifactId>smp-maven-plugin</artifactId> <artifactId>smp-maven-plugin</artifactId>
@@ -511,9 +562,15 @@
<plugin> <plugin>
<groupId>org.apache.maven.plugins</groupId> <groupId>org.apache.maven.plugins</groupId>
<artifactId>maven-war-plugin</artifactId> <artifactId>maven-war-plugin</artifactId>
<version>2.2</version> <version>3.1.0</version>
<configuration> <configuration>
<filteringDeploymentDescriptors>true</filteringDeploymentDescriptors> <filteringDeploymentDescriptors>true</filteringDeploymentDescriptors>
<webResources>
<resource>
<directory>target/openapi</directory>
<targetPath>WEB-INF/classes</targetPath>
</resource>
</webResources>
</configuration> </configuration>
</plugin> </plugin>

View File

@@ -0,0 +1,3 @@
# openapi docs from code
describe hateoas

View File

@@ -3,6 +3,10 @@ package sonia.scm.api.v2.resources;
import com.google.inject.Inject; import com.google.inject.Inject;
import com.webcohesion.enunciate.metadata.rs.ResponseCode; import com.webcohesion.enunciate.metadata.rs.ResponseCode;
import com.webcohesion.enunciate.metadata.rs.StatusCodes; import com.webcohesion.enunciate.metadata.rs.StatusCodes;
import io.swagger.v3.oas.annotations.enums.SecuritySchemeIn;
import io.swagger.v3.oas.annotations.enums.SecuritySchemeType;
import io.swagger.v3.oas.annotations.security.SecurityScheme;
import io.swagger.v3.oas.annotations.security.SecuritySchemes;
import org.apache.shiro.SecurityUtils; import org.apache.shiro.SecurityUtils;
import org.apache.shiro.authc.AuthenticationException; import org.apache.shiro.authc.AuthenticationException;
import org.apache.shiro.subject.Subject; import org.apache.shiro.subject.Subject;
@@ -19,6 +23,22 @@ import javax.ws.rs.core.Response;
import java.net.URI; import java.net.URI;
import java.util.Optional; import java.util.Optional;
@SecuritySchemes({
@SecurityScheme(
name = "Basic Authentication",
description = "HTTP Basic authentication with username and password",
scheme = "Basic",
type = SecuritySchemeType.HTTP
),
@SecurityScheme(
name = "Bearer Token Authentication",
in = SecuritySchemeIn.HEADER,
paramName = "Authorization",
scheme = "Bearer",
bearerFormat = "JWT",
type = SecuritySchemeType.APIKEY
)
})
@Path(AuthenticationResource.PATH) @Path(AuthenticationResource.PATH)
@AllowAnonymousAccess @AllowAnonymousAccess
public class AuthenticationResource { public class AuthenticationResource {

View File

@@ -3,6 +3,10 @@ package sonia.scm.api.v2.resources;
import com.webcohesion.enunciate.metadata.rs.ResponseCode; import com.webcohesion.enunciate.metadata.rs.ResponseCode;
import com.webcohesion.enunciate.metadata.rs.StatusCodes; import com.webcohesion.enunciate.metadata.rs.StatusCodes;
import com.webcohesion.enunciate.metadata.rs.TypeHint; import com.webcohesion.enunciate.metadata.rs.TypeHint;
import io.swagger.v3.oas.annotations.Operation;
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 sonia.scm.repository.NamespaceAndName; import sonia.scm.repository.NamespaceAndName;
import sonia.scm.repository.Repository; import sonia.scm.repository.Repository;
import sonia.scm.repository.RepositoryManager; import sonia.scm.repository.RepositoryManager;
@@ -87,14 +91,39 @@ public class RepositoryResource {
@GET @GET
@Path("") @Path("")
@Produces(VndMediaType.REPOSITORY) @Produces(VndMediaType.REPOSITORY)
@TypeHint(RepositoryDto.class) @Operation(summary = "Returns a single repository", description = "Returns the repository for the given namespace and name.", tags = "Repository")
@StatusCodes({ @ApiResponse(
@ResponseCode(code = 200, condition = "success"), responseCode = "200",
@ResponseCode(code = 401, condition = "not authenticated / invalid credentials"), description = "success",
@ResponseCode(code = 403, condition = "not authorized, the current user has no privileges to read the repository"), content = @Content(
@ResponseCode(code = 404, condition = "not found, no repository with the specified name available in the namespace"), mediaType = VndMediaType.REPOSITORY,
@ResponseCode(code = 500, condition = "internal server error") schema = @Schema(implementation = RepositoryDto.class)
}) )
)
@ApiResponse(
responseCode = "401",
description = "not authenticated / invalid credentials"
)
@ApiResponse(
responseCode = "403",
description = "not authorized, the current user has no privileges to read the repository"
)
@ApiResponse(
responseCode = "404",
description = "not found, no repository with the specified name available in the namespace",
content = @Content(
mediaType = VndMediaType.ERROR_TYPE,
schema = @Schema(implementation = ErrorDto.class)
)
)
@ApiResponse(
responseCode = "500",
description = "internal server error",
content = @Content(
mediaType = VndMediaType.ERROR_TYPE,
schema = @Schema(implementation = ErrorDto.class)
)
)
public Response get(@PathParam("namespace") String namespace, @PathParam("name") String name){ public Response get(@PathParam("namespace") String namespace, @PathParam("name") String name){
return adapter.get(loadBy(namespace, name), repositoryToDtoMapper::map); return adapter.get(loadBy(namespace, name), repositoryToDtoMapper::map);
} }
@@ -168,7 +197,7 @@ public class RepositoryResource {
} }
@Path("branches/") @Path("branches/")
public BranchRootResource branches(@PathParam("namespace") String namespace, @PathParam("name") String name) { public BranchRootResource branches() {
return branchRootResource.get(); return branchRootResource.get();
} }

View File

@@ -1,5 +1,8 @@
package sonia.scm.api.v2.resources; package sonia.scm.api.v2.resources;
import io.swagger.v3.oas.annotations.OpenAPIDefinition;
import io.swagger.v3.oas.annotations.tags.Tag;
import javax.inject.Inject; import javax.inject.Inject;
import javax.inject.Provider; import javax.inject.Provider;
import javax.ws.rs.Path; import javax.ws.rs.Path;
@@ -7,6 +10,11 @@ import javax.ws.rs.Path;
/** /**
* RESTful Web Service Resource to manage repositories. * RESTful Web Service Resource to manage repositories.
*/ */
@OpenAPIDefinition(
tags = {
@Tag(name = "Repository", description = "Repository related endpoints")
}
)
@Path(RepositoryRootResource.REPOSITORIES_PATH_V2) @Path(RepositoryRootResource.REPOSITORIES_PATH_V2)
public class RepositoryRootResource { public class RepositoryRootResource {
static final String REPOSITORIES_PATH_V2 = "v2/repositories/"; static final String REPOSITORIES_PATH_V2 = "v2/repositories/";