Added SteamAPI and achievement searching
This commit is contained in:
parent
b229ff9a15
commit
627cc810ed
61 changed files with 2781 additions and 903 deletions
|
@ -4,11 +4,15 @@ import achievements.misc.DbConnection;
|
|||
import org.springframework.boot.SpringApplication;
|
||||
import org.springframework.boot.autoconfigure.SpringBootApplication;
|
||||
import org.springframework.boot.autoconfigure.security.servlet.SecurityAutoConfiguration;
|
||||
import org.springframework.boot.web.client.RestTemplateBuilder;
|
||||
import org.springframework.context.annotation.Bean;
|
||||
import org.springframework.scheduling.annotation.EnableScheduling;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
import org.springframework.web.servlet.config.annotation.CorsRegistry;
|
||||
import org.springframework.web.servlet.config.annotation.WebMvcConfigurer;
|
||||
|
||||
import java.time.Duration;
|
||||
|
||||
@SpringBootApplication(exclude = SecurityAutoConfiguration.class)
|
||||
@EnableScheduling
|
||||
public class Application {
|
||||
|
@ -34,4 +38,9 @@ public class Application {
|
|||
}
|
||||
};
|
||||
}
|
||||
|
||||
@Bean
|
||||
public RestTemplate restTemplate() {
|
||||
return new RestTemplate();
|
||||
}
|
||||
}
|
17
backend/src/main/java/achievements/apis/PlatformAPI.java
Normal file
17
backend/src/main/java/achievements/apis/PlatformAPI.java
Normal file
|
@ -0,0 +1,17 @@
|
|||
package achievements.apis;
|
||||
|
||||
import achievements.data.APIResponse;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
public abstract class PlatformAPI {
|
||||
|
||||
protected int id;
|
||||
protected RestTemplate rest;
|
||||
|
||||
protected PlatformAPI(int id, RestTemplate rest) {
|
||||
this.id = id;
|
||||
this.rest = rest;
|
||||
}
|
||||
|
||||
public abstract APIResponse get(String userId);
|
||||
}
|
102
backend/src/main/java/achievements/apis/SteamAPI.java
Normal file
102
backend/src/main/java/achievements/apis/SteamAPI.java
Normal file
|
@ -0,0 +1,102 @@
|
|||
package achievements.apis;
|
||||
|
||||
import achievements.apis.steam.GetOwnedGameBody;
|
||||
import achievements.apis.steam.GetPlayerAchievementsBody;
|
||||
import achievements.apis.steam.GetSchemaForGameBody;
|
||||
import achievements.data.APIResponse;
|
||||
import org.springframework.http.HttpEntity;
|
||||
import org.springframework.http.HttpHeaders;
|
||||
import org.springframework.http.HttpMethod;
|
||||
import org.springframework.http.MediaType;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
import org.springframework.web.util.UriComponentsBuilder;
|
||||
|
||||
import java.io.FileInputStream;
|
||||
import java.io.IOException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.Arrays;
|
||||
import java.util.HashMap;
|
||||
import java.util.Properties;
|
||||
|
||||
public class SteamAPI extends PlatformAPI {
|
||||
|
||||
private String apiKey;
|
||||
|
||||
public SteamAPI(int id, RestTemplate rest) {
|
||||
super(id, rest);
|
||||
try {
|
||||
var file = new FileInputStream("storage/apis/" + id + ".properties");
|
||||
var properties = new Properties();
|
||||
properties.load(file);
|
||||
|
||||
apiKey = properties.getProperty("api-key");
|
||||
file.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
|
||||
@Override
|
||||
public APIResponse get(String userId) {
|
||||
var headers = new HttpHeaders();
|
||||
headers.setAccept(Arrays.asList(MediaType.APPLICATION_JSON));
|
||||
var entity = new HttpEntity<String>(headers);
|
||||
var ownedGamesUrl = UriComponentsBuilder.fromHttpUrl("http://api.steampowered.com/IPlayerService/GetOwnedGames/v1/")
|
||||
.queryParam("key", apiKey)
|
||||
.queryParam("steamid", userId)
|
||||
.queryParam("include_appinfo", true)
|
||||
.queryParam("include_played_free_games", true)
|
||||
.toUriString();
|
||||
|
||||
var gameSchemaBaseUrl = UriComponentsBuilder.fromHttpUrl("https://api.steampowered.com/ISteamUserStats/GetSchemaForGame/v2/")
|
||||
.queryParam("key", apiKey);
|
||||
var playerAchievementsBaseUrl = UriComponentsBuilder.fromHttpUrl("https://api.steampowered.com/ISteamUserStats/GetPlayerAchievements/v1/")
|
||||
.queryParam("key", apiKey)
|
||||
.queryParam("steamid", userId);
|
||||
|
||||
var games = new ArrayList<APIResponse.Game>();
|
||||
var ownedResponse = rest.exchange(ownedGamesUrl, HttpMethod.GET, entity, GetOwnedGameBody.class).getBody();
|
||||
for (var game : ownedResponse.getResponse().getGames()) {
|
||||
var newGame = new APIResponse.Game();
|
||||
newGame.setPlatformGameId(Integer.toString(game.getAppid()));
|
||||
newGame.setName(game.getName());
|
||||
newGame.setThumbnail("https://cdn.cloudflare.steamstatic.com/steamcommunity/public/images/apps/" + game.getAppid() + "/" + game.getImg_logo_url() + ".jpg");
|
||||
newGame.setPlayed(game.getPlaytime_forever() > 0);
|
||||
|
||||
var achievements = new HashMap<String, APIResponse.Game.Achievement>();
|
||||
|
||||
var gameSchemaUrl = gameSchemaBaseUrl.cloneBuilder()
|
||||
.queryParam("appid", game.getAppid())
|
||||
.toUriString();
|
||||
var playerAchievementsUrl = playerAchievementsBaseUrl.cloneBuilder()
|
||||
.queryParam("appid", game.getAppid())
|
||||
.toUriString();
|
||||
|
||||
|
||||
var schemaResponse = rest.exchange(gameSchemaUrl, HttpMethod.GET, entity, GetSchemaForGameBody.class).getBody().getGame().getAvailableGameStats();
|
||||
if (schemaResponse != null && schemaResponse.getAchievements() != null) {
|
||||
for (var schema : schemaResponse.getAchievements()) {
|
||||
var achievement = new APIResponse.Game.Achievement();
|
||||
achievement.setName(schema.getDisplayName());
|
||||
achievement.setDescription(schema.getDescription());
|
||||
achievement.setStages(1);
|
||||
achievement.setThumbnail(schema.getIcon());
|
||||
achievements.put(schema.getName(), achievement);
|
||||
}
|
||||
|
||||
var playerAchievementsResponse = rest.exchange(playerAchievementsUrl, HttpMethod.GET, entity, GetPlayerAchievementsBody.class).getBody().getPlayerstats().getAchievements();
|
||||
for (var achievement : playerAchievementsResponse) {
|
||||
achievements.get(achievement.getApiname()).setProgress(achievement.getAchieved());
|
||||
}
|
||||
|
||||
newGame.setAchievements(new ArrayList<>(achievements.values()));
|
||||
if (newGame.getAchievements().size() > 0) {
|
||||
games.add(newGame);
|
||||
}
|
||||
}
|
||||
}
|
||||
var response = new APIResponse();
|
||||
response.setGames(games);
|
||||
return response;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,96 @@
|
|||
package achievements.apis.steam;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class GetOwnedGameBody {
|
||||
|
||||
public static class Response {
|
||||
|
||||
public static class Game {
|
||||
@JsonProperty("appid")
|
||||
private int appid;
|
||||
@JsonProperty("name")
|
||||
private String name;
|
||||
@JsonProperty("playtime_forever")
|
||||
private int playtime_forever;
|
||||
@JsonProperty("img_icon_url")
|
||||
private String img_icon_url;
|
||||
@JsonProperty("img_logo_url")
|
||||
private String img_logo_url;
|
||||
|
||||
public int getAppid() {
|
||||
return appid;
|
||||
}
|
||||
|
||||
public void setAppid(int appid) {
|
||||
this.appid = appid;
|
||||
}
|
||||
|
||||
public int getPlaytime_forever() {
|
||||
return playtime_forever;
|
||||
}
|
||||
|
||||
public void setPlaytime_forever(int playtime_forever) {
|
||||
this.playtime_forever = playtime_forever;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public String getImg_icon_url() {
|
||||
return img_icon_url;
|
||||
}
|
||||
|
||||
public void setImg_icon_url(String img_icon_url) {
|
||||
this.img_icon_url = img_icon_url;
|
||||
}
|
||||
|
||||
public String getImg_logo_url() {
|
||||
return img_logo_url;
|
||||
}
|
||||
|
||||
public void setImg_logo_url(String img_logo_url) {
|
||||
this.img_logo_url = img_logo_url;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("game_count")
|
||||
private int game_count;
|
||||
@JsonProperty("games")
|
||||
private List<Game> games;
|
||||
|
||||
public int getGame_count() {
|
||||
return game_count;
|
||||
}
|
||||
|
||||
public void setGame_count(int game_count) {
|
||||
this.game_count = game_count;
|
||||
}
|
||||
|
||||
public List<Game> getGames() {
|
||||
return games;
|
||||
}
|
||||
|
||||
public void setGames(List<Game> games) {
|
||||
this.games = games;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("response")
|
||||
private Response response;
|
||||
|
||||
public Response getResponse() {
|
||||
return response;
|
||||
}
|
||||
|
||||
public void setResponse(Response response) {
|
||||
this.response = response;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,54 @@
|
|||
package achievements.apis.steam;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class GetPlayerAchievementsBody {
|
||||
public static class PlayerStats {
|
||||
public static class Achievement {
|
||||
@JsonProperty("apiname")
|
||||
private String apiname;
|
||||
@JsonProperty("achieved")
|
||||
private int achieved;
|
||||
|
||||
public String getApiname() {
|
||||
return apiname;
|
||||
}
|
||||
|
||||
public void setApiname(String apiname) {
|
||||
this.apiname = apiname;
|
||||
}
|
||||
|
||||
public int getAchieved() {
|
||||
return achieved;
|
||||
}
|
||||
|
||||
public void setAchieved(int achieved) {
|
||||
this.achieved = achieved;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("achievements")
|
||||
private List<Achievement> achievements;
|
||||
|
||||
public List<Achievement> getAchievements() {
|
||||
return achievements;
|
||||
}
|
||||
|
||||
public void setAchievements(List<Achievement> achievements) {
|
||||
this.achievements = achievements;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("playerstats")
|
||||
private PlayerStats playerstats;
|
||||
|
||||
public PlayerStats getPlayerstats() {
|
||||
return playerstats;
|
||||
}
|
||||
|
||||
public void setPlayerstats(PlayerStats playerstats) {
|
||||
this.playerstats = playerstats;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,87 @@
|
|||
package achievements.apis.steam;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class GetSchemaForGameBody {
|
||||
public static class Game {
|
||||
public static class GameStats {
|
||||
public static class Achievement {
|
||||
@JsonProperty("name")
|
||||
private String name;
|
||||
@JsonProperty("displayName")
|
||||
private String displayName;
|
||||
@JsonProperty("description")
|
||||
private String description;
|
||||
@JsonProperty("icon")
|
||||
private String icon;
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public String getDisplayName() {
|
||||
return displayName;
|
||||
}
|
||||
|
||||
public void setDisplayName(String displayName) {
|
||||
this.displayName = displayName;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
public String getIcon() {
|
||||
return icon;
|
||||
}
|
||||
|
||||
public void setIcon(String icon) {
|
||||
this.icon = icon;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("achievements")
|
||||
private List<Achievement> achievements;
|
||||
|
||||
public List<Achievement> getAchievements() {
|
||||
return achievements;
|
||||
}
|
||||
|
||||
public void setAchievements(List<Achievement> achievements) {
|
||||
this.achievements = achievements;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("availableGameStats")
|
||||
private GameStats availableGameStats;
|
||||
|
||||
public GameStats getAvailableGameStats() {
|
||||
return availableGameStats;
|
||||
}
|
||||
|
||||
public void setAvailableGameStats(GameStats availableGameStats) {
|
||||
this.availableGameStats = availableGameStats;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("game")
|
||||
private Game game;
|
||||
|
||||
public Game getGame() {
|
||||
return game;
|
||||
}
|
||||
|
||||
public void setGame(Game game) {
|
||||
this.game = game;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,27 @@
|
|||
package achievements.controllers;
|
||||
|
||||
import achievements.services.ImageService;
|
||||
import achievements.services.AchievementService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
@RestController
|
||||
@RequestMapping("/achievement")
|
||||
public class AchievementController {
|
||||
|
||||
@Autowired
|
||||
private AchievementService achievementService;
|
||||
@Autowired
|
||||
private ImageService imageService;
|
||||
|
||||
@GetMapping(value = "/{achievement}/image")
|
||||
public void getProfilePicture(@PathVariable("achievement") int achievement, HttpServletResponse response) {
|
||||
var icon = achievementService.getIcon(achievement);
|
||||
imageService.send(icon, "achievement", response);
|
||||
}
|
||||
}
|
|
@ -14,7 +14,7 @@ import org.springframework.web.bind.annotation.RestController;
|
|||
|
||||
@RestController
|
||||
@RequestMapping("/auth")
|
||||
public class LoginController {
|
||||
public class AuthController {
|
||||
|
||||
@Autowired
|
||||
private AuthenticationService authService;
|
|
@ -0,0 +1,27 @@
|
|||
package achievements.controllers;
|
||||
|
||||
import achievements.services.ImageService;
|
||||
import achievements.services.GameService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
|
||||
@RestController
|
||||
@RequestMapping("/game")
|
||||
public class GameController {
|
||||
|
||||
@Autowired
|
||||
private GameService gameService;
|
||||
@Autowired
|
||||
private ImageService imageService;
|
||||
|
||||
@GetMapping(value = "/{game}/image")
|
||||
public void getProfilePicture(@PathVariable("game") int game, HttpServletResponse response) {
|
||||
var icon = gameService.getIcon(game);
|
||||
imageService.send(icon, "game", response);
|
||||
}
|
||||
}
|
|
@ -1,42 +1,27 @@
|
|||
package achievements.controllers;
|
||||
|
||||
import achievements.services.ImageService;
|
||||
import achievements.services.PlatformService;
|
||||
import org.apache.tomcat.util.http.fileupload.IOUtils;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.web.bind.annotation.GetMapping;
|
||||
import org.springframework.web.bind.annotation.PathVariable;
|
||||
import org.springframework.web.bind.annotation.RequestMapping;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.IOException;
|
||||
|
||||
@RestController
|
||||
@RequestMapping("/platform")
|
||||
public class PlatformController {
|
||||
|
||||
@Autowired
|
||||
private PlatformService platforms;
|
||||
private ImageService imageService;
|
||||
@Autowired
|
||||
private PlatformService platformService;
|
||||
|
||||
@GetMapping(value = "/platform/image/{id}", produces = "application/json")
|
||||
public void getPlatformImage(@PathVariable("id") int id, HttpServletResponse response) {
|
||||
try {
|
||||
var file = new File("images/platform/" + id + ".png");
|
||||
if (file.exists()) {
|
||||
var stream = new FileInputStream(file);
|
||||
IOUtils.copy(stream, response.getOutputStream());
|
||||
|
||||
response.setContentType("image/png");
|
||||
response.setStatus(200);
|
||||
response.flushBuffer();
|
||||
stream.close();
|
||||
} else {
|
||||
response.setStatus(HttpStatus.BAD_REQUEST.value());
|
||||
}
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
|
||||
}
|
||||
@GetMapping(value = "/{platform}/image")
|
||||
public void getIcon(@PathVariable("platform") int platform, HttpServletResponse response) {
|
||||
var icon = platformService.getIcon(platform);
|
||||
imageService.send(icon, "platform", response);
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,26 @@
|
|||
package achievements.controllers;
|
||||
|
||||
import achievements.data.query.SearchAchievements;
|
||||
import achievements.services.SearchService;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.web.bind.annotation.PostMapping;
|
||||
import org.springframework.web.bind.annotation.RequestBody;
|
||||
import org.springframework.web.bind.annotation.RestController;
|
||||
|
||||
@RestController
|
||||
public class SearchController {
|
||||
|
||||
@Autowired
|
||||
private SearchService searchService;
|
||||
|
||||
@PostMapping(value = "/achievements", consumes = "application/json", produces = "application/json")
|
||||
public ResponseEntity searchAchievements(@RequestBody SearchAchievements searchAchievements) {
|
||||
var achievements = searchService.searchAchievements(searchAchievements);
|
||||
if (achievements != null) {
|
||||
return ResponseEntity.ok(achievements);
|
||||
} else {
|
||||
return ResponseEntity.badRequest().body("[]");
|
||||
}
|
||||
}
|
||||
}
|
|
@ -2,20 +2,18 @@ package achievements.controllers;
|
|||
|
||||
import achievements.data.APError;
|
||||
import achievements.data.APPostRequest;
|
||||
import achievements.data.query.AddPlatformRequest;
|
||||
import achievements.data.query.RemovePlatformRequest;
|
||||
import achievements.data.query.AddPlatform;
|
||||
import achievements.data.query.RemovePlatform;
|
||||
import achievements.data.query.SetUsername;
|
||||
import achievements.services.ImageService;
|
||||
import achievements.services.UserService;
|
||||
import org.apache.tomcat.util.http.fileupload.IOUtils;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.http.HttpStatus;
|
||||
import org.springframework.http.ResponseEntity;
|
||||
import org.springframework.util.FileCopyUtils;
|
||||
import org.springframework.web.bind.annotation.*;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.*;
|
||||
|
||||
@RestController
|
||||
@RequestMapping("/user")
|
||||
|
@ -24,6 +22,9 @@ public class UserController {
|
|||
@Autowired
|
||||
private UserService userService;
|
||||
|
||||
@Autowired
|
||||
private ImageService imageService;
|
||||
|
||||
@GetMapping(value = "/{user}", produces = "application/json")
|
||||
public ResponseEntity getProfile(@PathVariable("user") int user) {
|
||||
var profile = userService.getProfile(user);
|
||||
|
@ -45,38 +46,21 @@ public class UserController {
|
|||
|
||||
@GetMapping(value = "/{user}/image")
|
||||
public void getProfilePicture(@PathVariable("user") int user, HttpServletResponse response) {
|
||||
var pfp = userService.getProfileImageType(user);
|
||||
if (pfp == null) {
|
||||
|
||||
} else {
|
||||
var file = new File("images/user/" + pfp[0] + "." + pfp[1]);
|
||||
response.setContentType("image/" + pfp[2]);
|
||||
try {
|
||||
var stream = new FileInputStream(file);
|
||||
IOUtils.copy(stream, response.getOutputStream());
|
||||
|
||||
response.flushBuffer();
|
||||
stream.close();
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
}
|
||||
var profileImage = userService.getProfileImage(user);
|
||||
imageService.send(profileImage, "user", response);
|
||||
}
|
||||
|
||||
@PostMapping(value = "/{user}/image", consumes = "multipart/form-data", produces = "application/json")
|
||||
public ResponseEntity setProfilePicture(@PathVariable("user") int user, @RequestPart APPostRequest session, @RequestPart MultipartFile file) {
|
||||
try {
|
||||
var type = userService.setProfileImageType(user, session.getKey(), file.getContentType());
|
||||
var type = userService.setProfileImage(user, session.getKey(), file);
|
||||
if ("not_an_image".equals(type)) {
|
||||
return ResponseEntity.badRequest().body("{ \"code\": 1, \"message\": \"Not an image type\" }");
|
||||
} else if ("unsupported_type".equals(type)) {
|
||||
return ResponseEntity.badRequest().body("{ \"code\": 1, \"message\": \"Unsupported file type\" }");
|
||||
} else if ("forbidden".equals(type)) {
|
||||
return ResponseEntity.status(HttpStatus.FORBIDDEN).body("{ \"code\": 2, \"message\": \"Invalid credentials\" }");
|
||||
} else if (!"unknown".equals(type)) {
|
||||
var pfp = new FileOutputStream("images/user/" + user + "." + type);
|
||||
FileCopyUtils.copy(file.getInputStream(), pfp);
|
||||
pfp.close();
|
||||
} else if ("success".equals(type)) {
|
||||
return ResponseEntity.status(HttpStatus.CREATED).body("{ \"code\": 0, \"message\": \"Success\" }");
|
||||
}
|
||||
|
||||
|
@ -87,7 +71,7 @@ public class UserController {
|
|||
}
|
||||
|
||||
@PostMapping(value = "/{user}/platforms/add", consumes = "application/json", produces = "application/json")
|
||||
public ResponseEntity addPlatformForUser(@PathVariable("user") int userId, @RequestBody AddPlatformRequest request) {
|
||||
public ResponseEntity addPlatformForUser(@PathVariable("user") int userId, @RequestBody AddPlatform request) {
|
||||
var result = userService.addPlatform(userId, request);
|
||||
if (result == 0) {
|
||||
return ResponseEntity.status(HttpStatus.CREATED).body("{}");
|
||||
|
@ -97,7 +81,7 @@ public class UserController {
|
|||
}
|
||||
|
||||
@PostMapping(value = "/{user}/platforms/remove", consumes = "application/json", produces = "application/json")
|
||||
public ResponseEntity removePlatformForUser(@PathVariable("user") int userId, @RequestBody RemovePlatformRequest request) {
|
||||
public ResponseEntity removePlatformForUser(@PathVariable("user") int userId, @RequestBody RemovePlatform request) {
|
||||
var result = userService.removePlatform(userId, request);
|
||||
if (result == 0) {
|
||||
return ResponseEntity.status(HttpStatus.CREATED).body("{}");
|
||||
|
|
126
backend/src/main/java/achievements/data/APIResponse.java
Normal file
126
backend/src/main/java/achievements/data/APIResponse.java
Normal file
|
@ -0,0 +1,126 @@
|
|||
package achievements.data;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import java.util.List;
|
||||
|
||||
public class APIResponse {
|
||||
|
||||
public static class Game {
|
||||
|
||||
public static class Achievement {
|
||||
@JsonProperty("name")
|
||||
private String name;
|
||||
@JsonProperty("description")
|
||||
private String description;
|
||||
@JsonProperty("stages")
|
||||
private int stages;
|
||||
@JsonProperty("progress")
|
||||
private int progress;
|
||||
@JsonProperty("thumbnail")
|
||||
private String thumbnail;
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public String getDescription() {
|
||||
return description;
|
||||
}
|
||||
|
||||
public void setDescription(String description) {
|
||||
this.description = description;
|
||||
}
|
||||
|
||||
public int getStages() {
|
||||
return stages;
|
||||
}
|
||||
|
||||
public void setStages(int stages) {
|
||||
this.stages = stages;
|
||||
}
|
||||
|
||||
public int getProgress() {
|
||||
return progress;
|
||||
}
|
||||
|
||||
public void setProgress(int progress) {
|
||||
this.progress = progress;
|
||||
}
|
||||
|
||||
public String getThumbnail() {
|
||||
return thumbnail;
|
||||
}
|
||||
|
||||
public void setThumbnail(String thumbnail) {
|
||||
this.thumbnail = thumbnail;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("platformGameId")
|
||||
private String platformGameId;
|
||||
@JsonProperty("name")
|
||||
private String name;
|
||||
@JsonProperty("played")
|
||||
private boolean played;
|
||||
@JsonProperty("thumbnail")
|
||||
private String thumbnail;
|
||||
@JsonProperty("achievements")
|
||||
private List<Achievement> achievements;
|
||||
|
||||
public String getPlatformGameId() {
|
||||
return platformGameId;
|
||||
}
|
||||
|
||||
public void setPlatformGameId(String platformGameId) {
|
||||
this.platformGameId = platformGameId;
|
||||
}
|
||||
|
||||
public String getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(String name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public boolean isPlayed() {
|
||||
return played;
|
||||
}
|
||||
|
||||
public void setPlayed(boolean played) {
|
||||
this.played = played;
|
||||
}
|
||||
|
||||
public String getThumbnail() {
|
||||
return thumbnail;
|
||||
}
|
||||
|
||||
public void setThumbnail(String thumbnail) {
|
||||
this.thumbnail = thumbnail;
|
||||
}
|
||||
|
||||
public List<Achievement> getAchievements() {
|
||||
return achievements;
|
||||
}
|
||||
|
||||
public void setAchievements(List<Achievement> achievements) {
|
||||
this.achievements = achievements;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("games")
|
||||
private List<Game> games;
|
||||
|
||||
public List<Game> getGames() {
|
||||
return games;
|
||||
}
|
||||
|
||||
public void setGames(List<Game> games) {
|
||||
this.games = games;
|
||||
}
|
||||
}
|
|
@ -1,122 +1,38 @@
|
|||
package achievements.data;
|
||||
|
||||
import achievements.data.query.NumericFilter;
|
||||
import achievements.data.query.StringFilter;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
public class Achievement {
|
||||
|
||||
public static class Query {
|
||||
|
||||
@JsonProperty("sessionKey")
|
||||
private String sessionKey;
|
||||
@JsonProperty("name")
|
||||
private StringFilter name;
|
||||
@JsonProperty("stages")
|
||||
private NumericFilter stages;
|
||||
@JsonProperty("completion")
|
||||
private NumericFilter completion;
|
||||
@JsonProperty("difficulty")
|
||||
private NumericFilter difficulty;
|
||||
@JsonProperty("quality")
|
||||
private NumericFilter quality;
|
||||
|
||||
public Query(String sessionKey, StringFilter name, NumericFilter stages, NumericFilter completion, NumericFilter difficulty, NumericFilter quality) {
|
||||
this.sessionKey = sessionKey;
|
||||
this.name = name;
|
||||
this.stages = stages;
|
||||
this.completion = completion;
|
||||
this.difficulty = difficulty;
|
||||
this.quality = quality;
|
||||
}
|
||||
|
||||
public String getSessionKey() {
|
||||
return sessionKey;
|
||||
}
|
||||
|
||||
public void setSessionKey(String sessionKey) {
|
||||
this.sessionKey = sessionKey;
|
||||
}
|
||||
|
||||
public StringFilter getName() {
|
||||
return name;
|
||||
}
|
||||
|
||||
public void setName(StringFilter name) {
|
||||
this.name = name;
|
||||
}
|
||||
|
||||
public NumericFilter getStages() {
|
||||
return stages;
|
||||
}
|
||||
|
||||
public void setStages(NumericFilter stages) {
|
||||
this.stages = stages;
|
||||
}
|
||||
|
||||
public NumericFilter getCompletion() {
|
||||
return completion;
|
||||
}
|
||||
|
||||
public void setCompletion(NumericFilter completion) {
|
||||
this.completion = completion;
|
||||
}
|
||||
|
||||
public NumericFilter getDifficulty() {
|
||||
return difficulty;
|
||||
}
|
||||
|
||||
public void setDifficulty(NumericFilter difficulty) {
|
||||
this.difficulty = difficulty;
|
||||
}
|
||||
|
||||
public NumericFilter getQuality() {
|
||||
return quality;
|
||||
}
|
||||
|
||||
public void setQuality(NumericFilter quality) {
|
||||
this.quality = quality;
|
||||
}
|
||||
}
|
||||
|
||||
@JsonProperty("ID")
|
||||
private int id;
|
||||
private int ID;
|
||||
@JsonProperty("game")
|
||||
private int gameId;
|
||||
private String game;
|
||||
@JsonProperty("name")
|
||||
private String name;
|
||||
@JsonProperty("description")
|
||||
private String description;
|
||||
@JsonProperty("stages")
|
||||
private int stages;
|
||||
@JsonProperty("completion")
|
||||
private float completion;
|
||||
private Integer completion;
|
||||
@JsonProperty("difficulty")
|
||||
private float difficulty;
|
||||
private Float difficulty;
|
||||
@JsonProperty("quality")
|
||||
private float quality;
|
||||
private Float quality;
|
||||
|
||||
public Achievement(int id, int gameId, String name, String description, int stages, float completion, float difficulty, float quality) {
|
||||
this.id = id;
|
||||
this.gameId = gameId;
|
||||
this.name = name;
|
||||
this.description = description;
|
||||
this.stages = stages;
|
||||
this.completion = completion;
|
||||
this.difficulty = difficulty;
|
||||
this.quality = quality;
|
||||
public int getID() {
|
||||
return ID;
|
||||
}
|
||||
|
||||
public int getId() { return id; }
|
||||
|
||||
public void setId(int id) { this.id = id; }
|
||||
|
||||
public int getGameId() {
|
||||
return gameId;
|
||||
public void setID(int ID) {
|
||||
this.ID = ID;
|
||||
}
|
||||
|
||||
public void setGameId(int gameId) {
|
||||
this.gameId = gameId;
|
||||
public String getGame() {
|
||||
return game;
|
||||
}
|
||||
|
||||
public void setGame(String game) {
|
||||
this.game = game;
|
||||
}
|
||||
|
||||
public String getName() { return name; }
|
||||
|
@ -127,31 +43,27 @@ public class Achievement {
|
|||
|
||||
public void setDescription(String description) { this.description = description; }
|
||||
|
||||
public int getStages() { return stages; }
|
||||
|
||||
public void setStages(int stages) { this.stages = stages; }
|
||||
|
||||
public float getCompletion() {
|
||||
public Integer getCompletion() {
|
||||
return completion;
|
||||
}
|
||||
|
||||
public void setCompletion(float completion) {
|
||||
public void setCompletion(Integer completion) {
|
||||
this.completion = completion;
|
||||
}
|
||||
|
||||
public float getDifficulty() {
|
||||
public Float getDifficulty() {
|
||||
return difficulty;
|
||||
}
|
||||
|
||||
public void setDifficulty(float difficulty) {
|
||||
public void setDifficulty(Float difficulty) {
|
||||
this.difficulty = difficulty;
|
||||
}
|
||||
|
||||
public float getQuality() {
|
||||
public Float getQuality() {
|
||||
return quality;
|
||||
}
|
||||
|
||||
public void setQuality(float quality) {
|
||||
public void setQuality(Float quality) {
|
||||
this.quality = quality;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -1,20 +1,11 @@
|
|||
package achievements.data;
|
||||
|
||||
import achievements.data.query.StringFilter;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
public class Game {
|
||||
|
||||
public static class Query {
|
||||
@JsonProperty("name")
|
||||
private StringFilter name;
|
||||
@JsonProperty("platforms")
|
||||
private StringFilter platforms;
|
||||
}
|
||||
|
||||
@JsonProperty("ID")
|
||||
private int id;
|
||||
@JsonProperty("name")
|
||||
|
@ -24,13 +15,6 @@ public class Game {
|
|||
@JsonProperty("achievementCount")
|
||||
private int achievementCount;
|
||||
|
||||
public Game(int id, String name, String platform) {
|
||||
this.id = id;
|
||||
this.name = name;
|
||||
this.platforms = new ArrayList<>();
|
||||
this.platforms.add(platform);
|
||||
}
|
||||
|
||||
public int getId() { return id; }
|
||||
|
||||
public void setId(int id) { this.id = id; }
|
||||
|
|
|
@ -1,6 +1,5 @@
|
|||
package achievements.data;
|
||||
|
||||
import achievements.data.query.StringFilter;
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
import java.util.List;
|
||||
|
|
|
@ -11,14 +11,17 @@ public class Session {
|
|||
private int id;
|
||||
@JsonProperty("hue")
|
||||
private int hue;
|
||||
@JsonProperty("admin")
|
||||
private boolean admin;
|
||||
@JsonIgnore
|
||||
private boolean used;
|
||||
|
||||
public Session(String key, int id, int hue) {
|
||||
this.key = key;
|
||||
this.id = id;
|
||||
this.hue = hue;
|
||||
this.used = false;
|
||||
public Session(String key, int id, int hue, boolean admin) {
|
||||
this.key = key;
|
||||
this.id = id;
|
||||
this.hue = hue;
|
||||
this.admin = admin;
|
||||
this.used = false;
|
||||
}
|
||||
|
||||
public String getKey() {
|
||||
|
@ -45,7 +48,15 @@ public class Session {
|
|||
this.hue = hue;
|
||||
}
|
||||
|
||||
public boolean getUsed() {
|
||||
public boolean isAdmin() {
|
||||
return admin;
|
||||
}
|
||||
|
||||
public void setAdmin(boolean admin) {
|
||||
this.admin = admin;
|
||||
}
|
||||
|
||||
public boolean isUsed() {
|
||||
return used;
|
||||
}
|
||||
|
||||
|
|
|
@ -2,7 +2,7 @@ package achievements.data.query;
|
|||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
public class AddPlatformRequest {
|
||||
public class AddPlatform {
|
||||
@JsonProperty("sessionKey")
|
||||
private String sessionKey;
|
||||
@JsonProperty("platformId")
|
|
@ -1,32 +0,0 @@
|
|||
package achievements.data.query;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
public class NumericFilter {
|
||||
|
||||
@JsonProperty("min")
|
||||
private Float min;
|
||||
@JsonProperty("max")
|
||||
private Float max;
|
||||
|
||||
public NumericFilter(Float min, Float max) {
|
||||
this.min = min;
|
||||
this.max = max;
|
||||
}
|
||||
|
||||
public Float getMin() {
|
||||
return min;
|
||||
}
|
||||
|
||||
public void setMin(Float min) {
|
||||
this.min = min;
|
||||
}
|
||||
|
||||
public Float getMax() {
|
||||
return max;
|
||||
}
|
||||
|
||||
public void setMax(Float max) {
|
||||
this.max = max;
|
||||
}
|
||||
}
|
|
@ -2,7 +2,7 @@ package achievements.data.query;
|
|||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
public class RemovePlatformRequest {
|
||||
public class RemovePlatform {
|
||||
@JsonProperty("sessionKey")
|
||||
private String sessionKey;
|
||||
@JsonProperty("platformId")
|
|
@ -0,0 +1,97 @@
|
|||
package achievements.data.query;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
public class SearchAchievements {
|
||||
|
||||
@JsonProperty("searchTerm")
|
||||
private String searchTerm;
|
||||
@JsonProperty("userId")
|
||||
private Integer userId;
|
||||
@JsonProperty("completed")
|
||||
private boolean completed;
|
||||
@JsonProperty("minCompletion")
|
||||
private Float minCompletion;
|
||||
@JsonProperty("maxCompletion")
|
||||
private Float maxCompletion;
|
||||
@JsonProperty("minDifficulty")
|
||||
private Float minDifficulty;
|
||||
@JsonProperty("maxDifficulty")
|
||||
private Float maxDifficulty;
|
||||
@JsonProperty("minQuality")
|
||||
private Float minQuality;
|
||||
@JsonProperty("maxQuality")
|
||||
private Float maxQuality;
|
||||
|
||||
public String getSearchTerm() {
|
||||
return searchTerm;
|
||||
}
|
||||
|
||||
public void setSearchTerm(String searchTerm) {
|
||||
this.searchTerm = searchTerm;
|
||||
}
|
||||
|
||||
public Integer getUserId() {
|
||||
return userId;
|
||||
}
|
||||
|
||||
public void setUserId(Integer userId) {
|
||||
this.userId = userId;
|
||||
}
|
||||
|
||||
public boolean isCompleted() {
|
||||
return completed;
|
||||
}
|
||||
|
||||
public void setCompleted(boolean completed) {
|
||||
this.completed = completed;
|
||||
}
|
||||
|
||||
public Float getMinCompletion() {
|
||||
return minCompletion;
|
||||
}
|
||||
|
||||
public void setMinCompletion(Float minCompletion) {
|
||||
this.minCompletion = minCompletion;
|
||||
}
|
||||
|
||||
public Float getMaxCompletion() {
|
||||
return maxCompletion;
|
||||
}
|
||||
|
||||
public void setMaxCompletion(Float maxCompletion) {
|
||||
this.maxCompletion = maxCompletion;
|
||||
}
|
||||
|
||||
public Float getMinDifficulty() {
|
||||
return minDifficulty;
|
||||
}
|
||||
|
||||
public void setMinDifficulty(Float minDifficulty) {
|
||||
this.minDifficulty = minDifficulty;
|
||||
}
|
||||
|
||||
public Float getMaxDifficulty() {
|
||||
return maxDifficulty;
|
||||
}
|
||||
|
||||
public void setMaxDifficulty(Float maxDifficulty) {
|
||||
this.maxDifficulty = maxDifficulty;
|
||||
}
|
||||
|
||||
public Float getMinQuality() {
|
||||
return minQuality;
|
||||
}
|
||||
|
||||
public void setMinQuality(Float minQuality) {
|
||||
this.minQuality = minQuality;
|
||||
}
|
||||
|
||||
public Float getMaxQuality() {
|
||||
return maxQuality;
|
||||
}
|
||||
|
||||
public void setMaxQuality(Float maxQuality) {
|
||||
this.maxQuality = maxQuality;
|
||||
}
|
||||
}
|
|
@ -1,21 +0,0 @@
|
|||
package achievements.data.query;
|
||||
|
||||
import com.fasterxml.jackson.annotation.JsonProperty;
|
||||
|
||||
public class StringFilter {
|
||||
|
||||
@JsonProperty("query")
|
||||
private String query;
|
||||
|
||||
public StringFilter(String query) {
|
||||
this.query = query;
|
||||
}
|
||||
|
||||
public String getQuery() {
|
||||
return query;
|
||||
}
|
||||
|
||||
public void setQuery(String query) {
|
||||
this.query = query;
|
||||
}
|
||||
}
|
41
backend/src/main/java/achievements/misc/APIList.java
Normal file
41
backend/src/main/java/achievements/misc/APIList.java
Normal file
|
@ -0,0 +1,41 @@
|
|||
package achievements.misc;
|
||||
|
||||
import achievements.apis.PlatformAPI;
|
||||
import achievements.apis.SteamAPI;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Component;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.util.HashMap;
|
||||
import java.util.Map;
|
||||
|
||||
@Component
|
||||
public class APIList {
|
||||
|
||||
@Autowired
|
||||
private RestTemplate rest;
|
||||
|
||||
public final Map<Integer, PlatformAPI> apis = new HashMap<>();
|
||||
|
||||
@PostConstruct
|
||||
private void init() {
|
||||
/*db = dbs.getConnection();
|
||||
try {
|
||||
|
||||
var stmt = db.prepareCall("{call GetPlatforms()}");
|
||||
var results = stmt.executeQuery();
|
||||
|
||||
while (results.next()) {
|
||||
var id = results.getInt("ID");
|
||||
|
||||
// Wanted to pull some skekery with dynamic class loading and external api jars, but...time is of the essence and I need to cut scope as much as possible
|
||||
apis.put(id, new ????(id, rest));
|
||||
}
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}*/
|
||||
|
||||
apis.put(0, new SteamAPI(0, rest));
|
||||
}
|
||||
}
|
|
@ -13,12 +13,12 @@ public class SessionManager {
|
|||
private HashMap<String, Session> sessions;
|
||||
|
||||
public SessionManager() {
|
||||
sessions = new HashMap();
|
||||
sessions = new HashMap<>();
|
||||
}
|
||||
|
||||
public Session generate(int user, int hue) {
|
||||
public Session generate(int user, int hue, boolean admin) {
|
||||
var key = HashManager.encode(HashManager.generateBytes(16));
|
||||
var session = new Session(key, user, hue);
|
||||
var session = new Session(key, user, hue, admin);
|
||||
sessions.put(key, session);
|
||||
return session;
|
||||
}
|
||||
|
@ -32,8 +32,13 @@ public class SessionManager {
|
|||
}
|
||||
|
||||
public boolean validate(int user, String key) {
|
||||
var foreign = sessions.get(key);
|
||||
return foreign != null && user == foreign.getId();
|
||||
var session = sessions.get(key);
|
||||
return session != null && user == session.getId();
|
||||
}
|
||||
|
||||
public boolean validateAdmin(int user, String key) {
|
||||
var session = sessions.get(key);
|
||||
return session != null && user == session.getId() && session.isAdmin();
|
||||
}
|
||||
|
||||
public boolean refresh(String key) {
|
||||
|
@ -51,7 +56,7 @@ public class SessionManager {
|
|||
public void clean() {
|
||||
var remove = new ArrayList<String>();
|
||||
sessions.forEach((key, session) -> {
|
||||
if (!session.getUsed()) {
|
||||
if (!session.isUsed()) {
|
||||
remove.add(session.getKey());
|
||||
} else {
|
||||
session.setUsed(false);
|
||||
|
|
111
backend/src/main/java/achievements/services/APIService.java
Normal file
111
backend/src/main/java/achievements/services/APIService.java
Normal file
|
@ -0,0 +1,111 @@
|
|||
package achievements.services;
|
||||
|
||||
import achievements.misc.APIList;
|
||||
import achievements.misc.DbConnection;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.web.client.RestTemplate;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.io.File;
|
||||
import java.io.FileOutputStream;
|
||||
import java.sql.Connection;
|
||||
import java.sql.Types;
|
||||
|
||||
@Service
|
||||
public class APIService {
|
||||
|
||||
@Autowired
|
||||
private RestTemplate rest;
|
||||
@Autowired
|
||||
private APIList apis;
|
||||
@Autowired
|
||||
private DbConnection dbs;
|
||||
private Connection db;
|
||||
|
||||
@PostConstruct
|
||||
private void init() {
|
||||
db = dbs.getConnection();
|
||||
}
|
||||
|
||||
private String getFileType(String imagePath) {
|
||||
var path = imagePath.split("\\.");
|
||||
return path[path.length - 1];
|
||||
}
|
||||
|
||||
public int importUserPlatform(int userId, int platformId, String platformUserId) {
|
||||
try {
|
||||
var response = apis.apis.get(platformId).get(platformUserId);
|
||||
|
||||
var addIfNotGame = db.prepareCall("{call AddIfNotGame(?, ?, ?)}");
|
||||
var addGameToPlatform = db.prepareCall("{call AddGameToPlatform(?, ?, ?)}");
|
||||
var addGameToUser = db.prepareCall("{call AddGameToPlatform(?, ?, ?)}");
|
||||
var addIfNotAchievement = db.prepareCall("{call AddIfNotAchievement(?, ?, ?, ?, ?, ?)}");
|
||||
var setAchievementProgressForUser = db.prepareCall("{call SetAchievementProgressForUser(?, ?, ?, ?)}");
|
||||
|
||||
addIfNotGame.registerOutParameter(3, Types.INTEGER);
|
||||
addIfNotAchievement.registerOutParameter(6, Types.INTEGER);
|
||||
|
||||
for (var game : response.getGames()) {
|
||||
addIfNotGame.setString(1, game.getName());
|
||||
addIfNotGame.setString(2, getFileType(game.getThumbnail()));
|
||||
addIfNotGame.execute();
|
||||
var gameId = addIfNotGame.getInt(3);
|
||||
|
||||
addGameToPlatform.setInt(1, gameId);
|
||||
addGameToPlatform.setInt(2, platformId);
|
||||
addGameToPlatform.setString(3, platformUserId);
|
||||
addGameToPlatform.execute();
|
||||
|
||||
var gameThumbnail = new File("storage/images/game/" + gameId + "." + getFileType(game.getThumbnail()));
|
||||
if (!gameThumbnail.exists()) {
|
||||
var bytes = rest.getForObject(game.getThumbnail(), byte[].class);
|
||||
var stream = new FileOutputStream(gameThumbnail);
|
||||
stream.write(bytes);
|
||||
stream.close();
|
||||
}
|
||||
|
||||
addGameToUser.setInt(1, gameId);
|
||||
addGameToUser.setInt(2, userId);
|
||||
addGameToUser.setInt(3, platformId);
|
||||
addGameToUser.execute();
|
||||
|
||||
for (var achievement : game.getAchievements()) {
|
||||
addIfNotAchievement.setInt(1, gameId);
|
||||
addIfNotAchievement.setString(2, achievement.getName());
|
||||
addIfNotAchievement.setString(3, achievement.getDescription());
|
||||
addIfNotAchievement.setInt(4, achievement.getStages());
|
||||
addIfNotAchievement.setString(5, getFileType(achievement.getThumbnail()));
|
||||
addIfNotAchievement.execute();
|
||||
var achievementId = addIfNotAchievement.getInt(6);
|
||||
|
||||
var achievementIcon = new File("storage/images/achievement/" + achievementId + "." + getFileType(achievement.getThumbnail()));
|
||||
if (!achievementIcon.exists()) {
|
||||
var bytes = rest.getForObject(achievement.getThumbnail(), byte[].class);
|
||||
var stream = new FileOutputStream(achievementIcon);
|
||||
stream.write(bytes);
|
||||
stream.close();
|
||||
}
|
||||
|
||||
if (game.isPlayed()) {
|
||||
setAchievementProgressForUser.setInt(1, userId);
|
||||
setAchievementProgressForUser.setInt(2, platformId);
|
||||
setAchievementProgressForUser.setInt(3, achievementId);
|
||||
setAchievementProgressForUser.setInt(4, achievement.getProgress());
|
||||
setAchievementProgressForUser.execute();
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
addIfNotGame.close();
|
||||
addGameToPlatform.close();
|
||||
addIfNotAchievement.close();
|
||||
setAchievementProgressForUser.close();
|
||||
|
||||
return 0;
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,34 @@
|
|||
package achievements.services;
|
||||
|
||||
import achievements.misc.DbConnection;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.sql.Connection;
|
||||
|
||||
@Service
|
||||
public class AchievementService {
|
||||
|
||||
@Autowired
|
||||
private DbConnection dbs;
|
||||
private Connection db;
|
||||
|
||||
@Autowired
|
||||
private ImageService imageService;
|
||||
|
||||
@PostConstruct
|
||||
private void init() {
|
||||
db = dbs.getConnection();
|
||||
}
|
||||
|
||||
public String[] getIcon(int achievementId) {
|
||||
try {
|
||||
var stmt = db.prepareCall("{call GetAchievementIcon(?)}");
|
||||
return imageService.getImageType(stmt, achievementId);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
|
@ -68,7 +68,8 @@ public class AuthenticationService {
|
|||
statement.getInt(1),
|
||||
session.generate(
|
||||
statement.getInt(6),
|
||||
statement.getInt(7)
|
||||
statement.getInt(7),
|
||||
false
|
||||
)
|
||||
);
|
||||
statement.close();
|
||||
|
@ -95,7 +96,8 @@ public class AuthenticationService {
|
|||
0,
|
||||
session.generate(
|
||||
result.getInt("ID"),
|
||||
result.getInt("Hue")
|
||||
result.getInt("Hue"),
|
||||
result.getBoolean("Admin")
|
||||
)
|
||||
);
|
||||
} else {
|
||||
|
|
34
backend/src/main/java/achievements/services/GameService.java
Normal file
34
backend/src/main/java/achievements/services/GameService.java
Normal file
|
@ -0,0 +1,34 @@
|
|||
package achievements.services;
|
||||
|
||||
import achievements.misc.DbConnection;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.sql.Connection;
|
||||
|
||||
@Service
|
||||
public class GameService {
|
||||
|
||||
@Autowired
|
||||
private DbConnection dbs;
|
||||
private Connection db;
|
||||
|
||||
@Autowired
|
||||
private ImageService imageService;
|
||||
|
||||
@PostConstruct
|
||||
private void init() {
|
||||
db = dbs.getConnection();
|
||||
}
|
||||
|
||||
public String[] getIcon(int gameId) {
|
||||
try {
|
||||
var stmt = db.prepareCall("{call GetAchievementIcon(?)}");
|
||||
return imageService.getImageType(stmt, gameId);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
|
@ -0,0 +1,80 @@
|
|||
package achievements.services;
|
||||
|
||||
import org.apache.tomcat.util.http.fileupload.IOUtils;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.servlet.http.HttpServletResponse;
|
||||
import java.io.File;
|
||||
import java.io.FileInputStream;
|
||||
import java.io.IOException;
|
||||
import java.sql.CallableStatement;
|
||||
import java.sql.SQLException;
|
||||
import java.util.HashMap;
|
||||
|
||||
@Service
|
||||
public class ImageService {
|
||||
public static final HashMap<String, String> MIME_TO_EXT = new HashMap<>();
|
||||
public static final HashMap<String, String> EXT_TO_MIME = new HashMap<>();
|
||||
static {
|
||||
MIME_TO_EXT.put("apng", "apng");
|
||||
MIME_TO_EXT.put("avif", "avif");
|
||||
MIME_TO_EXT.put("gif", "gif" );
|
||||
MIME_TO_EXT.put("jpeg", "jpg" );
|
||||
MIME_TO_EXT.put("png", "png" );
|
||||
MIME_TO_EXT.put("svg+xml", "svg" );
|
||||
MIME_TO_EXT.put("webp", "webp");
|
||||
|
||||
EXT_TO_MIME.put("apng", "apng" );
|
||||
EXT_TO_MIME.put("avif", "avif" );
|
||||
EXT_TO_MIME.put("gif", "gif" );
|
||||
EXT_TO_MIME.put("jpg", "jpeg" );
|
||||
EXT_TO_MIME.put("png", "png" );
|
||||
EXT_TO_MIME.put("svg", "svg+xml");
|
||||
EXT_TO_MIME.put("webp", "webp" );
|
||||
}
|
||||
|
||||
public String[] getImageType(CallableStatement stmt, int id) {
|
||||
try {
|
||||
stmt.setInt(1, id);
|
||||
|
||||
var result = stmt.executeQuery();
|
||||
if (result.next()) {
|
||||
var type = result.getString(1);
|
||||
if (type != null) {
|
||||
return new String[] { id + "." + type, EXT_TO_MIME.get(type) };
|
||||
}
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
} catch (NumberFormatException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public void send(String[] image, String type, HttpServletResponse response) {
|
||||
var file = (File) null;
|
||||
var mimeType = (String) null;
|
||||
if (image == null) {
|
||||
file = new File("storage/images/default/" + type + ".png");
|
||||
mimeType = "png";
|
||||
} else {
|
||||
file = new File("storage/images/" + type + "/" + image[0]);
|
||||
mimeType = image[1];
|
||||
}
|
||||
try {
|
||||
var stream = new FileInputStream(file);
|
||||
IOUtils.copy(stream, response.getOutputStream());
|
||||
|
||||
response.setStatus(200);
|
||||
response.setContentType("image/" + mimeType);
|
||||
response.flushBuffer();
|
||||
stream.close();
|
||||
|
||||
return;
|
||||
} catch (IOException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
response.setStatus(500);
|
||||
}
|
||||
}
|
|
@ -14,8 +14,21 @@ public class PlatformService {
|
|||
private DbConnection dbs;
|
||||
private Connection db;
|
||||
|
||||
@Autowired
|
||||
private ImageService imageService;
|
||||
|
||||
@PostConstruct
|
||||
private void init() {
|
||||
db = dbs.getConnection();
|
||||
}
|
||||
|
||||
public String[] getIcon(int platformId) {
|
||||
try {
|
||||
var stmt = db.prepareCall("{call GetPlatformIcon(?)}");
|
||||
return imageService.getImageType(stmt, platformId);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
||||
|
|
|
@ -0,0 +1,59 @@
|
|||
package achievements.services;
|
||||
|
||||
import achievements.data.Achievement;
|
||||
import achievements.data.query.SearchAchievements;
|
||||
import achievements.misc.DbConnection;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.sql.Connection;
|
||||
import java.sql.SQLException;
|
||||
import java.util.ArrayList;
|
||||
import java.util.List;
|
||||
|
||||
@Service
|
||||
public class SearchService {
|
||||
|
||||
@Autowired
|
||||
private DbConnection dbs;
|
||||
private Connection db;
|
||||
|
||||
@PostConstruct
|
||||
private void init() {
|
||||
db = dbs.getConnection();
|
||||
}
|
||||
|
||||
public List<Achievement> searchAchievements(SearchAchievements query) {
|
||||
try {
|
||||
var stmt = db.prepareCall("{call SearchAchievements(?, ?, ?, ?, ?, ?, ?, ?, ?)}");
|
||||
stmt.setString(1, query.getSearchTerm());
|
||||
stmt.setBoolean(3, query.isCompleted());
|
||||
if (query.getUserId() != null) { stmt.setInt( 2, query.getUserId() ); } else { stmt.setString(2, null); }
|
||||
if (query.getMinCompletion() != null) { stmt.setFloat(4, query.getMinCompletion()); } else { stmt.setString(4, null); }
|
||||
if (query.getMaxCompletion() != null) { stmt.setFloat(5, query.getMaxCompletion()); } else { stmt.setString(5, null); }
|
||||
if (query.getMinDifficulty() != null) { stmt.setFloat(6, query.getMinDifficulty()); } else { stmt.setString(6, null); }
|
||||
if (query.getMaxDifficulty() != null) { stmt.setFloat(7, query.getMaxDifficulty()); } else { stmt.setString(7, null); }
|
||||
if (query.getMinQuality() != null) { stmt.setFloat(8, query.getMinQuality() ); } else { stmt.setString(8, null); }
|
||||
if (query.getMaxQuality() != null) { stmt.setFloat(9, query.getMaxQuality() ); } else { stmt.setString(9, null); }
|
||||
var results = stmt.executeQuery();
|
||||
|
||||
var achievements = new ArrayList<Achievement>();
|
||||
while (results.next()) {
|
||||
var achievement = new Achievement();
|
||||
achievement.setID (results.getInt ("ID" ));
|
||||
achievement.setGame (results.getString("Game" ));
|
||||
achievement.setName (results.getString("Name" ));
|
||||
achievement.setCompletion(results.getInt ("Completion")); if (results.wasNull()) { achievement.setCompletion(null); }
|
||||
achievement.setDifficulty(results.getFloat ("Difficulty")); if (results.wasNull()) { achievement.setDifficulty(null); }
|
||||
achievement.setQuality (results.getFloat ("Quality" )); if (results.wasNull()) { achievement.setQuality (null); }
|
||||
achievements.add(achievement);
|
||||
}
|
||||
|
||||
return achievements;
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
}
|
|
@ -1,19 +1,24 @@
|
|||
package achievements.services;
|
||||
|
||||
import achievements.data.Profile;
|
||||
import achievements.data.query.AddPlatformRequest;
|
||||
import achievements.data.query.RemovePlatformRequest;
|
||||
import achievements.data.query.AddPlatform;
|
||||
import achievements.data.query.RemovePlatform;
|
||||
import achievements.data.query.SetUsername;
|
||||
import achievements.misc.DbConnection;
|
||||
import org.springframework.beans.factory.annotation.Autowired;
|
||||
import org.springframework.stereotype.Service;
|
||||
import org.springframework.util.FileCopyUtils;
|
||||
import org.springframework.web.multipart.MultipartFile;
|
||||
|
||||
import javax.annotation.PostConstruct;
|
||||
import java.io.File;
|
||||
import java.io.FileOutputStream;
|
||||
import java.sql.Connection;
|
||||
import java.sql.SQLException;
|
||||
import java.sql.Types;
|
||||
import java.util.ArrayList;
|
||||
import java.util.HashMap;
|
||||
|
||||
import static achievements.services.ImageService.MIME_TO_EXT;
|
||||
|
||||
@Service
|
||||
public class UserService {
|
||||
|
@ -25,6 +30,12 @@ public class UserService {
|
|||
@Autowired
|
||||
private AuthenticationService auth;
|
||||
|
||||
@Autowired
|
||||
private APIService apiService;
|
||||
|
||||
@Autowired
|
||||
private ImageService imageService;
|
||||
|
||||
@PostConstruct
|
||||
private void init() {
|
||||
db = dbs.getConnection();
|
||||
|
@ -97,55 +108,51 @@ public class UserService {
|
|||
return -1;
|
||||
}
|
||||
|
||||
private static final HashMap<String, String> VALID_IMAGE_TYPES = new HashMap<>();
|
||||
static {
|
||||
VALID_IMAGE_TYPES.put("apng", "apng");
|
||||
VALID_IMAGE_TYPES.put("avif", "avif");
|
||||
VALID_IMAGE_TYPES.put("gif", "gif" );
|
||||
VALID_IMAGE_TYPES.put("jpeg", "jpg" );
|
||||
VALID_IMAGE_TYPES.put("png", "png" );
|
||||
VALID_IMAGE_TYPES.put("svg+xml", "svg" );
|
||||
VALID_IMAGE_TYPES.put("webp", "webp");
|
||||
}
|
||||
public String[] getProfileImageType(int userId) {
|
||||
public String[] getProfileImage(int userId) {
|
||||
try {
|
||||
var stmt = db.prepareCall("{call GetUserImage(?)}");
|
||||
stmt.setInt(1, userId);
|
||||
|
||||
var result = stmt.executeQuery();
|
||||
if (result.next()) {
|
||||
var type = result.getString("PFP");
|
||||
if (type == null) {
|
||||
return new String[] { "default", "png", "png" };
|
||||
} else {
|
||||
return new String[] { Integer.toString(userId), VALID_IMAGE_TYPES.get(type), type };
|
||||
}
|
||||
}
|
||||
} catch (SQLException e) {
|
||||
e.printStackTrace();
|
||||
} catch (NumberFormatException e) {
|
||||
return imageService.getImageType(stmt, userId);
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return null;
|
||||
}
|
||||
|
||||
public String setProfileImageType(int userId, String sessionKey, String type) {
|
||||
public String setProfileImage(int userId, String sessionKey, MultipartFile file) {
|
||||
try {
|
||||
var type = file.getContentType();
|
||||
if (type.matches("image/.*")) {
|
||||
type = type.substring(6);
|
||||
var extension = VALID_IMAGE_TYPES.get(type);
|
||||
type = MIME_TO_EXT.get(type);
|
||||
if (!auth.session().validate(userId, sessionKey)) {
|
||||
return "forbidden";
|
||||
} else if (extension == null) {
|
||||
} else if (type == null) {
|
||||
return "unsupported_type";
|
||||
} else {
|
||||
var stmt = db.prepareCall("{call SetUserImage(?, ?)}");
|
||||
var stmt = db.prepareCall("{call SetUserImage(?, ?, ?)}");
|
||||
stmt.setInt(1, userId);
|
||||
stmt.setString(2, type);
|
||||
stmt.registerOutParameter(3, Types.VARCHAR);
|
||||
|
||||
stmt.execute();
|
||||
var oldType = stmt.getString(3);
|
||||
|
||||
return extension;
|
||||
// Delete old file
|
||||
if (oldType != null && type != oldType) {
|
||||
var oldFile = new File("storage/images/user/" + userId + "." + oldType);
|
||||
if (oldFile.exists()) {
|
||||
oldFile.delete();
|
||||
}
|
||||
}
|
||||
|
||||
// Save new file (will overwrite old if file type didn't change)
|
||||
{
|
||||
var image = new FileOutputStream("storage/images/user/" + userId + "." + type);
|
||||
FileCopyUtils.copy(file.getInputStream(), image);
|
||||
image.close();
|
||||
}
|
||||
|
||||
return "success";
|
||||
}
|
||||
} else {
|
||||
return "not_an_image";
|
||||
|
@ -156,28 +163,41 @@ public class UserService {
|
|||
return "unknown";
|
||||
}
|
||||
|
||||
public int addPlatform(int userId, AddPlatformRequest request) {
|
||||
try {
|
||||
if (auth.session().validate(userId, request.getSessionKey())) {
|
||||
var stmt = db.prepareCall("{call AddPlatform(?, ?, ?)}");
|
||||
stmt.setInt(1, userId);
|
||||
stmt.setInt(2, request.getPlatformId());
|
||||
stmt.setString(3, request.getPlatformUserId());
|
||||
public int addPlatform(int userId, AddPlatform request) {
|
||||
if (auth.session().validate(userId, request.getSessionKey())) {
|
||||
try {
|
||||
db.setAutoCommit(false);
|
||||
try {
|
||||
var stmt = db.prepareCall("{call AddUserToPlatform(?, ?, ?)}");
|
||||
stmt.setInt(1, userId);
|
||||
stmt.setInt(2, request.getPlatformId());
|
||||
stmt.setString(3, request.getPlatformUserId());
|
||||
|
||||
stmt.execute();
|
||||
stmt.execute();
|
||||
|
||||
return 0;
|
||||
int successful = apiService.importUserPlatform(userId, request.getPlatformId(), request.getPlatformUserId());
|
||||
|
||||
if (successful == 0) {
|
||||
db.commit();
|
||||
db.setAutoCommit(true);
|
||||
return 0;
|
||||
}
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
db.rollback();
|
||||
db.setAutoCommit(true);
|
||||
} catch(SQLException e){
|
||||
e.printStackTrace();
|
||||
}
|
||||
} catch (Exception e) {
|
||||
e.printStackTrace();
|
||||
}
|
||||
return -1;
|
||||
}
|
||||
|
||||
public int removePlatform(int userId, RemovePlatformRequest request) {
|
||||
public int removePlatform(int userId, RemovePlatform request) {
|
||||
try {
|
||||
if (auth.session().validate(userId, request.getSessionKey())) {
|
||||
var stmt = db.prepareCall("{call RemovePlatform(?, ?)}");
|
||||
var stmt = db.prepareCall("{call RemoveUserFromPlatform(?, ?)}");
|
||||
stmt.setInt(1, userId);
|
||||
stmt.setInt(2, request.getPlatformId());
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue