dependencyList = $dependencyList; $this->delayTimes = $delayTimes; } /** * @inheritDoc */ public function init(Task $task) { if (!empty($this->dependencyList)) $task->addConstraint(new DependencyConstraint($this->dependencyList, $this->delayTimes)); } /** * @inheritDoc */ public function primaryHandler(Task $task): bool { // First find all the dependencies try { $dependencies = $this->fetchDependencies($task); $this->output = json_encode($dependencies); return true; } catch (TasksException $e) { $this->output = 'Failed to fetch dependencies. TasksException: ' . $e->getMessage(); return false; } } /** * @inheritDoc */ public function getOutput(): string { return $this->output; } /** * @inheritDoc */ public function postHandler(Task $task) { // First find all the dependencies try { $dependencies = $this->fetchDependencies($task); $this->output = json_encode($dependencies); return true; } catch (TasksException $e) { $this->output = 'Failed to fetch dependencies. TasksException: ' . $e->getMessage(); return false; } } /** * @inheritDoc */ public function getPostOutput(): string { return $this->output; } /** * @inheritDoc */ public function getParentHandler(): ?Handler { return $this->parentHandler; } /** * @inheritDoc */ public function setParentHandler(Handler $parentHandler): void { $this->parentHandler = $parentHandler; } /** * @inheritDoc */ public function setParentInput(string $input): void { // Parent output gets set at this handler's output. // Only if this class has something to intervene it will override the parent output // Which should be always... but alas. $this->output = $input; } /** * @param Task $task * @return array * @throws TasksException */ protected function fetchDependencies(Task $task): array { // When it receives the task, all dependencies should already be handled // the primary handler will therefore connect with the DependencyConstraint and fetch dependencies $constraints = $task->getConstraints(); // First prepare a list of dependencies $dependencies = []; $dependencyConstraints = []; foreach ($constraints as $constraint) { if ($constraint instanceof Constraint) $dependencyConstraints[] = $constraint; } // If no dependencies found, throw exception if (empty($dependencyConstraints)) return $dependencies; // Afterwards build a list of dependencies /** @var DependencyConstraint $constraint */ foreach ($dependencyConstraints as $constraint) { foreach ($constraint->getDependencies() as $dependency) { if (!isset($dependencies[$dependency])) $dependencies[$dependency] = []; } } // Now that all dependencies are determined, fetch all the output $tasks = $this->loadTasksLib(); $taskStorage = $tasks->getTaskStorage(); foreach ($dependencies as $dependency => $data) { // Fetch the task try { $dependencyTask = $taskStorage->getTaskById($dependency); // Then fetch all output $dependencies[$dependency]['status'] = $dependencyTask->getStatus(); $dependencies[$dependency]['output'] = $dependencyTask->getOutput(); $dependencies[$dependency]['errors'] = $dependencyTask->getErrors(); $dependencies[$dependency]['post'] = $dependencyTask->getPostOutput(); $dependencies[$dependency]['postErrors'] = $dependencyTask->getPostErrors(); } catch (TasksException $e) { $dependencies[$dependency]['status'] = Task::FAILED; $dependencies[$dependency]['output'] = null; $dependencies[$dependency]['errors'] = 'Task not found.'; $dependencies[$dependency]['post'] = null; $dependencies[$dependency]['postErrors'] = null; } } return $dependencies; } /** * Load the tasks library, so that dependencies can get scanned later * * @return Tasks * @throws TasksException */ private function loadTasksLib(): Tasks { try { /** @var Libraries $libraries */ $libraries = Factory::getInstance('libraries'); /** @var Tasks $tasks */ $tasks = $libraries->get('async'); return $tasks; } catch (FactoryException | LibraryException $e) { throw new TasksException("Could not constrain task. Async library could not be loaded."); } } }