ItEr34S15CUAdministracionCategoriaCoste: implementing the relation between HourCost and CostCategory.

Implemented the necessary methods to manage it so it can be navigated bidirectionally.
Implemented tests to try it.
TODO: implement Date attributes using the class org.joda.time.LocalDate instead of java.util.Date.
TODO: implement the validator HourCostNotOverlapping.
This commit is contained in:
Jacobo Aragunde Pérez 2009-12-02 20:58:18 +01:00 committed by Javier Moran Rua
parent 2a5add0c35
commit 529bfc2456
7 changed files with 160 additions and 0 deletions

View file

@ -21,6 +21,7 @@
package org.navalplanner.business.costcategories.daos;
import org.navalplanner.business.common.daos.GenericDAOHibernate;
import org.navalplanner.business.common.exceptions.InstanceNotFoundException;
import org.navalplanner.business.costcategories.entities.HourCost;
import org.springframework.beans.factory.config.BeanDefinition;
import org.springframework.context.annotation.Scope;
@ -34,4 +35,15 @@ import org.springframework.stereotype.Repository;
public class HourCostDAO extends GenericDAOHibernate<HourCost, Long> implements
IHourCostDAO {
@Override
public void remove(Long id) throws InstanceNotFoundException {
try {
find(id).getCategory().removeHourCost(find(id));
}
catch(InstanceNotFoundException e) {
//it was already deleted from its parent
//we do nothing
}
super.remove(id);
}
}

View file

@ -21,6 +21,7 @@
package org.navalplanner.business.costcategories.daos;
import org.navalplanner.business.common.daos.IGenericDAO;
import org.navalplanner.business.common.exceptions.InstanceNotFoundException;
import org.navalplanner.business.costcategories.entities.HourCost;
/**
@ -28,4 +29,6 @@ import org.navalplanner.business.costcategories.entities.HourCost;
*/
public interface IHourCostDAO extends IGenericDAO<HourCost, Long> {
@Override
public void remove(Long id) throws InstanceNotFoundException;
}

View file

@ -20,6 +20,11 @@
package org.navalplanner.business.costcategories.entities;
import java.util.Date;
import java.util.HashSet;
import java.util.Set;
import org.hibernate.validator.AssertTrue;
import org.hibernate.validator.NotEmpty;
import org.navalplanner.business.common.BaseEntity;
@ -31,6 +36,8 @@ public class CostCategory extends BaseEntity {
@NotEmpty
private String name;
private Set<HourCost> hourCosts = new HashSet<HourCost>();
// Default constructor, needed by Hibernate
protected CostCategory() {
@ -51,4 +58,39 @@ public class CostCategory extends BaseEntity {
public void setName(String name) {
this.name = name;
}
public Set<HourCost> getHourCosts() {
return hourCosts;
}
public void addHourCost(HourCost hourCost) {
hourCosts.add(hourCost);
if(hourCost.getCategory()!=this)
hourCost.setCategory(this);
}
public void removeHourCost(HourCost hourCost) {
hourCosts.remove(hourCost);
if(hourCost.getCategory()==this)
hourCost.setCategory(null);
}
public boolean canAddHourCost(HourCost hourCost) {
boolean overlap = false;
Date initDate = hourCost.getInitDate();
Date endDate = hourCost.getEndDate();
for(HourCost listElement:hourCosts) {
if((listElement.getEndDate().compareTo(initDate)>=0 && listElement.getEndDate().compareTo(endDate)<=0) ||
(listElement.getInitDate().compareTo(initDate)>=0 && listElement.getInitDate().compareTo(endDate)<=0))
overlap = true;
}
return !overlap;
}
@AssertTrue
public boolean HourCostNotOverlapping() {
//TODO: implement a method to validate HourCost time intervals
//complementary with canAddHourCost(), this method is run when calling DAO.save()
return true;
}
}

View file

@ -42,6 +42,9 @@ public class HourCost extends BaseEntity {
@NotNull
private TypeOfWorkHours type;
@NotNull
private CostCategory category;
// Default constructor, needed by Hibernate
protected HourCost() {
@ -87,4 +90,17 @@ public class HourCost extends BaseEntity {
public void setType(TypeOfWorkHours type) {
this.type = type;
}
public CostCategory getCategory() {
return category;
}
public void setCategory(CostCategory category) {
CostCategory oldCategory = this.category;
this.category = category;
if(oldCategory!=null)
oldCategory.removeHourCost(this);
if(category!=null && !category.getHourCosts().contains(this))
category.addHourCost(this);
}
}

View file

@ -13,6 +13,10 @@
<property name="name" unique="true"/>
<set name="hourCosts" inverse="true" cascade="all">
<key column="COST_CATEGORY_ID"/>
<one-to-many class="HourCost"/>
</set>
</class>
<!-- HourCost -->
@ -32,6 +36,8 @@
<many-to-one name="type" class="TypeOfWorkHours" column="TYPE_OF_WORK_HOURS_ID" />
<many-to-one name="category" class="CostCategory" column="COST_CATEGORY_ID"/>
</class>
<!-- TypeOfWorkHours -->

View file

@ -23,10 +23,13 @@ package org.navalplanner.business.test.costcategories.daos;
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertNotNull;
import static org.junit.Assert.assertNull;
import static org.junit.Assert.assertTrue;
import static org.navalplanner.business.BusinessGlobalNames.BUSINESS_SPRING_CONFIG_FILE;
import static org.navalplanner.business.test.BusinessGlobalNames.BUSINESS_SPRING_CONFIG_TEST_FILE;
import java.math.BigDecimal;
import java.util.Date;
import java.util.List;
import java.util.UUID;
@ -35,6 +38,7 @@ import org.junit.runner.RunWith;
import org.navalplanner.business.common.exceptions.InstanceNotFoundException;
import org.navalplanner.business.costcategories.daos.ICostCategoryDAO;
import org.navalplanner.business.costcategories.entities.CostCategory;
import org.navalplanner.business.costcategories.entities.HourCost;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.test.context.ContextConfiguration;
import org.springframework.test.context.junit4.SpringJUnit4ClassRunner;
@ -88,4 +92,44 @@ public class CostCategoryDAOTest {
List<CostCategory> list = costCategoryDAO.list(CostCategory.class);
assertEquals(previous + 1, list.size());
}
@Test
public void testCanAddHourCost() {
CostCategory costCategory = createValidCostCategory();
HourCost hourCost1 = HourCost.create(BigDecimal.ONE, new Date(2009, 11,1));
hourCost1.setEndDate(new Date(2009, 11,10));
costCategory.addHourCost(hourCost1);
HourCost hourCost2 = HourCost.create(BigDecimal.ONE, new Date(2009, 11,1));
hourCost2.setEndDate(new Date(2009, 11,10));
assertFalse(costCategory.canAddHourCost(hourCost2));
hourCost2.setInitDate(new Date(2009,10,15));
hourCost2.setEndDate(new Date(2009,11,1));
assertFalse(costCategory.canAddHourCost(hourCost2));
hourCost2.setInitDate(new Date(2009,11,10));
hourCost2.setEndDate(new Date(2009,11,10));
assertFalse(costCategory.canAddHourCost(hourCost2));
hourCost2.setInitDate(new Date(2009,10,15));
hourCost2.setEndDate(new Date(2009,10,20));
assertTrue(costCategory.canAddHourCost(hourCost2));
}
@Test
public void testListHourCosts() {
CostCategory costCategory = createValidCostCategory();
HourCost hourCost = HourCost.create(BigDecimal.ONE, new Date(2009,11,1));
int previous = costCategory.getHourCosts().size();
costCategory.addHourCost(hourCost);
costCategoryDAO.save(costCategory);
assertEquals(previous + 1, costCategory.getHourCosts().size());
costCategory.removeHourCost(hourCost);
costCategoryDAO.save(costCategory);
assertEquals(previous, costCategory.getHourCosts().size());
assertNull(hourCost.getCategory());
}
}

View file

@ -35,8 +35,10 @@ import java.util.UUID;
import org.junit.Test;
import org.junit.runner.RunWith;
import org.navalplanner.business.common.exceptions.InstanceNotFoundException;
import org.navalplanner.business.costcategories.daos.ICostCategoryDAO;
import org.navalplanner.business.costcategories.daos.IHourCostDAO;
import org.navalplanner.business.costcategories.daos.ITypeOfWorkHoursDAO;
import org.navalplanner.business.costcategories.entities.CostCategory;
import org.navalplanner.business.costcategories.entities.HourCost;
import org.navalplanner.business.costcategories.entities.TypeOfWorkHours;
import org.springframework.beans.factory.annotation.Autowired;
@ -62,6 +64,9 @@ public class HourCostDAOTest {
@Autowired
ITypeOfWorkHoursDAO typeOfWorkHoursDAO;
@Autowired
ICostCategoryDAO costCategoryDAO;
@Test
public void testInSpringContainer() {
assertNotNull(hourCostDAO);
@ -73,6 +78,11 @@ public class HourCostDAOTest {
TypeOfWorkHours.create(UUID.randomUUID().toString(), UUID.randomUUID().toString());
hourCost.setType(type);
typeOfWorkHoursDAO.save(type);
CostCategory costCategory = CostCategory.create(UUID.randomUUID().toString());
hourCost.setCategory(costCategory);
costCategoryDAO.save(costCategory);
return hourCost;
}
@ -99,4 +109,31 @@ public class HourCostDAOTest {
List<HourCost> list = hourCostDAO.list(HourCost.class);
assertEquals(previous + 1, list.size());
}
@Test
public void testCategoryNavigation() {
HourCost hourCost = createValidHourCost();
assertTrue(hourCost.getCategory().getHourCosts().contains(hourCost));
}
@Test
public void testHourCostNotInTwoCategories() {
HourCost hourCost = createValidHourCost();
CostCategory costCategory1 = CostCategory.create(UUID.randomUUID().toString());
CostCategory costCategory2 = CostCategory.create(UUID.randomUUID().toString());
hourCost.setCategory(costCategory1);
hourCost.setCategory(costCategory2);
hourCostDAO.save(hourCost);
assertFalse(costCategory1.getHourCosts().contains(hourCost));
assertTrue(costCategory2.getHourCosts().contains(hourCost));
costCategory1.addHourCost(hourCost);
costCategory2.addHourCost(hourCost);
hourCostDAO.save(hourCost);
assertFalse(costCategory1.getHourCosts().contains(hourCost));
assertTrue(costCategory2.getHourCosts().contains(hourCost));
}
}