diff --git a/src/main/java/org/olat/course/assessment/manager/AssessmentNotificationsHandler.java b/src/main/java/org/olat/course/assessment/manager/AssessmentNotificationsHandler.java index a3fb324475adec4e8447392b5dfc1e6d49e66f05..983e5cbd55e754fc6165c082f8b5e5e8aade4510 100644 --- a/src/main/java/org/olat/course/assessment/manager/AssessmentNotificationsHandler.java +++ b/src/main/java/org/olat/course/assessment/manager/AssessmentNotificationsHandler.java @@ -124,14 +124,11 @@ public class AssessmentNotificationsHandler implements NotificationsHandler { public SubscriptionContext getAssessmentSubscriptionContext(Identity ident, ICourse course) { SubscriptionContext sctx = null; if (ident == null || canSubscribeForAssessmentNotification(ident, course)) { - // Creates a new SubscriptionContext only if not found into cache - if (sctx == null) { - // a subscription context showing to the root node (the course's root - // node is started when clicking such a notification) - CourseNode cn = course.getRunStructure().getRootNode(); - Long resourceableId = course.getResourceableId(); - sctx = new SubscriptionContext(CourseModule.ORES_COURSE_ASSESSMENT, resourceableId, cn.getIdent()); - } + // a subscription context showing to the root node (the course's root + // node is started when clicking such a notification) + CourseNode cn = course.getRunStructure().getRootNode(); + Long resourceableId = course.getResourceableId(); + sctx = new SubscriptionContext(CourseModule.ORES_COURSE_ASSESSMENT, resourceableId, cn.getIdent()); } return sctx; } @@ -255,7 +252,7 @@ public class AssessmentNotificationsHandler implements NotificationsHandler { * </ul> */ private List<AssessableCourseNode> getCourseTestNodes(ICourse course) { - List<AssessableCourseNode> assessableNodes = new ArrayList<AssessableCourseNode>(); + List<AssessableCourseNode> assessableNodes = new ArrayList<>(); Structure courseStruct = course.getRunStructure(); CourseNode rootNode = courseStruct.getRootNode(); @@ -294,10 +291,7 @@ public class AssessmentNotificationsHandler implements NotificationsHandler { && !course.getCourseEnvironment().getCourseGroupManager().getCourseEntry().getRepositoryEntryStatus().isClosed(); } - /** - * @see org.olat.core.commons.services.notifications.NotificationsHandler#createSubscriptionInfo(org.olat.core.commons.services.notifications.Subscriber, - * java.util.Locale, java.util.Date) - */ + @Override public SubscriptionInfo createSubscriptionInfo(final Subscriber subscriber, Locale locale, Date compareDate) { SubscriptionInfo si = null; Publisher p = subscriber.getPublisher(); @@ -315,15 +309,15 @@ public class AssessmentNotificationsHandler implements NotificationsHandler { // exceptions, course // can't be loaded when already deleted if (notificationsManager.isPublisherValid(p) && compareDate.before(latestNews)) { - Long courseId = new Long(p.getData()); + Long courseId = Long.valueOf(p.getData()); final ICourse course = loadCourseFromId(courseId); if (courseStatus(course)) { // course admins or users with the course right to have full access to // the assessment tool will have full access to user tests CourseGroupManager cgm = course.getCourseEnvironment().getCourseGroupManager(); - final boolean hasFullAccess = (cgm.isIdentityCourseAdministrator(identity) ? true : cgm.hasRight(identity, - CourseRights.RIGHT_ASSESSMENT)); - final Set<Identity> coachedUsers = new HashSet<Identity>(); + final boolean hasFullAccess = cgm.isIdentityCourseAdministrator(identity) + || cgm.hasRight(identity, CourseRights.RIGHT_ASSESSMENT); + final Set<Identity> coachedUsers = new HashSet<>(); if (!hasFullAccess) { // initialize list of users, only when user has not full access List<BusinessGroup> coachedGroups = cgm.getOwnedBusinessGroups(identity); diff --git a/src/main/java/org/olat/modules/scorm/OLATApiAdapter.java b/src/main/java/org/olat/modules/scorm/OLATApiAdapter.java index 3b2502cf0b3d9304288fa174b305106da97825be..3f27abb8415c47715beca49af360fd8facc65e8d 100644 --- a/src/main/java/org/olat/modules/scorm/OLATApiAdapter.java +++ b/src/main/java/org/olat/modules/scorm/OLATApiAdapter.java @@ -44,7 +44,6 @@ import java.util.Set; import org.olat.core.logging.LogDelegator; import org.olat.core.logging.OLATRuntimeException; -import org.olat.core.util.FileUtils; import org.olat.core.util.StringHelper; import org.olat.modules.scorm.manager.ScormManager; import org.olat.modules.scorm.server.beans.LMSDataFormBean; @@ -63,10 +62,9 @@ import ch.ethz.pfplms.scorm.api.ApiAdapter; * @author guido */ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm.api.ApiAdapterInterface { - private final ApiAdapter core; - //private ScormTrackingManager scormTracking; - - private Hashtable<String,String> olatScoCmi = new Hashtable<String,String>(); + private final ApiAdapter core; + + private Hashtable<String,String> olatScoCmi = new Hashtable<>(); private String olatStudentId; private String olatStudentName; @@ -81,7 +79,7 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm private LMSDataHandler odatahandler; private ScormManager scormManager; private SettingsHandlerImpl scormSettingsHandler; - private final List<ScormAPICallback> apiCallbacks = new ArrayList<ScormAPICallback>(2); + private final List<ScormAPICallback> apiCallbacks = new ArrayList<>(2); // private Properties scoresProp; // keys: sahsId; values = raw score of an sco private Properties lessonStatusProp; @@ -126,31 +124,21 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm scorePropsFile = new File(savePath, "_olat_score.properties"); scoresProp = new Properties(); if (scorePropsFile.exists()) { - InputStream is = null; - try { - is = new BufferedInputStream(new FileInputStream(scorePropsFile)); + try(InputStream is = new BufferedInputStream(new FileInputStream(scorePropsFile))) { scoresProp.load(is); } catch (IOException e) { throw e; } - finally { - if (is != null) FileUtils.closeSafely(is); - } } lessonStatusPropsFile = new File(savePath, "_olat_lesson_status.properties"); lessonStatusProp = new Properties(); if (lessonStatusPropsFile.exists()) { - InputStream is = null; - try { - is = new BufferedInputStream(new FileInputStream(lessonStatusPropsFile)); + try(InputStream is = new BufferedInputStream(new FileInputStream(lessonStatusPropsFile))) { lessonStatusProp.load(is); } catch (IOException e) { throw e; } - finally { - if (is != null) FileUtils.closeSafely(is); - } } scormManager = new ScormManager(cpRoot.getAbsolutePath(), true, true, true, scormSettingsHandler); @@ -274,12 +262,10 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm LMSDataFormBean lmsDataBean = new LMSDataFormBean(); lmsDataBean.setItemID(olatScoId); - //TODO:gs pass the dataBean for use, and do not get it a second time lmsDataBean.setNextAction("5"); lmsDataBean.setLmsAction("update"); - Map <String,String>cmiData = new HashMap<String,String>(); + Map <String,String>cmiData = new HashMap<>(); - //TODO:gs:c make it possible only to update the changed cmi data. if (ins.size() > 0){ Set <String> set = ins.keySet(); for(Iterator<String> it = set.iterator();it.hasNext();){ @@ -320,30 +306,20 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm synchronized(this) { //o_clusterOK by:fj: instance is spawned by the ScormAPIandDisplayController if(StringHelper.containsNonWhitespace(rawScore)) { scoresProp.put(olatScoId, rawScore); - OutputStream os = null; - try { - os = new BufferedOutputStream(new FileOutputStream(scorePropsFile)); + try(OutputStream os = new BufferedOutputStream(new FileOutputStream(scorePropsFile))) { scoresProp.store(os, null); } catch (IOException e) { throw new OLATRuntimeException(this.getClass(), "could not save scorm-properties-file: "+scorePropsFile.getAbsolutePath(), e); } - finally { - FileUtils.closeSafely(os); - } } if(StringHelper.containsNonWhitespace(lessonStatus)) { lessonStatusProp.put(olatScoId, lessonStatus); - OutputStream os = null; - try { - os = new BufferedOutputStream(new FileOutputStream(lessonStatusPropsFile)); + try(OutputStream os = new BufferedOutputStream(new FileOutputStream(lessonStatusPropsFile))) { lessonStatusProp.store(os, null); } catch (IOException e) { throw new OLATRuntimeException(this.getClass(), "could not save scorm-properties-file: "+scorePropsFile.getAbsolutePath(), e); } - finally { - FileUtils.closeSafely(os); - } } // notify if (!apiCallbacks.isEmpty()) { @@ -421,7 +397,6 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm * @return true if the item is completed */ public boolean isItemCompleted(String itemId){ - //TODO:gs make method faster by caching lmsBean, but when to set out of date? LMSDataFormBean lmsDataBean = new LMSDataFormBean(); lmsDataBean.setItemID(itemId); lmsDataBean.setLmsAction("get"); @@ -435,7 +410,6 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm * @return true if item has any not fullfilled preconditions */ public boolean hasItemPrerequisites(String itemId) { - //TODO:gs make method faster by caching lmsBean, but when to set out of date? LMSDataFormBean lmsDataBean = new LMSDataFormBean(); lmsDataBean.setItemID(itemId); lmsDataBean.setLmsAction("get"); @@ -453,7 +427,7 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm odatahandler = new LMSDataHandler(scormManager, lmsDataBean, scormSettingsHandler); LMSResultsBean lmsBean = odatahandler.getResultsBean(); String[][] preReqTbl = lmsBean.getPreReqTable(); - Map <String,String>itemsStatus = new HashMap<String,String>(); + Map <String,String>itemsStatus = new HashMap<>(); //put table into map for(int i=0; i < preReqTbl.length; i++){ if(preReqTbl[i][1].equals("not attempted")) preReqTbl[i][1] ="not_attempted"; @@ -467,7 +441,6 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm * @return the previos Sco itemId */ public Integer getPreviousSco(String recentId) { - // TODO:gs make method faster by caching lmsBean, but when to set out of date? LMSDataFormBean lmsDataBean = new LMSDataFormBean(); lmsDataBean.setItemID(recentId); lmsDataBean.setLmsAction("get"); @@ -481,7 +454,7 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm break; } } - return new Integer(previousNavScoId); + return Integer.valueOf(previousNavScoId); } /** @@ -489,7 +462,6 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm * @return the next Sco itemId */ public Integer getNextSco(String recentId) { - // TODO:gs make method faster by chaching lmsBean, but when to set out of date? LMSDataFormBean lmsDataBean = new LMSDataFormBean(); lmsDataBean.setItemID(recentId); lmsDataBean.setLmsAction("get"); @@ -503,7 +475,7 @@ public class OLATApiAdapter extends LogDelegator implements ch.ethz.pfplms.scorm break; } } - return new Integer(nextNavScoId); + return Integer.valueOf(nextNavScoId); } /**************************************************************************************** diff --git a/src/main/java/org/olat/modules/scorm/ScormAPIMapper.java b/src/main/java/org/olat/modules/scorm/ScormAPIMapper.java index 3a41494cb6fde67267eee3e222319df64a749b79..b8a4bf6e6dba72addd8f3928993d9b336c5ad6b2 100644 --- a/src/main/java/org/olat/modules/scorm/ScormAPIMapper.java +++ b/src/main/java/org/olat/modules/scorm/ScormAPIMapper.java @@ -49,6 +49,7 @@ import org.olat.core.logging.Tracing; import org.olat.core.util.StringHelper; import org.olat.course.CourseFactory; import org.olat.course.ICourse; +import org.olat.course.assessment.manager.AssessmentNotificationsHandler; import org.olat.course.nodes.ScormCourseNode; import org.olat.course.nodes.scorm.ScormEditController; import org.olat.course.run.scoring.ScoreEvaluation; @@ -199,7 +200,7 @@ public class ScormAPIMapper implements Mapper, ScormAPICallback, Serializable { if (currentPassed == null || !currentPassed.booleanValue()) { // </OLATEE-27> boolean increment = !attemptsIncremented && finish; - ScoreEvaluation sceval = new ScoreEvaluation(new Float(0.0f), Boolean.valueOf(passed)); + ScoreEvaluation sceval = new ScoreEvaluation(Float.valueOf(0.0f), Boolean.valueOf(passed)); scormNode.updateUserScoreEvaluation(sceval, userCourseEnv, identity, increment, Role.user); if(increment) { attemptsIncremented = true; @@ -214,12 +215,17 @@ public class ScormAPIMapper implements Mapper, ScormAPICallback, Serializable { } } else { boolean increment = !attemptsIncremented && finish; - ScoreEvaluation sceval = new ScoreEvaluation(new Float(0.0f), Boolean.valueOf(passed)); + ScoreEvaluation sceval = new ScoreEvaluation(Float.valueOf(0.0f), Boolean.valueOf(passed)); scormNode.updateUserScoreEvaluation(sceval, userCourseEnv, identity, false, Role.user); if(increment) { attemptsIncremented = true; } } + + if(finish) { + Long courseId = userCourseEnv.getCourseEnvironment().getCourseResourceableId(); + CoreSpringFactory.getImpl(AssessmentNotificationsHandler.class).markPublisherNews(identity, courseId); + } if (log.isDebug()) { String msg = "for scorm node:" + scormNode.getIdent() + " (" + scormNode.getShortTitle() + ") a lmsCommit for scoId " @@ -254,7 +260,7 @@ public class ScormAPIMapper implements Mapper, ScormAPICallback, Serializable { if (score > (currentScore != null ? currentScore : -1f)) { // </OLATEE-27> boolean increment = !attemptsIncremented && finish; - ScoreEvaluation sceval = new ScoreEvaluation(new Float(score), Boolean.valueOf(passed)); + ScoreEvaluation sceval = new ScoreEvaluation(Float.valueOf(score), Boolean.valueOf(passed)); scormNode.updateUserScoreEvaluation(sceval, userCourseEnv, identity, increment, Role.user); if(increment) { attemptsIncremented = true; @@ -274,12 +280,17 @@ public class ScormAPIMapper implements Mapper, ScormAPICallback, Serializable { } // </OLATEE-27> boolean increment = !attemptsIncremented && finish; - ScoreEvaluation sceval = new ScoreEvaluation(new Float(score), Boolean.valueOf(passed)); + ScoreEvaluation sceval = new ScoreEvaluation(Float.valueOf(score), Boolean.valueOf(passed)); scormNode.updateUserScoreEvaluation(sceval, userCourseEnv, identity, false, Role.user); if(increment) { attemptsIncremented = true; } } + + if(finish) { + Long courseId = userCourseEnv.getCourseEnvironment().getCourseResourceableId(); + CoreSpringFactory.getImpl(AssessmentNotificationsHandler.class).markPublisherNews(identity, courseId); + } if (log.isDebug()) { String msg = "for scorm node:" + scormNode.getIdent() + " (" + scormNode.getShortTitle() + ") a lmsCommit for scoId "