introduced EndDateable
This commit is contained in:
@ -74,12 +74,13 @@ public abstract class AbstractController<T> {
|
|||||||
@TransactionAttribute(TransactionAttributeType.REQUIRED)
|
@TransactionAttribute(TransactionAttributeType.REQUIRED)
|
||||||
@Transactional
|
@Transactional
|
||||||
@Lock(LockType.WRITE)
|
@Lock(LockType.WRITE)
|
||||||
public void create(T entity) throws ControllerException {
|
public T create(T entity) throws ControllerException {
|
||||||
if (Updateable.class.isAssignableFrom(entity.getClass())) {
|
if (Updateable.class.isAssignableFrom(entity.getClass())) {
|
||||||
Updateable updateable = (Updateable) entity;
|
Updateable updateable = (Updateable) entity;
|
||||||
applyUpdateableChanges(updateable, true);
|
applyUpdateableChanges(updateable, true);
|
||||||
}
|
}
|
||||||
em.persist(entity);
|
em.persist(entity);
|
||||||
|
return entity;
|
||||||
}
|
}
|
||||||
|
|
||||||
@TransactionAttribute(TransactionAttributeType.REQUIRED)
|
@TransactionAttribute(TransactionAttributeType.REQUIRED)
|
||||||
|
|||||||
@ -0,0 +1,106 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2019 Joern Muehlencord <joern at muehlencord.de>.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package de.muehlencord.shared.account.business;
|
||||||
|
|
||||||
|
import de.muehlencord.shared.account.util.EndDateable;
|
||||||
|
import de.muehlencord.shared.account.util.Updateable;
|
||||||
|
import de.muehlencord.shared.util.DateUtil;
|
||||||
|
import java.util.ArrayList;
|
||||||
|
import java.util.Date;
|
||||||
|
import java.util.List;
|
||||||
|
import javax.ejb.Lock;
|
||||||
|
import javax.ejb.LockType;
|
||||||
|
import javax.ejb.TransactionAttribute;
|
||||||
|
import javax.ejb.TransactionAttributeType;
|
||||||
|
import javax.persistence.TypedQuery;
|
||||||
|
import javax.persistence.criteria.CriteriaBuilder;
|
||||||
|
import javax.persistence.criteria.CriteriaQuery;
|
||||||
|
import javax.persistence.criteria.Order;
|
||||||
|
import javax.persistence.criteria.Predicate;
|
||||||
|
import javax.persistence.criteria.Root;
|
||||||
|
import javax.transaction.Transactional;
|
||||||
|
|
||||||
|
/**
|
||||||
|
*
|
||||||
|
* @author Joern Muehlencord <joern at muehlencord.de>
|
||||||
|
* @param <T> an entity which needs to extend EndDateable
|
||||||
|
*/
|
||||||
|
public abstract class AbstractEnddateableController<T extends EndDateable<T>> extends AbstractController<T> {
|
||||||
|
|
||||||
|
private final Class<T> endDateableClass;
|
||||||
|
|
||||||
|
public AbstractEnddateableController(Class<T> clazz) {
|
||||||
|
super(clazz);
|
||||||
|
this.endDateableClass = clazz;
|
||||||
|
}
|
||||||
|
|
||||||
|
@TransactionAttribute(TransactionAttributeType.REQUIRED)
|
||||||
|
@Transactional
|
||||||
|
@Lock(LockType.WRITE)
|
||||||
|
@Override
|
||||||
|
public void delete(T entity) throws ControllerException {
|
||||||
|
T entityToUpdate = attach(entity);
|
||||||
|
if (Updateable.class.isAssignableFrom(entityToUpdate.getClass())) {
|
||||||
|
Updateable updateable = (Updateable) entityToUpdate;
|
||||||
|
applyUpdateableChanges(updateable, false);
|
||||||
|
}
|
||||||
|
entityToUpdate.setValidTo(DateUtil.getCurrentTimeInUTC());
|
||||||
|
em.merge(entityToUpdate);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Override
|
||||||
|
@TransactionAttribute(TransactionAttributeType.REQUIRED)
|
||||||
|
@Transactional
|
||||||
|
@Lock(LockType.WRITE)
|
||||||
|
public T create(T entity) throws ControllerException {
|
||||||
|
entity.setValidFrom(DateUtil.getCurrentTimeInUTC());
|
||||||
|
return super.create(entity);
|
||||||
|
}
|
||||||
|
|
||||||
|
@TransactionAttribute(TransactionAttributeType.REQUIRED)
|
||||||
|
@Transactional
|
||||||
|
@Lock(LockType.WRITE)
|
||||||
|
@Override
|
||||||
|
public T update(T entity) throws ControllerException {
|
||||||
|
T newEntity = entity.cloneEndDateable();
|
||||||
|
delete(entity);
|
||||||
|
return create (newEntity);
|
||||||
|
}
|
||||||
|
|
||||||
|
@Lock(LockType.READ)
|
||||||
|
@Override
|
||||||
|
public List<T> findAll(List<String> orderFields) {
|
||||||
|
Date now = DateUtil.getCurrentTimeInUTC();
|
||||||
|
final CriteriaBuilder cb = em.getCriteriaBuilder();
|
||||||
|
final CriteriaQuery<T> criteria = cb.createQuery(endDateableClass);
|
||||||
|
final Root<T> root = criteria.from(endDateableClass);
|
||||||
|
|
||||||
|
Predicate alreadyValid = cb.lessThanOrEqualTo(root.get("validFrom"), now);
|
||||||
|
|
||||||
|
Predicate validToNotSet = cb.isNull(root.get("validTo"));
|
||||||
|
Predicate isBeforeValidTo = cb.greaterThanOrEqualTo(root.get("validTo"), now);
|
||||||
|
Predicate stillValid = cb.or (isBeforeValidTo, validToNotSet);
|
||||||
|
Predicate isValid = cb.and(alreadyValid, stillValid);
|
||||||
|
criteria.where(isValid);
|
||||||
|
|
||||||
|
List<Order> orderList = new ArrayList<>();
|
||||||
|
orderFields.stream().forEachOrdered(field -> orderList.add(cb.asc(root.get(field))));
|
||||||
|
final TypedQuery<T> query = em.createQuery(criteria.orderBy(orderList));
|
||||||
|
|
||||||
|
return query.getResultList();
|
||||||
|
}
|
||||||
|
|
||||||
|
}
|
||||||
@ -0,0 +1,37 @@
|
|||||||
|
/*
|
||||||
|
* Copyright 2019 Joern Muehlencord <joern at muehlencord.de>.
|
||||||
|
*
|
||||||
|
* Licensed under the Apache License, Version 2.0 (the "License");
|
||||||
|
* you may not use this file except in compliance with the License.
|
||||||
|
* You may obtain a copy of the License at
|
||||||
|
*
|
||||||
|
* http://www.apache.org/licenses/LICENSE-2.0
|
||||||
|
*
|
||||||
|
* Unless required by applicable law or agreed to in writing, software
|
||||||
|
* distributed under the License is distributed on an "AS IS" BASIS,
|
||||||
|
* WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
||||||
|
* See the License for the specific language governing permissions and
|
||||||
|
* limitations under the License.
|
||||||
|
*/
|
||||||
|
package de.muehlencord.shared.account.util;
|
||||||
|
|
||||||
|
import java.util.Date;
|
||||||
|
|
||||||
|
/**
|
||||||
|
* Enddateable entities are not deleted but an enddate is set to "now"
|
||||||
|
*
|
||||||
|
* @author Joern Muehlencord <joern at muehlencord.de>
|
||||||
|
*/
|
||||||
|
public interface EndDateable<T> {
|
||||||
|
|
||||||
|
T cloneEndDateable();
|
||||||
|
|
||||||
|
Date getValidFrom();
|
||||||
|
|
||||||
|
Date getValidTo();
|
||||||
|
|
||||||
|
void setValidFrom(Date validFrom);
|
||||||
|
|
||||||
|
void setValidTo(Date validTo);
|
||||||
|
|
||||||
|
}
|
||||||
Reference in New Issue
Block a user