source: tags/release-1_7_0RC1/tools/create_listing_file.php @ 30563

Last change on this file since 30563 was 1823, checked in by laurent_duretz, 17 years ago

Integration of remote site protection in generate action

  • Property svn:eol-style set to native
  • Property svn:keywords set to Author Date Id Revision
File size: 54.2 KB
Line 
1<?php
2// +-----------------------------------------------------------------------+
3// | PhpWebGallery - a PHP based picture gallery                           |
4// | Copyright (C) 2002-2003 Pierrick LE GALL - pierrick@phpwebgallery.net |
5// | Copyright (C) 2003-2005 PhpWebGallery Team - http://phpwebgallery.net |
6// +-----------------------------------------------------------------------+
7// | branch        : BSF (Best So Far)
8// | file          : $RCSfile$
9// | last update   : $Date: 2007-02-15 18:50:08 +0000 (Thu, 15 Feb 2007) $
10// | last modifier : $Author: laurent_duretz $
11// | revision      : $Revision: 1823 $
12// +-----------------------------------------------------------------------+
13// | This program is free software; you can redistribute it and/or modify  |
14// | it under the terms of the GNU General Public License as published by  |
15// | the Free Software Foundation                                          |
16// |                                                                       |
17// | This program is distributed in the hope that it will be useful, but   |
18// | WITHOUT ANY WARRANTY; without even the implied warranty of            |
19// | MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU      |
20// | General Public License for more details.                              |
21// |                                                                       |
22// | You should have received a copy of the GNU General Public License     |
23// | along with this program; if not, write to the Free Software           |
24// | Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, |
25// | USA.                                                                  |
26// +-----------------------------------------------------------------------+
27
28// +-----------------------------------------------------------------------+
29// |                                User configuration                     |
30// +-----------------------------------------------------------------------+
31
32// ****** Gallery configuration ****** //
33// Srcipt version
34$conf['version'] = 'Alligator';
35
36// URL of main gallery
37$conf['gallery'] = 'http://';
38
39// prefix for thumbnails in "thumbnail" sub directories
40$conf['prefix_thumbnail'] = 'TN-';
41
42// $conf['file_ext'] lists all extensions (case insensitive) allowed for your PhpWebGallery installation
43$conf['file_ext'] = array('jpg','JPG','jpeg','JPEG','png','PNG','gif','GIF','mpg','zip', 'avi','mp3','ogg');
44
45// $conf['picture_ext'] must be a subset of $conf['file_ext']
46$conf['picture_ext'] = array('jpg','JPG','jpeg','JPEG','png','PNG','gif','GIF');
47
48// ****** Time limitation functionality ****** //
49// max execution time before refresh in seconds
50$conf['max_execution_time'] = (5*ini_get('max_execution_time'))/6; // 25 seconds with default PHP configuration
51
52// refresh delay is seconds
53$conf['refresh_delay'] = 0;
54
55// ****** EXIF support functionality ****** //
56// $conf['use_exif'] set to true if you want to use Exif information
57$conf['use_exif'] = false;
58
59// use_exif_mapping: same behaviour as use_iptc_mapping
60$conf['use_exif_mapping'] = array(
61  'date_creation' => 'DateTimeOriginal'
62  );
63
64// ****** IPTC support functionality ****** //
65// $conf['use_iptc'] set to true if you want to use IPTC informations of the
66// element according to get_sync_iptc_data function mapping, otherwise, set
67// to false
68$conf['use_iptc'] = false;
69
70// use_iptc_mapping : in which IPTC fields will PhpWebGallery find image
71// information ? This setting is used during metadata synchronisation. It
72// associates a phpwebgallery_images column name to a IPTC key
73$conf['use_iptc_mapping'] = array(
74  'keywords'        => '2#025',
75  'date_creation'   => '2#055',
76  'author'          => '2#122',
77  'name'            => '2#005',
78  'comment'         => '2#120');
79
80// ****** Directory protection functionality ****** //
81// Define if directories have to be protected if they are not
82$conf['protect'] = false;
83
84// index.php content for command 'protect'
85$conf['protect_content'] = '<?php header("Location: '.$conf['gallery'].'") ?>';
86
87// true/false : show/hide warnings
88$conf['protect_warnings'] = true;
89
90// ****** Thumbnails generation functionality ****** //
91// Define if images have to be reduced if they are not
92$conf['thumbnail'] = false;
93
94// Define method to generate thumbnails :
95// - fixed (width and height required);
96// - width (only width required);
97// - height (only height required);
98// - ratio (only ratio is required)
99// - exif (no other parameter required)
100$conf['thumbnail_method'] = 'ratio';
101
102// Height in pixels (greater than 0)
103$conf['thumbnail_height'] = 96;
104
105// Width in pixels (greater than 0)
106$conf['thumbnail_width'] = 96;
107
108// Ratio between original and thumbnail size (strictly between 0 and 1)
109$conf['thumbnail_ratio'] = 0.2;
110
111// Define thumbnail format : jpeg, png or gif (will be verified)
112$conf['thumbnail_format'] = 'jpeg';
113
114// ****** Directory mapping ****** //
115// directories names
116$conf['thumbs'] = 'thumbnail'; // thumbnails
117$conf['high'] = 'pwg_high'; // high resolution
118$conf['represent'] = 'pwg_representative'; // non pictures representative files
119
120// +-----------------------------------------------------------------------+
121// |                                Advanced script configuration          |
122// +-----------------------------------------------------------------------+
123
124// url of icon directory in yoga template
125$pwg_conf['icon_dir'] = $conf['gallery'].'/template/yoga/icon/';
126
127// list of actions managed by this script
128$pwg_conf['scan_action'] = array('clean', 'test', 'generate');
129
130// url of this script
131$pwg_conf['this_url'] = 'http://'.$_SERVER['SERVER_NAME'].$_SERVER['PHP_SELF'];
132
133// list of reserved directory names
134$pwg_conf['reserved_directory_names'] = array($conf['thumbs'], $conf['high'], $conf['represent'], ".", "..", ".svn");
135
136// content of index.php generated in protect action
137$pwg_conf['protect_content'] = '<?php header("Location: '.$conf['gallery'].'") ?>';
138
139// backup of PHP safe_mode INI parameter (used for time limitation)
140$pwg_conf['safe_mode'] = (ini_get('safe_mode') == '1') ? true : false;
141
142// This parameter will be fixed in pwg_init()
143$pwg_conf['gd_version_major'] = '';
144$pwg_conf['gd_version_full'] = '';
145$pwg_conf['gd_supported_format'] = array();
146
147// +-----------------------------------------------------------------------+
148// |                               Functions                               |
149// +-----------------------------------------------------------------------+
150
151/**
152 * write line in log file
153 *
154 * @param string line
155 * @return string
156 */
157function pwg_log($line)
158{
159  $log_file = fopen(__FILE__.'.log', 'a');
160  fwrite($log_file, $line);
161  fclose($log_file);
162}
163
164/**
165 * Check web server graphical capabilities
166 *
167 * @return string
168 */
169function pwg_check_graphics()
170{
171  //~ pwg_log('>>>>> pwg_check_graphics() >>>>>'."\n");
172 
173  global $conf, $pwg_conf;
174  $log = '';
175 
176  // Verify gd library for thumbnail generation
177  if ($conf['thumbnail'] and !is_callable('gd_info'))
178  {
179    $log .= '          <code class="warning">Warning -</code> Your server can not generate thumbnails. Thumbnail creation switched off.<br />'."\n";
180    // Switch off thumbnail generation
181    $conf['thumbnail'] = false;
182    return $log;
183  }
184 
185  // Verify thumnail format
186  if ($conf['thumbnail'])
187  {
188    $info = gd_info();
189   
190    // Backup GD major version
191    $pwg_conf['gd_version_full'] = ereg_replace('[[:alpha:][:space:]()]+', '', $info['GD Version']);
192    list($pwg_conf['gd_version_major']) = preg_split('/[.]+/', $pwg_conf['gd_version_full']);
193   
194    // Backup input/output format support
195    array_push($pwg_conf['gd_supported_format'], $info['JPG Support'] ? 'jpeg' : NULL);
196    array_push($pwg_conf['gd_supported_format'], $info['PNG Support'] ? 'png' : NULL);
197    array_push($pwg_conf['gd_supported_format'], ($info['GIF Read Support'] and $info['GIF Create Support']) ? 'gif' : NULL);
198   
199    // Check output format support
200    if (!in_array($conf['thumbnail_format'], $pwg_conf['gd_supported_format']))
201    {
202      $log .= '          <code class="warning">Warning -</code> Your server does not support thumbnail\'s <code>';
203      $log .= $conf['thumbnail_format'].'</code> format. Thumbnail creation switched off.<br />'."\n";
204    }
205   
206    switch ($conf['thumbnail_method'])
207    {
208      case 'exif':
209      {
210        // exif_thumbnail() must be callable
211        if (!is_callable('exif_thumbnail'))
212        {
213          $log .= '          <code class="warning">Warning -</code> Your server does not support thumbnail creation through EXIF datas. Thumbnail creation switched off.<br />'."\n";
214        }
215        break;
216      }
217      case 'fixed':
218      {
219        // $conf['thumbnail_width'] > 0
220        if (!is_numeric($conf['thumbnail_width']) or $conf['thumbnail_width'] <= 0)
221        {
222          $log .= '          <code class="failure">Failure -</code> Bad value <code>thumbnail_width = ';
223          $log .= var_export($conf['thumbnail_width'], true).'</code>. Thumbnail creation switched off.<br />'."\n";
224        }
225        // $conf['thumbnail_height'] > 0
226        if (!is_numeric($conf['thumbnail_height']) or $conf['thumbnail_height'] <= 0)
227        {
228          $log .= '          <code class="failure">Failure -</code> Bad value <code>thumbnail_height = ';
229          $log .= var_export($conf['thumbnail_height'], true).'</code>. Thumbnail creation switched off.<br />'."\n";
230        }
231        break;
232      }
233      case 'ratio':
234      {
235        // 0 < $conf['thumbnail_ratio'] < 1
236        if (!is_numeric($conf['thumbnail_ratio']) or $conf['thumbnail_ratio'] <= 0 or $conf['thumbnail_ratio'] >= 1)
237        {
238          $log .= '          <code class="failure">Failure -</code> Bad value <code>thumbnail_ratio = ';
239          $log .= var_export($conf['thumbnail_ratio'], true).'</code>. Thumbnail creation switched off.<br />'."\n";
240        }
241        break;
242      }
243      case 'width':
244      {
245        // $conf['thumbnail_width'] > 0
246        if (!is_numeric($conf['thumbnail_width']) or $conf['thumbnail_width'] <= 0)
247        {
248          $log .= '          <code class="failure">Failure -</code> Bad value <code>thumbnail_width = ';
249          $log .= var_export($conf['thumbnail_width'], true).'</code>. Thumbnail creation switched off.<br />'."\n";
250        }
251        break;
252      }
253      case 'height':
254      {
255        // $conf['thumbnail_height'] > 0
256        if (!is_numeric($conf['thumbnail_height']) or $conf['thumbnail_height'] <= 0)
257        {
258          $log .= '          <code class="failure">Failure -</code> Bad value <code>thumbnail_height = ';
259          $log .= var_export($conf['thumbnail_height'], true).'</code>. Thumbnail creation switched off.<br />'."\n";
260        }
261        break;
262      }
263      default:
264      {
265        // unknown method
266          $log .= '          <code class="failure">Failure -</code> Bad value <code>thumbnail_method = ';
267          $log .= var_export($conf['thumbnail_method'], true).'</code>. Thumbnail creation switched off.<br />'."\n";
268        break;
269      }
270    }
271   
272    if (strlen($log))
273    {
274      $conf['thumbnail'] = false;
275    }
276  }
277 
278  //~ pwg_log('<<<<< pwg_check_graphics() returns '.var_export($log, TRUE).' <<<<<'."\n");
279  return $log;
280}
281
282/**
283 * returns xml </dirX> lines
284 *
285 * @param integer $dir_start
286 * @param integer $dir_number
287 * @return string
288 */
289function pwg_close_level($dir_start, $dir_number)
290{
291  //~ pwg_log('>>>>> pwg_close_level($dir_start = '.var_export($dir_start, TRUE).', $dir_number = '.var_export($dir_number, TRUE).') >>>>>'."\n");
292 
293  $lines ='';
294  do
295  {
296    $lines .= str_repeat(' ', 2*$dir_start).'</dir'.$dir_start.">\n";
297    $dir_number--;
298    $dir_start--;
299  }
300  while(($dir_number > 0) && ($dir_start >= 0));
301 
302  //~ pwg_log('<<<<< pwg_close_level returns '.var_export($lines, TRUE).' <<<<<'."\n");
303  return $lines;
304}
305
306/**
307 * return a cleaned IPTC value
308 *
309 * @param string value
310 * @return string
311 */
312function pwg_clean_iptc_value($value)
313{
314  //~ pwg_log('>>>>> pwg_clean_iptc_value ($value = '.var_export($value, TRUE).') >>>>>'."\n");
315 
316  // strip leading zeros (weird Kodak Scanner software)
317  while (isset($value[0]) and $value[0] == chr(0))
318  {
319    $value = substr($value, 1);
320  }
321  // remove binary nulls
322  $value = str_replace(chr(0x00), ' ', $value);
323
324  //~ pwg_log('<<<<< pwg_clean_iptc_value() returns '.var_export($value, TRUE).' <<<<<'."\n");
325  return $value;
326}
327
328/**
329 * returns informations from IPTC metadata, mapping is done at the beginning
330 * of the function
331 *
332 * @param string $filename
333 * @param string $map
334 * @return array
335 */
336function pwg_get_iptc_data($filename, $map)
337{
338  //~ pwg_log('>>>>> pwg_get_iptc_data ($filename = '.var_export($filename, TRUE).', $map = '.var_export($map, TRUE).') >>>>>'."\n");
339 
340  $result = array();
341
342  // Read IPTC data
343  $iptc = array();
344
345  $imginfo = array();
346  getimagesize($filename, $imginfo);
347
348  if (isset($imginfo['APP13']))
349  {
350    $iptc = iptcparse($imginfo['APP13']);
351    if (is_array($iptc))
352    {
353      $rmap = array_flip($map);
354      foreach (array_keys($rmap) as $iptc_key)
355      {
356        if (isset($iptc[$iptc_key][0]))
357        {
358          if ($iptc_key == '2#025')
359          {
360            $value = implode(',', array_map('pwg_clean_iptc_value', $iptc[$iptc_key]));
361          }
362          else
363          {
364            $value = pwg_clean_iptc_value($iptc[$iptc_key][0]);
365          }
366
367          foreach (array_keys($map, $iptc_key) as $pwg_key)
368          {
369            $result[$pwg_key] = $value;
370          }
371        }
372      }
373    }
374  }
375 
376  //~ pwg_log('<<<<< pwg_get_iptc_data() returns '.var_export($result, TRUE).' <<<<<'."\n");
377  return $result;
378}
379
380/**
381 * returns informations from IPTC metadata
382 *
383 * @param string $file
384 * @return array iptc
385 */
386function pwg_get_sync_iptc_data($file)
387{
388  //~ pwg_log('>>>>> pwg_get_sync_iptc_data ($file = '.var_export($file, TRUE).') >>>>>'."\n");
389
390  global $conf;
391
392  $map = $conf['use_iptc_mapping'];
393  $datefields = array('date_creation', 'date_available');
394
395  $iptc = pwg_get_iptc_data($file, $map);
396
397  foreach ($iptc as $pwg_key => $value)
398  {
399    if (in_array($pwg_key, $datefields))
400    {
401      if ( preg_match('/(\d{4})(\d{2})(\d{2})/', $value, $matches))
402      {
403        $value = $matches[1].'-'.$matches[2].'-'.$matches[3];
404      }
405    }
406    if ($pwg_key == 'keywords')
407    {
408      // official keywords separator is the comma
409      $value = preg_replace('/[.;]/', ',', $value);
410      $value = preg_replace('/^,+|,+$/', '', $value);
411    }
412    $iptc[$pwg_key] = htmlentities($value);
413  }
414
415  $iptc['keywords'] = implode(',', array_unique(explode(',', $iptc['keywords'])));
416
417  //~ pwg_log('<<<<< pwg_get_sync_iptc_data() returns '.var_export($iptc, TRUE).' <<<<<'."\n");
418  return $iptc;
419}
420
421/**
422 * return extension of the representative file
423 *
424 * @param string $file_dir
425 * @param string $file_short
426 * @return string
427 */
428function pwg_get_representative_ext($file_dir, $file_short)
429{
430  //~ pwg_log('>>>>> pwg_get_representative_ext($file_dir = '.var_export($file_dir, TRUE).', $file_short = '.var_export($file_short, TRUE).') >>>>>'."\n");
431 
432  global $conf;
433 
434  $rep_ext = '';
435  foreach ($conf['picture_ext'] as $ext)
436  {
437    if (file_exists($file_dir.'/'.$conf['represent'].'/'.$file_short.'.'.$ext))
438    {
439      $rep_ext = $ext;
440      break;
441    }
442  }
443 
444  //~ pwg_log('<<<<< pwg_get_representative_ext() returns '.var_export($rep_ext, TRUE).' <<<<<'."\n");
445  return $rep_ext; 
446}
447
448/**
449 * return 'true' if high resolution picture exists else ''
450 *
451 * @param string $file_dir
452 * @param string $file_base
453 * @return boolean
454 */
455function pwg_get_high($file_dir, $file_base)
456{
457  //~ pwg_log('>>>>> pwg_get_high($file = '.var_export($file_dir, TRUE).', $line = '.var_export($file_base, TRUE).') >>>>>'."\n");
458 
459  global $conf;
460 
461  $high = false;
462  if (file_exists($file_dir.'/'.$conf['high'].'/'.$file_base))
463  {
464    $high = true;
465  }
466 
467  //~ pwg_log('<<<<< pwg_get_high() returns '.var_export($high, TRUE).' <<<<<'."\n");
468  return $high; 
469}
470
471/**
472 * return filename without extension
473 *
474 * @param string $filename
475 * @return string
476 */
477function pwg_get_filename_wo_extension($filename)
478{
479  //~ pwg_log('>>>>> _get_filename_wo_extension($filename = '.var_export($filename, TRUE).') >>>>>'."\n");
480 
481  $short_name = substr($filename, 0, strrpos($filename, '.'));
482 
483  //~ pwg_log('<<<<< _get_filename_wo_extension() returns '.var_export($short_name, TRUE).' <<<<<'."\n");
484  return $short_name;
485}
486
487/**
488 * return extension of the thumbnail and complete error_log
489 *
490 * @param string $file_dir
491 * @param string $file_short
492 * @param string $file_ext
493 * @param string &$error_log
494 * @return string
495 */
496function pwg_get_thumbnail_ext($file_dir, $file_short, $file_ext, &$error_log)
497{
498  //~ pwg_log('>>>>> pwg_get_thumbnail_ext($file_dir = '.var_export($file_dir, TRUE).', $file_short = '.var_export($file_short, TRUE).') >>>>>'."\n");
499 
500  global $conf;
501 
502  $thumb_ext = '';
503  foreach ($conf['picture_ext'] as $ext)
504  {
505    if (file_exists($file_dir.'/'.$conf['thumbs'].'/'.$conf['prefix_thumbnail'].$file_short.'.'.$ext))
506    {
507      $thumb_ext = $ext;
508      break;
509    }
510  }
511 
512  if ($thumb_ext == '')
513  {
514    if ($conf['thumbnail'])
515    {
516      $log = pwg_icon_file($file_dir, $file_short, $file_ext);
517      if (strpos($log, 'success'))
518      {
519        $thumb_ext = $conf['thumbnail_format'];
520      }
521      $error_log .= $log; 
522    }
523  }
524 
525  //~ pwg_log('<<<<< pwg_get_thumbnail_ext() returns '.var_export($thumb_ext, TRUE).' <<<<<'."\n");
526  return $thumb_ext; 
527}
528
529
530/**
531 * return error logs
532 *
533 * @param string $file_dir
534 * @param string $file_short
535 * @param string $file_ext
536 * @return string
537 */
538function pwg_icon_file($file_dir, $file_short, $file_ext)
539{
540  //~ pwg_log('>>>>> pwg_icon_file($file_dir = '.var_export($file_dir, TRUE).', $file_short = '.var_export($file_short, TRUE).') >>>>>'."\n");
541 
542  global $conf, $pwg_conf;
543 
544  $error_log = '';
545 
546  // Get original properties (width, height)
547  if ($image_size = getimagesize($file_dir.'/'.$file_short.'.'.$file_ext))
548  {
549    $src_width = $image_size[0];
550    $src_height = $image_size[1];
551  }
552  else
553  {
554    $error_log .= '          <code class="failure">Failure -</code> Can not generate icon for <code>';
555    $error_log .= $file_dir.'/'.$file_short.'.'.$file_ext.'</code>';
556    $error_log .= ' <img src="'.$pwg_conf['icon_dir'].'add_tag.png" title="width/height are unreadable" /><br />'."\n";
557    return $error_log;
558  }
559 
560  // Check input format
561  $dst_format = $conf['thumbnail_format'];
562  $src_format = ($file_ext == 'jpg' or $file_ext == 'JPG') ? 'jpeg' : strtolower($file_ext);
563  if (!in_array($src_format, $pwg_conf['gd_supported_format']))
564  {
565    $error_log .= '          <code class="failure">Failure -</code> Can not generate icon for <code>';
566    $error_log .= $file_dir.'/'.$file_short.'.'.$file_ext.'</code>';
567    $error_log .= ' <img src="'.$pwg_conf['icon_dir'].'add_tag.png" title="format not supported" /><br />'."\n";
568    return $error_log;
569  }
570 
571  // Calculate icon properties (width, height)
572  switch ($conf['thumbnail_method'])
573  {
574    case 'fixed':
575    {
576      $dst_width  = $conf['thumbnail_width'];
577      $dst_height = $conf['thumbnail_height'];
578      break;
579    }
580    case 'width':
581    {
582      $dst_width  = $conf['thumbnail_width'];
583      $dst_height = $dst_width * $src_height / $src_width;
584      break;
585    }
586    case 'height':
587    {
588      $dst_height = $conf['thumbnail_height'];
589      $dst_width  = $dst_height * $src_width / $src_height;
590      break;
591    }
592    case 'ratio':
593    {
594      $dst_width  = round($src_width * $conf['thumbnail_ratio']);
595      $dst_height = round($src_height * $conf['thumbnail_ratio']);
596      break;
597    }
598    case 'exif':
599    default:
600    {
601      // Nothing to do
602    }
603  }
604 
605  // Creating icon
606  if ($conf['thumbnail_method'] == 'exif')
607  {
608    $src = exif_thumbnail($file_dir.'/'.$file_short.'.'.$file_ext, $width, $height, $imagetype);
609    if ($src === false)
610    {
611      $error_log .= '          <code class="failure">Failure -</code> No EXIF thumbnail in <code>';
612      $error_log .= $file_dir.'/'.$file_short.'.'.$file_ext.'</code><br />'."\n";
613      return $error_log;
614    }
615    $dst = imagecreatefromstring($src);
616    if ($src === false)
617    {
618      $error_log .= '          <code class="failure">Failure -</code> EXIF thumbnail format not supported in <code>';
619      $error_log .= $file_dir.'/'.$file_short.'.'.$file_ext.'</code><br />'."\n";
620      return $error_log;
621    }
622  }
623  else
624  {
625    if (($pwg_conf['gd_version_major'] != 2)) // or ($conf['thumbnail_format'] == 'gif'))
626    {
627      $dst = imagecreate($dst_width, $dst_height);
628    }
629    else
630    {
631      $dst = imagecreatetruecolor($dst_width, $dst_height);
632    }
633    $src = call_user_func('imagecreatefrom'.$src_format, $file_dir.'/'.$file_short.'.'.$file_ext);
634    if (!$src)
635    {
636      $error_log .= '          <code class="failure">Failure -</code> Internal error for <code>imagecreatefrom'.$src_format.'()</code>';
637      $error_log .= 'with <code>'.$file_dir.'/'.$file_short.'.'.$file_ext.'</code><br />'."\n";
638      return $error_log;
639    }
640     
641    if (($pwg_conf['gd_version_major'] != 2))
642    {
643      if (!imagecopyresized($dst, $src, 0, 0, 0, 0, $dst_width, $dst_height, $src_width, $src_height))
644      {
645        $error_log .= '          <code class="failure">Failure -</code> Internal error for <code>imagecopyresized()</code>';
646        $error_log .= 'with <code>'.$file_dir.'/'.$file_short.'.'.$file_ext.'</code><br />'."\n";
647        return $error_log;
648      }
649    }
650    else
651    {
652      if (!imagecopyresampled($dst, $src, 0, 0, 0, 0, $dst_width, $dst_height, $src_width, $src_height))
653      {
654        $error_log .= '          <code class="failure">Failure -</code> Internal error for <code>imagecopyresampled()</code>';
655        $error_log .= 'with <code>'.$file_dir.'/'.$file_short.'.'.$file_ext.'</code><br />'."\n";
656        return $error_log;
657      }
658    }
659  }
660 
661  if (!call_user_func('image'.$dst_format, $dst, $file_dir.'/'.$conf['thumbs'].'/'.$conf['prefix_thumbnail'].$file_short.'.'.$conf['thumbnail_format']))
662  {
663    $error_log .= '          <code class="failure">Failure -</code> Can not write <code>';
664    $error_log .= $file_dir.'/'.$conf['thumbs'].'/'.$conf['prefix_thumbnail'].$file_short.'.'.$file_ext.'</code> to generate thumbnail<br />'."\n";
665    return $error_log;
666  }
667 
668  $error_log .= '          <code class="success">Success -</code> Thumbnail generated for <code>';
669  $error_log .= $file_dir.'/'.$file_short.'.'.$file_ext.'</code><br />'."\n";
670
671  //~ pwg_log('<<<<< pwg_icon_file() returns '.var_export($error_log, TRUE).' <<<<<'."\n");
672  return $error_log; 
673}
674
675/**
676 * completes xml line <element .../> and returns error log
677 *
678 * @param string $file
679 * @param string &$line
680 * @return string
681 */
682function pwg_scan_file($file_full, &$line)
683{
684  //~ pwg_log('>>>>> pwg_scan_file($file = '.var_export($file_full, TRUE).', $line = '.var_export($line, TRUE).') >>>>>'."\n");
685 
686  global $conf, $pwg_conf;
687 
688  $error_log ='';
689 
690  $file_base  = basename($file_full);
691  $file_short = pwg_get_filename_wo_extension($file_base);
692  $file_ext   = pwg_get_file_extension($file_base);
693  $file_dir   = dirname($file_full);
694
695  $element['file'] = $file_base;
696  $element['path'] = 'http://'.dirname($_SERVER['SERVER_NAME'].$_SERVER['PHP_SELF']).substr($file_dir, 1).'/'.$file_base;
697 
698  if (in_array($file_ext, $conf['picture_ext']))
699  {
700    // Here we scan a picture : thumbnail is mandatory, high is optionnal, representative is not scanned
701    $element['tn_ext'] = pwg_get_thumbnail_ext($file_dir, $file_short, $file_ext, $error_log);
702    if ($element['tn_ext'] != '')
703    {
704      // picture has a thumbnail, get image width, heigth, size in Mo
705      $element['filesize'] = floor(filesize($file_full) / 1024);
706      if ($image_size = getimagesize($file_full))
707      {
708        $element['width'] = $image_size[0];
709        $element['height'] = $image_size[1];
710      }
711     
712      // get high resolution
713      if (pwg_get_high($file_dir, $file_base))
714      {
715        $element['has_high'] = 'true';
716      }
717     
718      // get EXIF meta datas
719      if ($conf['use_exif'])
720      {
721        // Verify activation of exif module
722        if (extension_loaded('exif'))
723        {
724          if ($exif = read_exif_data($file_full))
725          {
726            foreach ($conf['use_exif_mapping'] as $pwg_key => $exif_key )
727            {
728              if (isset($exif[$exif_key]))
729              {
730                if ( in_array($pwg_key, array('date_creation','date_available') ) )
731                {
732                  if (preg_match('/^(\d{4}):(\d{2}):(\d{2})/', $exif[$exif_key], $matches))
733                    {
734                      $element[$pwg_key] = $matches[1].'-'.$matches[2].'-'.$matches[3];
735                    }
736                }
737                else
738                {
739                  $element[$pwg_key] = $exif[$exif_key];
740                }
741              }
742            }
743          }
744        }
745      }
746     
747      // get IPTC meta datas
748      if ($conf['use_iptc'])
749      {
750        $iptc = pwg_get_sync_iptc_data($file_full);
751        if (count($iptc) > 0)
752        {
753          foreach (array_keys($iptc) as $key)
754          {
755            $element[$key] = addslashes($iptc[$key]);
756          }
757        }
758      }
759     
760    }
761    else
762    {
763      $error_log .= '          <code class="failure">Failure -</code> Thumbnail is missing for <code>'.$file_dir.'/'.$file_base.'</code>';
764      $error_log .= ' <img src="'.$pwg_conf['icon_dir'].'add_tag.png" title="'.$file_dir.'/thumbnail/'.$conf['prefix_thumbnail'].$file_short;
765      $error_log .= '.xxx ('.implode(', ', $conf['picture_ext']).')" /><br />'."\n";
766    }
767  }
768  else
769  {
770    // Here we scan a non picture file : thumbnail and high are unused, representative is optionnal
771    $ext = pwg_get_representative_ext($file_dir, $file_short);
772    if ($ext != '')
773    {
774      $element['representative_ext'] = $ext;
775    }
776  }
777 
778  if (strlen($error_log) == 0)
779  {
780    $line = pwg_get_indent('element').'<element ';
781    foreach($element as $key => $value)
782    {
783      $line .= $key.'="'.$value.'" ';
784    }
785    $line .= '/>'."\n";
786  }
787 
788  //~ pwg_log('<<<<< pwg_scan_file() returns '.var_export($error_log, TRUE).' <<<<<'."\n");
789  return $error_log;
790}
791
792/**
793 * returns current level in tree
794 *
795 * @return integer
796 */
797function pwg_get_level($dir)
798{
799  //~ pwg_log('>>>>> pwg_get_level($dir = '.var_export($dir, TRUE).') >>>>>'."\n");
800 
801  $level = substr_count($dir, '/') - 1; // -1 because of ./ at the beginning of path
802 
803  //~ pwg_log('<<<<< pwg_get_level() returns '.var_export($level, TRUE).' <<<<<'."\n");
804  return $level;
805}
806
807/**
808 * returns indentation of element
809 *
810 * @param string $element_type : 'root', 'element', 'dir'
811 * @return string
812 */
813function pwg_get_indent($element_type)
814{
815  //~ pwg_log('>>>>> pwg_get_indent($element_type = '.var_export($element_type, TRUE).') >>>>>'."\n");
816 
817  $level = substr_count($_SESSION['scan_list_fold'][0], '/') - 1; // because of ./ at the beginning
818  switch($element_type)
819  {
820    case 'dir' :
821    {
822      $indent = str_repeat(' ', 2*pwg_get_level($_SESSION['scan_list_fold'][0]));
823      break;
824    }
825    case 'root' :
826    {
827      $indent = str_repeat(' ', 2*pwg_get_level($_SESSION['scan_list_fold'][0])+2);
828      break;
829    }
830    case 'element' :
831    {
832      $indent = str_repeat(' ', 2*pwg_get_level($_SESSION['scan_list_fold'][0])+4);
833      break;
834    }
835    default :
836    {
837      $indent = '';
838      break;
839    }
840  }
841 
842  //~ pwg_log('<<<<< pwg_get_indent() returns '.var_export(strlen($indent), TRUE).' spaces <<<<<'."\n");
843  return $indent;
844}
845
846/**
847 * create index.php in directory and reserved sub_directories, return logs
848 *
849 * @param string dir
850 * @return string
851 */
852function pwg_protect_directories($directory)
853{
854  //~ pwg_log('>>>>> pwg_protect_directories($directory = '.var_export($directory, true).') >>>>>'."\n");
855 
856  global $conf;
857 
858  $error_log = '';
859  $dirlist = array($directory, $directory.'/'.$conf['thumbs'], $directory.'/'.$conf['high'], $directory.'/'.$conf['represent']);
860 
861  foreach ($dirlist as $dir)
862  {
863    if (file_exists($dir))
864    {
865      if (!file_exists($dir.'/index.php'))
866      {
867        $file = @fopen($dir.'/index.php', 'w');
868        if ($file != false)
869        {
870          fwrite($file, $conf['protect_content']); // the return code should be verified
871          $error_log .= '          <code class="success">Success -</code> index.php created in directory <a href="'.$dir.'">'.$dir."</a><br />\n";
872        }
873        else
874        {
875          $error_log .= '          <code class="failure">Failure -</code> Can not create index.php in directory <code>'.$dir."</code><br />\n";
876        }
877      }
878      else
879      {
880        if ($conf['protect_warnings'])
881        {
882          $error_log .= '          <code class="warning">Warning -</code> index.php already exists in directory <a href="'.$dir.'">'.$dir."</a><br />\n";
883        }
884      }
885    }
886  }
887 
888  //~ pwg_log('<<<<< pwg_protect_directories() returns '.var_export($error_log, true).' <<<<<'."\n");
889  return $error_log;
890}
891
892/**
893 * returns file extension (.xxx)
894 *
895 * @param string $file
896 * @return string
897 */
898function pwg_get_file_extension($file)
899{
900  //~ pwg_log('>>>>> pwg_get_file_extension($file = '.var_export($file, true).') >>>>>'."\n");
901 
902  $ext = substr(strrchr($file, '.'), 1, strlen ($file));
903 
904  //~ pwg_log('<<<<< pwg_get_file_extension() returns '.var_export($ext, true).' <<<<<'."\n");
905  return $ext;
906}
907
908/**
909 * completes directory list of supported files and returns error logs
910 *
911 * @param string $directory
912 * @return string
913 */
914function pwg_get_file_list($directory)
915{
916  //~ pwg_log('>>>>> pwg_get_file_list($directory = '.var_export($directory, true).') >>>>>'."\n");
917 
918  global $conf, $pwg_conf;
919
920  $errorLog = '';
921  $dir = opendir($directory);
922  while (($file = readdir($dir)) !== false)
923  {
924    switch (filetype($directory."/".$file))
925    {
926      case 'file' :
927      {
928        if (in_array(pwg_get_file_extension($file), $conf['file_ext']))
929        {
930          // The file pointed is a regular file with a supported extension
931          array_push($_SESSION['scan_list_file'], $directory.'/'.$file);
932          //~ pwg_log('--->> Push in $_SESSION[scan_list_file] value "'.$directory.'/'.$file.'"'."\n");
933          if (!preg_match('/^[a-zA-Z0-9-_.]+$/', $file))
934          {
935            $errorLog .= '          <code class="failure">Failure -</code> Invalid file name for <code>'.$file.'</code> in <code>'.$directory.'</code>';
936            $errorLog .= ' <img src="'.$pwg_conf['icon_dir'].'add_tag.png"';
937            $errorLog .= ' title="Name should be composed of letters, figures, -, _ or . ONLY" /><br />'."\n";
938          }
939        }
940        break; // End of filetype FILE
941      }
942      case 'dir' :
943      {
944        if(!in_array($file, $pwg_conf['reserved_directory_names']))
945        {
946          // The file pointed is a directory but neither system directory nor reserved by PWG
947          array_push($_SESSION['scan_list_fold'], $directory.'/'.$file);
948          //~ pwg_log('--->> Push in $_SESSION[scan_list_fold] value "'.$directory.'/'.$file.'"'."\n");
949          if (!preg_match('/^[a-zA-Z0-9-_.]+$/', $file))
950          {
951            $errorLog .= '          <code class="failure">Failure -</code> Invalid directory name for <code>'.$directory.'/'.$file.'</code>';
952            $errorLog .= ' <img src="'.$pwg_conf['icon_dir'].'add_tag.png"';
953            $errorLog .= ' title="Name should be composed of letters, figures, -, _ or . ONLY" /><br />'."\n";
954          }
955        }
956        break; // End of filetype DIR
957      }
958      case 'fifo' :
959      case 'char' :
960      case 'block' :
961      case 'link' :
962      case 'unknown':
963      default :
964      {
965        // PWG does not manage these cases
966        break;
967      }
968    }
969  }
970  closedir($dir);
971 
972  //~ pwg_log('<<<<< pwg_get_file_list() returns '.var_export($errorLog, true).' <<<<<'."\n");
973
974  return $errorLog;
975}
976
977/**
978 * returns a float value coresponding to the number of seconds since the
979 * unix epoch (1st January 1970) and the microseconds are precised :
980 * e.g. 1052343429.89276600
981 *
982 * @return float
983 */
984function pwg_get_moment()
985{
986  //~ pwg_log('>>>>> pwg_get_moment() >>>>>'."\n");
987 
988  $t1 = explode(' ', microtime());
989  $t2 = explode('.', $t1[0]);
990  $t2 = $t1[1].'.'.$t2[1];
991
992  //~ pwg_log('<<<<< pwg_get_moment() returns '.var_export($t2, true).' <<<<<'."\n");
993  return $t2;
994}
995
996/**
997 * return true if HTTP_REFERER and PHP_SELF are similar
998 *
999 * return boolean
1000 */
1001function pwg_referer_is_me()
1002{
1003  //~ pwg_log('>>>>> pwg_referer_is_me() >>>>>'."\n");
1004 
1005  $response = false;
1006  $server = 'http://'.$_SERVER['SERVER_NAME'].$_SERVER['PHP_SELF'];
1007  $caller = (isset($_SERVER['HTTP_REFERER'])) ? $_SERVER['HTTP_REFERER'] : '';
1008
1009  if (strcasecmp($server, $caller) == 0) {
1010    $response = true;
1011  }
1012
1013  //~ pwg_log('<<<<< pwg_referer_is_me() returns '.var_export($response, true).' <<<<<'."\n");
1014  return $response;
1015}
1016
1017// +-----------------------------------------------------------------------+
1018// |                                pwg_<ACTION>_<STEP> Functions          |
1019// +-----------------------------------------------------------------------+
1020
1021function pwg_test_start()
1022{
1023  //~ pwg_log('>>>>> pwg_test_start() >>>>>'."\n");
1024
1025  global $g_message, $conf;
1026 
1027  if (isset($_REQUEST['version']))
1028  {
1029    if ($_REQUEST['version'] != $conf['version'])
1030    {
1031      $g_message = '0';
1032    }
1033    else
1034    {
1035      $g_message = '1';
1036    }
1037  }
1038  else
1039  {
1040    $g_message  = '1';
1041  }
1042  $_SESSION['scan_step'] = 'exit';
1043 
1044  //~ pwg_log('<<<<< pwg_test_start() <<<<<'."\n");
1045}
1046
1047function pwg_test_exit()
1048{
1049  //~ pwg_log('>>>>> pwg_test_exit() >>>>>'."\n");
1050
1051  global $g_header, $g_message, $g_footer, $conf, $pwg_conf;
1052 
1053  if (pwg_referer_is_me())
1054  {
1055    $g_header  = ' : <span class="success">Test</span>'."\n";
1056    $g_footer  = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>'."\n";
1057   
1058    // Write version
1059    $g_message  = '        <h3>Script version</h3>'."\n";
1060    $g_message .= '        This script is tagged : <code class="failure">'.$conf['version'].'</code>'."\n";
1061    // write GD support
1062    if (!is_callable('gd_info'))
1063    {
1064      $g_message .= '        <code class="failure">Failure -</code> Your server can not generate imagess<br />'."\n";
1065    }
1066    else
1067    {
1068      $info = gd_info();
1069      $gd_full_version = ereg_replace('[[:alpha:][:space:]()]+', '', $info['GD Version']);
1070      list($gd_version) = preg_split('/[.]+/', $gd_full_version);
1071     
1072      $g_message .= '        <h3>Image generation</h3>'."\n";
1073      $g_message .= '        <code class="success">Success -</code> Your server can generate images<br />'."\n";
1074      $g_message .= '        <code class="warning">Warning -</code> Your server support GD'.$gd_version.' (v'.$gd_full_version.')<br />'."\n";
1075      $format_list = array();
1076      $format = ($info['GIF Create Support']) ? '<code>gif</code>' : NULL;
1077      array_push($format_list, $format);
1078      $format = ($info['JPG Support']) ? '<code>jpg</code>' : NULL;
1079      array_push($format_list, $format);
1080      $format = ($info['PNG Support']) ? '<code>png</code>' : NULL;
1081      array_push($format_list, $format);
1082      $g_message .= '        <code class="warning">Warning -</code> Your server support format: '.implode(', ', $format_list)."\n";
1083    }
1084   
1085    $g_message .= '        <h3>Directory parsing</h3>'."\n";
1086    if ($pwg_conf['safe_mode'])
1087    {
1088      $g_message .= '        <code class="warning">Warning -</code> Your server does not support to resize execution time'."\n";
1089    }
1090    else
1091    {
1092      $g_message .= '        <code class="success">Success -</code> Your server supports to resize execution time'."\n";
1093    }
1094  }
1095  else
1096  {
1097    // compare version in GET parameter with $conf['version']
1098    if ($g_message == '1')
1099    {
1100      exit('<pre>PWG-INFO-2: test successful</pre>');
1101    }
1102    else
1103    {
1104      exit('<pre>PWG-ERROR-4: PhpWebGallery versions differs</pre>');
1105    }
1106  }
1107 
1108  //~ pwg_log('<<<<< pwg_test_exit() <<<<<'."\n");
1109}
1110
1111function pwg_clean_start()
1112{
1113  //~ pwg_log('>>>>> pwg_clean_start() >>>>>'."\n");
1114 
1115  global $g_message;
1116 
1117  if(@unlink('./listing.xml'))
1118  {
1119    $g_message = '1';
1120  }
1121  else
1122  {
1123    $g_message = '0';
1124  }
1125
1126  $_SESSION['scan_step'] = 'exit';
1127 
1128  //~ pwg_log('<<<<< pwg_clean_start() <<<<<'."\n");
1129}
1130
1131function pwg_clean_exit()
1132{
1133  //~ pwg_log('>>>>> pwg_clean_exit() >>>>>'."\n");
1134
1135  global $g_header, $g_message, $g_footer, $conf, $pwg_conf;
1136 
1137  if(pwg_referer_is_me())
1138  {
1139    $g_header = ' : <span class="success">Clean</span>';
1140    if ($g_message == '1')
1141    {
1142      $g_message = '        <code class="success">Success -</code> <code>listing.xml</code> file deleted'."\n";
1143    }
1144    else
1145    {
1146      $g_message = '        <code class="failure">Failure -</code> <code>listing.xml</code> does not exist or is read only'."\n";
1147    }
1148    $g_footer = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>';
1149  }
1150  else
1151  {
1152    if ($g_message == '1')
1153    {
1154      exit('<pre>PWG-INFO-3 : listing.xml file deleted</pre>');
1155    }
1156    else
1157    {
1158      exit('<pre>PWG-ERROR-3 : listing.xml does not exist</pre>');
1159    }
1160  }
1161 
1162  //~ pwg_log('<<<<< pwg_clean_exit() <<<<<'."\n");
1163}
1164
1165function pwg_generate_start()
1166{
1167  //~ pwg_log('>>>>> pwg_generate_start() >>>>>'."\n");
1168  //~ pwg_log("GENARATE start >>>\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE start >>>\n");
1169
1170  global $g_listing, $conf;
1171 
1172  // Flush line <informations>
1173  $xml_header_url = 'http://'.dirname($_SERVER['SERVER_NAME'].$_SERVER['PHP_SELF']).'/';
1174  $xml_header_date = date('Y-m-d');
1175  $xml_header_version = htmlentities($conf['version']);
1176 
1177  $attrs = array();
1178  if ($conf['use_iptc'])
1179  {
1180    $attrs = array_merge($attrs, array_keys($conf['use_iptc_mapping']) );
1181  }
1182  if ($conf['use_exif'])
1183  {
1184    $attrs = array_merge($attrs, array_keys($conf['use_exif_mapping']) );
1185  }
1186  $xml_header_metadata = implode(',',array_unique($attrs));
1187 
1188  $xml_header = '<informations';
1189  $xml_header .= ' generation_date="'.$xml_header_date.'"';
1190  $xml_header .= ' phpwg_version="'.$xml_header_version.'"';
1191  $xml_header .= ' metadata="'.$xml_header_metadata.'"';
1192  $xml_header .= ' url="'.$xml_header_url.'"';
1193  $xml_header .= '>'."\n";
1194 
1195  fwrite($g_listing, $xml_header);
1196 
1197  // Initialization of directory and file lists
1198  $_SESSION['scan_list_fold'] = array();
1199  $_SESSION['scan_list_file'] = array();
1200  $_SESSION['scan_logs'] .= pwg_get_file_list('.');
1201  sort($_SESSION['scan_list_fold']);
1202         
1203  // Erase first file list because root directory does not contain images.
1204  $_SESSION['scan_list_file'] = array();
1205           
1206  // What are we doing at next step
1207  if(count($_SESSION['scan_list_fold']) > 0)
1208  {
1209    $_SESSION['scan_step'] = 'list';
1210  }
1211  else
1212  {
1213    $_SESSION['scan_step'] = 'stop';
1214  }
1215 
1216  //~ pwg_log("GENARATE start <<<\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE start <<<\n");
1217  //~ pwg_log('<<<<< pwg_generate_start() <<<<<'."\n");
1218}
1219
1220function pwg_generate_list()
1221{
1222  //~ pwg_log('>>>>> pwg_generate_list() >>>>>'."\n");
1223  //~ pwg_log("GENARATE list >>>\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE list >>>\n");
1224 
1225  global $g_listing;
1226 
1227  // Flush line <dirX name=""> in xml file
1228  $dirname = basename($_SESSION['scan_list_fold'][0]);
1229  $line = pwg_get_indent('dir').'<dir'.pwg_get_level($_SESSION['scan_list_fold'][0]).' name="'.$dirname.'">'."\n";
1230  fwrite($g_listing, $line);
1231 
1232  // Get list of files and directories
1233  $_SESSION['scan_logs'] .= pwg_get_file_list($_SESSION['scan_list_fold'][0]);
1234  sort($_SESSION['scan_list_fold']); // Mandatory to keep the tree order
1235  sort($_SESSION['scan_list_file']); // Easier to read when sorted
1236 
1237  // Flush line <root>
1238  $line = pwg_get_indent('root').'<root>'."\n";
1239  fwrite($g_listing, $line);
1240 
1241  // What are we doing at next step
1242  $_SESSION['scan_step'] = 'scan';
1243 
1244  //~ pwg_log("GENARATE list <<<\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE list <<<\n");
1245  //~ pwg_log('<<<<< pwg_generate_list() <<<<<'."\n");
1246}
1247
1248function pwg_generate_scan()
1249{
1250  //~ pwg_log('>>>>> pwg_generate_scan() >>>>>'."\n");
1251  //~ pwg_log("GENARATE scan >>>\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE scan >>>\n");
1252 
1253  global $g_listing, $conf;
1254 
1255  while (pwg_continue() and count($_SESSION['scan_list_file']) > 0)
1256  {
1257    $line = '';
1258    $_SESSION['scan_logs'] .= pwg_scan_file($_SESSION['scan_list_file'][0], $line);
1259   
1260    if (strlen($line) > 0)
1261    {
1262      fwrite($g_listing, $line);
1263    }
1264    //~ pwg_log('---<< Pull of $_SESSION[scan_list_file] value "'.$_SESSION['scan_list_file'][0].'"'."\n");
1265    array_shift($_SESSION['scan_list_file']);
1266    $_SESSION['scan_cnt_file']++;
1267  }
1268         
1269  if (count($_SESSION['scan_list_file']) <= 0)
1270  {
1271    $_SESSION['scan_step'] = 'prot';
1272  }
1273 
1274  //~ pwg_log("GENERATE scan <<<\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE scan <<<\n");
1275  //~ pwg_log('<<<<< pwg_generate_scan() <<<<<'."\n");
1276}
1277
1278function pwg_generate_prot()
1279{
1280  //~ pwg_log('>>>>> pwg_generate_prot() >>>>>'."\n");
1281  //~ pwg_log("GENARATE prot >>>\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE prot >>>\n");
1282 
1283  global $conf, $g_listing;
1284 
1285  // Flush line </root>
1286  $line = pwg_get_indent('root').'</root>'."\n";
1287  fwrite($g_listing, $line);
1288 
1289  if ($conf['protect'])
1290  {
1291    $_SESSION['scan_logs'] .= pwg_protect_directories($_SESSION['scan_list_fold'][0]);
1292  }
1293 
1294  // How many directories to close
1295  $current_level = pwg_get_level($_SESSION['scan_list_fold'][0]);
1296  if (isset($_SESSION['scan_list_fold'][1]))
1297  {
1298    //~ pwg_log('---<< Pull of $_SESSION[scan_list_fold] value "'.$_SESSION['scan_list_fold'][0].'"'."\n");
1299    array_shift($_SESSION['scan_list_fold']);
1300    $_SESSION['scan_cnt_fold']++;
1301    $next_level = pwg_get_level($_SESSION['scan_list_fold'][0]);
1302    $_SESSION['scan_step'] = 'list';
1303  }
1304  else
1305  {
1306    $next_level = -1;
1307    $_SESSION['scan_cnt_fold']++;
1308    $_SESSION['scan_step'] = 'stop';
1309  }
1310 
1311  if ($current_level == $next_level)
1312  {
1313    fwrite($g_listing, pwg_close_level($current_level, 1));
1314  }
1315  else
1316  {
1317    if (($current_level > $next_level))
1318    {
1319      fwrite($g_listing, pwg_close_level($current_level, $current_level-$next_level+1));
1320    } // Nothing to do if current_level < next_level
1321  }
1322
1323  //~ pwg_log("GENERATE prot <<<\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE prot <<<\n");
1324  //~ pwg_log('<<<<< pwg_generate_prot() <<<<<'."\n");
1325}
1326
1327function pwg_generate_stop()
1328{
1329  //~ pwg_log('>>>>> pwg_generate_stop() >>>>>'."\n");
1330  //~ pwg_log("GENARATE stop >>>\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE stop >>>\n");
1331 
1332  global $pwg_conf, $g_listing, $g_header, $g_message, $g_footer;
1333 
1334  // Flush line </informations>
1335  fwrite($g_listing, '</informations>'."\n");
1336 
1337  // backup error log before cleaning session
1338  $time_elapsed = number_format(pwg_get_moment() - $_SESSION['scan_time'], 3, '.', ' ');
1339 
1340  $g_header   = ' : <span class="success">Generate</span>';
1341  $g_message  = '        <div>'."\n".$_SESSION['scan_logs'].'        </div>'."\n";
1342  $g_message .= '        <div><code class="success">'.$_SESSION['scan_cnt_fold'].'</code> directories parsed<br />'."\n";
1343  $g_message .= '        <code class="success">'.$_SESSION['scan_cnt_file'].'</code> files scanned</div>'."\n";
1344  $g_message .= '        <div>View <a href="listing.xml">listing.xml</a></div>'."\n";
1345  $g_message .= '        <div style="{text-align: right;}">Listing generated in : <code>'.$time_elapsed.' s</code></div>';
1346  $g_footer   = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>';
1347     
1348  // What are we doing at next step
1349  $_SESSION['scan_step'] = 'exit';
1350 
1351  //~ pwg_log("GENARATE stop <<<\n".var_export($_SESSION['scan_list_fold'], true)."\n".var_export($_SESSION['scan_list_file'], true)."\nGENERATE stop <<<\n");
1352  //~ pwg_log('<<<<< pwg_generate_stop() <<<<<'."\n");
1353}
1354
1355// +-----------------------------------------------------------------------+
1356// |                                ALWAYS CALLED FUNCTIONS                |
1357// +-----------------------------------------------------------------------+
1358
1359/**
1360 * This function check step and time ellapsed to determine end of loop
1361 *
1362 * @return bool
1363 */
1364function pwg_continue()
1365{
1366  //~ pwg_log('>>>>> pwg_continue() >>>>>'."\n");
1367 
1368  global $conf, $pwg_conf, $g_refresh, $g_header, $g_message, $g_footer, $start_time;
1369 
1370  if (!isset($_SESSION['scan_step']) or $_SESSION['scan_step'] == 'exit')
1371  {
1372    // evident end of process
1373    $return = false;
1374  }
1375  else
1376  {
1377    if ($pwg_conf['safe_mode'])
1378    {
1379      // can not reset the time
1380      $time_elapsed = pwg_get_moment() - $start_time;
1381      if ($time_elapsed < $conf['max_execution_time'])
1382      {
1383        $return = true;
1384      }
1385      else
1386      {
1387        $start_time = $_SESSION['scan_time'];
1388        $formated_time = number_format(pwg_get_moment() - $start_time, 3, '.', ' ');
1389
1390        $g_refresh = '<meta http-equiv="Refresh" content="'.$conf['refresh_delay'].'">'."\n";
1391        $g_header  = ' : <span class="success">'.ucfirst($_SESSION['scan_action']).'</span>';
1392        $g_message = '';
1393        if ($_SESSION['scan_cnt_fold'] != 0)
1394        {
1395          $g_message .= '<code class="success">'.$_SESSION['scan_cnt_fold'].'</code> directories scanned<br />'."\n";
1396        }
1397        if ($_SESSION['scan_cnt_file'] != 0)
1398        {
1399          $g_message .= '<code class="success">'.$_SESSION['scan_cnt_file'].'</code> files scanned<br />'."\n";
1400        }
1401        $nb = count($_SESSION['scan_list_fold']);
1402        if ($nb > 0)
1403        {
1404          $g_message .= '<code class="warning">'.$nb.'</code> directories to scan<br />'."\n";
1405        }
1406        $nb = count($_SESSION['scan_list_file']);
1407        if ($nb > 0)
1408        {
1409          $g_message .= '<code class="warning">'.$nb.'</code> files to scan<br />'."\n";
1410        }
1411        $g_message .= '        <div style="{text-align: right;}">Time elapsed : <code>'.$formated_time.' s</code></div>';
1412        $g_footer  = '<a href="'.$pwg_conf['this_url'].'?action='.$_SESSION['scan_action'].'" title="Continue"><img src="'.$pwg_conf['icon_dir'].'right.png" /></a>'."\n";
1413       
1414        $return = false;
1415      }
1416    }
1417    else
1418    {
1419      // reset the time
1420      set_time_limit(intval(ini_get('max_execution_time')));
1421      $return = true;
1422    }
1423  }
1424  //~ pwg_log('<<<<< pwg_continue() returns '.var_export($return, true).' <<<<<'."\n");
1425 
1426  return $return;
1427}
1428
1429/**
1430 * This function :
1431 * -> Verify the script call
1432 * -> Lock the script
1433 * -> Open listing.xml if action is 'generate'
1434 * -> Initialize output and session variables
1435 *
1436 * @return nothing
1437 */
1438function pwg_init()
1439{
1440  //~ pwg_log('>>>>> pwg_init() >>>>>'."\n");
1441
1442  global $g_message, $g_listing, $g_footer, $conf, $pwg_conf, $start_time;
1443  $init_message = '';
1444 
1445  // Lock other script sessions, this lock will be remove during 'exit' step
1446  if (!isset($_SESSION['scan_step']))
1447  {
1448    $fp = @fopen(__FILE__.'.lock', 'x+'); // return false if __FILE__.lock exists or if cannot create
1449    if ($fp == false)
1450    {
1451      $g_header   = $_SESSION['scan_action'];
1452      $g_message  = '        <code class="failure">Failure -</code> Another script is running';
1453      $g_message .= ' <img src="'.$pwg_conf['icon_dir'].'add_tag.png" title="Delete file '.__FILE__.'.lock and retry" />';
1454      $g_message .= "\n";
1455      $g_footer   = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>'."\n";
1456      $_SESSION['scan_step'] = 'exit';
1457      //~ pwg_log('<<<<< pwg_init() failure <<<<<'."\n");
1458      return;
1459    }
1460    else
1461    {
1462      fwrite($fp, session_id()); // Writing session_id to trace lock
1463      fclose($fp);
1464      $_SESSION['scan_step'] = 'init';
1465    }
1466  }
1467 
1468  // Verify and backup parameter action. This backup will be removed during step 'exit'
1469  if (isset($_REQUEST['action']))
1470  {
1471    if (in_array($_REQUEST['action'], $pwg_conf['scan_action']))
1472    {
1473      if (isset($_SESSION['scan_action']))
1474      {
1475        if ($_SESSION['scan_action'] != $_REQUEST['action'])
1476        {
1477          // Fatal error
1478          $g_message  = '        <code class="failure">Failure -</code> Parameter <code>action</code> differs between url and session';
1479          $g_message .= "\n";
1480          $g_footer   = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>'."\n";
1481          $_SESSION['scan_step'] = 'exit';
1482          //~ pwg_log('<<<<< pwg_init() failure <<<<<'."\n");
1483          return;
1484        }
1485      }
1486      else
1487      {
1488        $_SESSION['scan_action'] = $_REQUEST['action'];
1489      }
1490    }
1491    else
1492    {
1493      // Fatal error
1494      $g_message  = '        <code class="failure">Failure -</code> Problem with <code>action</code> parameter';
1495      $g_message .= ' <img src="'.$pwg_conf['icon_dir'].'add_tag.png" title="empty, '.implode(', ', $pwg_conf['scan_action']).'" />';
1496      $g_message .= "\n";
1497      $g_footer   = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>'."\n";
1498      $_SESSION['scan_step'] = 'exit';
1499      //~ pwg_log('<<<<< pwg_init() failure <<<<<'."\n");
1500      return;
1501    }
1502  }
1503  else
1504  {
1505    // Here we are on welcome page
1506    $g_message  = '        <ul>'."\n";
1507    $g_message .= '          <li><a href="'.$pwg_conf['this_url'].'?action=test" title="Display/Compare script version">Test</a></li>'."\n";
1508    $g_message .= '          <li><a href="'.$pwg_conf['this_url'].'?action=clean" title="Delete listing.xml if exists">Clean</a></li>'."\n";
1509    $g_message .= '          <li><a href="'.$pwg_conf['this_url'].'?action=generate" title="Scan all images from this directory and write informations in listing.xml">Listing</a></li>'."\n";
1510    $g_message .= '        </ul>'."\n";
1511    $g_footer   = '<a href="'.$conf['gallery'].'/admin.php?page=site_manager" title="Main gallery :: site manager">';
1512    $g_footer  .= '<img src="'.$pwg_conf['icon_dir'].'home.png" /></a>'."\n";
1513    $_SESSION['scan_step'] = 'exit';
1514    $_SESSION['scan_action'] = '';
1515  }
1516 
1517  // Actions to do at the init of generate
1518  if ($_SESSION['scan_action'] == 'generate')
1519  {
1520    // Open XML file
1521    $mode = ($_SESSION['scan_step'] == 'init') ? 'w' : 'a'; // Erase old listing.xml at the beginning of generation (mode w)
1522    $g_listing = @fopen('listing.xml', $mode);
1523    if ($g_listing === false)
1524    {
1525      $g_header   = $_SESSION['scan_action'];
1526      $g_message  = '        <code class="failure">Failure -</code> Can not write file <code>listing.xml</code>';
1527      $g_message .= "\n";
1528      $g_footer   = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>'."\n";
1529      $_SESSION['scan_step'] = 'exit';
1530      //~ pwg_log('<<<<< pwg_init() failure <<<<<'."\n");
1531      return;
1532    }
1533   
1534    // Check graphical capabilities
1535    $init_message = pwg_check_graphics();
1536  }
1537   
1538  // Initializing session counters. This counters will be completely unset during step 'exit'
1539  if ($_SESSION['scan_step'] == 'init')
1540  {
1541    $_SESSION['scan_list_file'] = array();
1542    $_SESSION['scan_list_fold'] = array();
1543    $_SESSION['scan_cnt_file'] = 0;
1544    $_SESSION['scan_cnt_fold'] = 0;
1545    $_SESSION['scan_time'] = $start_time;
1546    $_SESSION['scan_step'] = 'start';
1547    $_SESSION['scan_logs'] = $init_message;
1548  }
1549 
1550  //~ pwg_log('<<<<< pwg_init() success <<<<<'."\n");
1551}
1552
1553/**
1554 * This function :
1555 * -> Close listing.xml if action is 'generate'
1556 * -> Unlock the script
1557 * -> Erase session variables
1558 *
1559 * @return nothing
1560 */
1561function pwg_exit()
1562{
1563  //~ pwg_log('>>>>> pwg_exit() >>>>>'."\n");
1564 
1565  global $g_listing;
1566 
1567  // Close XML file
1568  if ($_SESSION['scan_action'] == 'generate' and $g_listing != false)
1569  {
1570    fclose($g_listing);
1571  }
1572 
1573  // Unlock script
1574  unlink(__FILE__.'.lock');
1575 
1576  // Erase session counters
1577  unset($_SESSION['scan_list_file']);
1578  unset($_SESSION['scan_list_fold']);
1579  unset($_SESSION['scan_cnt_file']);
1580  unset($_SESSION['scan_cnt_fold']);
1581  unset($_SESSION['scan_time']);
1582  unset($_SESSION['scan_step']);
1583  $local_action = $_SESSION['scan_action'];
1584  unset($_SESSION['scan_action']);
1585  unset($_SESSION['scan_logs']);
1586  session_destroy();
1587 
1588  // Call specific action post process
1589  if (is_callable('pwg_'.$local_action.'_exit'))
1590  {
1591    call_user_func('pwg_'.$local_action.'_exit');
1592  }
1593 
1594  //~ pwg_log('<<<<< pwg_exit() <<<<<'."\n");
1595}
1596
1597// +-----------------------------------------------------------------------+
1598// |                                Script                                 |
1599// +-----------------------------------------------------------------------+
1600session_save_path('.');
1601session_start();
1602
1603$start_time = pwg_get_moment();
1604
1605// Initializing message for web page
1606$g_refresh = '';
1607$g_header  = '';
1608$g_message = '';
1609$g_footer  = '';
1610$g_listing = '';
1611
1612pwg_init();
1613
1614while(pwg_continue())
1615{
1616  if (is_callable('pwg_'.$_SESSION['scan_action'].'_'.$_SESSION['scan_step']))
1617  {
1618    call_user_func('pwg_'.$_SESSION['scan_action'].'_'.$_SESSION['scan_step']); // Run the step : start, list, scan, stop are available
1619  }
1620  else
1621  {
1622    $g_header   = $_SESSION['scan_action'];
1623    $g_message  = '        <code class="failure">Failure -</code> INTERNAL STEP ERROR : <code>pwg_'.$_SESSION['scan_action'].'_'.$_SESSION['scan_step'].'()</code> undefined';
1624    $g_message .= "\n";
1625    $g_footer   = '<a href="'.$pwg_conf['this_url'].'" title="Main menu"><img src="'.$pwg_conf['icon_dir'].'up.png" /></a>'."\n";
1626    $_SESSION['scan_step'] = 'exit';
1627  }
1628}
1629
1630if ($_SESSION['scan_step'] == 'exit')
1631{
1632  pwg_exit();
1633}
1634
1635?>
1636<html>
1637  <head>
1638  <?php echo $g_refresh; ?>
1639  <title>Manage distant gallery</title>
1640  </head>
1641    <style type="text/css">
1642      code {font-weight: bold}
1643      img {border-style: none; vertical-align: middle}
1644      ul {list-style-image: url(<?php echo $pwg_conf['icon_dir']; ?>add_tag.png)}     
1645      .success {color: green}
1646      .warning {color: orange}
1647      .failure {color: red}
1648      .header {text-align: center; font-variant: small-caps; font-weight: bold;}
1649      .p {color: #F93;}
1650      .w {color: #ccc;}
1651      .g {color: #69C;}
1652      .pwg {text-decoration: none; border-bottom-style: dotted; border-bottom-width: 1px;}
1653      .content {width: 75%; position: absolute; top: 10%; left: 12%;}
1654      .footer {text-align: right;}
1655      .pwg_block {float: left;}
1656    </style>
1657  <body>
1658    <div class="content">
1659      <fieldset class="header">
1660        <span class="p">Php</span>
1661        <span class="w">Web</span>
1662        <span class="g">Gallery</span>
1663        &nbsp;distant site<? echo $g_header; ?>
1664      </fieldset>
1665      <fieldset>
1666<?php echo $g_message; ?>
1667      </fieldset>
1668      <fieldset class="footer">
1669        <div class="pwg_block">
1670          Powered by <a href="http://www.phpwebgallery.net" class="pwg"><span class="p">Php</span><span class="w">Web</span><span class="g">Gallery</span></a>
1671        </div>
1672        <?php echo $g_footer; ?>
1673      </fieldset>
1674    </div>
1675  </body>
1676</html>
Note: See TracBrowser for help on using the repository browser.