package hu.sch.ejb; import hu.sch.domain.Group; import hu.sch.domain.Membership; import hu.sch.domain.Post; import hu.sch.domain.PostType; import hu.sch.domain.enums.SvieMembershipType; import hu.sch.domain.enums.SvieStatus; import hu.sch.domain.logging.EventType; import hu.sch.domain.user.User; import hu.sch.services.LogManagerLocal; import hu.sch.services.MembershipManagerLocal; import hu.sch.services.exceptions.MembershipAlreadyExistsException; import java.util.Date; import java.util.HashSet; import java.util.List; import java.util.Set; import javax.ejb.Stateless; import javax.inject.Inject; import javax.persistence.EntityManager; import javax.persistence.NoResultException; import javax.persistence.NonUniqueResultException; import javax.persistence.PersistenceContext; import javax.persistence.PersistenceException; import javax.persistence.Query; import javax.persistence.TypedQuery; import org.hibernate.exception.ConstraintViolationException; import org.slf4j.Logger; import org.slf4j.LoggerFactory; /** * * @author tomi */ @Stateless public class MembershipManagerBean implements MembershipManagerLocal { private static Logger logger = LoggerFactory.getLogger(MembershipManagerBean.class); @PersistenceContext private EntityManager em; @Inject LogManagerLocal logManager; @Override public void joinGroup(Group group, User user, Date start, Date end, boolean isAuthorized) throws MembershipAlreadyExistsException { Membership ms = new Membership(); User _user = em.find(User.class, user.getId()); Group _group = em.find(Group.class, group.getId()); ms.setUser(_user); ms.setGroup(_group); ms.setStart(start); ms.setEnd(null); if (!isAuthorized) { Post post = new Post(); post.setMembership(ms); Query q = em.createNamedQuery(PostType.searchForPostType); q.setParameter("pn", "feldolgozás alatt"); PostType postType = (PostType) q.getSingleResult(); post.setPostType(postType); Set<Post> posts = new HashSet<Post>(); posts.add(post); ms.setPosts(posts); em.persist(post); } _user.getMemberships().add(ms); _group.getMemberships().add(ms); em.persist(ms); em.merge(_user); em.merge(_group); try { em.flush(); } catch (PersistenceException ex) { if (ex.getCause().getClass().equals(ConstraintViolationException.class)) { // már van ilyen tagság throw new MembershipAlreadyExistsException(group, user); } else { // valami egyéb rondaság, dobjuk vissza :) throw ex; } } logManager.createLogEntry(group, user, EventType.JELENTKEZES); } @Override public void deleteMembership(Membership membership) { Membership temp = em.find(Membership.class, membership.getId()); User user = membership.getUser(); boolean userChanged = false; em.remove(temp); em.flush(); if (user.getSvieMembershipType().equals(SvieMembershipType.RENDESTAG) && user.getSvieStatus().equals(SvieStatus.ELFOGADVA) && membership.getGroup().getIsSvie()) { try { Query q = em.createQuery("SELECT ms.user FROM Membership ms " + "WHERE ms.user = :user AND ms.group.isSvie = true"); q.setParameter("user", user); q.getSingleResult(); } catch (NoResultException nre) { user.setSvieMembershipType(SvieMembershipType.PARTOLOTAG); userChanged = true; } } if (user.getSviePrimaryMembership() != null && membership.getId().equals(user.getSviePrimaryMembership().getId())) { user.setSviePrimaryMembership(null); userChanged = true; } if (userChanged) { em.merge(user); } logManager.createLogEntry(membership.getGroup(), membership.getUser(), EventType.TAGSAGTORLES); } @Override public Membership findMembership(Long groupId, Long userId) { try { return em.createNamedQuery(Membership.findMembershipForUserAndGroup, Membership.class) .setParameter("userId", userId) .setParameter("groupId", groupId) .getSingleResult(); } catch (NoResultException ex) { logger.warn("Could not find membership for {} group id and {} user id", groupId, userId); } catch (NonUniqueResultException ex) { logger.error("More than one membership for group id ({}) - user id ({}) pair.", groupId, userId); } return null; } @Override public Membership findMembership(Long id) { return em.find(Membership.class, id); } @Override public void activateMembership(Membership membership) { membership.setEnd(null); em.merge(membership); } @Override public void inactivateMembership(Membership membership) { membership.setEnd(new Date()); em.merge(membership); } @Override public Group fetchMembershipsFor(Group group) { Query q = em.createNamedQuery(Membership.findMembershipsForGroup) .setParameter("id", group.getId()); group.setMemberships(q.getResultList()); return group; } @Override public List<Membership> findMembershipsForUser(User user) { TypedQuery<Membership> q = em.createQuery( "SELECT DISTINCT ms FROM Membership ms " + "JOIN FETCH ms.group " + "LEFT JOIN FETCH ms.posts p " + "LEFT JOIN FETCH p.postType " + "WHERE ms.user = :user " + "AND ms.end IS NULL " + "ORDER BY ms.group.id", Membership.class); q.setParameter("user", user); return q.getResultList(); } @Override public List<Membership> findActiveMembershipsForGroup(Long groupId) { return new GroupMembershipFetcher(em, groupId).findActive(); } @Override public List<Membership> findInactiveMembershipsForGroup(Long groupId) { return new GroupMembershipFetcher(em, groupId).findInactive(); } }