Clone the repository
- git clone {repository._links.httpProtocol.href}
+ git clone {href}
Create a new repository
@@ -30,7 +33,7 @@ class ProtocolInformation extends React.Component {
git commit -m "added readme"
- git remote add origin {repository._links.httpProtocol.href}
+ git remote add origin {href}
git push -u origin master
@@ -39,7 +42,7 @@ class ProtocolInformation extends React.Component {
Push an existing repository
- git remote add origin {repository._links.httpProtocol.href}
+ git remote add origin {href}
git push -u origin master
diff --git a/scm-plugins/scm-hg-plugin/src/main/js/ProtocolInformation.js b/scm-plugins/scm-hg-plugin/src/main/js/ProtocolInformation.js
index 28c1e53a07..03fc41450a 100644
--- a/scm-plugins/scm-hg-plugin/src/main/js/ProtocolInformation.js
+++ b/scm-plugins/scm-hg-plugin/src/main/js/ProtocolInformation.js
@@ -1,5 +1,6 @@
//@flow
import React from "react";
+import { repositories } from "@scm-manager/ui-components";
import type { Repository } from "@scm-manager/ui-types";
type Props = {
@@ -10,14 +11,15 @@ class ProtocolInformation extends React.Component {
render() {
const { repository } = this.props;
- if (!repository._links.httpProtocol) {
+ const href = repositories.getProtocolLinkByType(repository, "http");
+ if (!href) {
return null;
}
return (
Clone the repository
- hg clone {repository._links.httpProtocol.href}
+ hg clone {href}
Create a new repository
@@ -26,7 +28,7 @@ class ProtocolInformation extends React.Component {
echo "[paths]" > .hg/hgrc
- echo "default = {repository._links.httpProtocol.href}" > .hg/hgrc
+ echo "default = {href}" > .hg/hgrc
echo "# {repository.name}" > README.md
@@ -44,7 +46,7 @@ class ProtocolInformation extends React.Component {
# add the repository url as default to your .hg/hgrc e.g:
- default = {repository._links.httpProtocol.href}
+ default = {href}
# push to remote repository
diff --git a/scm-plugins/scm-svn-plugin/src/main/js/ProtocolInformation.js b/scm-plugins/scm-svn-plugin/src/main/js/ProtocolInformation.js
index ccff4118ba..0ba195887f 100644
--- a/scm-plugins/scm-svn-plugin/src/main/js/ProtocolInformation.js
+++ b/scm-plugins/scm-svn-plugin/src/main/js/ProtocolInformation.js
@@ -1,5 +1,6 @@
//@flow
import React from "react";
+import { repositories } from "@scm-manager/ui-components";
import type { Repository } from "@scm-manager/ui-types";
type Props = {
@@ -10,14 +11,15 @@ class ProtocolInformation extends React.Component {
render() {
const { repository } = this.props;
- if (!repository._links.httpProtocol) {
+ const href = repositories.getProtocolLinkByType(repository, "http");
+ if (!href) {
return null;
}
return (
Checkout the repository
- svn checkout {repository._links.httpProtocol.href}
+ svn checkout {href}
);
diff --git a/scm-ui-components/packages/ui-components/src/index.js b/scm-ui-components/packages/ui-components/src/index.js
index 4865540868..2e1c51b7dc 100644
--- a/scm-ui-components/packages/ui-components/src/index.js
+++ b/scm-ui-components/packages/ui-components/src/index.js
@@ -2,8 +2,9 @@
import * as validation from "./validation.js";
import * as urls from "./urls";
+import * as repositories from "./repositories.js";
-export { validation, urls };
+export { validation, urls, repositories };
export { default as DateFromNow } from "./DateFromNow.js";
export { default as ErrorNotification } from "./ErrorNotification.js";
@@ -18,6 +19,8 @@ export { default as ProtectedRoute } from "./ProtectedRoute.js";
export { apiClient, NOT_FOUND_ERROR, UNAUTHORIZED_ERROR } from "./apiclient.js";
+
+
export * from "./buttons";
export * from "./forms";
export * from "./layout";
diff --git a/scm-ui-components/packages/ui-components/src/repositories.js b/scm-ui-components/packages/ui-components/src/repositories.js
new file mode 100644
index 0000000000..104cb9a691
--- /dev/null
+++ b/scm-ui-components/packages/ui-components/src/repositories.js
@@ -0,0 +1,19 @@
+// @flow
+import type { Repository } from "@scm-manager/ui-types";
+
+// util methods for repositories
+
+export function getProtocolLinkByType(repository: Repository, type: string) {
+ let protocols = repository._links.protocol;
+ if (protocols) {
+ if (!Array.isArray(protocols)) {
+ protocols = [protocols];
+ }
+ for (let proto of protocols) {
+ if (proto.name === type) {
+ return proto.href;
+ }
+ }
+ }
+ return null;
+}
diff --git a/scm-ui-components/packages/ui-components/src/repositories.test.js b/scm-ui-components/packages/ui-components/src/repositories.test.js
new file mode 100644
index 0000000000..ccd972ad03
--- /dev/null
+++ b/scm-ui-components/packages/ui-components/src/repositories.test.js
@@ -0,0 +1,99 @@
+// @flow
+
+import type { Repository } from "@scm-manager/ui-types";
+import { getProtocolLinkByType, getTypePredicate } from "./repositories";
+
+describe("getProtocolLinkByType tests", () => {
+
+ it("should return the http protocol link", () => {
+
+ const repository: Repository = {
+ namespace: "scm",
+ name: "core",
+ type: "git",
+ _links: {
+ protocol: [{
+ name: "http",
+ href: "http://scm.scm-manager.org/repo/scm/core"
+ }]
+ }
+ };
+
+ const link = getProtocolLinkByType(repository, "http");
+ expect(link).toBe("http://scm.scm-manager.org/repo/scm/core");
+ });
+
+ it("should return the http protocol link from multiple protocols", () => {
+
+ const repository: Repository = {
+ namespace: "scm",
+ name: "core",
+ type: "git",
+ _links: {
+ protocol: [{
+ name: "http",
+ href: "http://scm.scm-manager.org/repo/scm/core"
+ },{
+ name: "ssh",
+ href: "git@scm.scm-manager.org:scm/core"
+ }]
+ }
+ };
+
+ const link = getProtocolLinkByType(repository, "http");
+ expect(link).toBe("http://scm.scm-manager.org/repo/scm/core");
+ });
+
+ it("should return the http protocol, even if the protocol is a single link", () => {
+
+ const repository: Repository = {
+ namespace: "scm",
+ name: "core",
+ type: "git",
+ _links: {
+ protocol: {
+ name: "http",
+ href: "http://scm.scm-manager.org/repo/scm/core"
+ }
+ }
+ };
+
+ const link = getProtocolLinkByType(repository, "http");
+ expect(link).toBe("http://scm.scm-manager.org/repo/scm/core");
+ });
+
+ it("should return null, if such a protocol does not exists", () => {
+
+ const repository: Repository = {
+ namespace: "scm",
+ name: "core",
+ type: "git",
+ _links: {
+ protocol: [{
+ name: "http",
+ href: "http://scm.scm-manager.org/repo/scm/core"
+ },{
+ name: "ssh",
+ href: "git@scm.scm-manager.org:scm/core"
+ }]
+ }
+ };
+
+ const link = getProtocolLinkByType(repository, "awesome");
+ expect(link).toBeNull();
+ });
+
+ it("should return null, if no protocols are available", () => {
+
+ const repository: Repository = {
+ namespace: "scm",
+ name: "core",
+ type: "git",
+ _links: {}
+ };
+
+ const link = getProtocolLinkByType(repository, "http");
+ expect(link).toBeNull();
+ });
+
+});
diff --git a/scm-ui-components/packages/ui-types/src/hal.js b/scm-ui-components/packages/ui-types/src/hal.js
index ab22203835..248c5e5453 100644
--- a/scm-ui-components/packages/ui-types/src/hal.js
+++ b/scm-ui-components/packages/ui-types/src/hal.js
@@ -1,9 +1,10 @@
// @flow
export type Link = {
- href: string
+ href: string,
+ name?: string
};
-export type Links = { [string]: Link };
+export type Links = { [string]: Link | Link[] };
export type Collection = {
_embedded: Object,
diff --git a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/BranchChangesetCollectionToDtoMapper.java b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/BranchChangesetCollectionToDtoMapper.java
new file mode 100644
index 0000000000..afe8ad318b
--- /dev/null
+++ b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/BranchChangesetCollectionToDtoMapper.java
@@ -0,0 +1,26 @@
+package sonia.scm.api.v2.resources;
+
+import sonia.scm.PageResult;
+import sonia.scm.repository.Changeset;
+import sonia.scm.repository.Repository;
+
+import javax.inject.Inject;
+
+public class BranchChangesetCollectionToDtoMapper extends ChangesetCollectionToDtoMapperBase {
+
+ private final ResourceLinks resourceLinks;
+
+ @Inject
+ public BranchChangesetCollectionToDtoMapper(ChangesetToChangesetDtoMapper changesetToChangesetDtoMapper, ResourceLinks resourceLinks) {
+ super(changesetToChangesetDtoMapper);
+ this.resourceLinks = resourceLinks;
+ }
+
+ public CollectionDto map(int pageNumber, int pageSize, PageResult pageResult, Repository repository, String branch) {
+ return this.map(pageNumber, pageSize, pageResult, repository, () -> createSelfLink(repository, branch));
+ }
+
+ private String createSelfLink(Repository repository, String branch) {
+ return resourceLinks.branch().history(repository.getNamespaceAndName(), branch);
+ }
+}
diff --git a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/BranchRootResource.java b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/BranchRootResource.java
index 9763f11def..7414f5c21f 100644
--- a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/BranchRootResource.java
+++ b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/BranchRootResource.java
@@ -3,6 +3,7 @@ package sonia.scm.api.v2.resources;
import com.webcohesion.enunciate.metadata.rs.ResponseCode;
import com.webcohesion.enunciate.metadata.rs.StatusCodes;
import com.webcohesion.enunciate.metadata.rs.TypeHint;
+import sonia.scm.NotFoundException;
import sonia.scm.PageResult;
import sonia.scm.repository.Branches;
import sonia.scm.repository.Changeset;
@@ -32,14 +33,14 @@ public class BranchRootResource {
private final BranchToBranchDtoMapper branchToDtoMapper;
private final BranchCollectionToDtoMapper branchCollectionToDtoMapper;
- private final ChangesetCollectionToDtoMapper changesetCollectionToDtoMapper;
+ private final BranchChangesetCollectionToDtoMapper branchChangesetCollectionToDtoMapper;
@Inject
- public BranchRootResource(RepositoryServiceFactory serviceFactory, BranchToBranchDtoMapper branchToDtoMapper, BranchCollectionToDtoMapper branchCollectionToDtoMapper, ChangesetCollectionToDtoMapper changesetCollectionToDtoMapper) {
+ public BranchRootResource(RepositoryServiceFactory serviceFactory, BranchToBranchDtoMapper branchToDtoMapper, BranchCollectionToDtoMapper branchCollectionToDtoMapper, BranchChangesetCollectionToDtoMapper changesetCollectionToDtoMapper) {
this.serviceFactory = serviceFactory;
this.branchToDtoMapper = branchToDtoMapper;
this.branchCollectionToDtoMapper = branchCollectionToDtoMapper;
- this.changesetCollectionToDtoMapper = changesetCollectionToDtoMapper;
+ this.branchChangesetCollectionToDtoMapper = changesetCollectionToDtoMapper;
}
/**
@@ -98,6 +99,14 @@ public class BranchRootResource {
@DefaultValue("0") @QueryParam("page") int page,
@DefaultValue("10") @QueryParam("pageSize") int pageSize) throws Exception {
try (RepositoryService repositoryService = serviceFactory.create(new NamespaceAndName(namespace, name))) {
+ boolean branchExists = repositoryService.getBranchesCommand()
+ .getBranches()
+ .getBranches()
+ .stream()
+ .anyMatch(branch -> branchName.equals(branch.getName()));
+ if (!branchExists){
+ throw new NotFoundException("branch", branchName);
+ }
Repository repository = repositoryService.getRepository();
RepositoryPermissions.read(repository).check();
ChangesetPagingResult changesets = repositoryService.getLogCommand()
@@ -107,7 +116,7 @@ public class BranchRootResource {
.getChangesets();
if (changesets != null && changesets.getChangesets() != null) {
PageResult pageResult = new PageResult<>(changesets.getChangesets(), changesets.getTotal());
- return Response.ok(changesetCollectionToDtoMapper.map(page, pageSize, pageResult, repository)).build();
+ return Response.ok(branchChangesetCollectionToDtoMapper.map(page, pageSize, pageResult, repository, branchName)).build();
} else {
return Response.ok().build();
}
diff --git a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/ChangesetCollectionToDtoMapper.java b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/ChangesetCollectionToDtoMapper.java
index 2f7ac86e14..24ee9b0ce1 100644
--- a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/ChangesetCollectionToDtoMapper.java
+++ b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/ChangesetCollectionToDtoMapper.java
@@ -5,31 +5,22 @@ import sonia.scm.repository.Changeset;
import sonia.scm.repository.Repository;
import javax.inject.Inject;
-import java.util.Optional;
-import java.util.function.Supplier;
-public class ChangesetCollectionToDtoMapper extends PagedCollectionToDtoMapper {
+public class ChangesetCollectionToDtoMapper extends ChangesetCollectionToDtoMapperBase {
- private final ChangesetToChangesetDtoMapper changesetToChangesetDtoMapper;
- protected final ResourceLinks resourceLinks;
+ private final ResourceLinks resourceLinks;
@Inject
public ChangesetCollectionToDtoMapper(ChangesetToChangesetDtoMapper changesetToChangesetDtoMapper, ResourceLinks resourceLinks) {
- super("changesets");
- this.changesetToChangesetDtoMapper = changesetToChangesetDtoMapper;
+ super(changesetToChangesetDtoMapper);
this.resourceLinks = resourceLinks;
}
public CollectionDto map(int pageNumber, int pageSize, PageResult pageResult, Repository repository) {
- return this.map(pageNumber, pageSize, pageResult, repository, () -> createSelfLink(repository));
+ return super.map(pageNumber, pageSize, pageResult, repository, () -> createSelfLink(repository));
}
- public CollectionDto map(int pageNumber, int pageSize, PageResult pageResult, Repository repository, Supplier selfLinkSupplier) {
- return super.map(pageNumber, pageSize, pageResult, selfLinkSupplier.get(), Optional.empty(), changeset -> changesetToChangesetDtoMapper.map(changeset, repository));
- }
-
- protected String createSelfLink(Repository repository) {
+ private String createSelfLink(Repository repository) {
return resourceLinks.changeset().all(repository.getNamespace(), repository.getName());
}
}
-
diff --git a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/ChangesetCollectionToDtoMapperBase.java b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/ChangesetCollectionToDtoMapperBase.java
new file mode 100644
index 0000000000..e29a0a92b2
--- /dev/null
+++ b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/ChangesetCollectionToDtoMapperBase.java
@@ -0,0 +1,23 @@
+package sonia.scm.api.v2.resources;
+
+import sonia.scm.PageResult;
+import sonia.scm.repository.Changeset;
+import sonia.scm.repository.Repository;
+
+import java.util.Optional;
+import java.util.function.Supplier;
+
+class ChangesetCollectionToDtoMapperBase extends PagedCollectionToDtoMapper {
+
+ private final ChangesetToChangesetDtoMapper changesetToChangesetDtoMapper;
+
+ ChangesetCollectionToDtoMapperBase(ChangesetToChangesetDtoMapper changesetToChangesetDtoMapper) {
+ super("changesets");
+ this.changesetToChangesetDtoMapper = changesetToChangesetDtoMapper;
+ }
+
+ CollectionDto map(int pageNumber, int pageSize, PageResult pageResult, Repository repository, Supplier selfLinkSupplier) {
+ return super.map(pageNumber, pageSize, pageResult, selfLinkSupplier.get(), Optional.empty(), changeset -> changesetToChangesetDtoMapper.map(changeset, repository));
+ }
+}
+
diff --git a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/FileHistoryCollectionToDtoMapper.java b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/FileHistoryCollectionToDtoMapper.java
index 692b2f57b1..af7fb2ed83 100644
--- a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/FileHistoryCollectionToDtoMapper.java
+++ b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/FileHistoryCollectionToDtoMapper.java
@@ -6,19 +6,22 @@ import sonia.scm.repository.Repository;
import javax.inject.Inject;
-public class FileHistoryCollectionToDtoMapper extends ChangesetCollectionToDtoMapper {
+public class FileHistoryCollectionToDtoMapper extends ChangesetCollectionToDtoMapperBase {
+ private final ResourceLinks resourceLinks;
+
@Inject
public FileHistoryCollectionToDtoMapper(ChangesetToChangesetDtoMapper changesetToChangesetDtoMapper, ResourceLinks resourceLinks) {
- super(changesetToChangesetDtoMapper, resourceLinks);
+ super(changesetToChangesetDtoMapper);
+ this.resourceLinks = resourceLinks;
}
public CollectionDto map(int pageNumber, int pageSize, PageResult pageResult, Repository repository, String revision, String path) {
return super.map(pageNumber, pageSize, pageResult, repository, () -> createSelfLink(repository, revision, path));
}
- protected String createSelfLink(Repository repository, String revision, String path) {
- return super.resourceLinks.fileHistory().self(repository.getNamespace(), repository.getName(), revision, path);
+ private String createSelfLink(Repository repository, String revision, String path) {
+ return resourceLinks.fileHistory().self(repository.getNamespace(), repository.getName(), revision, path);
}
}
diff --git a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/PermissionRootResource.java b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/PermissionRootResource.java
index 2a587bc2fe..b7f6df8c2d 100644
--- a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/PermissionRootResource.java
+++ b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/PermissionRootResource.java
@@ -162,7 +162,7 @@ public class PermissionRootResource {
RepositoryPermissions.permissionWrite(repository).check();
String extractedPermissionName = getPermissionName(permissionName);
if (!isPermissionExist(new PermissionDto(extractedPermissionName, isGroupPermission(permissionName)), repository)) {
- throw new NotFoundException("the permission " + extractedPermissionName + " does not exist");
+ throw new NotFoundException("permission", extractedPermissionName);
}
permission.setGroupPermission(isGroupPermission(permissionName));
if (!extractedPermissionName.equals(permission.getName())) {
diff --git a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/TagToTagDtoMapper.java b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/TagToTagDtoMapper.java
index 917b4b7789..ee0488e037 100644
--- a/scm-webapp/src/main/java/sonia/scm/api/v2/resources/TagToTagDtoMapper.java
+++ b/scm-webapp/src/main/java/sonia/scm/api/v2/resources/TagToTagDtoMapper.java
@@ -28,7 +28,7 @@ public abstract class TagToTagDtoMapper {
Links.Builder linksBuilder = linkingTo()
.self(resourceLinks.tag().self(namespaceAndName.getNamespace(), namespaceAndName.getName(), target.getName()))
.single(link("sources", resourceLinks.source().self(namespaceAndName.getNamespace(), namespaceAndName.getName(), target.getRevision())))
- .single(link("changesets", resourceLinks.changeset().self(namespaceAndName.getNamespace(), namespaceAndName.getName(), target.getRevision())));
+ .single(link("changeset", resourceLinks.changeset().self(namespaceAndName.getNamespace(), namespaceAndName.getName(), target.getRevision())));
target.add(linksBuilder.build());
}
}
diff --git a/scm-webapp/src/test/java/sonia/scm/api/v2/resources/BranchRootResourceTest.java b/scm-webapp/src/test/java/sonia/scm/api/v2/resources/BranchRootResourceTest.java
index 13ed9cddcd..4994c11b08 100644
--- a/scm-webapp/src/test/java/sonia/scm/api/v2/resources/BranchRootResourceTest.java
+++ b/scm-webapp/src/test/java/sonia/scm/api/v2/resources/BranchRootResourceTest.java
@@ -67,7 +67,7 @@ public class BranchRootResourceTest extends RepositoryTestBase {
@InjectMocks
private BranchToBranchDtoMapperImpl branchToDtoMapper;
- private ChangesetCollectionToDtoMapper changesetCollectionToDtoMapper;
+ private BranchChangesetCollectionToDtoMapper changesetCollectionToDtoMapper;
private BranchRootResource branchRootResource;
@@ -90,7 +90,7 @@ public class BranchRootResourceTest extends RepositoryTestBase {
@Before
public void prepareEnvironment() throws Exception {
- changesetCollectionToDtoMapper = new ChangesetCollectionToDtoMapper(changesetToChangesetDtoMapper, resourceLinks);
+ changesetCollectionToDtoMapper = new BranchChangesetCollectionToDtoMapper(changesetToChangesetDtoMapper, resourceLinks);
BranchCollectionToDtoMapper branchCollectionToDtoMapper = new BranchCollectionToDtoMapper(branchToDtoMapper, resourceLinks);
branchRootResource = new BranchRootResource(serviceFactory, branchToDtoMapper, branchCollectionToDtoMapper, changesetCollectionToDtoMapper);
super.branchRootResource = Providers.of(branchRootResource);
@@ -152,6 +152,10 @@ public class BranchRootResourceTest extends RepositoryTestBase {
when(logCommandBuilder.setPagingLimit(anyInt())).thenReturn(logCommandBuilder);
when(logCommandBuilder.setBranch(anyString())).thenReturn(logCommandBuilder);
when(logCommandBuilder.getChangesets()).thenReturn(changesetPagingResult);
+ Branches branches = mock(Branches.class);
+ List branchList = Lists.newArrayList(new Branch("master",id));
+ when(branches.getBranches()).thenReturn(branchList);
+ when(branchesCommandBuilder.getBranches()).thenReturn(branches);
MockHttpRequest request = MockHttpRequest.get(BRANCH_URL + "/changesets/");
MockHttpResponse response = new MockHttpResponse();
dispatcher.invoke(request, response);
@@ -161,6 +165,5 @@ public class BranchRootResourceTest extends RepositoryTestBase {
assertTrue(response.getContentAsString().contains(String.format("\"name\":\"%s\"", authorName)));
assertTrue(response.getContentAsString().contains(String.format("\"mail\":\"%s\"", authorEmail)));
assertTrue(response.getContentAsString().contains(String.format("\"description\":\"%s\"", commit)));
- assertTrue(response.getContentAsString().contains(String.format("\"description\":\"%s\"", commit)));
}
}
diff --git a/scm-webapp/src/test/java/sonia/scm/repository/DefaultRepositoryManagerTest.java b/scm-webapp/src/test/java/sonia/scm/repository/DefaultRepositoryManagerTest.java
index b7d231cf38..a67c275bc0 100644
--- a/scm-webapp/src/test/java/sonia/scm/repository/DefaultRepositoryManagerTest.java
+++ b/scm-webapp/src/test/java/sonia/scm/repository/DefaultRepositoryManagerTest.java
@@ -38,6 +38,7 @@ import com.github.sdorra.shiro.SubjectAware;
import com.google.common.collect.ImmutableSet;
import com.google.common.collect.Sets;
import org.apache.shiro.authz.UnauthorizedException;
+import org.apache.shiro.util.ThreadContext;
import org.junit.Rule;
import org.junit.Test;
import org.junit.rules.ExpectedException;
@@ -94,6 +95,10 @@ import static org.mockito.Mockito.when;
)
public class DefaultRepositoryManagerTest extends ManagerTestBase {
+ {
+ ThreadContext.unbindSubject();
+ }
+
@Rule
public ShiroRule shiro = new ShiroRule();