/* * This file is part of gwap, an open platform for games with a purpose * * Copyright (C) 2013 * Project play4science * Lehr- und Forschungseinheit für Programmier- und Modellierungssprachen * Ludwig-Maximilians-Universität München * * This program is free software: you can redistribute it and/or modify * it under the terms of the GNU Affero General Public License as published by * the Free Software Foundation, either version 3 of the License, or * (at your option) any later version. * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU Affero General Public License for more details. * * You should have received a copy of the GNU Affero General Public License * along with this program. If not, see <http://www.gnu.org/licenses/>. */ package gwap.widget; import gwap.model.GameType; import gwap.model.Highscore; import gwap.model.Person; import gwap.tools.CustomSourceBean; import gwap.wrapper.HighscoreSet; import java.io.Serializable; import java.util.ArrayList; import java.util.Calendar; import java.util.Date; import java.util.GregorianCalendar; import java.util.HashSet; import java.util.List; import java.util.Set; import javax.persistence.EntityManager; import javax.persistence.NoResultException; import javax.persistence.Query; import org.jboss.seam.Component; import org.jboss.seam.ScopeType; import org.jboss.seam.annotations.AutoCreate; import org.jboss.seam.annotations.Create; import org.jboss.seam.annotations.Destroy; import org.jboss.seam.annotations.Factory; import org.jboss.seam.annotations.In; import org.jboss.seam.annotations.Logger; import org.jboss.seam.annotations.Name; import org.jboss.seam.annotations.Scope; import org.jboss.seam.annotations.datamodel.DataModel; import org.jboss.seam.log.Log; @Name("highscoreBean") @Scope(ScopeType.PAGE) @AutoCreate public class HighscoreBean implements Serializable { private static final long serialVersionUID = 1L; @Create public void init() { log.info("Creating"); } @Destroy public void destroy() { log.info("Destroying"); } @Logger private Log log; @In private EntityManager entityManager; @In(required=false) private Person person; @In private CustomSourceBean customSourceBean; @DataModel private List<HighscoreSet> highscores=null; @DataModel private List<Highscore> highscoreAll; @DataModel private List<Highscore> highscoreDaily; @DataModel private List<Highscore> highscoreMonthly; @DataModel private List<Highscore> highscoreLastMonth; public List<HighscoreSet> getHighscores() { if (highscores==null) updateHighscores(); return highscores; } @Factory("highscores") @SuppressWarnings("unchecked") public void updateHighscores() { highscores = new ArrayList<HighscoreSet>(); String platform = (String) Component.getInstance("platform"); Query query = entityManager.createNamedQuery("gameType.byEnabledPlatform"); query.setParameter("platform", platform); List<GameType> gameTypes=query.getResultList(); for (GameType g : gameTypes) { HighscoreSet set=new HighscoreSet(); set.setGameType(g); if ("accentiurbani".equals(platform)) { set.setHighscoreAll(updateHighscorePerGameSession(g)); } else if ("elearning".equals(platform)) { set.setHighscoreDaily(updateHighscorePerGameSessionDistinctPersonDaily(g)); set.setHighscoreAll(updateHighscorePerGameSessionDistinctPerson(g)); } else { // set.setHighscoreAll(updateHighscore(g)); set.setHighscoreMonthly(updateHighscoreMonthly(g)); set.setHighscoreLastMonth(updateHighscoreLastMonth(g)); set.setHighscoreDaily(updateHighscoreDaily(g)); } highscores.add(set); } } public List<Highscore> updateHighscorePerGameSession(GameType gameType) { log.info("Updating Highscore per GameSession"); Query query = customSourceBean.query("highscore.byGameSession"); query.setMaxResults(20); query.setParameter("gametype", gameType); List<Highscore> res = query.getResultList(); modifyHighscore(res, entityManager); return res; } public List<Highscore> updateHighscorePerGameSessionDistinctPerson(GameType gameType) { log.info("Updating Highscore per GameSession distinct person"); Query query = customSourceBean.query("highscore.byGameSession"); query.setParameter("gametype", gameType); List<Highscore> temp = query.getResultList(); List<Highscore> res = new ArrayList<Highscore>(); Set<Long> distinctPersonIds = new HashSet<Long>(); for (Highscore highscore : temp) { if (!distinctPersonIds.contains(highscore.getPersonId())) { distinctPersonIds.add(highscore.getPersonId()); res.add(highscore); if (res.size() == 20) break; } } modifyHighscore(res, entityManager); return res; } public List<Highscore> updateHighscorePerGameSessionDistinctPersonDaily(GameType gameType) { log.info("Updating Highscore per GameSession distinct person"); Query query = customSourceBean.query("highscore.byGameSessionAndInterval"); query.setParameter("gametype", gameType); query.setParameter("dateUpperBound", new Date()); Calendar calendar = new GregorianCalendar(); calendar.add(Calendar.DAY_OF_YEAR, -1); query.setParameter("dateLowerBound", calendar.getTime()); List<Highscore> temp = query.getResultList(); List<Highscore> res = new ArrayList<Highscore>(); Set<Long> distinctPersonIds = new HashSet<Long>(); for (Highscore highscore : temp) { if (!distinctPersonIds.contains(highscore.getPersonId())) { distinctPersonIds.add(highscore.getPersonId()); res.add(highscore); if (res.size() == 20) break; } } modifyHighscore(res, entityManager); return res; } public List<Highscore> updateHighscoreDaily(GameType gameType) { Date now = new Date(); Calendar calendar = new GregorianCalendar(); calendar.setTime(now); calendar.add(Calendar.DAY_OF_YEAR, -1); Date yesterday = calendar.getTime(); return updateHighscoreByInterval(gameType, yesterday); } public List<Highscore> updateHighscoreMonthly(GameType gameType) { Date now = new Date(); Calendar calendar = new GregorianCalendar(); calendar.setTime(now); calendar.set(Calendar.DAY_OF_MONTH, 1); calendar.set(Calendar.HOUR_OF_DAY, 0); calendar.set(Calendar.MINUTE, 0); calendar.set(Calendar.SECOND, 0); Date beginOfMonth = calendar.getTime(); return updateHighscoreByInterval(gameType, beginOfMonth); } public List<Highscore> updateHighscoreLastMonth(GameType gameType) { Date now = new Date(); // first Day of this month Calendar calendarUpper= new GregorianCalendar(); calendarUpper.setTime(now); calendarUpper.set(Calendar.DAY_OF_MONTH, 1); calendarUpper.set(Calendar.HOUR_OF_DAY, 0); calendarUpper.set(Calendar.MINUTE, 0); calendarUpper.set(Calendar.SECOND, 0); Date beginOfThisMonth = calendarUpper.getTime(); // first Day of last month Calendar calendarLower = (Calendar) calendarUpper.clone(); calendarLower.add(Calendar.MONTH, -1); Date beginOfLastMonth = calendarLower.getTime(); return updateHighscoreByInterval(gameType, beginOfLastMonth, beginOfThisMonth); } public List<Highscore> updateHighscoreByInterval(GameType gameType, Date dateLowerBound) { return updateHighscoreByInterval(gameType, dateLowerBound, new Date()); } public List<Highscore> updateHighscoreByInterval(GameType gameType, Date dateLowerBound, Date dateUpperBound) { log.info("Updating Highscore"); Query query; query = customSourceBean.query("highscore.byInterval"); query.setParameter("gametype", gameType); query.setParameter("dateUpperBound", dateUpperBound); query.setParameter("dateLowerBound", dateLowerBound); query.setMaxResults(5); List<Highscore> res = query.getResultList(); if (person != null) { boolean containedTopX = false; for (Highscore highscore : res) { if (highscore.getPersonId().equals(person.getId())) { containedTopX = true; break; } } if (!containedTopX) { Query queryPerson = entityManager.createNamedQuery("highscore.byPersonAndInterval"); queryPerson.setParameter("gametype", gameType); queryPerson.setParameter("dateUpperBound", dateUpperBound); queryPerson.setParameter("dateLowerBound", dateLowerBound); queryPerson.setParameter("pid", person.getId()); try { Highscore personalHighscore = (Highscore) queryPerson.getSingleResult(); personalHighscore.setPerson(person); res.add(personalHighscore); } catch (NoResultException e) { } } } modifyHighscore(res, entityManager); return res; } public static void modifyHighscore(List<Highscore> highscoreList, EntityManager entityManager) { Query query = entityManager.createNamedQuery("person.byId"); for (Highscore highscore : highscoreList) { if (highscore.getPersonId() != null) { query.setParameter("id", highscore.getPersonId()); highscore.setPerson((Person)query.getSingleResult()); } } } }