Skip to content

Commit

Permalink
Display team composition
Browse files Browse the repository at this point in the history
  • Loading branch information
axel3rd committed Sep 8, 2024
1 parent d304a33 commit f85f9a5
Show file tree
Hide file tree
Showing 4 changed files with 268 additions and 176 deletions.
3 changes: 2 additions & 1 deletion README.md
Original file line number Diff line number Diff line change
Expand Up @@ -83,14 +83,15 @@ To fully automate update your weekly actions on your *MPG* leagues, you can use
The main output is displaying:

* Injured players, to remove of your team
* Your team composition as remind
* Your team line by line, ordered by efficiency score (*Eff.*), with the players quotation/prices (*Q.*):

```
========== Your league name (leagueId) ==========
Out: Aouar Houssem (M - 34.88) - INJURY_ORANGE - Inconnu (depuis 12/11) - Inconnu
Out: Ambroise Oyongo (D - 11.85) - INJURY_ORANGE - Blessure au genou (depuis 04/11) - Inconnu
Optimized team:
Optimized team (Compo: 343):
+---+--------------------+-------+----+
| P | Player name | Eff. | Q. |
+---+--------------------+-------+----+
Expand Down
1 change: 0 additions & 1 deletion sonar-project.properties

This file was deleted.

88 changes: 36 additions & 52 deletions src/main/java/org/blondin/mpg/Games.java
Original file line number Diff line number Diff line change
Expand Up @@ -53,19 +53,17 @@ public void process(League league, ApiClients apiClients, Config config) {
List<Player> players = team.getSquad().values().stream().collect(Collectors.toList());

// Complete auction and calculate efficiency (notes should be in injured players display), and save for transactions proposal
completeAuctionAndcalculateEfficiency(players, apiClients.getStats(), ChampionshipTypeWrapper.toStats(league.getChampionship()), config,
false, true);
completeAuctionAndcalculateEfficiency(players, apiClients.getStats(), ChampionshipTypeWrapper.toStats(league.getChampionship()), config, false, true);
List<Player> playersTeam = players.stream().collect(Collectors.toList());

// Remove out players (and write them)
removeOutPlayers(players, apiClients.getOutPlayers(), ChampionshipTypeWrapper.toOut(league.getChampionship()), true);

// Sort by efficiency
Collections.sort(players,
Comparator.comparing(Player::getPosition).thenComparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed());
Collections.sort(players, Comparator.comparing(Player::getPosition).thenComparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed());

// Write optimized team
writeTeamOptimized(players, config.isDebug());
writeTeamOptimized(players, coach.getComposition(), config.isDebug());

// Auto-update team
if (config.isTeampUpdate()) {
Expand All @@ -74,24 +72,21 @@ public void process(League league, ApiClients apiClients, Config config) {

if (config.isTransactionsProposal()) {
if (Mode.NORMAL.equals(league.getMode())) {
LOG.info(
"\nTransaction proposals can not be achieved, you should buy 'MPG expert mode' for this league (very fun, not expensive!)");
LOG.info("\nTransaction proposals can not be achieved, you should buy 'MPG expert mode' for this league (very fun, not expensive!)");
} else {
LOG.info("\nTransactions proposal ...");
CurrentDay cd = apiClients.getStats().getStats(ChampionshipTypeWrapper.toStats(league.getChampionship())).getInfos()
.getAnnualStats().getCurrentDay();
CurrentDay cd = apiClients.getStats().getStats(ChampionshipTypeWrapper.toStats(league.getChampionship())).getInfos().getAnnualStats().getCurrentDay();
if (!cd.isStatsDayReached()) {
LOG.info("\nWARNING: Last day stats have not fully reached! Please retry tomorrow");
}
List<Player> playersAvailable = apiClients.getMpg().getAvailablePlayers(league.getDivisionId()).getList();
completePlayersClub(playersAvailable, apiClients.getMpg().getClubs());
removeOutPlayers(playersAvailable, apiClients.getOutPlayers(), ChampionshipTypeWrapper.toOut(league.getChampionship()), false);
completeAuctionAndcalculateEfficiency(playersAvailable, apiClients.getStats(),
ChampionshipTypeWrapper.toStats(league.getChampionship()), config, false, false);
completeAuctionAndcalculateEfficiency(playersAvailable, apiClients.getStats(), ChampionshipTypeWrapper.toStats(league.getChampionship()), config, false, false);

Integer currentPlayersBuy = team.getBids().stream().map(Player::getPricePaid).collect(Collectors.summingInt(Integer::intValue));
writeTransactionsProposal(cd.getDay(), playersTeam, playersAvailable, team.getBudget() - currentPlayersBuy,
apiClients.getOutPlayers(), ChampionshipTypeWrapper.toOut(league.getChampionship()), config);
writeTransactionsProposal(cd.getDay(), playersTeam, playersAvailable, team.getBudget() - currentPlayersBuy, apiClients.getOutPlayers(),
ChampionshipTypeWrapper.toOut(league.getChampionship()), config);
}
}
} catch (NoMoreGamesException e) {
Expand All @@ -104,7 +99,7 @@ public void process(League league, ApiClients apiClients, Config config) {
* Teams players is only id and price paid => replace by real player
*
* @param teamPlayers teams
* @param pool players
* @param pool players
*/
static void completePlayersTeam(Map<String, Player> teamPlayers, PoolPlayers pool) {
List<String> players2Remove = new ArrayList<>();
Expand All @@ -123,8 +118,7 @@ static void completePlayersTeam(Map<String, Player> teamPlayers, PoolPlayers poo
}
}

private static void updateTeamWithRetry(MpgClient mpgClient, Division division, Team team, Coach coach, List<Player> players, PoolPlayers pool,
Config config) {
private static void updateTeamWithRetry(MpgClient mpgClient, Division division, Team team, Coach coach, List<Player> players, PoolPlayers pool, Config config) {
LOG.info("\nUpdating team ...");
CoachRequest request = getCoachRequest(team, coach, players, division.getGameRemaining(), config);
if (StringUtils.isNotBlank(request.getCaptain())) {
Expand Down Expand Up @@ -156,16 +150,14 @@ private static void updateTeamWithRetry(MpgClient mpgClient, Division division,
}
}

private static void writeTransactionsProposal(int currentDay, List<Player> playersTeam, List<Player> playersAvailable, int budget,
InjuredSuspendedWrapperClient outPlayersClient, ChampionshipOutType championship, Config config) {
private static void writeTransactionsProposal(int currentDay, List<Player> playersTeam, List<Player> playersAvailable, int budget, InjuredSuspendedWrapperClient outPlayersClient,
ChampionshipOutType championship, Config config) {

// Players with bad efficiency
List<Player> players2Sell = playersTeam.stream().filter(p -> p.getEfficiency() <= config.getEfficiencySell(p.getPosition()))
.collect(Collectors.toList());
List<Player> players2Sell = playersTeam.stream().filter(p -> p.getEfficiency() <= config.getEfficiencySell(p.getPosition())).collect(Collectors.toList());

// Remove goalkeeper(s) (if exist) and same team as the first
List<Player> goalkeepers = playersTeam.stream().filter(p -> p.getPosition().equals(Position.G))
.sorted(Comparator.comparing(Player::getEfficiency).reversed()).collect(Collectors.toList());
List<Player> goalkeepers = playersTeam.stream().filter(p -> p.getPosition().equals(Position.G)).sorted(Comparator.comparing(Player::getEfficiency).reversed()).collect(Collectors.toList());
final Player goalFirst = goalkeepers.isEmpty() ? new Player() : goalkeepers.get(0);
if (!goalkeepers.isEmpty()) {
players2Sell.removeIf(p -> p.getPosition().equals(Position.G) && p.getClubId().equals(goalkeepers.get(0).getClubId()));
Expand All @@ -177,8 +169,7 @@ private static void writeTransactionsProposal(int currentDay, List<Player> playe
AsciiTable at = getTable(TABLE_POSITION, TABLE_PLAYER_NAME, TABLE_EFFICIENCY, TABLE_QUOTE);
for (Player player : players2Sell) {
cash += player.getQuotation();
AT_Row row = at.addRow(player.getPosition(), player.getName(), FORMAT_DECIMAL_DOUBLE.format(player.getEfficiency()),
player.getQuotation());
AT_Row row = at.addRow(player.getPosition(), player.getName(), FORMAT_DECIMAL_DOUBLE.format(player.getEfficiency()), player.getQuotation());
setTableFormatRowPaddingSpace(row);
row.getCells().get(2).getContext().setTextAlignment(TextAlignment.RIGHT);
}
Expand All @@ -188,40 +179,36 @@ private static void writeTransactionsProposal(int currentDay, List<Player> playe
}
LOG.info("Budget: {}", cash);

Player defenderLast = playersTeam.stream().filter(p -> p.getPosition().equals(Position.D))
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation)).collect(Collectors.toList()).get(0);
Player midfielderLast = playersTeam.stream().filter(p -> p.getPosition().equals(Position.M))
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation)).collect(Collectors.toList()).get(0);
Player attackerLast = playersTeam.stream().filter(p -> p.getPosition().equals(Position.A))
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation)).collect(Collectors.toList()).get(0);
Player defenderLast = playersTeam.stream().filter(p -> p.getPosition().equals(Position.D)).sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation))
.collect(Collectors.toList()).get(0);
Player midfielderLast = playersTeam.stream().filter(p -> p.getPosition().equals(Position.M)).sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation))
.collect(Collectors.toList()).get(0);
Player attackerLast = playersTeam.stream().filter(p -> p.getPosition().equals(Position.A)).sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation))
.collect(Collectors.toList()).get(0);
cash += defenderLast.getQuotation() + midfielderLast.getQuotation() + attackerLast.getQuotation();
LOG.info("Budget if last field players by line sold: {}", cash);

final int budgetPotential = cash;
List<Player> players2buy = new ArrayList<>();
players2buy.addAll(playersAvailable.stream().filter(p -> p.getPosition().equals(Position.G)).filter(p -> p.getQuotation() <= budgetPotential)
.filter(p -> p.getEfficiency() > goalFirst.getEfficiency()).filter(p -> p.getEfficiency() > config.getEfficiencySell(Position.G))
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3)
.collect(Collectors.toList()));
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3).collect(Collectors.toList()));
players2buy.addAll(playersAvailable.stream().filter(p -> p.getPosition().equals(Position.D)).filter(p -> p.getQuotation() <= budgetPotential)
.filter(p -> p.getEfficiency() > defenderLast.getEfficiency()).filter(p -> p.getEfficiency() > config.getEfficiencySell(Position.D))
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3)
.collect(Collectors.toList()));
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3).collect(Collectors.toList()));
players2buy.addAll(playersAvailable.stream().filter(p -> p.getPosition().equals(Position.M)).filter(p -> p.getQuotation() <= budgetPotential)
.filter(p -> p.getEfficiency() > midfielderLast.getEfficiency()).filter(p -> p.getEfficiency() > config.getEfficiencySell(Position.M))
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3)
.collect(Collectors.toList()));
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3).collect(Collectors.toList()));
players2buy.addAll(playersAvailable.stream().filter(p -> p.getPosition().equals(Position.A)).filter(p -> p.getQuotation() <= budgetPotential)
.filter(p -> p.getEfficiency() > attackerLast.getEfficiency()).filter(p -> p.getEfficiency() > config.getEfficiencySell(Position.A))
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3)
.collect(Collectors.toList()));
.sorted(Comparator.comparing(Player::getEfficiency).thenComparing(Player::getQuotation).reversed()).limit(3).collect(Collectors.toList()));

if (!players2buy.isEmpty()) {
LOG.info("Player(s) to buy (3 best choice by line):");
AsciiTable at = getTable(TABLE_POSITION, TABLE_PLAYER_NAME, TABLE_EFFICIENCY, TABLE_QUOTE);
for (Player player : players2buy) {
org.blondin.mpg.out.model.Player outPlayer = outPlayersClient.getPlayer(championship, player.getName(),
PositionWrapper.toOut(player.getPosition()), player.getClubName(), OutType.INJURY_GREEN);
org.blondin.mpg.out.model.Player outPlayer = outPlayersClient.getPlayer(championship, player.getName(), PositionWrapper.toOut(player.getPosition()), player.getClubName(),
OutType.INJURY_GREEN);
String s = player.getName();
if (outPlayer != null) {
s += String.format(" (%s - %s - %s)", outPlayer.getOutType(), outPlayer.getDescription(), outPlayer.getLength());
Expand All @@ -239,18 +226,17 @@ private static void writeTransactionsProposal(int currentDay, List<Player> playe

}

static List<Player> removeOutPlayers(List<Player> players, InjuredSuspendedWrapperClient outPlayersClient, ChampionshipOutType championship,
boolean displayOut) {
static List<Player> removeOutPlayers(List<Player> players, InjuredSuspendedWrapperClient outPlayersClient, ChampionshipOutType championship, boolean displayOut) {
List<Player> outPlayers = new ArrayList<>();
for (Player player : players) {
org.blondin.mpg.out.model.Player outPlayer = outPlayersClient.getPlayer(championship, player.getName(),
PositionWrapper.toOut(player.getPosition()), player.getClubName(), OutType.INJURY_GREEN);
org.blondin.mpg.out.model.Player outPlayer = outPlayersClient.getPlayer(championship, player.getName(), PositionWrapper.toOut(player.getPosition()), player.getClubName(),
OutType.INJURY_GREEN);
if (outPlayer != null) {
outPlayers.add(player);
if (displayOut) {
String eff = FORMAT_DECIMAL_DOUBLE.format(player.getEfficiency());
LOG.info("Out: {} ({} - Eff.:{} / Q.:{} / Paid:{}) - {} - {} - {}", player.getName(), player.getPosition(), eff,
player.getQuotation(), player.getPricePaid(), outPlayer.getOutType(), outPlayer.getDescription(), outPlayer.getLength());
LOG.info("Out: {} ({} - Eff.:{} / Q.:{} / Paid:{}) - {} - {} - {}", player.getName(), player.getPosition(), eff, player.getQuotation(), player.getPricePaid(),
outPlayer.getOutType(), outPlayer.getDescription(), outPlayer.getLength());
}
}
}
Expand All @@ -266,8 +252,8 @@ static List<Player> removeOutPlayers(List<Player> players, InjuredSuspendedWrapp
return players;
}

private static void writeTeamOptimized(List<Player> players, boolean isDebug) {
LOG.info("\nOptimized team:");
private static void writeTeamOptimized(List<Player> players, int composition, boolean isDebug) {
LOG.info("\nOptimized team (Compo: {}):", composition);
AsciiTable at = getTable(TABLE_POSITION, TABLE_PLAYER_NAME, TABLE_EFFICIENCY, TABLE_QUOTE);
Position lp = Position.G;
for (Player player : players) {
Expand Down Expand Up @@ -311,8 +297,7 @@ private static CoachRequest getCoachRequest(Team team, Coach coach, List<Player>

String playerIdForBonus = midfielders.get(0).getId();
request.setBonusSelected(selectBonus(coach.getBonusSelected(), team.getBonuses(), gameRemaining, config.isUseBonus(), playerIdForBonus));
String playerIdForCaptain = request.getBonusSelected() != null
&& SelectedBonus.BONUS_BOOT_ONE_PLAYER.equals(request.getBonusSelected().getName())
String playerIdForCaptain = request.getBonusSelected() != null && SelectedBonus.BONUS_BOOT_ONE_PLAYER.equals(request.getBonusSelected().getName())
&& !midfielders.get(1).getId().equals(request.getBonusSelected().getPlayerId()) ? midfielders.get(1).getId() : playerIdForBonus;
request.setCaptain(selectCapatain(coach.getCaptain(), playerIdForCaptain, playerIdForBonus, config.isUseBonus()));

Expand Down Expand Up @@ -391,8 +376,7 @@ static String selectCapatain(String previousCaptain, String captainIdIfNeeded, S
return captainIdIfNeeded;
}

static SelectedBonus selectBonus(SelectedBonus previousBonus, Map<String, Integer> bonuses, int matchsRemaining, boolean useBonus,
String playerIdIfNeeded) {
static SelectedBonus selectBonus(SelectedBonus previousBonus, Map<String, Integer> bonuses, int matchsRemaining, boolean useBonus, String playerIdIfNeeded) {
if (!useBonus || (previousBonus != null && previousBonus.getName() != null)) {
return previousBonus;
}
Expand Down
Loading

0 comments on commit f85f9a5

Please sign in to comment.