fixed automatic exam state update error

This commit is contained in:
anhefti 2019-12-02 12:49:05 +01:00
parent 898a3c4d59
commit b2f0f1e81b
4 changed files with 42 additions and 6 deletions

View file

@ -28,6 +28,17 @@ public interface ExamDAO extends ActivatableEntityDAO<Exam, Exam>, BulkActionSup
* happened */
Result<Collection<Long>> allIdsOfInstituion(Long institutionId);
/** Updates the exam status for specified exam
*
* @param examId The exam identifier
* @param status the exam status to update to
* @param updateId the update identifier to check update write lock
* @return Result refer to updated Exam or to an error if happened */
@CacheEvict(
cacheNames = ExamSessionCacheService.CACHE_NAME_RUNNING_EXAM,
key = "#examId")
Result<Exam> updateState(Long examId, ExamStatus status, String updateId);
/** Saves the Exam and updates the running exam cache. */
@Override
@CacheEvict(

View file

@ -165,6 +165,29 @@ public class ExamDAOImpl implements ExamDAO {
});
}
@Override
public Result<Exam> updateState(final Long examId, final ExamStatus status, final String updateId) {
return recordById(examId)
.map(examRecord -> {
if (BooleanUtils.isTrue(BooleanUtils.toBooleanObject(examRecord.getUpdating()))) {
if (!updateId.equals(examRecord.getLastupdate())) {
throw new IllegalStateException("Exam is currently locked: " + examRecord);
}
}
final ExamRecord newExamRecord = new ExamRecord(
examRecord.getId(),
null, null, null, null, null, null, null, null,
status.name(),
null, null, null, null);
this.examRecordMapper.updateByPrimaryKeySelective(newExamRecord);
return this.examRecordMapper.selectByPrimaryKey(examId);
})
.flatMap(this::toDomainModel)
.onError(TransactionHandler::rollback);
}
@Override
@Transactional
public Result<Exam> save(final Exam exam) {
@ -173,7 +196,7 @@ public class ExamDAOImpl implements ExamDAO {
// check internal persistent write-lock
final ExamRecord oldRecord = this.examRecordMapper.selectByPrimaryKey(exam.id);
if (BooleanUtils.isTrue(BooleanUtils.toBooleanObject(oldRecord.getUpdating()))) {
throw new IllegalStateException("Exam is currently locked: " + String.valueOf(exam));
throw new IllegalStateException("Exam is currently locked: " + exam);
}
final ExamRecord examRecord = new ExamRecord(

View file

@ -177,7 +177,7 @@ public class ExamSessionServiceImpl implements ExamSessionService {
flushCache(exam);
}
log.warn("Exam {} is not currently running", examId);
log.info("Exam {} is not currently running", examId);
return Result.ofError(new NoSuchElementException(
"No currenlty running exam found for id: " + examId));

View file

@ -86,9 +86,10 @@ class ExamUpdateHandler {
return this.examDAO
.placeLock(exam.id, updateId)
.flatMap(e -> this.examDAO.save(new Exam(
.flatMap(e -> this.examDAO.updateState(
exam.id,
ExamStatus.RUNNING)))
ExamStatus.RUNNING,
updateId))
.flatMap(this::applySebClientRestriction)
.flatMap(e -> this.examDAO.releaseLock(e.id, updateId))
.onError(error -> this.examDAO.forceUnlock(exam.id)
@ -103,9 +104,10 @@ class ExamUpdateHandler {
return this.examDAO
.placeLock(exam.id, updateId)
.flatMap(e -> this.examDAO.save(new Exam(
.flatMap(e -> this.examDAO.updateState(
exam.id,
ExamStatus.FINISHED)))
ExamStatus.FINISHED,
updateId))
.flatMap(this::releaseSebClientRestriction)
.flatMap(e -> this.examDAO.releaseLock(e.id, updateId))
.onError(error -> this.examDAO.forceUnlock(exam.id))