Search in sources :

Example 1 with IdmCheckConcurrentExecution

use of eu.bcvsolutions.idm.core.scheduler.api.domain.IdmCheckConcurrentExecution in project CzechIdMng by bcvsolutions.

the class DefaultLongRunningTaskManager method processCreated.

/**
 * Executes long running task on this instance
 */
@Override
@Transactional
public synchronized List<LongRunningFutureTask<?>> processCreated() {
    String instanceId = configurationService.getInstanceId();
    LOG.debug("Processing created tasks from long running task queue on instance id [{}]", instanceId);
    // Prevent to mess up logged identity authentication => tasks can be started manually => will be visible in audit
    if (!securityService.isAuthenticated()) {
        securityService.setSystemAuthentication();
    }
    // 
    Set<String> processedTaskTypes = Sets.newHashSet();
    List<LongRunningFutureTask<?>> taskList = new ArrayList<LongRunningFutureTask<?>>();
    for (IdmLongRunningTaskDto task : service.findAllByInstance(instanceId, OperationState.CREATED)) {
        String taskType = task.getTaskType();
        UUID taskId = task.getId();
        // 
        if (processedTaskTypes.contains(taskType)) {
            LOG.debug("Task type [{}] is already processed.", taskType);
            continue;
        }
        // check concurrent tasks before task is executed
        try {
            Class<?> executorClass = Class.forName(taskType);
            if (executorClass.isAnnotationPresent(IdmCheckConcurrentExecution.class)) {
                IdmCheckConcurrentExecution disallowConcurrentExecution = executorClass.getAnnotation(IdmCheckConcurrentExecution.class);
                Class<? extends LongRunningTaskExecutor<?>>[] disallowConcurrentTaskTypes = disallowConcurrentExecution.taskTypes();
                if (disallowConcurrentTaskTypes.length > 0 && CollectionUtils.containsAny(processedTaskTypes, Arrays.asList(disallowConcurrentTaskTypes).stream().map(Class::getCanonicalName).collect(Collectors.toList()))) {
                    LOG.debug("Concurrent task for task type [{}] is already processed.", taskType);
                    processedTaskTypes.add(taskType);
                    continue;
                }
            }
        } catch (ClassNotFoundException ex) {
            LOG.warn("Class [{}] for long running task [{}] not found. Task execution will be skipped.", taskType, task.getId());
        }
        // 
        try {
            LongRunningFutureTask<?> futureTask = processCreated(taskId);
            if (futureTask != null) {
                taskList.add(futureTask);
                // prevent to persisted task starts twice
                Class<?> executorClass = AutowireHelper.getTargetClass(futureTask.getExecutor());
                if (executorClass.isAnnotationPresent(DisallowConcurrentExecution.class)) {
                    processedTaskTypes.add(taskType);
                }
                if (executorClass.isAnnotationPresent(IdmCheckConcurrentExecution.class)) {
                    IdmCheckConcurrentExecution disallowConcurrentExecution = executorClass.getAnnotation(IdmCheckConcurrentExecution.class);
                    Class<? extends LongRunningTaskExecutor<?>>[] disallowConcurrentTaskTypes = disallowConcurrentExecution.taskTypes();
                    if (disallowConcurrentTaskTypes.length == 0) {
                        processedTaskTypes.add(taskType);
                    }
                }
                // task is processed => remove from failed tasks to log exception again, when task fails in future
                failedLoggedTask.remove(taskId);
            }
        } catch (ResultCodeException ex) {
            // we want to process other task, if some task fails and log just once
            processedTaskTypes.add(taskType);
            if (!failedLoggedTask.contains(taskId)) {
                // we want to know in log, some scheduled task is not complete before next execution attempt
                ExceptionUtils.log(LOG, ex);
                failedLoggedTask.add(taskId);
            }
        }
    }
    return taskList;
}
Also used : IdmLongRunningTaskDto(eu.bcvsolutions.idm.core.scheduler.api.dto.IdmLongRunningTaskDto) ArrayList(java.util.ArrayList) ResultCodeException(eu.bcvsolutions.idm.core.api.exception.ResultCodeException) IdmCheckConcurrentExecution(eu.bcvsolutions.idm.core.scheduler.api.domain.IdmCheckConcurrentExecution) LongRunningTaskExecutor(eu.bcvsolutions.idm.core.scheduler.api.service.LongRunningTaskExecutor) LongRunningFutureTask(eu.bcvsolutions.idm.core.scheduler.api.dto.LongRunningFutureTask) UUID(java.util.UUID) Transactional(org.springframework.transaction.annotation.Transactional)

Example 2 with IdmCheckConcurrentExecution

use of eu.bcvsolutions.idm.core.scheduler.api.domain.IdmCheckConcurrentExecution in project CzechIdMng by bcvsolutions.

the class AbstractLongRunningTaskExecutor method validate.

/**
 * Validates task before start e.q. if task already running or to prevent run task concurrently.
 *
 * Look out: override this method additively
 *
 * @param task persisted task to validate
 */
@Override
public void validate(IdmLongRunningTaskDto task) {
    Assert.notNull(task, "Long running task has to be prepared before task is started");
    // 
    if (task.isRunning()) {
        throw new ResultCodeException(CoreResultCode.LONG_RUNNING_TASK_IS_RUNNING, ImmutableMap.of("taskId", task.getId()));
    }
    if (!OperationState.isRunnable(task.getResultState())) {
        throw new ResultCodeException(CoreResultCode.LONG_RUNNING_TASK_IS_PROCESSED, ImmutableMap.of("taskId", task.getId()));
    }
    // 
    // check concurrent task is not running (or waiting => operation state is used)
    String taskType = task.getTaskType();
    if (this.getClass().isAnnotationPresent(DisallowConcurrentExecution.class)) {
        IdmLongRunningTaskFilter filter = new IdmLongRunningTaskFilter();
        filter.setTaskType(taskType);
        filter.setOperationState(OperationState.RUNNING);
        // ignore waiting tasks
        filter.setRunning(Boolean.TRUE);
        List<UUID> runningTasks = longRunningTaskService.findIds(filter, null).getContent().stream().filter(t -> {
            // not self
            return !t.equals(task.getId());
        }).collect(Collectors.toList());
        if (!runningTasks.isEmpty()) {
            throw new ConcurrentExecutionException(CoreResultCode.LONG_RUNNING_TASK_IS_RUNNING, ImmutableMap.of("taskId", getName()));
        }
    }
    if (this.getClass().isAnnotationPresent(IdmCheckConcurrentExecution.class)) {
        List<String> disallowConcurrentTaskTypes = new ArrayList<>();
        IdmCheckConcurrentExecution disallowConcurrentExecution = this.getClass().getAnnotation(IdmCheckConcurrentExecution.class);
        Class<? extends LongRunningTaskExecutor<?>>[] taskTypes = disallowConcurrentExecution.taskTypes();
        if (taskTypes.length == 0) {
            disallowConcurrentTaskTypes.add(taskType);
        } else {
            disallowConcurrentTaskTypes.addAll(// TODO: move to utils somewhere - DRY manager
            Arrays.asList(taskTypes).stream().map(Class::getCanonicalName).collect(Collectors.toList()));
        }
        // TODO: filter.setTaskTypes(...)
        disallowConcurrentTaskTypes.forEach(concurrentTaskType -> {
            IdmLongRunningTaskFilter filter = new IdmLongRunningTaskFilter();
            filter.setTaskType(concurrentTaskType);
            filter.setOperationState(OperationState.RUNNING);
            // ignore waiting tasks
            filter.setRunning(Boolean.TRUE);
            List<UUID> runningTasks = longRunningTaskService.findIds(filter, null).getContent().stream().filter(t -> {
                // not self
                return !t.equals(task.getId());
            }).collect(Collectors.toList());
            if (!runningTasks.isEmpty()) {
                throw new AcceptedException(CoreResultCode.LONG_RUNNING_TASK_ACCEPTED, ImmutableMap.of("taskId", getName()));
            }
        });
    }
}
Also used : Arrays(java.util.Arrays) IdmProcessedTaskItemDto(eu.bcvsolutions.idm.core.scheduler.api.dto.IdmProcessedTaskItemDto) IdmEntityEventDto(eu.bcvsolutions.idm.core.api.dto.IdmEntityEventDto) ZonedDateTime(java.time.ZonedDateTime) Autowired(org.springframework.beans.factory.annotation.Autowired) HashMap(java.util.HashMap) TransactionContext(eu.bcvsolutions.idm.core.api.domain.TransactionContext) ConfigurationService(eu.bcvsolutions.idm.core.api.service.ConfigurationService) ArrayList(java.util.ArrayList) AutowireHelper(eu.bcvsolutions.idm.core.api.utils.AutowireHelper) AbstractDto(eu.bcvsolutions.idm.core.api.dto.AbstractDto) LookupService(eu.bcvsolutions.idm.core.api.service.LookupService) Propagation(org.springframework.transaction.annotation.Propagation) OperationResultDto(eu.bcvsolutions.idm.core.api.dto.OperationResultDto) OperationResult(eu.bcvsolutions.idm.core.api.entity.OperationResult) ResultCodeException(eu.bcvsolutions.idm.core.api.exception.ResultCodeException) EntityUtils(eu.bcvsolutions.idm.core.api.utils.EntityUtils) Map(java.util.Map) DisallowConcurrentExecution(org.quartz.DisallowConcurrentExecution) TransactionContextHolder(eu.bcvsolutions.idm.core.api.domain.TransactionContextHolder) IdmLongRunningTaskFilter(eu.bcvsolutions.idm.core.scheduler.api.dto.filter.IdmLongRunningTaskFilter) LongRunningTaskEventType(eu.bcvsolutions.idm.core.scheduler.api.event.LongRunningTaskEvent.LongRunningTaskEventType) ConcurrentExecutionException(eu.bcvsolutions.idm.core.scheduler.api.exception.ConcurrentExecutionException) BeanNameAware(org.springframework.beans.factory.BeanNameAware) IdmCheckConcurrentExecution(eu.bcvsolutions.idm.core.scheduler.api.domain.IdmCheckConcurrentExecution) EntityEventLock(eu.bcvsolutions.idm.core.api.event.EntityEventLock) ImmutableMap(com.google.common.collect.ImmutableMap) OperationState(eu.bcvsolutions.idm.core.api.domain.OperationState) AcceptedException(eu.bcvsolutions.idm.core.api.exception.AcceptedException) EnabledEvaluator(eu.bcvsolutions.idm.core.security.api.service.EnabledEvaluator) UUID(java.util.UUID) Collectors(java.util.stream.Collectors) ParameterConverter(eu.bcvsolutions.idm.core.api.utils.ParameterConverter) List(java.util.List) IdmLongRunningTaskDto(eu.bcvsolutions.idm.core.scheduler.api.dto.IdmLongRunningTaskDto) CoreResultCode(eu.bcvsolutions.idm.core.api.domain.CoreResultCode) Optional(java.util.Optional) LongRunningTaskEvent(eu.bcvsolutions.idm.core.scheduler.api.event.LongRunningTaskEvent) DefaultResultModel(eu.bcvsolutions.idm.core.api.dto.DefaultResultModel) ResultModel(eu.bcvsolutions.idm.core.api.dto.ResultModel) EntityEventManager(eu.bcvsolutions.idm.core.api.service.EntityEventManager) Transactional(org.springframework.transaction.annotation.Transactional) Assert(org.springframework.util.Assert) ResultCodeException(eu.bcvsolutions.idm.core.api.exception.ResultCodeException) ArrayList(java.util.ArrayList) ConcurrentExecutionException(eu.bcvsolutions.idm.core.scheduler.api.exception.ConcurrentExecutionException) IdmCheckConcurrentExecution(eu.bcvsolutions.idm.core.scheduler.api.domain.IdmCheckConcurrentExecution) AcceptedException(eu.bcvsolutions.idm.core.api.exception.AcceptedException) IdmLongRunningTaskFilter(eu.bcvsolutions.idm.core.scheduler.api.dto.filter.IdmLongRunningTaskFilter) UUID(java.util.UUID)

Aggregations

ResultCodeException (eu.bcvsolutions.idm.core.api.exception.ResultCodeException)2 IdmCheckConcurrentExecution (eu.bcvsolutions.idm.core.scheduler.api.domain.IdmCheckConcurrentExecution)2 IdmLongRunningTaskDto (eu.bcvsolutions.idm.core.scheduler.api.dto.IdmLongRunningTaskDto)2 ArrayList (java.util.ArrayList)2 UUID (java.util.UUID)2 Transactional (org.springframework.transaction.annotation.Transactional)2 ImmutableMap (com.google.common.collect.ImmutableMap)1 CoreResultCode (eu.bcvsolutions.idm.core.api.domain.CoreResultCode)1 OperationState (eu.bcvsolutions.idm.core.api.domain.OperationState)1 TransactionContext (eu.bcvsolutions.idm.core.api.domain.TransactionContext)1 TransactionContextHolder (eu.bcvsolutions.idm.core.api.domain.TransactionContextHolder)1 AbstractDto (eu.bcvsolutions.idm.core.api.dto.AbstractDto)1 DefaultResultModel (eu.bcvsolutions.idm.core.api.dto.DefaultResultModel)1 IdmEntityEventDto (eu.bcvsolutions.idm.core.api.dto.IdmEntityEventDto)1 OperationResultDto (eu.bcvsolutions.idm.core.api.dto.OperationResultDto)1 ResultModel (eu.bcvsolutions.idm.core.api.dto.ResultModel)1 OperationResult (eu.bcvsolutions.idm.core.api.entity.OperationResult)1 EntityEventLock (eu.bcvsolutions.idm.core.api.event.EntityEventLock)1 AcceptedException (eu.bcvsolutions.idm.core.api.exception.AcceptedException)1 ConfigurationService (eu.bcvsolutions.idm.core.api.service.ConfigurationService)1