Squiz Matrix  4.12.2
 All Data Structures Namespaces Functions Variables Pages
move_assets_to_dated_folders.php
1 <?php
38 function printUsage()
39 {
40  echo "Move assets into dated folders\n\n";
41  echo "Usage: move_assets_to_dated_folders [system root] --root=[root node asset ID] --type=[asset type code]\n";
42  echo " --field=[asset date field] --period=[time period] (--folder-link-type=[folder link type])\n";
43  echo " (--move-asset-status=[move asset status]) (--make-folders-live)\n\n";
44  echo "REQUIRED PARAMETERS ==========\n";
45  echo "system root : The Matrix System Root directory\n";
46  echo "root node asset ID : The asset under which child assets are to be moved\n";
47  echo "asset type code : The type of assets to be moved\n";
48  echo "asset date field : The date field determining the destination for each asset - either 'created' or 'published'\n";
49  echo "time period : A specification of the folder structure to be created - either 'year', 'month' or 'day'\n";
50  echo " eg; when 'asset date field' is 'created', 'day' will create or re-use a structure of 2008 > 03 > 28 for assets created on 28th March 2008\n\n";
51  echo "OPTIONAL PARAMETERS ==========\n";
52  echo "folder link type : The link type for newly-created folders (either 1 or 2). Type 2 links are used by default\n";
53  echo "move asset status : The status code which must be matched for each asset before moving (eg; set to '16' to move only 'Live' assets)\n";
54  echo "-make-folders-live : Set the new date folders to 'Live' upon creation. Otherwise they will be 'Under Construction'\n\n";
55 
56 }//end printUsage()
57 
58 
73 function searchExistingDatedFolder($parent_id, $create_timestamp, $period, $folder_link_type, $make_folders_live=FALSE)
74 {
75  $am =& $GLOBALS['SQ_SYSTEM']->am;
76 
77  // Year and month folder names. Month and day are zero-padded numbers
78  $year = date('Y', $create_timestamp);
79  $month = str_pad(date('m', $create_timestamp), 2, '0', STR_PAD_LEFT);
80  $day = str_pad(date('d', $create_timestamp), 2, '0', STR_PAD_LEFT);
81 
82  // Variable housekeeping
83  $matching_year_folder_id = 0;
84  $matching_month_folder_id = 0;
85  $matching_day_folder_id = 0;
86  $matching_folder_id = 0;
87 
88  $matching_year_folders = searchExistingAsset($parent_id, $year, 'folder');
89 
90  $num_found_assets = count($matching_year_folders);
91 
92  if ($num_found_assets > 1) {
93  echo "\n- FAILED - found ".$num_found_assets.' year folders for '.$year."\n";
94  return 0;
95  }
96 
97  if ($num_found_assets == 1) {
98  $matching_year_folder_id = $matching_year_folders[0];
99  }
100 
101  if ($matching_year_folder_id == 0) {
102  echo "\n- Creating Year Folder ".$year.'... ';
103  $matching_year_folder_id = createAsset('folder', $year, $parent_id, $folder_link_type);
104  echo 'asset #'.$matching_year_folder_id."\n";
105  if ($make_folders_live) {
106  setAssetStatus($matching_year_folder_id, SQ_STATUS_LIVE);
107  }
108  }
109 
110  $matching_folder_id = $matching_year_folder_id;
111 
112  // If we're looking for a month or day, dig deeper
113  if (($matching_year_folder_id > 0) && ($period != 'year')) {
114  $matching_month_folders = searchExistingAsset($matching_year_folder_id, $month, 'folder');
115 
116  $num_found_assets = count($matching_month_folders);
117 
118  if ($num_found_assets > 1) {
119  echo "\n- FAILED - found ".$num_found_assets.' month folders for year/month '.$year.'/'.$month."\n";
120  return 0;
121  }
122 
123  if ($num_found_assets == 1) {
124  $matching_month_folder_id = $matching_month_folders[0];
125  }
126 
127  if ($matching_month_folder_id == 0) {
128  echo "\n- Creating Month Folder ".$month.' under Year '.$year.'... ';
129  $matching_month_folder_id = createAsset('folder', $month, $matching_year_folder_id, $folder_link_type);
130  echo 'asset #'.$matching_month_folder_id."\n";
131  if ($make_folders_live) {
132  setAssetStatus($matching_month_folder_id, SQ_STATUS_LIVE);
133  }
134  }
135 
136  $matching_folder_id = $matching_month_folder_id;
137  }
138 
139  // Searching for a day - the last possible level
140  if (($matching_month_folder_id > 0) && ($period == 'day')) {
141  $matching_day_folders = searchExistingAsset($matching_month_folder_id, $day, 'folder');
142 
143  $num_found_assets = count($matching_day_folders);
144 
145  if ($num_found_assets > 1) {
146  echo "\n- FAILED - found ".$num_found_assets.' day folders for year/month/day '.$year.'/'.$month.'/'.$day."\n";
147  return 0;
148  }
149 
150  if ($num_found_assets == 1) {
151  $matching_day_folder_id = $matching_day_folders[0];
152  }
153 
154  if ($matching_day_folder_id == 0) {
155  echo "\n- Creating Day Folder ".$day.' under Year/Month '.$year.'/'.$month.'... ';
156  $matching_day_folder_id = createAsset('folder', $day, $matching_month_folder_id, $folder_link_type);
157  echo 'asset #'.$matching_day_folder_id."\n";
158  if ($make_folders_live) {
159  setAssetStatus($matching_day_folder_id, SQ_STATUS_LIVE);
160  }
161  }
162 
163  $matching_folder_id = $matching_day_folder_id;
164  }
165 
166  return $matching_folder_id;
167 
168 }//end searchExistingDatedFolder()
169 
170 
182 function searchExistingAsset($parent_id, $asset_name, $asset_type_code='')
183 {
184  $db = MatrixDAL::getDb();
185  $sql = 'SELECT l.minorid, a.name '.
186  'FROM sq_ast_lnk l, sq_ast a '.
187  'WHERE l.majorid = :majorid ';
188 
189  if (!empty($asset_type_code)) {
190  $sql .= 'AND a.type_code = :type_code ';
191  }
192 
193  $sql .= 'AND a.assetid = l.minorid '.
194  'AND a.name = :asset_name';
195 
196  try {
197  $query = MatrixDAL::preparePdoQuery($sql);
198  MatrixDAL::bindValueToPdo($query, 'majorid', $parent_id);
199  MatrixDAL::bindValueToPdo($query, 'asset_name', $asset_name);
200  if (!empty($asset_type_code)) {
201  MatrixDAL::bindValueToPdo($query, 'type_code', $asset_type_code);
202  }
203  $matching_assets = MatrixDAL::executePdoAssoc($query, 0);
204  } catch (Exception $e) {
205  throw new Exception('Unable to search for an existing '.$asset_name.' asset: '.$e->getMessage());
206  }
207 
208  return $matching_assets;
209 
210 }//end searchExistingAsset()
211 
212 
224 function createAsset($asset_type, $asset_name, $parent_asset_id, $link_type=SQ_LINK_TYPE_1)
225 {
226  $am =& $GLOBALS['SQ_SYSTEM']->am;
227  $am->includeAsset($asset_type);
228 
229  $new_asset_id = 0;
230  $new_asset = new $asset_type();
231 
232  $parent_asset =& $am->getAsset($parent_asset_id);
233  if ($parent_asset->id) {
234  $new_asset->setAttrValue('name', $asset_name);
235 
236  $link = Array(
237  'asset' => &$parent_asset,
238  'link_type' => $link_type,
239  'value' => '',
240  'sort_order' => NULL,
241  'is_dependant' => 0,
242  'is_exclusive' => 0,
243  );
244 
245  if ($new_asset->create($link)) {
246  $new_asset_id = $new_asset->id;
247  }
248  }
249  $am->forgetAsset($parent_asset);
250 
251  return $new_asset_id;
252 
253 }//end createAsset()
254 
255 
269 function moveAssetToDatedFolder($asset_id, $parent_id, $asset_date_field, $time_period, $folder_link_type, $make_folders_live=FALSE)
270 {
271  $result = FALSE;
272  $am =& $GLOBALS['SQ_SYSTEM']->am;
273 
274  $asset =& $am->getAsset($asset_id);
275  if ($asset->id) {
276  $asset_timestamp = $asset->created;
277  if ($asset_date_field == 'published') {
278  $asset_timestamp = $asset->published;
279  }
280 
281  if ($asset_timestamp != NULL) {
282  // Find a destination folder for our asset
283  $destination_folder_id = searchExistingDatedFolder($parent_id, $asset_timestamp, $time_period, $folder_link_type, $make_folders_live);
284 
285  if ($destination_folder_id > 0) {
286  if ($asset_id == $destination_folder_id) {
287  echo 'asset is our destination dated folder. SKIPPING this asset. ';
288 
289  // Continue anyway
290  $result = TRUE;
291  } else {
292  $result = moveAsset($asset->id, $parent_id, $destination_folder_id);
293  }
294  }
295  } else {
296  echo 'asset '.$asset_date_field.' date does not exist. SKIPPING this asset. ';
297 
298  // Continue anyway
299  $result = TRUE;
300  }
301  }
302 
303  $am->forgetAsset($asset);
304 
305  return $result;
306 
307 }//end moveAssetToDatedFolder()
308 
309 
320 function moveAsset($source_asset_id, $source_parent_id, $destination_parent_id)
321 {
322  $result = FALSE;
323 
324  $links = $GLOBALS['SQ_SYSTEM']->am->getLinks($source_asset_id, SQ_SC_LINK_SIGNIFICANT, '', TRUE, 'minor');
325  foreach ($links as $link) {
326  if ($link['majorid'] == $source_parent_id) {
327  $link_info = $GLOBALS['SQ_SYSTEM']->am->getLinkById($link['linkid'], $source_asset_id, 'minor');
328 
329  $assets[$source_asset_id][] = Array(
330  'linkid' => $link_info['linkid'],
331  'link_type' => $link_info['link_type'],
332  'parentid' => $link_info['majorid'],
333  );
334  }
335  }
336 
337  $hh =& $GLOBALS['SQ_SYSTEM']->getHipoHerder();
338  $vars = Array(
339  'link_action' => 'move',
340  'assets' => $assets,
341  'to_parent_assetid' => $destination_parent_id,
342  'to_parent_pos' => 1,
343  );
344 
345  $errors = $hh->freestyleHipo('hipo_job_create_links', $vars);
346  $result = (count($errors) == 0);
347  if (!$result) print_r($errors);
348 
349  return $result;
350 
351 }//end moveAsset()
352 
353 
363 function setAssetStatus($asset_id, $status)
364 {
365  $am =& $GLOBALS['SQ_SYSTEM']->am;
366  $vars = Array(
367  'new_status' => $status,
368  'assetid' => $asset_id,
369  );
370  $hh =& $GLOBALS['SQ_SYSTEM']->getHipoHerder();
371  $errors = $hh->freestyleHipo('hipo_job_edit_status', $vars);
372  return (count($errors) == 0);
373 
374 }//end setAssetStatus()
375 
376 
377 /************************** MAIN PROGRAM ****************************/
378 
379 error_reporting(E_ALL);
380 if (ini_get('memory_limit') != '-1') ini_set('memory_limit', '-1');
381 
382 if ((php_sapi_name() != 'cli')) {
383  printUsage();
384  trigger_error("You can only run this script from the command line\n", E_USER_ERROR);
385 }
386 
387 require_once 'Console/Getopt.php';
388 
389 $shortopt = '';
390 $longopt = Array('root=', 'type=', 'field=', 'period=', 'folder-link-type=', 'make-folders-live', 'move-asset-status=');
391 
392 $args = Console_Getopt::readPHPArgv();
393 array_shift($args);
394 $options = Console_Getopt::getopt($args, $shortopt, $longopt);
395 if (empty($options[0])) {
396  printUsage();
397  exit();
398 }
399 
400 $SYSTEM_ROOT = (isset($_SERVER['argv'][1])) ? $_SERVER['argv'][1] : '';
401 if (empty($SYSTEM_ROOT)) {
402  echo "ERROR: You need to supply the path to the System Root as the first argument\n";
403  printUsage();
404  exit();
405 }
406 
407 if (!is_dir($SYSTEM_ROOT) || !is_readable($SYSTEM_ROOT.'/core/include/init.inc')) {
408  echo "ERROR: Path provided doesn't point to a Matrix installation's System Root. Please provide correct path and try again.\n";
409  printUsage();
410  exit();
411 }
412 
413 require_once $SYSTEM_ROOT.'/core/include/init.inc';
414 $am =& $GLOBALS['SQ_SYSTEM']->am;
415 
416 $SYSTEM_ROOT = '';
417 $root_node = 0;
418 $asset_type_code = '';
419 $asset_date_field = '';
420 $time_period = '';
421 $folder_link_type = SQ_LINK_TYPE_2;
422 $make_folders_live = FALSE;
423 $move_asset_status = -1;
424 
425 $mandatory_options = Array('--root', '--type', '--field', '--period');
426 $found_options = Array();
427 
428 // Initial check for mandatory parameters
429 foreach ($options[0] as $option) {
430  $found_options[] = $option[0];
431 }
432 reset($options[0]);
433 
434 $num_found_options = 0;
435 foreach ($found_options as $found_option) {
436  if (in_array($found_option, $mandatory_options)) {
437  $num_found_options++;
438  }
439 }
440 
441 if ($num_found_options <> count($mandatory_options)) {
442  printUsage();
443  exit();
444 }
445 
446 // Process dynamic command-line parameters
447 foreach ($options[0] as $option) {
448  switch ($option[0]) {
449  case '--root':
450  $root_node = (isset($option[1])) ? (int)$option[1] : 0;
451  if ($root_node <= 0) {
452  echo "Please specify a root node asset ID (--root)\n";
453  printUsage();
454  exit();
455  }
456 
457  $parent_asset =& $am->getAsset($root_node);
458  if (!$parent_asset->id) {
459  echo "The specified root node asset was not found\n";
460  printUsage();
461  exit();
462  }
463  $am->forgetAsset($parent_asset);
464  break;
465 
466  case '--type':
467  $asset_type_code = (isset($option[1])) ? $option[1] : '';
468  if (empty($asset_type_code)) {
469  echo "Please specify an asset type (--type)\n";
470  printUsage();
471  exit();
472  } else {
473  // Verify that the supplied asset code is correct
474  $am->includeAsset($asset_type_code);
475  }
476  break;
477 
478  case '--field':
479  $asset_date_field = (isset($option[1])) ? strtolower($option[1]) : '';
480  if (empty($asset_date_field)) {
481  echo "Please specify an asset date field (--field)\n";
482  printUsage();
483  exit();
484  } else if (($asset_date_field != 'created') && ($asset_date_field != 'published')) {
485  echo "Please specify either 'created' or 'published' for the asset date field\n";
486  printUsage();
487  exit();
488  }
489  break;
490 
491  case '--period':
492  $time_period = (isset($option[1])) ? strtolower($option[1]) : '';
493  if (empty($time_period)) {
494  echo "Please specify a time period (--period)\n";
495  printUsage();
496  exit();
497  } else if (($time_period != 'year') && ($time_period != 'month') && ($time_period != 'day')) {
498  echo "Please specify either 'year', 'month' or 'day' for the time period\n";
499  printUsage();
500  exit();
501  }
502  break;
503 
504  case '--folder-link-type':
505  $folder_link_type = (isset($option[1])) ? (int)$option[1] : SQ_LINK_TYPE_2;
506  if (($folder_link_type != SQ_LINK_TYPE_1) && ($folder_link_type != SQ_LINK_TYPE_2)) {
507  echo "Please specify either link type 1 or 2 for the folder link type (--folder-link-type)\n";
508  printUsage();
509  exit();
510  }
511  break;
512 
513  case '--make-folders-live':
514  $make_folders_live = TRUE;
515  break;
516 
517  case '--move-asset-status':
518  $move_asset_status = (isset($option[1])) ? (int)$option[1] : -1;
519  break;
520  }//end switch
521 }//end foreach
522 
523 // Check that the correct root password was entered
524 $root_user =& $GLOBALS['SQ_SYSTEM']->am->getSystemAsset('root_user');
525 
526 // Log in as root
527 if (!$GLOBALS['SQ_SYSTEM']->setCurrentUser($root_user)) {
528  echo "ERROR: Failed login as root user\n";
529  exit();
530 }
531 
532 // All validated - ready to Folderise(tm)
533 
534 // Get the immediate children of the parent asset that match the supplied type code
535 $assets_to_move = $am->getChildren($root_node, $asset_type_code, TRUE, NULL, NULL, NULL, TRUE, 1, 1);
536 $failed_asset_move = Array();
537 
538 if (count($assets_to_move) > 0) {
539  // Move the child assets
540  foreach (array_keys($assets_to_move) as $asset_id_to_move) {
541  // Only process assets in our "move list" that match the "move state"
542  $asset =& $am->getAsset($asset_id_to_move);
543  if (($move_asset_status == -1) || ($asset->status == $move_asset_status)) {
544  echo '- Moving asset #'.$asset_id_to_move.'... ';
545  $result = moveAssetToDatedFolder($asset_id_to_move, $root_node, $asset_date_field, $time_period, $folder_link_type, $make_folders_live);
546  if ($result) {
547  echo "done\n";
548  } else {
549  echo "FAILED!\n";
550  $failed_asset_move[] = $asset_id_to_move;
551  }
552  }
553  $am->forgetAsset($asset);
554  }
555 
556  if (!empty($failed_asset_move) > 0) {
557  echo "\n*** The following assets could not be moved due to errors detailed above:\n";
558  foreach ($failed_asset_move as $failed_asset_move_id) {
559  echo '- Asset # '.$failed_asset_move_id."\n";
560  }
561  echo "\n";
562  }
563 } else {
564  echo "- No matching assets were found to move. Script aborted\n";
565 }
566 
567 $GLOBALS['SQ_SYSTEM']->restoreCurrentUser();
568 echo "- All done!\n";
569 
570 ?>