UpdateCowHealthJob.java

  1. package edu.ucsb.cs156.happiercows.jobs;

  2. import edu.ucsb.cs156.happiercows.entities.Commons;
  3. import edu.ucsb.cs156.happiercows.entities.CommonsPlus;
  4. import edu.ucsb.cs156.happiercows.entities.User;
  5. import edu.ucsb.cs156.happiercows.entities.UserCommons;
  6. import edu.ucsb.cs156.happiercows.repositories.CommonsRepository;
  7. import edu.ucsb.cs156.happiercows.repositories.UserCommonsRepository;
  8. import edu.ucsb.cs156.happiercows.repositories.UserRepository;
  9. import edu.ucsb.cs156.happiercows.services.jobs.JobContext;
  10. import edu.ucsb.cs156.happiercows.services.jobs.JobContextConsumer;
  11. import edu.ucsb.cs156.happiercows.services.CommonsPlusBuilderService;
  12. import edu.ucsb.cs156.happiercows.strategies.CowHealthUpdateStrategy;
  13. import lombok.AllArgsConstructor;
  14. import lombok.Getter;

  15. @AllArgsConstructor
  16. public class UpdateCowHealthJob implements JobContextConsumer {

  17.     @Getter
  18.     private CommonsRepository commonsRepository;
  19.     @Getter
  20.     private UserCommonsRepository userCommonsRepository;
  21.     @Getter
  22.     private UserRepository userRepository;
  23.     @Getter
  24.     private CommonsPlusBuilderService commonsPlusBuilderService;

  25.     @Override
  26.     public void accept(JobContext ctx) throws Exception {
  27.         ctx.log("Updating cow health...");


  28.         Iterable<Commons> allCommons = commonsRepository.findAll();
  29.         Iterable<CommonsPlus> allCommonsPlus = commonsPlusBuilderService.convertToCommonsPlus(allCommons);

  30.         for (CommonsPlus commonsPlus : allCommonsPlus) {


  31.             Commons commons = commonsPlus.getCommons();
  32.            
  33.             runUpdateJobInCommons(commons, commonsPlus, commonsPlusBuilderService, commonsRepository, userCommonsRepository, ctx);
  34.            
  35.         }

  36.         ctx.log("Cow health has been updated!");
  37.     }

  38.     // exposed for testing
  39.     public static double calculateNewCowHealthUsingStrategy(
  40.             CowHealthUpdateStrategy strategy,
  41.             CommonsPlus commonsPlus,
  42.             UserCommons userCommons,
  43.             int totalCows
  44.     ) {
  45.         var health = strategy.calculateNewCowHealth(commonsPlus, userCommons, totalCows);
  46.         return Math.max(0, Math.min(health, 100));
  47.     }

  48.     public static void calculateCowDeaths(UserCommons userCommons, JobContext ctx) {
  49.         if (userCommons.getCowHealth() == 0.0) {
  50.             userCommons.setCowDeaths(userCommons.getCowDeaths() + userCommons.getNumOfCows());
  51.             userCommons.setNumOfCows(0);
  52.             userCommons.setCowHealth(100.0);

  53.             ctx.log(" " + userCommons.getCowDeaths() + " cows for this user died." );
  54.         }
  55.     }

  56.     public static void runUpdateJobInCommons(Commons commons, CommonsPlus commonsPlus, CommonsPlusBuilderService commonsPlusBuilderService, CommonsRepository commonsRepository, UserCommonsRepository userCommonsRepository, JobContext ctx){
  57.         ctx.log("Commons " + commons.getName() + ", degradationRate: " + commons.getDegradationRate() + ", effectiveCapacity: " + commonsPlus.getEffectiveCapacity());

  58.             int numUsers = commonsRepository.getNumUsers(commons.getId()).orElseThrow(() -> new RuntimeException("Error calling getNumUsers(" + commons.getId() + ")"));

  59.             if (numUsers==0) {
  60.                 ctx.log("No users in this commons, skipping");
  61.                 return;
  62.             }

  63.             int carryingCapacity = commonsPlus.getEffectiveCapacity();
  64.             Iterable<UserCommons> allUserCommons = userCommonsRepository.findByCommonsId(commons.getId());

  65.             Integer totalCows = commonsRepository.getNumCows(commons.getId()).orElseThrow(() -> new RuntimeException("Error calling getNumCows(" + commons.getId() + ")"));

  66.             var isAboveCapacity = totalCows > carryingCapacity;
  67.             var cowHealthUpdateStrategy = isAboveCapacity ? commons.getAboveCapacityHealthUpdateStrategy() : commons.getBelowCapacityHealthUpdateStrategy();

  68.             for (UserCommons userCommons : allUserCommons) {
  69.                 User user = userCommons.getUser();

  70.                 var newCowHealth = calculateNewCowHealthUsingStrategy(cowHealthUpdateStrategy, commonsPlusBuilderService.toCommonsPlus(commons), userCommons, totalCows);
  71.                 ctx.log("User: " + user.getFullName() + ", numCows: " + userCommons.getNumOfCows() + ", cowHealth: " + userCommons.getCowHealth());

  72.                 double oldHealth = userCommons.getCowHealth();
  73.                 userCommons.setCowHealth(newCowHealth);
  74.                 calculateCowDeaths(userCommons, ctx);

  75.                 ctx.log(" old cow health: " + oldHealth + ", new cow health: " + userCommons.getCowHealth());
  76.                 userCommonsRepository.save(userCommons);
  77.             }

  78.     }
  79. }