edu.harvard.med.screensaver.model.users.ChecklistItemEvent.java Source code

Java tutorial

Introduction

Here is the source code for edu.harvard.med.screensaver.model.users.ChecklistItemEvent.java

Source

// $HeadURL$
// $Id$
//
// Copyright  2006, 2010, 2011, 2012 by the President and Fellows of Harvard College.
//
// Screensaver is an open-source project developed by the ICCB-L and NSRB labs
// at Harvard Medical School. This software is distributed under the terms of
// the GNU General Public License.

package edu.harvard.med.screensaver.model.users;

import java.util.SortedSet;

import javax.persistence.CascadeType;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.GenerationType;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.JoinTable;
import javax.persistence.ManyToMany;
import javax.persistence.ManyToOne;

import org.hibernate.annotations.Immutable;
import org.hibernate.annotations.Parameter;
import org.hibernate.annotations.Sort;
import org.hibernate.annotations.SortType;
import org.hibernate.annotations.Type;
import org.joda.time.LocalDate;

import edu.harvard.med.screensaver.model.AbstractEntityVisitor;
import edu.harvard.med.screensaver.model.AuditedAbstractEntity;
import edu.harvard.med.screensaver.model.DataModelViolationException;
import edu.harvard.med.screensaver.model.activities.AdministrativeActivity;
import edu.harvard.med.screensaver.model.annotations.ToMany;
import edu.harvard.med.screensaver.model.annotations.ToOne;
import edu.harvard.med.screensaver.model.meta.Cardinality;
import edu.harvard.med.screensaver.model.meta.RelationshipPath;

/**
 * A ChecklistItemEvent is used to either 1) mark a non-expirable ChecklistItem
 * as "completed" or 2) mark an expirable ChecklistItem as either "activated" or
 * "expired". All ChecklistItemEvents have an associated
 * AdministrativeActivity that records the administrator that entered the event
 * and the date it was entered.
 * 
 * @author <a mailto="andrew_tolopko@hms.harvard.edu">Andrew Tolopko</a>
 * @author <a mailto="john_sullivan@hms.harvard.edu">John Sullivan</a>
 */
@Entity
@Immutable
@org.hibernate.annotations.Proxy
@edu.harvard.med.screensaver.model.annotations.ContainedEntity(containingEntityClass = ScreeningRoomUser.class)
public class ChecklistItemEvent extends AuditedAbstractEntity<Integer> implements Comparable<ChecklistItemEvent> {
    private static final long serialVersionUID = 0L;

    public static final RelationshipPath<ChecklistItemEvent> screeningRoomUser = RelationshipPath
            .from(ChecklistItemEvent.class).to("screeningRoomUser", Cardinality.TO_ONE);
    public static final RelationshipPath<ChecklistItemEvent> checklistItem = RelationshipPath
            .from(ChecklistItemEvent.class).to("checklistItem", Cardinality.TO_ONE);

    private ChecklistItem _checklistItem;
    private ScreeningRoomUser _screeningRoomUser;
    private boolean _isExpiration;
    private boolean _isNotApplicable;
    private LocalDate _datePerformed;

    @Override
    public Object acceptVisitor(AbstractEntityVisitor visitor) {
        return visitor.visit(this);
    }

    /**
     * Get the id for the checklist item.
     * 
     * @return the id for the checklist item
     */
    @Id
    @org.hibernate.annotations.GenericGenerator(name = "checklist_item_event_id_seq", strategy = "sequence", parameters = {
            @Parameter(name = "sequence", value = "checklist_item_event_id_seq") })
    @GeneratedValue(strategy = GenerationType.SEQUENCE, generator = "checklist_item_event_id_seq")
    public Integer getChecklistItemEventId() {
        return getEntityId();
    }

    /**
     * Get the checklist item.
     * 
     * @return the checklist item
     */
    @ManyToOne(fetch = FetchType.LAZY, cascade = {})
    @JoinColumn(name = "checklistItemId", nullable = false, updatable = false)
    //@org.hibernate.annotations.Immutable
    @org.hibernate.annotations.ForeignKey(name = "fk_checklist_item_event_to_checklist_item")
    @org.hibernate.annotations.LazyToOne(org.hibernate.annotations.LazyToOneOption.PROXY)
    @org.hibernate.annotations.Cascade({})
    @edu.harvard.med.screensaver.model.annotations.ToOne(unidirectional = true)
    public ChecklistItem getChecklistItem() {
        return _checklistItem;
    }

    // TODO: we never intend to use this, but need it to allow unit tests to pass
    @ManyToMany(fetch = FetchType.LAZY, cascade = { CascadeType.PERSIST, CascadeType.MERGE })
    @JoinTable(name = "checklistItemEventUpdateActivity", joinColumns = @JoinColumn(name = "checklistItemEventId", nullable = false, updatable = false), inverseJoinColumns = @JoinColumn(name = "updateActivityId", nullable = false, updatable = false, unique = true))
    @org.hibernate.annotations.Cascade(value = { org.hibernate.annotations.CascadeType.SAVE_UPDATE })
    @Sort(type = SortType.NATURAL)
    @ToMany(singularPropertyName = "updateActivity", hasNonconventionalMutation = true /* model testing framework doesn't understand this is a containment relationship, and so requires addUpdateActivity() method*/)
    @Override
    public SortedSet<AdministrativeActivity> getUpdateActivities() {
        return _updateActivities;
    }

    /**
     * For checklist items that are {@link ChecklistItem#isExpirable() expirable},
     * get whether this checklist item event represents the activation or the
     * expiration event.
     */
    @Column(nullable = false, updatable = false, name = "isExpiration")
    public boolean isExpiration() {
        return _isExpiration;
    }

    /**
     * If set, indicates that this checklist item is "not applicable"
     */
    @Column(nullable = false, updatable = false, name = "isNotApplicable")
    public boolean isNotApplicable() {
        return _isNotApplicable;
    }

    /**
     * Get the screening room user.
     * 
     * @return the screening room user
     */
    @ManyToOne(fetch = FetchType.LAZY, cascade = { /*CascadeType.PERSIST, CascadeType.MERGE*/ })
    @JoinColumn(name = "screeningRoomUserId", nullable = false, updatable = false)
    @org.hibernate.annotations.ForeignKey(name = "fk_checklist_item_event_to_screening_room_user")
    @org.hibernate.annotations.Cascade({ /*org.hibernate.annotations.CascadeType.SAVE_UPDATE*/ })
    @org.hibernate.annotations.LazyToOne(org.hibernate.annotations.LazyToOneOption.PROXY)
    @ToOne(unidirectional = true)
    public ScreeningRoomUser getScreeningRoomUser() {
        return _screeningRoomUser;
    }

    /**
     * @return the date the checklist item was performed by the user or otherwise
     *         enacted
     */
    @Column(updatable = false)
    @Type(type = "edu.harvard.med.screensaver.db.usertypes.LocalDateType")
    //@Immutable
    public LocalDate getDatePerformed() {
        return _datePerformed;
    }

    /**
     * Set the date of the event.
     * 
     * @param datePerformed the new date of the event
     */
    private void setDatePerformed(LocalDate datePerformed) {
        _datePerformed = datePerformed;
    }

    /**
     * Construct an initialized "activation" or "completed" <code>ChecklistItemEvent</code> 
     * <p>
     * Intended only for use by {@link ScreeningRoomUser}.
     * 
     * @param checklistItem the checklist item
     * @param screeningRoomUser the screening room user to which this checklist
     *          item event applies
     * @param datePerformed the date the checklist item event was performed by the user
     *          or otherwise enacted
     */
    ChecklistItemEvent(ChecklistItem checklistItem, ScreeningRoomUser screeningRoomUser, LocalDate datePerformed,
            AdministratorUser recordedBy) {
        super(recordedBy);
        if (checklistItem == null || screeningRoomUser == null || datePerformed == null || recordedBy == null) {
            throw new NullPointerException();
        }
        _checklistItem = checklistItem;
        _screeningRoomUser = screeningRoomUser;
        _isExpiration = false;
        _isNotApplicable = false;
        _datePerformed = datePerformed;
    }

    /**
     * Construct an initialized "not applicable" <code>ChecklistItemEvent</code> 
     * <p>
     * Intended only for use by {@link ScreeningRoomUser}.
     **/
    ChecklistItemEvent(ChecklistItem checklistItem, ScreeningRoomUser screeningRoomUser, LocalDate datePerformed,
            AdministratorUser recordedBy, boolean isNotApplicable) {
        this(checklistItem, screeningRoomUser, datePerformed, recordedBy);
        _isNotApplicable = isNotApplicable;
    }

    public ChecklistItemEvent createChecklistItemExpirationEvent(LocalDate datePerformed,
            AdministratorUser recordedBy) {
        if (!getChecklistItem().isExpirable()) {
            throw new DataModelViolationException(
                    "cannot expire checklist item " + getChecklistItem().getItemName());
        }
        SortedSet<ChecklistItemEvent> checklistItemEvents = getScreeningRoomUser()
                .getChecklistItemEvents(getChecklistItem());
        if (checklistItemEvents.isEmpty()) {
            throw new DataModelViolationException(
                    "cannot add checklist item expiration when checklist item has not yet been activated");
        }
        ChecklistItemEvent previousEvent = checklistItemEvents.last();
        if (!previousEvent.equals(this)) {
            throw new DataModelViolationException(
                    "can only apply expiration to the last checklist event of this type");
        }
        if (previousEvent.isExpiration()) {
            throw new DataModelViolationException("can only expire a previously active checklist item");
        }
        if (previousEvent.isNotApplicable()) {
            throw new DataModelViolationException(
                    "can not expire a checklist item that has been marked \"not applicable\"");
        }
        if (datePerformed.compareTo(previousEvent.getDatePerformed()) < 0) {
            throw new DataModelViolationException(
                    "checklist item expiration date must be on or after the previous activation date");
        }
        ChecklistItemEvent checklistItemExpiration = new ChecklistItemEvent(this.getChecklistItem(),
                this.getScreeningRoomUser(), datePerformed, recordedBy);
        checklistItemExpiration._isExpiration = true;
        this.getScreeningRoomUser().getChecklistItemEvents().add(checklistItemExpiration);
        return checklistItemExpiration;
    }

    /**
     * Construct an uninitialized <code>ChecklistItem</code> object.
     * 
     * @motivation for hibernate and proxy/concrete subclass constructors
     * @motivation for user interface entity creation
     */
    public ChecklistItemEvent() {
    }

    // private methods

    /**
     * @motivation for hibernate
     */
    private void setChecklistItemEventId(Integer checklistItemEventId) {
        setEntityId(checklistItemEventId);
    }

    /**
     * @motivation for hibernate
     */
    private void setChecklistItem(ChecklistItem checklistItem) {
        _checklistItem = checklistItem;
    }

    /**
     * @motivation for hibernate
     */
    private void setScreeningRoomUser(ScreeningRoomUser screeningRoomUser) {
        _screeningRoomUser = screeningRoomUser;
    }

    private void setExpiration(boolean isExpiration) {
        _isExpiration = isExpiration;
    }

    private void setNotApplicable(boolean value) {
        _isNotApplicable = value;
    }

    private static ChecklistItemEventComparator _checklistItemEventComparator = new ChecklistItemEventComparator();

    public int compareTo(ChecklistItemEvent other) {
        return _checklistItemEventComparator.compare(this, other);
    }
}