diff --git a/src/main/java/com/faforever/api/clan/result/ClanResult.java b/src/main/java/com/faforever/api/clan/result/ClanResult.java index 693faa8d8..5d5fc8618 100644 --- a/src/main/java/com/faforever/api/clan/result/ClanResult.java +++ b/src/main/java/com/faforever/api/clan/result/ClanResult.java @@ -5,7 +5,7 @@ @Data public class ClanResult { - private final int id; + private final Integer id; private final String tag; private final String name; diff --git a/src/main/java/com/faforever/api/clan/result/PlayerResult.java b/src/main/java/com/faforever/api/clan/result/PlayerResult.java index fa4d4cfb5..8328d73e8 100644 --- a/src/main/java/com/faforever/api/clan/result/PlayerResult.java +++ b/src/main/java/com/faforever/api/clan/result/PlayerResult.java @@ -5,7 +5,7 @@ @Data public class PlayerResult { - private final int id; + private final Integer id; private final String login; public static PlayerResult of(Player newMember) { diff --git a/src/main/java/com/faforever/api/data/domain/AbstractEntity.java b/src/main/java/com/faforever/api/data/domain/AbstractEntity.java index d3b58325e..82979700b 100644 --- a/src/main/java/com/faforever/api/data/domain/AbstractEntity.java +++ b/src/main/java/com/faforever/api/data/domain/AbstractEntity.java @@ -14,14 +14,14 @@ @Setter @EqualsAndHashCode(of = "id") public abstract class AbstractEntity { - protected int id; + protected Integer id; protected OffsetDateTime createTime; protected OffsetDateTime updateTime; @Id @GeneratedValue(strategy = GenerationType.IDENTITY) @Column(name = "id") - public int getId() { + public Integer getId() { return id; } diff --git a/src/main/java/com/faforever/api/user/MeController.java b/src/main/java/com/faforever/api/user/MeController.java index 48ac39826..92a45fd48 100644 --- a/src/main/java/com/faforever/api/user/MeController.java +++ b/src/main/java/com/faforever/api/user/MeController.java @@ -1,37 +1,91 @@ package com.faforever.api.user; +import com.faforever.api.data.domain.Player; +import com.faforever.api.data.domain.UserGroup; +import com.faforever.api.player.PlayerService; import com.faforever.api.security.FafUserDetails; +import com.faforever.api.web.JsonApiSingleResource; import io.swagger.annotations.ApiOperation; import io.swagger.annotations.ApiResponse; -import io.swagger.annotations.ApiResponses; +import lombok.Builder; +import lombok.Value; import org.springframework.security.access.annotation.Secured; +import org.springframework.security.core.GrantedAuthority; import org.springframework.security.core.annotation.AuthenticationPrincipal; import org.springframework.web.bind.annotation.RequestMapping; import org.springframework.web.bind.annotation.RequestMethod; import org.springframework.web.bind.annotation.RestController; -import javax.servlet.http.HttpServletRequest; -import javax.servlet.http.HttpServletResponse; -import java.io.IOException; -import java.util.Objects; +import java.util.Set; +import java.util.stream.Collectors; /** * Provides the route {@code /me} which returns the currently logged in user's information. */ @RestController public class MeController { + private final PlayerService playerService; + + public MeController(PlayerService playerService) { + this.playerService = playerService; + } @RequestMapping(method = RequestMethod.GET, value = "/me") - @ApiOperation(value = "Returns the authentication object of the current user") - @ApiResponses(value = { - @ApiResponse(code = 200, message = "Success with JSON { id: ?, type: 'player'}"), - @ApiResponse(code = 400, message = "Bad Request")}) - @Secured({"ROLE_USER"}) - public void me(HttpServletRequest request, - HttpServletResponse response, - @AuthenticationPrincipal FafUserDetails authentication) throws IOException { - // TODO: Find a better way to call elide player route - - response.sendRedirect(String.format("/data/player/%d?%s", authentication.getId(), Objects.toString(request.getQueryString(), ""))); + @ApiOperation("Returns the authentication object of the current user") + @ApiResponse(code = 200, message = "Success with JsonApi compliant MeResult") + @Secured("ROLE_USER") + public JsonApiSingleResource me(@AuthenticationPrincipal FafUserDetails authentication) { + + Player player = playerService.getById(authentication.getId()); + Set grantedAuthorities = authentication.getAuthorities().stream() + .map(GrantedAuthority::getAuthority) + .collect(Collectors.toSet()); + + Set groups = player.getUserGroups().stream() + .map(UserGroup::getTechnicalName) + .collect(Collectors.toSet()); + + return MeResult.builder() + .userId(player.getId()) + .userName(player.getLogin()) + .email(player.getEmail()) + .clan(player.getClan() == null ? null : Clan.builder() + .id(player.getClan().getId()) + .tag(player.getClan().getTag()) + .name(player.getClan().getName()) + .build() + ) + .groups(groups) + .permissions(grantedAuthorities) + .build() + .asJsonApi(); + } + + @Value + @Builder + public static class MeResult { + Integer userId; + String userName; + String email; + Clan clan; + Set groups; + Set permissions; + + @SuppressWarnings("unchecked") + JsonApiSingleResource asJsonApi() { + return JsonApiSingleResource.ofProxy( + () -> "me", + () -> "me", + () -> this + ); + } + } + + @Value + @Builder + public static class Clan { + Integer id; + String tag; + String name; } } diff --git a/src/main/java/com/faforever/api/web/JsonApiResourceObject.java b/src/main/java/com/faforever/api/web/JsonApiResourceObject.java new file mode 100644 index 000000000..8d2040152 --- /dev/null +++ b/src/main/java/com/faforever/api/web/JsonApiResourceObject.java @@ -0,0 +1,9 @@ +package com.faforever.api.web; + +public interface JsonApiResourceObject { + String getType(); + + String getId(); + + Object getAttributes(); +} diff --git a/src/main/java/com/faforever/api/web/JsonApiResourceObjectProxy.java b/src/main/java/com/faforever/api/web/JsonApiResourceObjectProxy.java new file mode 100644 index 000000000..53778a5b1 --- /dev/null +++ b/src/main/java/com/faforever/api/web/JsonApiResourceObjectProxy.java @@ -0,0 +1,27 @@ +package com.faforever.api.web; + +import java.util.function.Supplier; + +class JsonApiResourceObjectProxy implements JsonApiResourceObject { + private final Supplier typeExtractor; + private final Supplier idExtractor; + private final Supplier attributesExtractor; + + JsonApiResourceObjectProxy(Supplier typeExtractor, Supplier idExtractor, Supplier attributesExtractor) { + this.typeExtractor = typeExtractor; + this.idExtractor = idExtractor; + this.attributesExtractor = attributesExtractor; + } + + public String getType() { + return typeExtractor.get(); + } + + public String getId() { + return idExtractor.get(); + } + + public T getAttributes() { + return attributesExtractor.get(); + } +} diff --git a/src/main/java/com/faforever/api/web/JsonApiSingleResource.java b/src/main/java/com/faforever/api/web/JsonApiSingleResource.java new file mode 100644 index 000000000..ef206ec07 --- /dev/null +++ b/src/main/java/com/faforever/api/web/JsonApiSingleResource.java @@ -0,0 +1,19 @@ +package com.faforever.api.web; + +import lombok.Value; + +import java.util.function.Supplier; + +@Value +public class JsonApiSingleResource { + JsonApiResourceObject data; + + public static JsonApiSingleResource of(JsonApiResourceObject singleDataObject) { + return new JsonApiSingleResource(singleDataObject); + } + + public static JsonApiSingleResource ofProxy(Supplier typeExtractor, Supplier idExtractor, + Supplier attributesExtractor) { + return new JsonApiSingleResource(new JsonApiResourceObjectProxy<>(typeExtractor, idExtractor, attributesExtractor)); + } +}