Skip to content
Snippets Groups Projects
Commit f3ae5b85 authored by srosse's avatar srosse
Browse files

OO-356: make the summary method of the reference manager robust against missing/corrupted courses

parent 31947317
No related branches found
No related tags found
No related merge requests found
...@@ -5,12 +5,13 @@ ...@@ -5,12 +5,13 @@
http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans
http://www.springframework.org/schema/beans/spring-beans-3.0.xsd"> http://www.springframework.org/schema/beans/spring-beans-3.0.xsd">
<bean id="resourceManager" class="org.olat.resource.OLATResourceManager"> <bean id="resourceManager" class="org.olat.resource.OLATResourceManager">
<property name="dbInstance" ref="database"/> <property name="dbInstance" ref="database"/>
</bean> </bean>
<bean id="referenceManager" class="org.olat.resource.references.ReferenceManager"> <bean id="referenceManager" class="org.olat.resource.references.ReferenceManager">
<constructor-arg ref="resourceManager" /> <property name="dbInstance" ref="database"/>
</bean> <property name="resourceManager" ref="resourceManager"/>
</bean>
</beans> </beans>
\ No newline at end of file
...@@ -26,14 +26,15 @@ ...@@ -26,14 +26,15 @@
package org.olat.resource.references; package org.olat.resource.references;
import java.util.ArrayList; import java.util.ArrayList;
import java.util.Iterator;
import java.util.List; import java.util.List;
import java.util.Locale; import java.util.Locale;
import org.hibernate.type.StandardBasicTypes; import org.olat.core.commons.persistence.DB;
import org.olat.core.commons.persistence.DBFactory; import org.olat.core.commons.persistence.DBFactory;
import org.olat.core.gui.translator.Translator; import org.olat.core.gui.translator.Translator;
import org.olat.core.id.OLATResourceable; import org.olat.core.id.OLATResourceable;
import org.olat.core.logging.OLog;
import org.olat.core.logging.Tracing;
import org.olat.core.manager.BasicManager; import org.olat.core.manager.BasicManager;
import org.olat.core.util.Util; import org.olat.core.util.Util;
import org.olat.course.CourseFactory; import org.olat.course.CourseFactory;
...@@ -54,11 +55,14 @@ import org.olat.resource.OLATResourceManager; ...@@ -54,11 +55,14 @@ import org.olat.resource.OLATResourceManager;
*/ */
public class ReferenceManager extends BasicManager { public class ReferenceManager extends BasicManager {
private static final OLog log = Tracing.createLoggerFor(ReferenceManager.class);
private static ReferenceManager INSTANCE; private static ReferenceManager INSTANCE;
private DB dbInstance;
private OLATResourceManager olatResourceManager; private OLATResourceManager olatResourceManager;
private ReferenceManager(OLATResourceManager olatResourceManager) { private ReferenceManager() {
this.olatResourceManager = olatResourceManager;
INSTANCE = this; INSTANCE = this;
} }
...@@ -67,6 +71,23 @@ public class ReferenceManager extends BasicManager { ...@@ -67,6 +71,23 @@ public class ReferenceManager extends BasicManager {
*/ */
public static ReferenceManager getInstance() { return INSTANCE; } public static ReferenceManager getInstance() { return INSTANCE; }
/**
* [used by Spring]
* @param dbInstance
*/
public void setDbInstance(DB dbInstance) {
this.dbInstance = dbInstance;
}
/**
* [used by Spring]
* @param olatResourceManager
*/
public void setResourceManager(OLATResourceManager olatResourceManager) {
this.olatResourceManager = olatResourceManager;
}
/** /**
* Add a new reference. The meaning of source and target is * Add a new reference. The meaning of source and target is
* such as the source references the target. * such as the source references the target.
...@@ -80,7 +101,7 @@ public class ReferenceManager extends BasicManager { ...@@ -80,7 +101,7 @@ public class ReferenceManager extends BasicManager {
OLATResourceImpl sourceImpl = (OLATResourceImpl)olatResourceManager.findResourceable(source); OLATResourceImpl sourceImpl = (OLATResourceImpl)olatResourceManager.findResourceable(source);
OLATResourceImpl targetImpl = (OLATResourceImpl)olatResourceManager.findResourceable(target); OLATResourceImpl targetImpl = (OLATResourceImpl)olatResourceManager.findResourceable(target);
ReferenceImpl ref = new ReferenceImpl(sourceImpl, targetImpl, userdata); ReferenceImpl ref = new ReferenceImpl(sourceImpl, targetImpl, userdata);
DBFactory.getInstance().saveObject(ref); dbInstance.saveObject(ref);
} }
/** /**
...@@ -90,12 +111,15 @@ public class ReferenceManager extends BasicManager { ...@@ -90,12 +111,15 @@ public class ReferenceManager extends BasicManager {
* @return List of renerences. * @return List of renerences.
*/ */
public List<ReferenceImpl> getReferences(OLATResourceable source) { public List<ReferenceImpl> getReferences(OLATResourceable source) {
OLATResourceImpl sourceImpl = (OLATResourceImpl)olatResourceManager.findResourceable(source); Long sourceKey = getResourceKey(source);
if (sourceImpl == null) return new ArrayList<ReferenceImpl>(0); if (sourceKey == null) {
return new ArrayList<ReferenceImpl>(0);
return DBFactory.getInstance().find( }
"select v from org.olat.resource.references.ReferenceImpl as v where v.source = ?", StringBuilder sb = new StringBuilder();
sourceImpl.getKey(), StandardBasicTypes.LONG); sb.append("select v from ").append(ReferenceImpl.class.getName()).append(" as v where v.source.key=:sourceKey");
return dbInstance.getCurrentEntityManager().createQuery(sb.toString(), ReferenceImpl.class)
.setParameter("sourceKey", sourceKey)
.getResultList();
} }
/** /**
...@@ -104,13 +128,31 @@ public class ReferenceManager extends BasicManager { ...@@ -104,13 +128,31 @@ public class ReferenceManager extends BasicManager {
* @param target * @param target
* @return List of references. * @return List of references.
*/ */
public List getReferencesTo(OLATResourceable target) { public List<ReferenceImpl> getReferencesTo(OLATResourceable target) {
OLATResourceImpl targetImpl = (OLATResourceImpl)olatResourceManager.findResourceable(target); Long targetKey = getResourceKey(target);
if (targetImpl == null) return new ArrayList(0); if (targetKey == null) {
return new ArrayList<ReferenceImpl>(0);
return DBFactory.getInstance().find( }
"select v from org.olat.resource.references.ReferenceImpl as v where v.target = ?", StringBuilder sb = new StringBuilder();
targetImpl.getKey(), StandardBasicTypes.LONG); sb.append("select v from ").append(ReferenceImpl.class.getName()).append(" as v where v.target.key=:targetKey");
return dbInstance.getCurrentEntityManager().createQuery(sb.toString(), ReferenceImpl.class)
.setParameter("targetKey", targetKey)
.getResultList();
}
private Long getResourceKey(OLATResourceable resource) {
Long sourceKey;
if(resource instanceof OLATResource) {
sourceKey = ((OLATResource)resource).getKey();
} else {
OLATResource sourceImpl = olatResourceManager.findResourceable(resource);
if (sourceImpl == null) {
sourceKey = null;
} else {
sourceKey = sourceImpl.getKey();
}
}
return sourceKey;
} }
/** /**
...@@ -131,16 +173,19 @@ public class ReferenceManager extends BasicManager { ...@@ -131,16 +173,19 @@ public class ReferenceManager extends BasicManager {
public String getReferencesToSummary(OLATResourceable target, Locale locale) { public String getReferencesToSummary(OLATResourceable target, Locale locale) {
Translator translator = Util.createPackageTranslator(this.getClass(), locale); Translator translator = Util.createPackageTranslator(this.getClass(), locale);
StringBuilder result = new StringBuilder(100); StringBuilder result = new StringBuilder(100);
List refs = getReferencesTo(target); List<ReferenceImpl> refs = getReferencesTo(target);
if (refs.size() == 0) return null; if (refs.size() == 0) return null;
for (Iterator iter = refs.iterator(); iter.hasNext();) { for (ReferenceImpl ref:refs) {
ReferenceImpl ref = (ReferenceImpl) iter.next();
OLATResourceImpl source = ref.getSource(); OLATResourceImpl source = ref.getSource();
// special treatment for referenced courses: find out the course title // special treatment for referenced courses: find out the course title
if (source.getResourceableTypeName().equals(CourseModule.getCourseTypeName())) { if (source.getResourceableTypeName().equals(CourseModule.getCourseTypeName())) {
ICourse course = CourseFactory.loadCourse(source); try {
result.append(translator.translate("ref.course", new String[] { course.getCourseTitle() })); ICourse course = CourseFactory.loadCourse(source);
result.append(translator.translate("ref.course", new String[] { course.getCourseTitle() }));
} catch (Exception e) {
log.error("", e);
result.append(translator.translate("ref.course", new String[] { "<strike>" + source.getKey().toString() + "</strike>" }));
}
} else { } else {
result.append(translator.translate("ref.generic", new String[] { source.getKey().toString() })); result.append(translator.translate("ref.generic", new String[] { source.getKey().toString() }));
} }
...@@ -161,11 +206,9 @@ public class ReferenceManager extends BasicManager { ...@@ -161,11 +206,9 @@ public class ReferenceManager extends BasicManager {
* @param olatResource an OLAT-Resource * @param olatResource an OLAT-Resource
*/ */
public void deleteAllReferencesOf(OLATResource olatResource) { public void deleteAllReferencesOf(OLATResource olatResource) {
List references = ReferenceManager.getInstance().getReferences(olatResource); List<ReferenceImpl> references = getReferences(olatResource);
for (Iterator iterator = references.iterator(); iterator.hasNext();) { for (ReferenceImpl ref:references) {
ReferenceImpl ref = (ReferenceImpl) iterator.next(); delete(ref);
ReferenceManager.getInstance().delete( ref);
} }
} }
} }
...@@ -28,17 +28,18 @@ package org.olat.resource.references; ...@@ -28,17 +28,18 @@ package org.olat.resource.references;
import static org.junit.Assert.assertTrue; import static org.junit.Assert.assertTrue;
import java.util.Iterator;
import java.util.List; import java.util.List;
import org.apache.log4j.Logger; import org.junit.Assert;
import org.junit.After;
import org.junit.Test; import org.junit.Test;
import org.olat.core.commons.persistence.DBFactory; import org.olat.core.commons.persistence.DB;
import org.olat.core.id.OLATResourceable;
import org.olat.core.util.resource.OresHelper; import org.olat.core.util.resource.OresHelper;
import org.olat.resource.OLATResource; import org.olat.resource.OLATResource;
import org.olat.resource.OLATResourceManager; import org.olat.resource.OLATResourceManager;
import org.olat.test.JunitTestHelper;
import org.olat.test.OlatTestCase; import org.olat.test.OlatTestCase;
import org.springframework.beans.factory.annotation.Autowired;
/** /**
...@@ -46,107 +47,125 @@ import org.olat.test.OlatTestCase; ...@@ -46,107 +47,125 @@ import org.olat.test.OlatTestCase;
*/ */
public class ReferenceManagerTest extends OlatTestCase { public class ReferenceManagerTest extends OlatTestCase {
private static Logger log = Logger.getLogger(ReferenceManagerTest.class.getName()); @Autowired
private static Long RESOURCABLE_ID_1 = new Long(123); private DB dbInstance;
private static Long RESOURCABLE_ID_2 = new Long(456); @Autowired
private static Long RESOURCABLE_ID_3 = new Long(457); private ReferenceManager referenceManager;
@Autowired
private OLATResourceManager resourceManager;
// Already tested in BusinessGroupTest : // Already tested in BusinessGroupTest :
// - getGroupsWithPermissionOnOlatResourceable // - getGroupsWithPermissionOnOlatResourceable
// - getIdentitiesWithPermissionOnOlatResourceable // - getIdentitiesWithPermissionOnOlatResourceable
/** /**
* *
*/ */
@Test public void testAddReference() { @Test
OLATResource oressource = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("type1", RESOURCABLE_ID_1)); public void testAddReference() {
OLATResource orestarget = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("type2targ", RESOURCABLE_ID_2)); OLATResource oressource = JunitTestHelper.createRandomResource();
OLATResource orestarget = JunitTestHelper.createRandomResource();
String udata = "üserdätä"; String udata = "üserdätä";
// add a reference // add a reference
ReferenceManager.getInstance().addReference(oressource, orestarget, udata); referenceManager.addReference(oressource, orestarget, udata);
DBFactory.getInstance().closeSession(); dbInstance.closeSession();
OLATResource orestarget2 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("type2targ", RESOURCABLE_ID_2)); OLATResourceable targetOres = OresHelper.createOLATResourceableInstance(orestarget.getResourceableTypeName(), orestarget.getResourceableId());
List refs = ReferenceManager.getInstance().getReferencesTo(orestarget2); OLATResource orestarget2 = resourceManager.findOrPersistResourceable(targetOres);
for (Iterator it_refs = refs.iterator(); it_refs.hasNext();) { List<ReferenceImpl> refs = referenceManager.getReferencesTo(orestarget2);
ReferenceImpl ref = (ReferenceImpl) it_refs.next(); Assert.assertNotNull(refs);
System.out.println("ref:"+ref); Assert.assertEquals("only one reference may exist", 1, refs.size());
} Assert.assertEquals(oressource, refs.get(0).getSource());
assertTrue("only one reference may exist", refs.size() == 1);
} }
@Test public void testReferencesToAndFrom() { @Test
public void testReferencesToAndFrom() {
// same resouceable id on purpose // same resouceable id on purpose
OLATResource s1 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("s1rrtype1", RESOURCABLE_ID_1)); OLATResource s1 = JunitTestHelper.createRandomResource();
OLATResource s2 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("s2rrtype1", RESOURCABLE_ID_1)); OLATResource s2 = JunitTestHelper.createRandomResource();
OLATResource s3 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("s31rrtype1", RESOURCABLE_ID_1)); OLATResource s3 = JunitTestHelper.createRandomResource();
OLATResource t1 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("t1rrtype1", RESOURCABLE_ID_1)); OLATResource t1 = JunitTestHelper.createRandomResource();
OLATResource t2 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("t2rrtype1", RESOURCABLE_ID_1)); OLATResource t2 = JunitTestHelper.createRandomResource();
// add references // add references
ReferenceManager.getInstance().addReference(s1,t1,"r11"); referenceManager.addReference(s1,t1,"r11");
ReferenceManager.getInstance().addReference(s2,t1,"r21"); referenceManager.addReference(s2,t1,"r21");
ReferenceManager.getInstance().addReference(s2,t2,"r22"); referenceManager.addReference(s2,t2,"r22");
ReferenceManager.getInstance().addReference(s3,t2,"r32"); referenceManager.addReference(s3,t2,"r32");
DBFactory.getInstance().closeSession(); dbInstance.closeSession();
// find the refs again // find the refs again with DB resource
List<ReferenceImpl> s1R =referenceManager.getReferences(s1);
List s1R = ReferenceManager.getInstance().getReferences(s1); Assert.assertEquals("s1 only has one reference", 1, s1R.size());
assertTrue("s1 only has one reference", s1R.size() == 1);
ReferenceImpl ref = (ReferenceImpl)s1R.get(0); ReferenceImpl ref = (ReferenceImpl)s1R.get(0);
assertTrue("source and s1 the same", OresHelper.equals(ref.getSource(), s1)); Assert.assertEquals("source and s1 the same", s1, ref.getSource());
assertTrue("target and t1 the same", OresHelper.equals(ref.getTarget(), t1)); Assert.assertEquals("target and t1 the same", t1, ref.getTarget());
// find the same refs again with resourceable
OLATResourceable s1Ores = OresHelper.createOLATResourceableInstance(s1.getResourceableTypeName(), s1.getResourceableId());
List<ReferenceImpl> s1Rb =referenceManager.getReferences(s1Ores);
Assert.assertEquals("s1 only has one reference", 1, s1Rb.size());
ReferenceImpl refb = (ReferenceImpl)s1R.get(0);
Assert.assertEquals("source and s1 the same", s1, refb.getSource());
Assert.assertEquals("target and t1 the same", t1, refb.getTarget());
// two refs from s2 // two refs from s2
List s2refs = ReferenceManager.getInstance().getReferences(s2); List<ReferenceImpl> s2refs = referenceManager.getReferences(s2);
assertTrue ("s2 holds two refs (to t1 and t2)", s2refs.size() == 2); Assert.assertEquals("s2 holds two refs (to t1 and t2)", 2, s2refs.size());
// two refs to t2 // two refs to t2
List t2refs = ReferenceManager.getInstance().getReferencesTo(t2); List<ReferenceImpl> t2refs = referenceManager.getReferencesTo(t2);
assertTrue ("t2 holds two source refs (to s2 and s3)", t2refs.size() == 2); Assert.assertEquals("t2 holds two source refs (to s2 and s3)", 2, t2refs.size());
} }
@Test public void testAddAndDeleteReference() { @Test
OLATResource oressource = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("type1", RESOURCABLE_ID_1)); public void testAddAndDeleteReference() {
OLATResource orestarget = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("type2targ", RESOURCABLE_ID_3)); OLATResource oressource = JunitTestHelper.createRandomResource();
OLATResource orestarget = JunitTestHelper.createRandomResource();
String udata = "üserdätä"; String udata = "üserdätä";
// add a reference // add a reference
ReferenceManager.getInstance().addReference(oressource, orestarget, udata); referenceManager.addReference(oressource, orestarget, udata);
DBFactory.getInstance().closeSession(); dbInstance.commitAndCloseSession();
OLATResource orestarget2 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("type2targ", RESOURCABLE_ID_3)); OLATResourceable orestarget2 = OresHelper.createOLATResourceableInstance(orestarget.getResourceableTypeName(), orestarget.getResourceableId());
List refs = ReferenceManager.getInstance().getReferencesTo(orestarget2); List<ReferenceImpl> refs = referenceManager.getReferencesTo(orestarget2);
assertTrue("only one reference may exist", refs.size() == 1); Assert.assertEquals("only one reference may exist", 1, refs.size());
for (Iterator it_refs = refs.iterator(); it_refs.hasNext();) { dbInstance.commitAndCloseSession();
ReferenceImpl ref = (ReferenceImpl) it_refs.next();
ReferenceManager.getInstance().delete(ref); for (ReferenceImpl ref : refs) {
referenceManager.delete(ref);
} }
dbInstance.commitAndCloseSession();
DBFactory.getInstance().closeSession();
// now make sure the reference was deleted // now make sure the reference was deleted
OLATResource orestarget3 = OLATResourceManager.getInstance().findOrPersistResourceable(OresHelper.createOLATResourceableInstance("type2targ", RESOURCABLE_ID_3)); OLATResourceable orestarget3 = OresHelper.createOLATResourceableInstance(orestarget.getResourceableTypeName(), orestarget.getResourceableId());
List norefs = ReferenceManager.getInstance().getReferencesTo(orestarget3); List<ReferenceImpl> norefs = referenceManager.getReferencesTo(orestarget3);
assertTrue("reference should now be deleted", norefs.size() == 0); assertTrue("reference should now be deleted", norefs.isEmpty());
} }
@Test
public void testAddAndDeleteAllReferences() {
OLATResource oressource = JunitTestHelper.createRandomResource();
OLATResource orestarget1 = JunitTestHelper.createRandomResource();
OLATResource orestarget2 = JunitTestHelper.createRandomResource();
// add the references
referenceManager.addReference(oressource, orestarget1, "üserdätä");
referenceManager.addReference(oressource, orestarget2, "éserdàtà");
dbInstance.commitAndCloseSession();
List<ReferenceImpl> refs = referenceManager.getReferences(oressource);
Assert.assertEquals("2 references exist", 2, refs.size());
dbInstance.commitAndCloseSession();
referenceManager.deleteAllReferencesOf(oressource);
dbInstance.commitAndCloseSession();
/* // now make sure the reference was deleted
* (non-Javadoc)
* List<ReferenceImpl> norefs = referenceManager.getReferences(oressource);
* @see junit.framework.TestCase#tearDown() assertTrue("reference should now be deleted", norefs.isEmpty());
*/
@After public void tearDown() throws Exception {
try {
//DB.getInstance().delete("select * from o_bookmark");
DBFactory.getInstance().closeSession();
} catch (Exception e) {
log.error("tearDown failed: ", e);
}
} }
} }
\ No newline at end of file
0% Loading or .
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment