diff --git a/lib/Alchemy/Phrasea/TaskManager/Editor/RecordMoverEditor.php b/lib/Alchemy/Phrasea/TaskManager/Editor/RecordMoverEditor.php index 9da1e6153c..cf59273ff5 100644 --- a/lib/Alchemy/Phrasea/TaskManager/Editor/RecordMoverEditor.php +++ b/lib/Alchemy/Phrasea/TaskManager/Editor/RecordMoverEditor.php @@ -81,57 +81,81 @@ class RecordMoverEditor extends AbstractEditor 0 + + + + ****************************************** --> EOF; } diff --git a/lib/Alchemy/Phrasea/TaskManager/Job/RecordMoverJob.php b/lib/Alchemy/Phrasea/TaskManager/Job/RecordMoverJob.php index 461eec020c..f53b3dbfb1 100644 --- a/lib/Alchemy/Phrasea/TaskManager/Job/RecordMoverJob.php +++ b/lib/Alchemy/Phrasea/TaskManager/Job/RecordMoverJob.php @@ -13,6 +13,9 @@ namespace Alchemy\Phrasea\TaskManager\Job; use Alchemy\Phrasea\Application; use Alchemy\Phrasea\TaskManager\Editor\RecordMoverEditor; +use \databox; +use Doctrine\DBAL\Connection; +use record_adapter; class RecordMoverJob extends AbstractJob { @@ -54,11 +57,13 @@ class RecordMoverJob extends AbstractJob protected function doJob(JobData $data) { $app = $data->getApplication(); - $task = $data->getTask(); - $settings = $task->getSettings(); + $settings = simplexml_load_string($data->getTask()->getSettings()); $logsql = (Boolean) $settings->logsql; - $tasks = (array) $settings->tasks; + $tasks = array(); + foreach($settings->tasks->task as $task) { + $tasks[] = $task; + } $data = $this->getData($app, $tasks, $logsql); @@ -69,6 +74,7 @@ class RecordMoverJob extends AbstractJob private function processData(Application $app, $row, $logsql) { + /** @var databox $databox */ $databox = $app['phraseanet.appbox']->get_databox($row['sbas_id']); $rec = $databox->get_record($row['record_id']); @@ -91,7 +97,8 @@ class RecordMoverJob extends AbstractJob $status[31 - $bit] = $val; } } - $rec->set_binary_status(implode('', $status)); + $status = implode('', $status); + $rec->set_binary_status($status); if ($logsql) { $this->log('debug', sprintf("on sbas %s set rid %s status to %s \n", $row['sbas_id'], $row['record_id'], $status)); } @@ -100,6 +107,7 @@ class RecordMoverJob extends AbstractJob case 'DELETE': if ($row['deletechildren'] && $rec->is_grouping()) { + /** @var record_adapter $child */ foreach ($rec->get_children() as $child) { $child->delete(); if ($logsql) { @@ -120,7 +128,6 @@ class RecordMoverJob extends AbstractJob private function getData(Application $app, array $tasks, $logsql) { $ret = []; - foreach ($tasks as $sxtask) { if (!$this->isStarted()) { break; @@ -128,7 +135,7 @@ class RecordMoverJob extends AbstractJob $task = $this->calcSQL($app, $sxtask); - if (!$task['active']) { + if (!$task['active'] || !$task['sql']) { continue; } @@ -137,6 +144,7 @@ class RecordMoverJob extends AbstractJob } try { + /** @var databox $databox */ $databox = $app['phraseanet.appbox']->get_databox($task['sbas_id']); } catch (\Exception $e) { $this->log('error', sprintf("can't connect sbas %s", $task['sbas_id'])); @@ -198,22 +206,28 @@ class RecordMoverJob extends AbstractJob ]; try { + /** @var databox $dbox */ $dbox = $app['phraseanet.appbox']->get_databox($sbas_id); $ret['basename'] = $dbox->get_label($app['locale']); $ret['basename_htmlencoded'] = htmlentities($ret['basename']); - switch ($ret['action']) { - case 'UPDATE': - $ret['sql'] = $this->calcUPDATE($app, $sbas_id, $sxtask, $playTest); - break; - case 'DELETE': - $ret['sql'] = $this->calcDELETE($app, $sbas_id, $sxtask, $playTest); - $ret['deletechildren'] = (int) ($sxtask['deletechildren']); - break; - default: - $ret['err'] = "bad action '" . $ret['action'] . "'"; - $ret['err_htmlencoded'] = htmlentities($ret['err']); - break; + try { + switch ($ret['action']) { + case 'UPDATE': + $ret['sql'] = $this->calcUPDATE($app, $sbas_id, $sxtask, $playTest); + break; + case 'DELETE': + $ret['sql'] = $this->calcDELETE($app, $sbas_id, $sxtask, $playTest); + $ret['deletechildren'] = (int)($sxtask['deletechildren']); + break; + default: + $ret['err'] = "bad action '" . $ret['action'] . "'"; + $ret['err_htmlencoded'] = htmlentities($ret['err']); + break; + } + } catch (\Exception $e) { + $ret['err'] = $e->getMessage(); + $ret['err_htmlencoded'] = htmlentities($e->getMessage()); } } catch (\Exception $e) { $ret['err'] = "bad sbas '" . $sbas_id . "'"; @@ -225,11 +239,8 @@ class RecordMoverJob extends AbstractJob private function calcUPDATE(Application $app, $sbas_id, &$sxtask, $playTest) { - $databox = $app['phraseanet.appbox']->get_databox($sbas_id); - $connbas = $databox->get_connection(); - $tws = array(); // NEGATION of updates, used to build the 'test' sql - // + // set coll_id ? if (($x = (int) ($sxtask->to->coll['id'])) > 0) { $tws[] = 'coll_id!=' . $x; @@ -252,9 +263,13 @@ class RecordMoverJob extends AbstractJob } // compute the 'where' clause - list($tw, $join) = $this->calcWhere($app, $sbas_id, $sxtask); + list($tw, $join, $err) = $this->calcWhere($app, $sbas_id, $sxtask); - // ... complete the where to buid the TEST + if(!empty($err)) { + throw(new \Exception($err)); + } + + // ... complete the where to build the TEST if (count($tws) == 1) { $tw[] = $tws[0]; } elseif (count($tws) > 1) { @@ -268,21 +283,21 @@ class RecordMoverJob extends AbstractJob } // build the real sql (select) - $sql = 'SELECT record_id FROM record' . $join; + $sql_real = 'SELECT record_id FROM record' . $join; if (count($tw) > 0) { - $sql .= ' WHERE ' . ((count($tw) == 1) ? $tw[0] : '(' . implode(') AND (', $tw) . ')'); + $sql_real .= ' WHERE ' . ((count($tw) == 1) ? $tw[0] : '(' . implode(') AND (', $tw) . ')'); } $ret = array( 'real' => array( - 'sql' => $sql, - 'sql_htmlencoded' => htmlentities($sql), + 'sql' => $sql_real, + 'sql_htmlencoded' => htmlentities($sql_real), ), - 'test' => array( - 'sql' => $sql_test, + 'test' => array( + 'sql' => $sql_test, 'sql_htmlencoded' => htmlentities($sql_test), - 'result' => NULL, - 'err' => NULL + 'result' => null, + 'err' => null ) ); @@ -296,7 +311,11 @@ class RecordMoverJob extends AbstractJob private function calcDELETE(Application $app, $sbas_id, &$sxtask, $playTest) { // compute the 'where' clause - list($tw, $join) = $this->calcWhere($app, $sbas_id, $sxtask); + list($tw, $join, $err) = $this->calcWhere($app, $sbas_id, $sxtask); + + if(!empty($err)) { + throw(new \Exception($err)); + } // build the TEST sql (select) $sql_test = 'SELECT SQL_CALC_FOUND_ROWS record_id FROM record' . $join; @@ -305,20 +324,20 @@ class RecordMoverJob extends AbstractJob $sql_test .= ' LIMIT 10'; // build the real sql (select) - $sql = 'SELECT record_id FROM record' . $join; + $sql_real = 'SELECT record_id FROM record' . $join; if (count($tw) > 0) - $sql .= ' WHERE ' . ((count($tw) == 1) ? $tw[0] : '(' . implode(') AND (', $tw) . ')'); + $sql_real .= ' WHERE ' . ((count($tw) == 1) ? $tw[0] : '(' . implode(') AND (', $tw) . ')'); $ret = [ 'real' => [ - 'sql' => $sql, - 'sql_htmlencoded' => htmlentities($sql), + 'sql' => $sql_real, + 'sql_htmlencoded' => htmlentities($sql_real), ], - 'test' => [ - 'sql' => $sql_test, + 'test' => [ + 'sql' => $sql_test, 'sql_htmlencoded' => htmlentities($sql_test), - 'result' => NULL, - 'err' => NULL + 'result' => null, + 'err' => null ] ]; @@ -331,6 +350,7 @@ class RecordMoverJob extends AbstractJob private function playTest(Application $app, $sbas_id, $sql) { + /** @var databox $databox */ $databox = $app['phraseanet.appbox']->get_databox($sbas_id); $connbas = $databox->get_connection(); $result = ['rids' => [], 'err' => '', 'n' => null]; @@ -344,7 +364,7 @@ class RecordMoverJob extends AbstractJob } $stmt->closeCursor(); } else { - $result['err'] = $connbas->last_error(); + $result['err'] = $connbas->errorInfo(); } return $result; @@ -352,16 +372,21 @@ class RecordMoverJob extends AbstractJob private function calcWhere(Application $app, $sbas_id, &$sxtask) { + $err = ""; + /** @var databox $databox */ $databox = $app['phraseanet.appbox']->get_databox($sbas_id); + /** @var Connection $connbas */ $connbas = $databox->get_connection(); + $struct = $databox->get_meta_structure(); + $tw = array(); $join = ''; $ijoin = 0; // criteria - if (($x = $sxtask->from->type['type']) !== NULL) { + if (($x = $sxtask->from->type['type']) !== null) { switch (strtoupper($x)) { case 'RECORD': $tw[] = 'parent_record_id!=record_id'; @@ -374,44 +399,65 @@ class RecordMoverJob extends AbstractJob // criteria foreach ($sxtask->from->text as $x) { - $ijoin++; - $comp = strtoupper($x['compare']); - if (in_array($comp, array('<', '>', '<=', '>=', '=', '!='))) { - $s = 'p' . $ijoin . '.name=' . $connbas->quote($x['field']) . ' AND p' . $ijoin . '.value' . $comp - . '' . $connbas->quote($x['value']) . ''; + $field = $struct->get_element_by_name($x['field']); + if($field != null) { + $ijoin++; + $comp = trim($x['compare']); + if (in_array($comp, array('<', '>', '<=', '>=', '=', '!='))) { + $s = 'p' . $ijoin . '.meta_struct_id=' . $connbas->quote($field->get_id()) . ' AND p' . $ijoin . '.value' . $comp + . '' . $connbas->quote($x['value']) . ''; - $tw[] = $s; - $join .= ' INNER JOIN prop AS p' . $ijoin . ' USING(record_id)'; + $tw[] = $s; + $join .= ' INNER JOIN metadatas AS p' . $ijoin . ' USING(record_id)'; + } else { + // bad comparison operator + $err .= sprintf("bad comparison operator (%s)\n", $comp); + } } else { - // bad comparison operator + // unknown field ? + $err .= sprintf("unknown field (%s)\n", $x['field']); } } // criteria foreach ($sxtask->from->date as $x) { - $ijoin++; - $s = 'p' . $ijoin . '.name=\'' . $x['field'] . '\' AND NOW()'; - $s .= strtoupper($x['direction']) == 'BEFORE' ? '<' : '>='; - $delta = (int) ($x['delta']); - if ($delta > 0) { - $s .= '(p' . $ijoin . '.value+INTERVAL ' . $delta . ' DAY)'; - } - elseif ($delta < 0) { - $s .= '(p' . $ijoin . '.value-INTERVAL ' . -$delta . ' DAY)'; + $field = $struct->get_element_by_name($x['field']); + if($field != null) { + $ijoin++; + $s = 'p' . $ijoin . '.meta_struct_id=' . $connbas->quote($field->get_id()) . ' AND NOW()'; + $dir = strtoupper($x['direction']); + if (in_array($dir, array('BEFORE', 'AFTER'))) { + // prevent malformed dates to act + $tw[] = '!ISNULL(CAST(p' . $ijoin . '.value AS DATETIME))'; + $s .= $dir == 'BEFORE' ? '<' : '>='; + $delta = (int)($x['delta']); + if ($delta > 0) { + $s .= '(p' . $ijoin . '.value+INTERVAL ' . $delta . ' DAY)'; + } elseif ($delta < 0) { + $s .= '(p' . $ijoin . '.value-INTERVAL ' . -$delta . ' DAY)'; + } else { + $s .= 'CAST(p' . $ijoin . '.value AS DATETIME)'; + } + + $tw[] = $s; + $join .= ' INNER JOIN metadatas AS p' . $ijoin . ' USING(record_id)'; + } else { + // bad direction + $err .= sprintf("bad direction (%s)\n", $x['direction']); + } } else { - $s .= 'p' . $ijoin . '.value'; + // unknown field ? + $err .= sprintf("unknown field (%s)\n", $x['field']); } - - $tw[] = $s; - $join .= ' INNER JOIN prop AS p' . $ijoin . ' USING(record_id)'; } // criteria - if (($x = $sxtask->from->coll) !== NULL) { + if (($x = $sxtask->from->coll) ) { $tcoll = explode(',', $x['id']); - foreach ($tcoll as $i => $c) - $tcoll[$i] = (int) $c; + foreach ($tcoll as $i => $c) { + $tcoll[$i] = (int)$c; + } if ($x['compare'] == '=') { if (count($tcoll) == 1) { $tw[] = 'coll_id = ' . $tcoll[0]; @@ -426,6 +472,7 @@ class RecordMoverJob extends AbstractJob } } else { // bad operator + $err .= sprintf("bad comparison operator (%s)\n", $x['compare']); } } @@ -443,6 +490,6 @@ class RecordMoverJob extends AbstractJob $tw[] = '(status & 0b' . $ma . ")=0"; } - return array($tw, $join); + return array($tw, $join, $err); } } diff --git a/templates/web/admin/task-manager/task-editor/archive.html.twig b/templates/web/admin/task-manager/task-editor/archive.html.twig index 2dcb9643e7..25bd1f16bb 100644 --- a/templates/web/admin/task-manager/task-editor/archive.html.twig +++ b/templates/web/admin/task-manager/task-editor/archive.html.twig @@ -63,30 +63,32 @@ {% block javascript %} + {% endblock %} diff --git a/templates/web/admin/task-manager/task-editor/ftp-pull.html.twig b/templates/web/admin/task-manager/task-editor/ftp-pull.html.twig index e97bfb5857..0f617c5a76 100644 --- a/templates/web/admin/task-manager/task-editor/ftp-pull.html.twig +++ b/templates/web/admin/task-manager/task-editor/ftp-pull.html.twig @@ -67,25 +67,25 @@ {% block javascript %} + {% endblock %} diff --git a/templates/web/admin/task-manager/task-editor/ftp.html.twig b/templates/web/admin/task-manager/task-editor/ftp.html.twig index a3caf494a5..49f6920a1b 100644 --- a/templates/web/admin/task-manager/task-editor/ftp.html.twig +++ b/templates/web/admin/task-manager/task-editor/ftp.html.twig @@ -17,17 +17,17 @@ {% block javascript %} + {% endblock %} diff --git a/templates/web/admin/task-manager/task-editor/record-mover.html.twig b/templates/web/admin/task-manager/task-editor/record-mover.html.twig index 121720922f..5d6f272e80 100644 --- a/templates/web/admin/task-manager/task-editor/record-mover.html.twig +++ b/templates/web/admin/task-manager/task-editor/record-mover.html.twig @@ -67,6 +67,8 @@ {% block javascript %} + {% endblock %} diff --git a/templates/web/admin/task-manager/task-editor/subdefs.html.twig b/templates/web/admin/task-manager/task-editor/subdefs.html.twig index 3c96e0eab1..ae66132bbd 100644 --- a/templates/web/admin/task-manager/task-editor/subdefs.html.twig +++ b/templates/web/admin/task-manager/task-editor/subdefs.html.twig @@ -66,6 +66,8 @@ {% block javascript %} + {% endblock %} diff --git a/templates/web/admin/task-manager/task-editor/task.html.twig b/templates/web/admin/task-manager/task-editor/task.html.twig index 60c0658d59..205c5aad74 100644 --- a/templates/web/admin/task-manager/task-editor/task.html.twig +++ b/templates/web/admin/task-manager/task-editor/task.html.twig @@ -48,11 +48,11 @@ - + {% endblock %} {% endblock %}