diff --git a/src/main/java/com/faforever/api/data/domain/Login.java b/src/main/java/com/faforever/api/data/domain/Login.java index 2a6ae9893..b682475b0 100644 --- a/src/main/java/com/faforever/api/data/domain/Login.java +++ b/src/main/java/com/faforever/api/data/domain/Login.java @@ -3,7 +3,6 @@ import com.faforever.api.data.checks.IsLoginOwner; import com.yahoo.elide.annotation.ReadPermission; import lombok.Setter; -import org.hibernate.annotations.Formula; import javax.persistence.Column; import javax.persistence.FetchType; @@ -25,7 +24,6 @@ public abstract class Login { private String steamId; private String userAgent; private BanInfo banInfo; - private String lowerCaseLogin; @Id @GeneratedValue @@ -38,13 +36,6 @@ public String getLogin() { return login; } - // TODO review this, I think it's not needed since elide should (with a never version?) filter case insensitive - // Needed for filter, e.g. at the clan app - @Formula("LOWER(login)") - public String getLowerCaseLogin() { - return lowerCaseLogin; - } - @Column(name = "email") @ReadPermission(expression = IsLoginOwner.EXPRESSION) public String getEmail() { diff --git a/src/test/java/com/faforever/api/clan/ClanControllerIntegrationTest.java b/src/test/java/com/faforever/api/clan/ClanControllerIntegrationTest.java index b538686d4..357844335 100644 --- a/src/test/java/com/faforever/api/clan/ClanControllerIntegrationTest.java +++ b/src/test/java/com/faforever/api/clan/ClanControllerIntegrationTest.java @@ -1,28 +1,23 @@ package com.faforever.api.clan; -import com.faforever.api.client.ClientType; -import com.faforever.api.client.OAuthClient; import com.faforever.api.client.OAuthClientRepository; import com.faforever.api.data.domain.Clan; import com.faforever.api.data.domain.ClanMembership; import com.faforever.api.data.domain.Player; -import com.faforever.api.data.domain.User; import com.faforever.api.player.PlayerRepository; import com.faforever.api.user.UserRepository; -import org.codehaus.jackson.JsonNode; -import org.codehaus.jackson.map.ObjectMapper; +import com.faforever.integration.factories.PlayerFactory; +import com.faforever.integration.factories.SessionFactory; +import com.faforever.integration.factories.SessionFactory.Session; import org.junit.After; import org.junit.Before; -import org.junit.Ignore; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.boot.test.context.SpringBootTest; -import org.springframework.security.authentication.encoding.ShaPasswordEncoder; import org.springframework.test.context.junit4.SpringRunner; import org.springframework.test.web.servlet.MockMvc; import org.springframework.test.web.servlet.ResultActions; import org.springframework.test.web.servlet.setup.MockMvcBuilders; -import org.springframework.util.Base64Utils; import org.springframework.web.context.WebApplicationContext; import javax.inject.Inject; @@ -37,11 +32,7 @@ @RunWith(SpringRunner.class) @SpringBootTest -@Ignore("This needs to be cleaned up big time.") public class ClanControllerIntegrationTest { - private static final String OAUTH_CLIENT_ID = "1234"; - private static final String OAUTH_SECRET = "secret"; - private final ShaPasswordEncoder shaPasswordEncoder; private MockMvc mvc; private WebApplicationContext context; private Filter springSecurityFilterChain; @@ -50,13 +41,6 @@ public class ClanControllerIntegrationTest { private ClanMembershipRepository clanMembershipRepository; private PlayerRepository playerRepository; private OAuthClientRepository oAuthClientRepository; - private ObjectMapper objectMapper; - private Player me; - - public ClanControllerIntegrationTest() { - shaPasswordEncoder = new ShaPasswordEncoder(256); - objectMapper = new ObjectMapper(); - } @Inject public void init(WebApplicationContext context, @@ -83,6 +67,7 @@ public void setUp() { .build(); } + // Dragonfire: This duplicated code cannot be avoided, each test must cleanup all the used repositories @After public void tearDown() { clanMembershipRepository.deleteAll(); @@ -95,74 +80,36 @@ public void tearDown() { assertEquals(0, oAuthClientRepository.count()); } - public String createUserAndGetAccessToken(String login, String password) throws Exception { - OAuthClient client = new OAuthClient() - .setId(OAUTH_CLIENT_ID) - .setName("test") - .setClientSecret(OAUTH_SECRET) - .setRedirectUris("test") - .setDefaultRedirectUri("test") - .setDefaultScope("test") - .setClientType(ClientType.PUBLIC); - oAuthClientRepository.save(client); - - User user = (User) new User() - .setPassword(shaPasswordEncoder.encodePassword(password, null)) - .setLogin(login) - .setEmail(login + "@faforever.com"); - userRepository.save(user); - me = playerRepository.findOne(user.getId()); - - String authorization = "Basic " - + new String(Base64Utils.encode((OAUTH_CLIENT_ID + ":" + OAUTH_SECRET).getBytes())); - ResultActions auth = mvc - .perform( - post("/oauth/token") - .header("Authorization", authorization) - .param("username", login) - .param("password", password) - .param("grant_type", "password")); - auth.andExpect(status().isOk()); - JsonNode node = objectMapper.readTree(auth.andReturn().getResponse().getContentAsString()); - return "Bearer " + node.get("access_token").asText(); - } - - private Player createPlayer(String login) throws Exception { - User user = (User) new User() - .setPassword("foo") - .setLogin(login) - .setEmail(login + "@faforever.com"); - userRepository.save(user); - return playerRepository.findOne(user.getId()); - } - @Test public void meDataWithoutClan() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); + String expected = String.format("{\"player\":{\"id\":%s,\"login\":\"%s\"},\"clan\":null}", - me.getId(), - me.getLogin()); + session.getPlayer().getId(), + session.getPlayer().getLogin()); assertEquals(1, playerRepository.count()); this.mvc.perform(get("/clans/me/") - .header("Authorization", accessToken)) + .header("Authorization", session.getToken())) .andExpect(content().string(expected)) .andExpect(status().isOk()); } @Test public void meDataWithClan() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); - Clan clan = new Clan().setLeader(me).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("123").setName("abcClanName"); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); clan.setMemberships(Collections.singletonList(myMembership)); clanRepository.save(clan); String expected = String.format("{\"player\":{\"id\":%s,\"login\":\"%s\"},\"clan\":{\"id\":%s,\"tag\":\"%s\",\"name\":\"%s\"}}", - me.getId(), - me.getLogin(), + session.getPlayer().getId(), + session.getPlayer().getLogin(), clan.getId(), clan.getTag(), clan.getName()); @@ -171,14 +118,15 @@ public void meDataWithClan() throws Exception { assertEquals(1, clanRepository.count()); assertEquals(1, clanMembershipRepository.count()); this.mvc.perform(get("/clans/me/") - .header("Authorization", accessToken)) + .header("Authorization", session.getToken())) .andExpect(content().string(expected)) .andExpect(status().isOk()); } @Test public void createClan() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); String clanName = "My Cool ClanName"; String tag = "123"; String description = "spaces Must Be Encoded"; @@ -189,7 +137,7 @@ public void createClan() throws Exception { ResultActions action = this.mvc.perform(post( String.format("/clans/create?tag=%s&name=%s&description=%s", tag, clanName, description)) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); int id = clanRepository.findAll().get(0).getId(); @@ -202,13 +150,14 @@ public void createClan() throws Exception { @Test public void createSecondClan() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); String clanName = "My Cool ClanName"; String tag = "123"; String description = "spaces Must Be Encoded"; - Clan clan = new Clan().setLeader(me).setTag("tag").setName("abcClan"); - ClanMembership membership = new ClanMembership().setPlayer(me).setClan(clan); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("tag").setName("abcClan"); + ClanMembership membership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); clan.setMemberships(Collections.singletonList(membership)); clanRepository.save(clan); @@ -218,7 +167,7 @@ public void createSecondClan() throws Exception { ResultActions action = this.mvc.perform(post( String.format("/clans/create?tag=%s&name=%s&description=%s", tag, clanName, description)) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(content().string("{\"errors\":[{\"title\":\"You are already in a clan\",\"detail\":\"Clan creator is already member of a clan\"}]}")) .andExpect(status().is(422)); @@ -229,8 +178,9 @@ public void createSecondClan() throws Exception { @Test public void createClanWithSameName() throws Exception { - Player otherLeader = createPlayer("Downloard"); - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Player otherLeader = PlayerFactory.createPlayer("Downloard", userRepository, playerRepository); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); String clanName = "My Cool ClanName"; String tag = "123"; String description = "spaces Must Be Encoded"; @@ -246,7 +196,7 @@ public void createClanWithSameName() throws Exception { ResultActions action = this.mvc.perform(post( String.format("/clans/create?tag=%s&name=%s&description=%s", tag, clanName, description)) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(content().string("{\"errors\":[{\"title\":\"Clan Name already in use\",\"detail\":\"The clan name 'My Cool ClanName' is already in use. Please choose a different clan name.\"}]}")) .andExpect(status().is(422)); @@ -257,8 +207,9 @@ public void createClanWithSameName() throws Exception { @Test public void createClanWithSameTag() throws Exception { - Player otherLeader = createPlayer("Downlord"); - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Player otherLeader = PlayerFactory.createPlayer("Downloard", userRepository, playerRepository); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); String clanName = "My Cool ClanName"; String tag = "123"; String description = "spaces Must Be Encoded"; @@ -274,7 +225,7 @@ public void createClanWithSameTag() throws Exception { ResultActions action = this.mvc.perform(post( String.format("/clans/create?tag=%s&name=%s&description=%s", tag, clanName, description)) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(content().string("{\"errors\":[{\"title\":\"Clan Tag already in use\",\"detail\":\"The clan tag 'My Cool ClanName' is already in use. Please choose a different clan tag.\"}]}")) .andExpect(status().is(422)); diff --git a/src/test/java/com/faforever/api/data/JsonApiClanIntegrationTest.java b/src/test/java/com/faforever/api/data/JsonApiClanIntegrationTest.java index 8d3dac21e..031a7f86d 100644 --- a/src/test/java/com/faforever/api/data/JsonApiClanIntegrationTest.java +++ b/src/test/java/com/faforever/api/data/JsonApiClanIntegrationTest.java @@ -2,30 +2,27 @@ import com.faforever.api.clan.ClanMembershipRepository; import com.faforever.api.clan.ClanRepository; -import com.faforever.api.client.ClientType; -import com.faforever.api.client.OAuthClient; import com.faforever.api.client.OAuthClientRepository; import com.faforever.api.data.domain.Clan; import com.faforever.api.data.domain.ClanMembership; import com.faforever.api.data.domain.Player; -import com.faforever.api.data.domain.User; import com.faforever.api.player.PlayerRepository; import com.faforever.api.user.UserRepository; +import com.faforever.integration.factories.PlayerFactory; +import com.faforever.integration.factories.SessionFactory; +import com.faforever.integration.factories.SessionFactory.Session; import org.codehaus.jackson.JsonNode; import org.codehaus.jackson.map.ObjectMapper; import org.codehaus.jackson.node.ObjectNode; import org.junit.After; import org.junit.Before; -import org.junit.Ignore; import org.junit.Test; import org.junit.runner.RunWith; import org.springframework.boot.test.context.SpringBootTest; -import org.springframework.security.authentication.encoding.ShaPasswordEncoder; import org.springframework.test.context.junit4.SpringRunner; import org.springframework.test.web.servlet.MockMvc; import org.springframework.test.web.servlet.ResultActions; import org.springframework.test.web.servlet.setup.MockMvcBuilders; -import org.springframework.util.Base64Utils; import org.springframework.web.context.WebApplicationContext; import javax.inject.Inject; @@ -38,16 +35,13 @@ import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.delete; import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.get; import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.patch; -import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post; import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.content; import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status; @RunWith(SpringRunner.class) @SpringBootTest -@Ignore("This needs to be cleaned up big time.") public class JsonApiClanIntegrationTest { - private static final String OAUTH_CLIENT_ID = "1234"; - private static final String OAUTH_SECRET = "secret"; + private MockMvc mvc; private WebApplicationContext context; private Filter springSecurityFilterChain; @@ -56,13 +50,11 @@ public class JsonApiClanIntegrationTest { private ClanMembershipRepository clanMembershipRepository; private PlayerRepository playerRepository; private OAuthClientRepository oAuthClientRepository; + private ObjectMapper objectMapper; - private ShaPasswordEncoder shaPasswordEncoder; - private Player me; public JsonApiClanIntegrationTest() { objectMapper = new ObjectMapper(); - shaPasswordEncoder = new ShaPasswordEncoder(256); } @Inject @@ -88,10 +80,9 @@ public void setUp() { .webAppContextSetup(context) .addFilter(springSecurityFilterChain) .build(); - me = null; } - // TODO @Dragonfire clean up the duplicated code + // Dragonfire: This duplicated code cannot be avoided, each test must cleanup all the used repositories @After public void tearDown() { clanMembershipRepository.deleteAll(); @@ -104,60 +95,20 @@ public void tearDown() { assertEquals(0, oAuthClientRepository.count()); } - // TODO @Dragonfire clean up the duplicated code - public String createUserAndGetAccessToken(String login, String password) throws Exception { - OAuthClient client = new OAuthClient() - .setId(OAUTH_CLIENT_ID) - .setName("test") - .setClientSecret(OAUTH_SECRET) - .setRedirectUris("test") - .setDefaultRedirectUri("test") - .setDefaultScope("test") - .setClientType(ClientType.PUBLIC); - oAuthClientRepository.save(client); - - User user = (User) new User() - .setPassword(shaPasswordEncoder.encodePassword(password, null)) - .setLogin(login) - .setEmail(login + "@faforever.com"); - userRepository.save(user); - me = playerRepository.findOne(user.getId()); - - String authorization = "Basic " - + new String(Base64Utils.encode((OAUTH_CLIENT_ID + ":" + OAUTH_SECRET).getBytes())); - ResultActions auth = mvc - .perform( - post("/oauth/token") - .header("Authorization", authorization) - .param("username", login) - .param("password", password) - .param("grant_type", "password")); - auth.andExpect(status().isOk()); - JsonNode node = objectMapper.readTree(auth.andReturn().getResponse().getContentAsString()); - return "Bearer " + node.get("access_token").asText(); - } - - private Player createPlayer(String login) throws Exception { - User user = (User) new User() - .setPassword("foo") - .setLogin(login) - .setEmail(login + "@faforever.com"); - userRepository.save(user); - return playerRepository.findOne(user.getId()); - } @Test public void cannotKickLeaderFromClan() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); - Clan clan = new Clan().setLeader(me).setTag("123").setName("abcClanName"); - ClanMembership membership = new ClanMembership().setPlayer(me).setClan(clan); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("123").setName("abcClanName"); + ClanMembership membership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); clan.setMemberships(Collections.singletonList(membership)); clanRepository.save(clan); assertEquals(1, clanMembershipRepository.count()); this.mvc.perform(delete("/data/clanMembership/" + membership.getId()) - .header("Authorization", accessToken)) + .header("Authorization", session.getToken())) .andExpect(content().string("{\"errors\":[\"ForbiddenAccessException\"]}")) .andExpect(status().is(403)); assertEquals(1, clanMembershipRepository.count()); @@ -165,58 +116,60 @@ public void cannotKickLeaderFromClan() throws Exception { @Test public void cannotKickAsMember() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); - Player bob = createPlayer("Bob"); + Player bob = PlayerFactory.createPlayer("Bob", userRepository, playerRepository); Clan clan = new Clan().setLeader(bob).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); ClanMembership bobsMembership = new ClanMembership().setPlayer(bob).setClan(clan); clan.setMemberships(Arrays.asList(myMembership, bobsMembership)); clanRepository.save(clan); assertEquals(2, clanMembershipRepository.count()); this.mvc.perform(delete("/data/clanMembership/" + bobsMembership.getId()) - .header("Authorization", accessToken)) + .header("Authorization", session.getToken())) .andExpect(content().string("{\"errors\":[\"ForbiddenAccessException\"]}")) .andExpect(status().is(403)); assertEquals(2, clanMembershipRepository.count()); } - // TODO @Dragonfire clean up the duplicated code @Test public void canKickMember() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); - Player bob = createPlayer("Bob"); - Clan clan = new Clan().setLeader(me).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + Player bob = PlayerFactory.createPlayer("Bob", userRepository, playerRepository); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("123").setName("abcClanName"); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); ClanMembership bobsMembership = new ClanMembership().setPlayer(bob).setClan(clan); clan.setMemberships(Arrays.asList(myMembership, bobsMembership)); clanRepository.save(clan); assertEquals(2, clanMembershipRepository.count()); this.mvc.perform(delete("/data/clanMembership/" + bobsMembership.getId()) - .header("Authorization", accessToken)) + .header("Authorization", session.getToken())) .andExpect(status().is(204)); assertEquals(1, clanMembershipRepository.count()); assertEquals(myMembership.getId(), clanMembershipRepository.findAll().get(0).getId()); } - // TODO @Dragonfire clean up the duplicated code + @Test public void canLeaveClan() throws Exception { - String accessToken = createUserAndGetAccessToken("Dragonfire", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken( + oAuthClientRepository, userRepository, playerRepository, mvc); - Player bob = createPlayer("Bob"); + Player bob = PlayerFactory.createPlayer("Bob", userRepository, playerRepository); Clan clan = new Clan().setLeader(bob).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); ClanMembership bobsMembership = new ClanMembership().setPlayer(bob).setClan(clan); clan.setMemberships(Arrays.asList(myMembership, bobsMembership)); clanRepository.save(clan); assertEquals(2, clanMembershipRepository.count()); this.mvc.perform(delete("/data/clanMembership/" + myMembership.getId()) - .header("Authorization", accessToken)) + .header("Authorization", session.getToken())) .andExpect(status().is(204)); assertEquals(1, clanMembershipRepository.count()); assertEquals(bobsMembership.getId(), clanMembershipRepository.findAll().get(0).getId()); @@ -225,9 +178,9 @@ public void canLeaveClan() throws Exception { @Test public void getFilteredPlayerForClanInvite() throws Exception { String[] players = new String[]{"Dragonfire", "DRAGON", "Fire of Dragon", "d r a g o n", "firedragon"}; - Arrays.stream(players).forEach(name -> noCatch(() -> createPlayer(name))); + Arrays.stream(players).forEach(name -> noCatch(() -> PlayerFactory.createPlayer(name, userRepository, playerRepository))); assertEquals(players.length, playerRepository.count()); - ResultActions action = this.mvc.perform(get("/data/player?filter=lowerCaseLogin==dragon*&sort=lowerCaseLogin")); + ResultActions action = this.mvc.perform(get("/data/player?filter=login==dragon*&sort=login")); JsonNode node = objectMapper.readTree(action.andReturn().getResponse().getContentAsString()); @@ -259,11 +212,12 @@ private String generateTransferLeadershipContent(int clanId, int newLeaderId) th @Test public void transferLeadership() throws Exception { - String accessToken = createUserAndGetAccessToken("Leader", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken("Leader", "foo", + oAuthClientRepository, userRepository, playerRepository, mvc); - Player bob = createPlayer("Bob"); - Clan clan = new Clan().setLeader(me).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + Player bob = PlayerFactory.createPlayer("Bob", userRepository, playerRepository); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("123").setName("abcClanName"); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); ClanMembership bobsMembership = new ClanMembership().setPlayer(bob).setClan(clan); clan.setMemberships(Arrays.asList(myMembership, bobsMembership)); clanRepository.save(clan); @@ -271,11 +225,11 @@ public void transferLeadership() throws Exception { String dataString = generateTransferLeadershipContent(clan.getId(), bob.getId()); clan = clanRepository.findOne(clan.getId()); - assertEquals(me.getId(), clan.getLeader().getId()); + assertEquals(session.getPlayer().getId(), clan.getLeader().getId()); ResultActions action = this.mvc.perform(patch("/data/clan/" + clan.getId()) .content(dataString) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(content().string("")) .andExpect(status().is(204)); @@ -285,47 +239,49 @@ public void transferLeadership() throws Exception { @Test public void transferLeadershipToOldLeader() throws Exception { - String accessToken = createUserAndGetAccessToken("Leader", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken("Leader", "foo", + oAuthClientRepository, userRepository, playerRepository, mvc); - Clan clan = new Clan().setLeader(me).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("123").setName("abcClanName"); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); clan.setMemberships(Collections.singletonList(myMembership)); clanRepository.save(clan); - String dataString = generateTransferLeadershipContent(clan.getId(), me.getId()); + String dataString = generateTransferLeadershipContent(clan.getId(), session.getPlayer().getId()); clan = clanRepository.findOne(clan.getId()); - assertEquals(me.getId(), clan.getLeader().getId()); + assertEquals(session.getPlayer().getId(), clan.getLeader().getId()); ResultActions action = this.mvc.perform(patch("/data/clan/" + clan.getId()) .content(dataString) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(content().string("")) .andExpect(status().is(204)); clan = clanRepository.findOne(clan.getId()); - assertEquals(me.getId(), clan.getLeader().getId()); + assertEquals(session.getPlayer().getId(), clan.getLeader().getId()); } @Test public void transferLeadershipToNonClanMember() throws Exception { - String accessToken = createUserAndGetAccessToken("Leader", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken("Leader", "foo", + oAuthClientRepository, userRepository, playerRepository, mvc); - Player bob = createPlayer("Bob"); + Player bob = PlayerFactory.createPlayer("Bob", userRepository, playerRepository); - Clan clan = new Clan().setLeader(me).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("123").setName("abcClanName"); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); clan.setMemberships(Collections.singletonList(myMembership)); clanRepository.save(clan); String dataString = generateTransferLeadershipContent(clan.getId(), bob.getId()); clan = clanRepository.findOne(clan.getId()); - assertEquals(me.getId(), clan.getLeader().getId()); + assertEquals(session.getPlayer().getId(), clan.getLeader().getId()); ResultActions action = this.mvc.perform(patch("/data/clan/" + clan.getId()) .content(dataString) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(status().is(422)); JsonNode resultNode = objectMapper.readTree(action.andReturn().getResponse().getContentAsString()); @@ -333,18 +289,19 @@ public void transferLeadershipToNonClanMember() throws Exception { assertEquals("Validation failed", resultNode.get("errors").get(0).get("title").asText()); clan = clanRepository.findOne(clan.getId()); - assertEquals(me.getId(), clan.getLeader().getId()); + assertEquals(session.getPlayer().getId(), clan.getLeader().getId()); } @Test public void transferLeadershipAsNonLeader() throws Exception { - String accessToken = createUserAndGetAccessToken("Leader", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken("Leader", "foo", + oAuthClientRepository, userRepository, playerRepository, mvc); - Player bob = createPlayer("Bob"); - Player charlie = createPlayer("Charlie"); + Player bob = PlayerFactory.createPlayer("Bob", userRepository, playerRepository); + Player charlie = PlayerFactory.createPlayer("Charlie", userRepository, playerRepository); Clan clan = new Clan().setLeader(bob).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); ClanMembership bobsMembership = new ClanMembership().setPlayer(bob).setClan(clan); ClanMembership charlieMembership = new ClanMembership().setPlayer(charlie).setClan(clan); clan.setMemberships(Arrays.asList(myMembership, bobsMembership, charlieMembership)); @@ -357,7 +314,7 @@ public void transferLeadershipAsNonLeader() throws Exception { ResultActions action = this.mvc.perform(patch("/data/clan/" + clan.getId()) .content(dataString) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(content().string("{\"errors\":[\"ForbiddenAccessException\"]}")) .andExpect(status().is(403)); @@ -367,18 +324,19 @@ public void transferLeadershipAsNonLeader() throws Exception { @Test public void deleteClan() throws Exception { - String accessToken = createUserAndGetAccessToken("Leader", "foo"); + Session session = SessionFactory.createUserAndGetAccessToken("Leader", "foo", + oAuthClientRepository, userRepository, playerRepository, mvc); - Clan clan = new Clan().setLeader(me).setTag("123").setName("abcClanName"); - ClanMembership myMembership = new ClanMembership().setPlayer(me).setClan(clan); + Clan clan = new Clan().setLeader(session.getPlayer()).setTag("123").setName("abcClanName"); + ClanMembership myMembership = new ClanMembership().setPlayer(session.getPlayer()).setClan(clan); clan.setMemberships(Collections.singletonList(myMembership)); clanRepository.save(clan); clan = clanRepository.findOne(clan.getId()); - assertEquals(me.getId(), clan.getLeader().getId()); + assertEquals(session.getPlayer().getId(), clan.getLeader().getId()); ResultActions action = this.mvc.perform(delete("/data/clan/" + clan.getId()) - .header("Authorization", accessToken)); + .header("Authorization", session.getToken())); action.andExpect(content().string("")) .andExpect(status().is(204)); diff --git a/src/test/java/com/faforever/integration/factories/PlayerFactory.java b/src/test/java/com/faforever/integration/factories/PlayerFactory.java new file mode 100644 index 000000000..e872ceaa2 --- /dev/null +++ b/src/test/java/com/faforever/integration/factories/PlayerFactory.java @@ -0,0 +1,17 @@ +package com.faforever.integration.factories; + +import com.faforever.api.data.domain.Player; +import com.faforever.api.data.domain.User; +import com.faforever.api.player.PlayerRepository; +import com.faforever.api.user.UserRepository; + +public class PlayerFactory { + public static Player createPlayer(String login, UserRepository userRepository, PlayerRepository playerRepository) throws Exception { + User user = (User) new User() + .setPassword("foo") + .setLogin(login) + .setEmail(login + "@faforever.com"); + userRepository.save(user); + return playerRepository.findOne(user.getId()); + } +} diff --git a/src/test/java/com/faforever/integration/factories/SessionFactory.java b/src/test/java/com/faforever/integration/factories/SessionFactory.java new file mode 100644 index 000000000..c9788acca --- /dev/null +++ b/src/test/java/com/faforever/integration/factories/SessionFactory.java @@ -0,0 +1,90 @@ +package com.faforever.integration.factories; + +import com.faforever.api.client.ClientType; +import com.faforever.api.client.OAuthClient; +import com.faforever.api.client.OAuthClientRepository; +import com.faforever.api.data.domain.Player; +import com.faforever.api.data.domain.User; +import com.faforever.api.player.PlayerRepository; +import com.faforever.api.user.UserRepository; +import lombok.Data; +import lombok.SneakyThrows; +import org.codehaus.jackson.JsonNode; +import org.codehaus.jackson.map.ObjectMapper; +import org.junit.Assert; +import org.springframework.security.authentication.encoding.ShaPasswordEncoder; +import org.springframework.test.web.servlet.MockMvc; +import org.springframework.test.web.servlet.ResultActions; +import org.springframework.util.Base64Utils; + +import static org.junit.Assert.assertEquals; +import static org.springframework.test.web.servlet.request.MockMvcRequestBuilders.post; +import static org.springframework.test.web.servlet.result.MockMvcResultMatchers.status; + +public class SessionFactory { + + private static final String OAUTH_CLIENT_ID = "1234"; + private static final String OAUTH_SECRET = "secret"; + + private static ObjectMapper objectMapper = new ObjectMapper(); + private static ShaPasswordEncoder shaPasswordEncoder = new ShaPasswordEncoder(256); + + @SneakyThrows + public static Session createUserAndGetAccessToken(OAuthClientRepository oAuthClientRepository, + UserRepository userRepository, + PlayerRepository playerRepository, + MockMvc mvc) { + return createUserAndGetAccessToken("Dragonfire", "foo", + oAuthClientRepository, userRepository, playerRepository, mvc); + } + + @SneakyThrows + public static Session createUserAndGetAccessToken(String login, + String password, + OAuthClientRepository oAuthClientRepository, + UserRepository userRepository, + PlayerRepository playerRepository, + MockMvc mvc) { + OAuthClient client = new OAuthClient() + .setId(OAUTH_CLIENT_ID) + .setName("test") + .setClientSecret(OAUTH_SECRET) + .setRedirectUris("test") + .setDefaultRedirectUri("test") + .setDefaultScope("test") + .setClientType(ClientType.PUBLIC); + oAuthClientRepository.save(client); + + long userCounter = userRepository.count(); + User user = (User) new User() + .setPassword(shaPasswordEncoder.encodePassword(password, null)) + .setLogin(login) + .setEmail(login + "@faforever.com"); + userRepository.save(user); + assertEquals((userCounter + 1), userRepository.count()); + + Player player = playerRepository.findOne(user.getId()); + Assert.assertNotNull(player); + + String authorization = "Basic " + + new String(Base64Utils.encode((OAUTH_CLIENT_ID + ":" + OAUTH_SECRET).getBytes())); + ResultActions auth = mvc + .perform( + post("/oauth/token") + .header("Authorization", authorization) + .param("username", login) + .param("password", password) + .param("grant_type", "password")); + auth.andExpect(status().isOk()); + JsonNode node = objectMapper.readTree(auth.andReturn().getResponse().getContentAsString()); + String token = node.get("access_token").asText(); + Assert.assertNotEquals("", token); + return new Session().setPlayer(player).setToken("Bearer " + token); + } + + @Data + public static class Session { + private Player player; + private String Token; + } +} diff --git a/src/test/resources/config/application.yml b/src/test/resources/config/application.yml index c6bbccfd8..8bf66d789 100644 --- a/src/test/resources/config/application.yml +++ b/src/test/resources/config/application.yml @@ -15,6 +15,13 @@ spring: console: enabled: true +security: + oauth2: + resource: + filter-order: 3 + faf-api: jwt: secret: banana + clan: + website-url-format: "http://example.com/%s"