package app.services.db; import app.entities.db.Gametime; import app.entities.other.SteamID; import app.entities.server.Server; import app.entities.Stats; import app.utils.SteamIDConverter; import org.springframework.beans.factory.annotation.Autowired; import org.springframework.beans.factory.annotation.Qualifier; import org.springframework.jdbc.core.JdbcTemplate; import org.springframework.jdbc.core.RowMapper; import org.springframework.stereotype.Service; import java.math.BigDecimal; import java.sql.ResultSet; import java.sql.SQLException; import java.sql.Timestamp; import java.util.*; import java.util.stream.Collectors; @Service public class UsertimeService { @Autowired @Qualifier("jt_ro") private JdbcTemplate jdbcTemplate; //Лучше это всегда держать в true private boolean last_map = true; private Stats stats; @Autowired public UsertimeService(Stats stats) { this.stats = stats; } //todo rework public HashMap> getPlayerLastplay(SteamID steamID) { List maps; HashMap> result = new HashMap<>(); for (Map.Entry stringServerEntry : stats.getServers().entrySet()) { if(last_map) { maps = getMap(stringServerEntry.getValue().getServer_id(), stringServerEntry.getValue().getGrab_maps_limit()); } else { maps = getMaps(stringServerEntry.getValue().getServer_id()); } if(maps.size() == 0) {continue;} for(String map: maps){ Timestamp lastplay = getLastplay(stringServerEntry.getValue().getServer_id(), steamID, map); if(lastplay != null) { if(!result.containsKey(stringServerEntry.getKey())){ result.put(stringServerEntry.getKey(), new HashMap<>()); } result.get(stringServerEntry.getKey()).put(map, lastplay.getTime()/1000); } } } return result; } //todo rework public HashMap> getPlayerUsertime(SteamID steamID) { List maps; HashMap> result = new HashMap<>(); for (Map.Entry stringServerEntry : stats.getServers().entrySet()) { if(last_map) { maps = getMap(stringServerEntry.getValue().getServer_id(), stringServerEntry.getValue().getGrab_maps_limit()); } else { maps = getMaps(stringServerEntry.getValue().getServer_id()); } if(maps.size() == 0) {continue;} for(String map: maps){ BigDecimal usertime = getTotalPlaytime(stringServerEntry.getValue().getServer_id(), steamID, map); if(usertime != null) { if(!result.containsKey(stringServerEntry.getKey())){ result.put(stringServerEntry.getKey(), new HashMap<>()); } result.get(stringServerEntry.getKey()).put(map, usertime); } } } return result; } public Timestamp getLastplay(String server_id, SteamID steamID, String map) { return jdbcTemplate.query("select timestamp from user_connections WHERE srv_id like ? AND map LIKE ? and connection_type LIKE ? AND account_id = ? ORDER BY user_connections.id DESC LIMIT 1", new Object[]{ server_id, map, "disconnect", steamID.account_id}, (rs, n) -> rs.getTimestamp("timestamp")) .stream().findFirst().orElse(null); } public BigDecimal getTotalPlaytime(String server_id, SteamID steamID, String map) { List l = jdbcTemplate.query("select sum(connect_duration) as total from user_connections WHERE srv_id like ? AND map LIKE ? and connection_type LIKE ? AND account_id = ?", new Object[]{ server_id, map, "disconnect", steamID.account_id }, (rs, n) -> rs.getBigDecimal("total")); //optional if has error return l.size() > 0?l.get(0):null; } public List getMap(String server_id, int limit) { return jdbcTemplate.query("select map from user_connections WHERE srv_id like ? group by map, id ORDER BY user_connections.id DESC LIMIT ?", new Object[]{ server_id, limit }, (rs, n) -> rs.getString("map")); } public List getMaps(String server_id) { return jdbcTemplate.query("select map from user_connections where srv_id like ? group by map", new Object[]{server_id}, (rs, n) -> rs.getString("map")); } public SteamID getSteamOnUsername(String username) { return jdbcTemplate.query("SELECT account_id FROM user_connections WHERE player_name = ? ORDER BY id DESC LIMIT 1", new Object[]{ username }, (rs, n) -> SteamIDConverter.getSteamID("[U:1:%d]".formatted(rs.getInt("account_id")))) .stream().findFirst().orElse(null); } public List getGametimeOnServer(SteamID steamID, String server, Integer limit, Integer offset) { return jdbcTemplate.query("SELECT * FROM user_connections WHERE srv_id like ? and account_id = ? AND connection_type LIKE ? ORDER BY user_connections.id DESC LIMIT ? OFFSET ?", new Object[]{ server, steamID.account_id, "disconnect", limit, offset}, (rs, n) -> new Gametime(rs)); } public Long getTotalGametimeOnServer(SteamID steamID, String server) { return jdbcTemplate.query("SELECT count(id) FROM user_connections WHERE srv_id like ? and account_id = ? AND connection_type LIKE ?", new Object[]{ server, steamID.account_id, "disconnect" }, (rs, n) -> rs.getLong(1)) .stream().findFirst().orElse(0L); } }