]> git.p6c8.net - devedit.git/commitdiff
- Began to change the behaviour of Dev-Editor's editing function:
authorpcanterino <>
Sun, 10 Apr 2005 09:24:20 +0000 (09:24 +0000)
committerpcanterino <>
Sun, 10 Apr 2005 09:24:20 +0000 (09:24 +0000)
  The concept of locking the file for other users before editing it is not very
  good, causes some problems and makes it difficult to add new features. So I
  decided to remove it.
  When Dev-Editor shows the form for editing a file, it calculates the MD5
  checksum and places it in the editing form. Before saving the file, the MD5
  checksum is calculated again and compared to the submitted one. If the two
  sums don't match, Dev-Editor does not save the file and shows the editing
  form.
  It seems to work, but the solution is currently VERY dirty...
- Removed the possibility to encode ISO-8859-1 HTML entities. There is no real
  use for this function.
- The extension of the configuration files is now "conf"
- Changed the names of some error messages:
  binary      -> binary_file
  cmd_unknown -> command_unknown
  create_ar   -> create_above_root
  not_exist   -> not_found

12 files changed:
devedit.conf [moved from devedit.dat with 66% similarity]
devedit.pl
errors.conf [new file with mode: 0644]
errors.dat [deleted file]
modules/Command.pm
modules/File/Access.pm
modules/File/UseList.pm [deleted file]
templates.conf [moved from templates.dat with 100% similarity]
templates/dirlist_file.htm
templates/editfile.htm
uselist [deleted file]
uselist.lock [deleted file]

similarity index 66%
rename from devedit.dat
rename to devedit.conf
index 05762cab47d20ac9f6a3e45c4e26321f84073f83..0da399c87b8b452afdb46dcbe77382278c855649 100644 (file)
@@ -11,11 +11,7 @@ max_file_size = 100000
 timeformat    = %d.%m.%Y %H:%M
 use_gmt       = 0
 
 timeformat    = %d.%m.%Y %H:%M
 use_gmt       = 0
 
-uselist_file  = uselist
-lock_file     = uselist.lock
-lock_timeout  = 10
-
-error_file    = errors.dat
-template_file = templates.dat
+error_file    = errors.conf
+template_file = templates.conf
 
 # End of configuration file
\ No newline at end of file
 
 # End of configuration file
\ No newline at end of file
index fc49a7189c1a911b72e9e28ec90eeb94450755a0..3eebb27623c7546e0c882559a274b0134aff9189 100644 (file)
@@ -6,7 +6,7 @@
 # Dev-Editor's main program
 #
 # Author:        Patrick Canterino <patrick@patshaping.de>
 # Dev-Editor's main program
 #
 # Author:        Patrick Canterino <patrick@patshaping.de>
-# Last modified: 2005-02-19
+# Last modified: 2005-04-09
 #
 
 use strict;
 #
 
 use strict;
@@ -17,7 +17,6 @@ use lib 'modules';
 
 use CGI;
 use Config::DevEdit;
 
 use CGI;
 use Config::DevEdit;
-use File::UseList;
 
 use Command;
 use Output;
 
 use Command;
 use Output;
@@ -28,7 +27,7 @@ $VERSION = '2.3.1';
 # Path to configuration file
 # Change if necessary!
 
 # Path to configuration file
 # Change if necessary!
 
-use constant CONFIGFILE => 'devedit.dat';
+use constant CONFIGFILE => 'devedit.conf';
 
 # Read the configuration file
 
 
 # Read the configuration file
 
@@ -80,7 +79,7 @@ if($newfile ne '' && $newfile !~ /^\s+$/)
 
  unless(($new_physical,$new_virtual) = check_path($config->{'fileroot'},$dir))
  {
 
  unless(($new_physical,$new_virtual) = check_path($config->{'fileroot'},$dir))
  {
-  abort($config->{'errors'}->{'create_ar'},'/');
+  abort($config->{'errors'}->{'create_above_root'},'/');
  }
 
  # Check if we have enough permissions to create a file
  }
 
  # Check if we have enough permissions to create a file
@@ -105,15 +104,6 @@ if(-e $temp_path || -l $temp_path)
 {
  if(my ($physical,$virtual) = check_path($config->{'fileroot'},$file))
  {
 {
  if(my ($physical,$virtual) = check_path($config->{'fileroot'},$file))
  {
-  # Create a File::UseList object and load the list
-
-  my $uselist = new File::UseList(listfile => $config->{'uselist_file'},
-                                  lockfile => $config->{'lock_file'},
-                                  timeout  => $config->{'lock_timeout'});
-
-  $uselist->lock or abort($config->{'errors'}->{'lock_failed'},undef,{USELIST => $uselist->{'listfile'}, LOCK_FILE => $uselist->{'lockfile'}});
-  $uselist->load;
-
   # Create a hash containing data submitted by the user
   # (some other necessary information are also included)
 
   # Create a hash containing data submitted by the user
   # (some other necessary information are also included)
 
@@ -121,7 +111,6 @@ if(-e $temp_path || -l $temp_path)
               virtual      => $virtual,
               new_physical => $new_physical,
               new_virtual  => $new_virtual,
               virtual      => $virtual,
               new_physical => $new_physical,
               new_virtual  => $new_virtual,
-              uselist      => $uselist,
               cgi          => $cgi,
               version      => $VERSION,
               configfile   => CONFIGFILE);
               cgi          => $cgi,
               version      => $VERSION,
               configfile   => CONFIGFILE);
@@ -130,9 +119,8 @@ if(-e $temp_path || -l $temp_path)
 
   my $output = exec_command($command,\%data,$config);
 
 
   my $output = exec_command($command,\%data,$config);
 
-  # ... unlock the list with files in use and show the output of the command
+  # ... and show the output of the command
 
 
-  $uselist->unlock or abort($config->{'errors'}->{'unlock_failed'},undef,{USELIST => $uselist->{'listfile'}, LOCK_FILE => $uselist->{'lockfile'}});
   print $$output;
  }
  else
   print $$output;
  }
  else
@@ -142,7 +130,7 @@ if(-e $temp_path || -l $temp_path)
 }
 else
 {
 }
 else
 {
- abort($config->{'errors'}->{'not_exist'},'/');
+ abort($config->{'errors'}->{'not_found'},'/');
 }
 
 #
 }
 
 #
diff --git a/errors.conf b/errors.conf
new file mode 100644 (file)
index 0000000..9ced686
--- /dev/null
@@ -0,0 +1,46 @@
+# This file contains the error messages of Dev-Editor
+
+above_root        = Accessing files and directories above the virtual root directory is forbidden.
+binary_file       = This editor is not able to view/edit binary files.
+chprop_link       = You are not allowed to change the properties of a symbolic link.
+chprop_root       = You are not allowed to change the properties of the root directory.
+command_unknown   = Unknown command: '{COMMAND}'
+copy_failed       = Could not copy '{FILE}' to '{NEW_FILE}'.
+create_above_root = You are not allowed to create files and directories above the virtual root directory.
+delete_failed     = Could not delete file '{FILE}'.
+dir_copy          = This editor is not able to copy directories.
+dir_edit          = You cannot edit directories.
+dir_no_create     = You have not enough permissions to create a file in directory '{DIR}'.
+dir_not_exist     = The directory where you want to create this file or directory does not exist.
+dir_read_fail     = Reading of directory '{DIR}' failed.
+dir_replace       = You are not allowed to replace a directory.
+edit_failed       = Saving of file '{FILE}' failed. The file could be damaged, please check its integrity.
+edit_file_changed = The file you want to edit changed meanwhile. Now, it looks like this: <a href="{SCRIPT}?command=show&amp;file={FILE}">{FILE}</a>. Please try to merge these two versions together of the file or save this file using a different name.
+exist_no_write    = The target file '{FILE}' already exists and you have not enough permissions to replace it.
+file_exists       = A file or directory called '{FILE}' already exists.
+file_too_large    = The file you want to view or edit is too large (max. {SIZE}&nbsp;Bytes).
+invalid_group     = '{GROUP}' seems to be an invalid group name. Please check it and try again.
+invalid_upload    = It seems that something is wrong with the file upload you want to submit.
+link_copy         = Copying symbolic links does not work.
+link_edit         = For security reasons, you cannot edit the target file of a symbolic link.
+link_replace      = You are not allowed to overwrite symbolic links.
+mkdir_failed      = Could not create directory '{DIR}'.
+mkfile_failed     = Could not create file '{FILE}'.
+no_copy           = You have not enough permissions to copy this file.
+no_delete         = You have not enough permissions to delete this file.
+no_dir_access     = You have not enough permissions to access this directory.
+no_directory      = '{FILE}' is not a directory.
+no_edit           = You have not enough permissions to edit this file.
+no_rename         = You have not enough permissions to move/rename this file.
+no_root_access    = You have not enough permissions to access the root directory.
+no_root_dir       = The root directory does not exist or is not a directory.
+no_users          = It seems that your system does not support users and groups.
+no_view           = You have not enough permissions to view this file.
+not_found         = File/directory does not exist.
+not_owner         = You are not the owner of '{FILE}', so you are not allowed to change its mode and its group.
+remove_root       = You are not allowed to remove the root directory.
+rename_failed     = Could not move/rename '{FILE}' to '{NEW_FILE}'.
+rename_root       = You are not allowed to move/rename the root directory.
+text_to_binary    = You are not allowed to write text data into a binary file.
+
+# End of configuration file
\ No newline at end of file
diff --git a/errors.dat b/errors.dat
deleted file mode 100644 (file)
index 5a54b08..0000000
+++ /dev/null
@@ -1,51 +0,0 @@
-# This file contains the error messages of Dev-Editor
-
-above_root     = Accessing files and directories above the virtual root directory is forbidden.
-binary         = This editor is not able to view/edit binary files.
-chprop_link    = You are not allowed to change the properties of a symbolic link.
-chprop_root    = You are not allowed to change the properties of the root directory.
-cmd_unknown    = Unknown command: '{COMMAND}'
-copy_failed    = Could not copy '{FILE}' to '{NEW_FILE}'.
-create_ar      = You are not allowed to create files and directories above the virtual root directory.
-delete_failed  = Could not delete file '{FILE}'.
-dir_copy       = This editor is not able to copy directories.
-dir_edit       = You cannot edit directories.
-dir_no_create  = You have not enough permissions to create a file in directory '{DIR}'.
-dir_not_exist  = The directory where you want to create this file or directory does not exist.
-dir_read_fail  = Reading of directory '{DIR}' failed.
-dir_replace    = You are not allowed to replace a directory.
-edit_failed    = Saving of file '{FILE}' failed. The file could be damaged, please check its integrity.
-exist_edited   = The target file '{FILE}' already exists and is edited by someone else.
-exist_no_write = The target file '{FILE}' already exists and you have not enough permissions to replace it.
-file_exists    = A file or directory called '{FILE}' already exists.
-file_too_large = The file you want to view or edit is too large (max. {SIZE}&nbsp;Bytes).
-in_use         = The file '{FILE}' is currently edited by someone else.
-invalid_group  = '{GROUP}' seems to be an invalid group name. Please check it and try again.
-invalid_upload = It seems that something is wrong with the file upload you want to submit.
-link_copy      = Copying symbolic links does not work.
-link_edit      = For security reasons, you cannot edit the target file of a symbolic link.
-link_replace   = You are not allowed to overwrite symbolic links.
-lock_failed    = Locking of '{USELIST}' failed. Try it again in a moment. If the problem persists, ask the administrator to check the lock file ('{LOCK_FILE}') and to recreate it if necessary.
-mkdir_failed   = Could not create directory '{DIR}'.
-mkfile_failed  = Could not create file '{FILE}'.
-no_copy        = You have not enough permissions to copy this file.
-no_delete      = You have not enough permissions to delete this file.
-no_dir_access  = You have not enough permissions to access this directory.
-no_directory   = '{FILE}' is not a directory.
-no_edit        = You have not enough permissions to edit this file.
-no_rename      = You have not enough permissions to move/rename this file.
-no_root_access = You have not enough permissions to access the root directory.
-no_root_dir    = The root directory does not exist or is not a directory.
-no_users       = It seems that your system does not support users and groups.
-no_view        = You have not enough permissions to view this file.
-not_exist      = File/directory does not exist.
-not_owner      = You are not the owner of '{FILE}', so you are not allowed to change its mode and its group.
-remove_root    = You are not allowed to remove the root directory.
-rename_failed  = Could not move/rename '{FILE}' to '{NEW_FILE}'.
-rename_root    = You are not allowed to move/rename the root directory.
-text_to_binary = You are not allowed to write text data into a binary file.
-ul_add_failed  = Could not add '{FILE}' to the list of files in use.
-ul_rm_failed   = Could not remove '{FILE}' from the list of files in use. Try it again using the 'unlock' command of Dev-Editor or by removing the file manually from '{USELIST}'.
-unlock_failed  = Unlocking of '{USELIST}' failed. Ask the administrator to check the lock file ('{LOCK_FILE}') and to recreate it if necessary.
-
-# End of configuration file
\ No newline at end of file
index ab4f8b8954689e49f489cc69519a278f755b6db7..edd01624d49d6402291881386ce3ac92c67b4da3 100644 (file)
@@ -6,17 +6,19 @@ package Command;
 # Execute Dev-Editor's commands
 #
 # Author:        Patrick Canterino <patrick@patshaping.de>
 # Execute Dev-Editor's commands
 #
 # Author:        Patrick Canterino <patrick@patshaping.de>
-# Last modified: 2005-03-18
+# Last modified: 2005-04-09
 #
 
 use strict;
 
 use vars qw(@EXPORT);
 
 #
 
 use strict;
 
 use vars qw(@EXPORT);
 
+use Fcntl;
 use File::Access;
 use File::Copy;
 use File::Path;
 
 use File::Access;
 use File::Copy;
 use File::Path;
 
+use Digest::MD5 qw(md5_hex);
 use POSIX qw(strftime);
 use Tool;
 
 use POSIX qw(strftime);
 use Tool;
 
@@ -27,12 +29,13 @@ use HTML::Entities;
 use Output;
 use Template;
 
 use Output;
 use Template;
 
+use Data::Dumper;
+
 my $script = encode_entities($ENV{'SCRIPT_NAME'});
 my $users  = eval('getpwuid(0)') && eval('getgrgid(0)');
 
 my %dispatch = ('show'       => \&exec_show,
                 'beginedit'  => \&exec_beginedit,
 my $script = encode_entities($ENV{'SCRIPT_NAME'});
 my $users  = eval('getpwuid(0)') && eval('getgrgid(0)');
 
 my %dispatch = ('show'       => \&exec_show,
                 'beginedit'  => \&exec_beginedit,
-                'canceledit' => \&exec_canceledit,
                 'endedit'    => \&exec_endedit,
                 'mkdir'      => \&exec_mkdir,
                 'mkfile'     => \&exec_mkfile,
                 'endedit'    => \&exec_endedit,
                 'mkdir'      => \&exec_mkdir,
                 'mkfile'     => \&exec_mkfile,
@@ -41,7 +44,6 @@ my %dispatch = ('show'       => \&exec_show,
                 'rename'     => \&exec_rename,
                 'remove'     => \&exec_remove,
                 'chprop'     => \&exec_chprop,
                 'rename'     => \&exec_rename,
                 'remove'     => \&exec_remove,
                 'chprop'     => \&exec_chprop,
-                'unlock'     => \&exec_unlock,
                 'about'      => \&exec_about
                );
 
                 'about'      => \&exec_about
                );
 
@@ -74,7 +76,7 @@ sub exec_command($$$)
   }
  }
 
   }
  }
 
- return error($config->{'errors'}->{'cmd_unknown'},'/',{COMMAND => encode_entities($command)});
+ return error($config->{'errors'}->{'command_unknown'},'/',{COMMAND => encode_entities($command)});
 }
 
 # exec_show()
 }
 
 # exec_show()
@@ -92,7 +94,6 @@ sub exec_show($$)
  my $physical       = $data->{'physical'};
  my $virtual        = $data->{'virtual'};
  my $upper_path     = encode_entities(upper_path($virtual));
  my $physical       = $data->{'physical'};
  my $virtual        = $data->{'virtual'};
  my $upper_path     = encode_entities(upper_path($virtual));
- my $uselist        = $data->{'uselist'};
 
  my $tpl = new Template;
 
 
  my $tpl = new Template;
 
@@ -166,7 +167,6 @@ sub exec_show($$)
    my $virt_path = encode_entities($virtual.$file);
 
    my @stat      = lstat($phys_path);
    my $virt_path = encode_entities($virtual.$file);
 
    my @stat      = lstat($phys_path);
-   my $in_use    = $uselist->in_use($virtual.$file);
    my $too_large = $config->{'max_file_size'} && $stat[7] > $config->{'max_file_size'};
 
    my $ftpl = new Template;
    my $too_large = $config->{'max_file_size'} && $stat[7] > $config->{'max_file_size'};
 
    my $ftpl = new Template;
@@ -181,14 +181,11 @@ sub exec_show($$)
    $ftpl->parse_if_block('link',-l $phys_path);
    $ftpl->parse_if_block('no_link',not -l $phys_path);
    $ftpl->parse_if_block('not_readable',not -r $phys_path);
    $ftpl->parse_if_block('link',-l $phys_path);
    $ftpl->parse_if_block('no_link',not -l $phys_path);
    $ftpl->parse_if_block('not_readable',not -r $phys_path);
-   $ftpl->parse_if_block('binary',-B $phys_path);
+   $ftpl->parse_if_block('binary_file',-B $phys_path);
    $ftpl->parse_if_block('readonly',not -w $phys_path);
 
    $ftpl->parse_if_block('viewable',(-r $phys_path && -T $phys_path && not $too_large) || -l $phys_path);
    $ftpl->parse_if_block('readonly',not -w $phys_path);
 
    $ftpl->parse_if_block('viewable',(-r $phys_path && -T $phys_path && not $too_large) || -l $phys_path);
-   $ftpl->parse_if_block('editable',((-r $phys_path && -w $phys_path && -T $phys_path && not $too_large) && not $in_use) && not -l $phys_path);
-
-   $ftpl->parse_if_block('in_use',$in_use);
-   $ftpl->parse_if_block('unused',not $in_use);
+   $ftpl->parse_if_block('editable',(-r $phys_path && -w $phys_path && -T $phys_path && not $too_large) && not -l $phys_path);
 
    $ftpl->parse_if_block('too_large',$config->{'max_file_size'} && $stat[7] > $config->{'max_file_size'});
 
 
    $ftpl->parse_if_block('too_large',$config->{'max_file_size'} && $stat[7] > $config->{'max_file_size'});
 
@@ -237,7 +234,7 @@ sub exec_show($$)
   # We have to do it in this way or empty files will be recognized
   # as binary files
 
   # We have to do it in this way or empty files will be recognized
   # as binary files
 
-  return error($config->{'errors'}->{'binary'},$upper_path) unless(-T $physical);
+  return error($config->{'errors'}->{'binary_file'},$upper_path) unless(-T $physical);
 
   # Is the file too large?
 
 
   # Is the file too large?
 
@@ -255,7 +252,7 @@ sub exec_show($$)
   $tpl->fillin('URL',encode_entities(equal_url($config->{'httproot'},$virtual)));
   $tpl->fillin('SCRIPT',$script);
 
   $tpl->fillin('URL',encode_entities(equal_url($config->{'httproot'},$virtual)));
   $tpl->fillin('SCRIPT',$script);
 
-  $tpl->parse_if_block('editable',-w $physical && $uselist->unused($virtual));
+  $tpl->parse_if_block('editable',-w $physical);
 
   $tpl->fillin('CONTENT',encode_entities($$content));
  }
 
   $tpl->fillin('CONTENT',encode_entities($$content));
  }
@@ -281,29 +278,24 @@ sub exec_beginedit($$)
  my $physical       = $data->{'physical'};
  my $virtual        = $data->{'virtual'};
  my $dir            = upper_path($virtual);
  my $physical       = $data->{'physical'};
  my $virtual        = $data->{'virtual'};
  my $dir            = upper_path($virtual);
- my $uselist        = $data->{'uselist'};
+ my $cgi            = $data->{'cgi'};
 
 
- return error($config->{'errors'}->{'link_edit'},$dir)                    if(-l $physical);
- return error($config->{'errors'}->{'dir_edit'}, $dir)                    if(-d $physical);
- return error($config->{'errors'}->{'in_use'},   $dir,{FILE => $virtual}) if($uselist->in_use($virtual));
- return error($config->{'errors'}->{'no_edit'},  $dir)                    unless(-r $physical && -w $physical);
+ return error($config->{'errors'}->{'link_edit'},$dir) if(-l $physical);
+ return error($config->{'errors'}->{'dir_edit'}, $dir) if(-d $physical);
+ return error($config->{'errors'}->{'no_edit'},  $dir) unless(-r $physical && -w $physical);
 
  # Check on binary files
 
 
  # Check on binary files
 
- return error($config->{'errors'}->{'binary'},$dir) unless(-T $physical);
+ return error($config->{'errors'}->{'binary_file'},$dir) unless(-T $physical);
 
  # Is the file too large?
 
  return error($config->{'errors'}->{'file_too_large'},$dir,{SIZE => $config->{'max_file_size'}}) if($config->{'max_file_size'} && -s $physical > $config->{'max_file_size'});
 
 
  # Is the file too large?
 
  return error($config->{'errors'}->{'file_too_large'},$dir,{SIZE => $config->{'max_file_size'}}) if($config->{'max_file_size'} && -s $physical > $config->{'max_file_size'});
 
- # Lock the file...
-
- ($uselist->add_file($virtual) and
-  $uselist->save)              or return error($config->{'errors'}->{'ul_add_failed'},$dir,{FILE => $virtual});
-
  # ... and show the editing form
 
  # ... and show the editing form
 
- my $content =  file_read($physical);
+ my $content =  file_read($physical,1);
+ my $md5sum  =  md5_hex($$content);
  $$content   =~ s/\015\012|\012|\015/\n/g;
 
  my $tpl = new Template;
  $$content   =~ s/\015\012|\012|\015/\n/g;
 
  my $tpl = new Template;
@@ -313,34 +305,17 @@ sub exec_beginedit($$)
  $tpl->fillin('DIR',$dir);
  $tpl->fillin('URL',equal_url($config->{'httproot'},$virtual));
  $tpl->fillin('SCRIPT',$script);
  $tpl->fillin('DIR',$dir);
  $tpl->fillin('URL',equal_url($config->{'httproot'},$virtual));
  $tpl->fillin('SCRIPT',$script);
+ $tpl->fillin('MD5SUM',$md5sum);
  $tpl->fillin('CONTENT',encode_entities($$content));
 
  $tpl->fillin('CONTENT',encode_entities($$content));
 
+ $tpl->parse_if_block('error',0);
+
  my $output = header(-type => 'text/html');
  $output   .= $tpl->get_template;
 
  return \$output;
 }
 
  my $output = header(-type => 'text/html');
  $output   .= $tpl->get_template;
 
  return \$output;
 }
 
-# exec_canceledit()
-#
-# Abort file editing
-#
-# Params: 1. Reference to user input hash
-#         2. Reference to config hash
-#
-# Return: Output of the command (Scalar Reference)
-
-sub exec_canceledit($$)
-{
- my ($data,$config) = @_;
- my $virtual        = $data->{'virtual'};
- my $dir            = upper_path($virtual);
- my $uselist        = $data->{'uselist'};
-
- file_unlock($uselist,$virtual) or return error($config->{'errors'}->{'ul_rm_failed'},$dir,{FILE => $virtual, USELIST => $uselist->{'listfile'}});
- return devedit_reload({command => 'show', file => $dir});
-}
-
 # exec_endedit()
 #
 # Save a file, unlock it and return to directory view
 # exec_endedit()
 #
 # Save a file, unlock it and return to directory view
@@ -356,54 +331,87 @@ sub exec_endedit($$)
  my $physical       = $data->{'physical'};
  my $virtual        = $data->{'virtual'};
  my $dir            = upper_path($virtual);
  my $physical       = $data->{'physical'};
  my $virtual        = $data->{'virtual'};
  my $dir            = upper_path($virtual);
- my $content        = $data->{'cgi'}->param('filecontent');
- my $uselist        = $data->{'uselist'};
+ my $cgi            = $data->{'cgi'};
+ my $content        = $cgi->param('filecontent');
+ my $md5sum         = $cgi->param('md5sum');
+ my $output;
+
+ if($content && $md5sum)
+ {
+  # Normalize newlines
 
 
- # We already unlock the file at the beginning of the subroutine,
- # because if we have to abort this routine, the file keeps locked.
- # No other user of Dev-Editor will access the file during this
- # routine because of the concept of File::UseList.
+  $content =~ s/\015\012|\012|\015/\n/g;
 
 
- file_unlock($uselist,$virtual) or return error($config->{'errors'}->{'ul_rm_failed'},$dir,{FILE => $virtual, USELIST => $uselist->{'listfile'}});
+  if($cgi->param('saveas') && $data->{'new_physical'} ne '' && $data->{'new_virtual'} ne '')
+  {
+   # Create the new filename
 
 
- # Normalize newlines
+   $physical = $data->{'new_physical'};
+   $virtual  = $data->{'new_virtual'};
+  }
 
 
- $content =~ s/\015\012|\012|\015/\n/g;
+  return error($config->{'errors'}->{'link_edit'},$dir)      if(-l $physical);
+  return error($config->{'errors'}->{'dir_edit'},$dir)       if(-d $physical);
+  return error($config->{'errors'}->{'no_edit'},$dir)        if(-e $physical && !(-r $physical && -w $physical));
+  return error($config->{'errors'}->{'text_to_binary'},$dir) if(-e $physical && not -T $physical);
 
 
- if($data->{'cgi'}->param('encode_iso'))
- {
-  # Encode all ISO-8859-1 special chars
+  # For technical reasons, we can't use file_save() for
+  # saving the file...
 
 
-  $content = encode_entities($content,"\200-\377");
- }
+  local *FILE;
 
 
- if($data->{'cgi'}->param('saveas') && $data->{'new_physical'} ne '' && $data->{'new_virtual'} ne '')
- {
-  # Create the new filename
+  sysopen(FILE,$physical,O_RDWR | O_CREAT) or return error($config->{'errors'}->{'edit_failed'},$dir,{FILE => $virtual});
+  file_lock(FILE,LOCK_EX)                  or do { close(FILE); return error($config->{'errors'}->{'edit_failed'},$dir,{FILE => $virtual}) };
+  binmode(FILE);
 
 
-  $physical = $data->{'new_physical'};
-  $virtual  = $data->{'new_virtual'};
+  my $md5 = new Digest::MD5;
+  $md5->addfile(*FILE);
 
 
-  # Check if someone else is editing the new file
+  my $md5_new = $md5->hexdigest;
 
 
-  return error($config->{'errors'}->{'in_use'},$dir,{FILE => $virtual}) if($uselist->in_use($virtual));
- }
+  if($md5_new ne $md5sum && not $cgi->param('saveas'))
+  {
+   # The file changed meanwhile
 
 
- return error($config->{'errors'}->{'link_edit'},$dir)      if(-l $physical);
- return error($config->{'errors'}->{'dir_edit'},$dir)       if(-d $physical);
- return error($config->{'errors'}->{'no_edit'},$dir)        if(-e $physical && !(-r $physical && -w $physical));
- return error($config->{'errors'}->{'text_to_binary'},$dir) if(-e $physical && not -T $physical);
+   my $tpl = new Template;
+   $tpl->read_file($config->{'templates'}->{'editfile'});
 
 
- if(file_save($physical,\$content))
- {
-  # The file was successfully saved!
+   $tpl->fillin('ERROR',$config->{'errors'}->{'edit_file_changed'});
 
 
-  return devedit_reload({command => 'show', file => $dir});
- }
- else
- {
-  return error($config->{'errors'}->{'edit_failed'},$dir,{FILE => $virtual});
+   $tpl->fillin('FILE',$virtual);
+   $tpl->fillin('DIR',$dir);
+   $tpl->fillin('URL',equal_url($config->{'httproot'},$virtual));
+   $tpl->fillin('SCRIPT',$script);
+   $tpl->fillin('MD5SUM',$md5_new);
+   $tpl->fillin('CONTENT',encode_entities($content));
+
+   $tpl->parse_if_block('error',1);
+
+   my $data = header(-type => 'text/html');
+   $data   .= $tpl->get_template;
+
+   $output  = \$data;
+  }
+  else
+  {
+   # The file was saved successfully!
+
+   seek(FILE,0,0);
+   truncate(FILE,0);
+
+   print FILE $content;
+
+   $output = devedit_reload({command => 'show', file => $dir});
+
+   #return error($config->{'errors'}->{'edit_failed'},$dir,{FILE => $virtual});
+  }
+
+  close(FILE);
+
+  return $output;
  }
  }
+
+ return devedit_reload({command => 'beginedit', file => $virtual});
 }
 
 # exec_mkfile()
 }
 
 # exec_mkfile()
@@ -511,8 +519,6 @@ sub exec_upload($$)
   my $file_phys = $physical.'/'.$filename;
   my $file_virt = $virtual.$filename;
 
   my $file_phys = $physical.'/'.$filename;
   my $file_virt = $virtual.$filename;
 
-  return error($config->{'errors'}->{'in_use'},$virtual,{FILE => $file_virt}) if($data->{'uselist'}->in_use($file_virt));
-
   if(-e $file_phys)
   {
    return error($config->{'errors'}->{'link_replace'},$virtual)                        if(-l $file_phys);
   if(-e $file_phys)
   {
    return error($config->{'errors'}->{'link_replace'},$virtual)                        if(-l $file_phys);
@@ -579,7 +585,6 @@ sub exec_copy($$)
 
   if(-e $new_physical)
   {
 
   if(-e $new_physical)
   {
-   return error($config->{'errors'}->{'exist_edited'},$new_dir,{FILE => $new_virtual})   if($data->{'uselist'}->in_use($data->{'new_virtual'}));
    return error($config->{'errors'}->{'link_replace'},$new_dir)                          if(-l $new_physical);
    return error($config->{'errors'}->{'dir_replace'},$new_dir)                           if(-d $new_physical);
    return error($config->{'errors'}->{'exist_no_write'},$new_dir,{FILE => $new_virtual}) unless(-w $new_physical);
    return error($config->{'errors'}->{'link_replace'},$new_dir)                          if(-l $new_physical);
    return error($config->{'errors'}->{'dir_replace'},$new_dir)                           if(-d $new_physical);
    return error($config->{'errors'}->{'exist_no_write'},$new_dir,{FILE => $new_virtual}) unless(-w $new_physical);
@@ -645,7 +650,6 @@ sub exec_rename($$)
 
  return error($config->{'errors'}->{'rename_root'},'/')                if($virtual eq '/');
  return error($config->{'errors'}->{'no_rename'},$dir)                 unless(-w upper_path($physical));
 
  return error($config->{'errors'}->{'rename_root'},'/')                if($virtual eq '/');
  return error($config->{'errors'}->{'no_rename'},$dir)                 unless(-w upper_path($physical));
- return error($config->{'errors'}->{'in_use'},$dir,{FILE => $virtual}) if($data->{'uselist'}->in_use($virtual));
 
  if($new_physical)
  {
 
  if($new_physical)
  {
@@ -655,7 +659,6 @@ sub exec_rename($$)
 
   if(-e $new_physical)
   {
 
   if(-e $new_physical)
   {
-   return error($config->{'errors'}->{'exist_edited'},$new_dir,{FILE => $new_virtual})   if($data->{'uselist'}->in_use($data->{'new_virtual'}));
    return error($config->{'errors'}->{'dir_replace'},$new_dir)                           if(-d $new_physical && not -l $new_physical);
    return error($config->{'errors'}->{'exist_no_write'},$new_dir,{FILE => $new_virtual}) unless(-w $new_physical);
 
    return error($config->{'errors'}->{'dir_replace'},$new_dir)                           if(-d $new_physical && not -l $new_physical);
    return error($config->{'errors'}->{'exist_no_write'},$new_dir,{FILE => $new_virtual}) unless(-w $new_physical);
 
@@ -749,8 +752,6 @@ sub exec_remove($$)
  {
   # Remove a file
 
  {
   # Remove a file
 
-  return error($config->{'errors'}->{'in_use'},$dir,{FILE => $virtual}) if($data->{'uselist'}->in_use($virtual));
-
   if($data->{'cgi'}->param('confirmed'))
   {
    unlink($physical) or return error($config->{'errors'}->{'delete_failed'},$dir,{FILE => $virtual});
   if($data->{'cgi'}->param('confirmed'))
   {
    unlink($physical) or return error($config->{'errors'}->{'delete_failed'},$dir,{FILE => $virtual});
@@ -794,7 +795,6 @@ sub exec_chprop($$)
  return error($config->{'errors'}->{'chprop_root'},'/')                   if($virtual eq '/');
  return error($config->{'errors'}->{'not_owner'},$dir,{FILE => $virtual}) unless(-o $physical);
  return error($config->{'errors'}->{'chprop_link'},$dir)                  if(-l $physical);
  return error($config->{'errors'}->{'chprop_root'},'/')                   if($virtual eq '/');
  return error($config->{'errors'}->{'not_owner'},$dir,{FILE => $virtual}) unless(-o $physical);
  return error($config->{'errors'}->{'chprop_link'},$dir)                  if(-l $physical);
- return error($config->{'errors'}->{'in_use'},$dir,{FILE => $virtual})    if($data->{'uselist'}->in_use($virtual));
 
  my $cgi   = $data->{'cgi'};
  my $mode  = $cgi->param('mode');
 
  my $cgi   = $data->{'cgi'};
  my $mode  = $cgi->param('mode');
@@ -860,47 +860,6 @@ sub exec_chprop($$)
  }
 }
 
  }
 }
 
-# exec_unlock()
-#
-# Remove a file from the list of used files and
-# return to directory view
-#
-# Params: 1. Reference to user input hash
-#         2. Reference to config hash
-#
-# Return: Output of the command (Scalar Reference)
-
-sub exec_unlock($$)
-{
- my ($data,$config) = @_;
- my $virtual        = $data->{'virtual'};
- my $uselist        = $data->{'uselist'};
- my $dir            = upper_path($virtual);
-
- return devedit_reload({command => 'show', file => $dir}) if($uselist->unused($virtual));
-
- if($data->{'cgi'}->param('confirmed'))
- {
-  file_unlock($uselist,$virtual) or return error($config->{'errors'}->{'ul_rm_failed'},$dir,{FILE => $virtual, USELIST => $uselist->{'listfile'}});
-  return devedit_reload({command => 'show', file => $dir});
- }
- else
- {
-  my $tpl = new Template;
-  $tpl->read_file($config->{'templates'}->{'confirm_unlock'});
-
-  $tpl->fillin('FILE',$virtual);
-  $tpl->fillin('DIR',$dir);
-  $tpl->fillin('URL',equal_url($config->{'httproot'},$virtual));
-  $tpl->fillin('SCRIPT',$script);
-
-  my $output = header(-type => 'text/html');
-  $output   .= $tpl->get_template;
-
-  return \$output;
- }
-}
-
 # exec_about()
 #
 # Display some information about Dev-Editor
 # exec_about()
 #
 # Display some information about Dev-Editor
index ad2bc13091da3884db25a4bccaf82d72278281a8..70a1c04a33257c53b0f2e9b3c588f202f441d8dd 100644 (file)
@@ -7,7 +7,7 @@ package File::Access;
 # using only one command
 #
 # Author:        Patrick Canterino <patrick@patshaping.de>
 # using only one command
 #
 # Author:        Patrick Canterino <patrick@patshaping.de>
-# Last modified: 2005-02-16
+# Last modified: 2005-04-09
 #
 
 use strict;
 #
 
 use strict;
@@ -27,7 +27,6 @@ use base qw(Exporter);
              file_lock
              file_read
              file_save
              file_lock
              file_read
              file_save
-             file_unlock
 
              LOCK_SH
              LOCK_EX
 
              LOCK_SH
              LOCK_EX
@@ -183,25 +182,6 @@ sub file_save($$;$)
  return 1;
 }
 
  return 1;
 }
 
-# file_unlock()
-#
-# Remove a file from the list of files in use
-#
-# Params: 1. File::UseList object
-#         2. File to remove
-#
-# Return: Status code (Boolean)
-
-sub file_unlock($$)
-{
- my ($uselist,$file) = @_;
-
- $uselist->remove_file($file) or return;
- $uselist->save               or return;
-
- return 1;
-}
-
 # it's true, baby ;-)
 
 1;
 # it's true, baby ;-)
 
 1;
diff --git a/modules/File/UseList.pm b/modules/File/UseList.pm
deleted file mode 100644 (file)
index 29db298..0000000
+++ /dev/null
@@ -1,281 +0,0 @@
-package File::UseList;
-
-#
-# File::UseList 1.3
-#
-# Run a list with files that are currently in use
-# (bases on Filing::UseList by Roland Bluethgen <calocybe@web.de>)
-#
-# Author:        Patrick Canterino <patrick@patshaping.de>
-# Last modified: 2004-12-03
-#
-
-use strict;
-
-use Carp qw(croak);
-use Fcntl;
-
-# new()
-#
-# Constructor
-#
-# Params: Hash: listfile => File with list of files in use
-#               lockfile => Lock file (Default: List file + .lock)
-#               timeout  => Lock timeout in seconds (Default: 10)
-#
-# Return: File::UseList object (Blessed Reference)
-
-sub new(%)
-{
- my ($class,%args) = @_;
-
- # Check if we got all the necessary information
-
- croak "Missing path to list file"             unless($args{'listfile'});
- $args{'lockfile'} = $args{'listfile'}.".lock" unless($args{'lockfile'}); # Default filename of lock file
- $args{'timeout'}  = 10                        unless($args{'timeout'});  # Default timeout
-
- # Add some other information
-
- $args{'files'}  = [];
- $args{'locked'} = 0;
-
- return bless(\%args,$class);
-}
-
-# lock()
-#
-# Lock list with files
-# (delete lock file)
-#
-# Params: -nothing-
-#
-# Return: Status code (Boolean)
-
-sub lock
-{
- my $self     = shift;
- my $lockfile = $self->{'lockfile'};
- my $timeout  = $self->{'timeout'};
-
- return 1 if($self->{'locked'});
-
- # Try to delete the lock file one time per second
- # until the timeout is reached
-
- for(my $x=$timeout;$x>=0;$x--)
- {
-  if(unlink($lockfile))
-  {
-   $self->{'locked'} = 1;
-   return 1;
-  }
-
-  sleep(1);
- }
-
- # Timeout
-
- return;
-}
-
-# unlock()
-#
-# Unlock list with files, but only if _we_ locked it
-# (create lock file)
-#
-# Params: -nothing-
-#
-# Return: Status code (Boolean)
-
-sub unlock
-{
- my $self     = shift;
- my $lockfile = $self->{'lockfile'};
- local *LOCKFILE;
-
- if($self->{'locked'})
- {
-  sysopen(LOCKFILE,$lockfile,O_WRONLY | O_CREAT | O_TRUNC) or return;
-  close(LOCKFILE)                                          or return;
-
-  $self->{'locked'} = 0;
-  return 1;
- }
-
- # The list wasn't lock by us or it isn't locked at all
-
- return;
-}
-
-# load()
-#
-# Load the list with files from the list file
-#
-# Params: -nothing-
-#
-# Return: Status code (Boolean)
-
-sub load
-{
- my $self = shift;
- my $file = $self->{'listfile'};
- local *FILE;
-
- # Read out the file and split the content line-per-line
-
- sysopen(FILE,$file,O_RDONLY) or return;
- read(FILE, my $content, -s $file);
- close(FILE)                  or return;
-
- my @files = split(/\015\012|\012|\015/,$content);
-
- # Remove useless lines
-
- for(my $x=0;$x<@files;$x++)
- {
-  if($files[$x] eq "" || $files[$x] =~ /^\s+$/)
-  {
-   splice(@files,$x,1);
-   $x--; # <-- very important!
-  }
- }
-
- $self->{'files'} = \@files;
- return 1;
-}
-
-# save()
-#
-# Write the list with files back to the list file
-#
-# Params: -nothing-
-#
-# Return: Status code (Boolean)
-
-sub save
-{
- my $self  = shift;
- my $file  = $self->{'listfile'};
- my $temp  = $file.".temp";
- my $files = $self->{'files'};
- local *FILE;
-
- my $data = (@$files) ? join("\n",@$files) : '';
-
- sysopen(FILE,$temp,O_WRONLY | O_CREAT | O_TRUNC) or return;
- print FILE $data                                 or do { close(FILE); return };
- close(FILE)                                      or return;
-
- rename($temp,$file)                              or return;
-
- return 1;
-}
-
-# add_file()
-#
-# Add a file to the list
-#
-# Params: File
-#
-# Return: Status code (Boolean)
-
-sub add_file($)
-{
- my ($self,$file) = @_;
- my $files = $self->{'files'};
-
- # Check if the file is already in the list
-
- return if($self->in_use($file));
-
- push(@$files,$file);
- return 1;
-}
-
-# remove_file()
-#
-# Remove a file from the list
-#
-# Params: File
-#
-# Return: Status code (Boolean)
-
-sub remove_file($)
-{
- my ($self,$file) = @_;
- my $files = $self->{'files'};
-
- # Check if the file is really in the list
-
- return if($self->unused($file));
-
- # Remove the file from the list
-
- for(my $x=0;$x<@$files;$x++)
- {
-  if($files->[$x] eq $file)
-  {
-   splice(@$files,$x,1);
-   return 1;
-  }
- }
-}
-
-# remove_all()
-#
-# Remove all files from the list
-#
-# Params: -nothing-
-#
-# Return: -nothing-
-
-sub remove_all
-{
- my $self = shift;
-
- $self->{'files'} = [];
-
- return;
-}
-
-# in_use()
-#
-# Check if a file is in the list
-#
-# Params: File to check
-#
-# Return: Status code (Boolean)
-
-sub in_use($)
-{
- my ($self,$file) = @_;
- my $files = $self->{'files'};
-
- foreach(@$files)
- {
-  return 1 if($_ eq $file);
- }
-
- return;
-}
-
-# unused()
-#
-# Check if a file is not in the list
-#
-# Params: File to check
-#
-# Return: Status code (Boolean)
-
-sub unused($)
-{
- return not shift->in_use(shift);
-}
-
-# it's true, baby ;-)
-
-1;
-
-#
-### End ###
\ No newline at end of file
similarity index 100%
rename from templates.dat
rename to templates.conf
index 5df126e013be7eb63427d420bec3a715897ae0f1..44d67a55f0a070c0108b132b41488c0a7f8f1aad 100644 (file)
@@ -2,5 +2,5 @@
 <td align="right" style="white-space:nowrap">{SIZE}</td>
 <td style="padding-left:15pt;white-space:nowrap;">{DATE}{IF gmt} (GMT){ENDIF}</td>
 <td style="padding-left:15pt;white-space:nowrap;">{FILE_NAME}</td>
 <td align="right" style="white-space:nowrap">{SIZE}</td>
 <td style="padding-left:15pt;white-space:nowrap;">{DATE}{IF gmt} (GMT){ENDIF}</td>
 <td style="padding-left:15pt;white-space:nowrap;">{FILE_NAME}</td>
-<td style="padding-left:15pt;white-space:nowrap;">({IF viewable}<a href="{SCRIPT}?command=show&amp;file={FILE}">View</a>{ELSE}<span style="color:#C0C0C0" title="{IF not_readable}Not readable{ELSE}{IF binary}Binary file{ELSE}{IF too_large}File too large{ENDIF}{ENDIF}{ENDIF}">View</span>{ENDIF} | {IF editable}<a href="{SCRIPT}?command=beginedit&amp;file={FILE}">Edit</a>{ELSE}<span style="color:#C0C0C0" title="{IF link}Symbolic link{ELSE}{IF not_readable}Not readable{ELSE}{IF readonly}Read only{ELSE}{IF binary}Binary file{ELSE}{IF too_large}File too large{ENDIF}{IF in_use}In use{ENDIF}{ENDIF}{ENDIF}{ENDIF}{ENDIF}">Edit</span>{ENDIF}{IF no_link} | <a href="{SCRIPT}?command=copy&amp;file={FILE}">Copy</a>{ENDIF}{IF unused}{IF dir_writeable} | <a href="{SCRIPT}?command=rename&amp;file={FILE}">Rename</a> | <a href="{SCRIPT}?command=remove&amp;file={FILE}">Delete</a>{ENDIF}{ENDIF}{IF no_link}{IF in_use} | <a href="{SCRIPT}?command=unlock&amp;file={FILE}">Unlock</a>{ENDIF} |{IF unused}{IF users} <a href="{SCRIPT}?command=chprop&amp;file={FILE}">Chmod/Chgrp</a> |{ENDIF}{ENDIF}{ELSE} |{ENDIF} <a href="{URL}" target="_blank">View in Browser</a>)</td>
+<td style="padding-left:15pt;white-space:nowrap;">({IF viewable}<a href="{SCRIPT}?command=show&amp;file={FILE}">View</a>{ELSE}<span style="color:#C0C0C0" title="{IF not_readable}Not readable{ELSE}{IF binary}Binary file{ELSE}{IF too_large}File too large{ENDIF}{ENDIF}{ENDIF}">View</span>{ENDIF} | {IF editable}<a href="{SCRIPT}?command=beginedit&amp;file={FILE}">Edit</a>{ELSE}<span style="color:#C0C0C0" title="{IF link}Symbolic link{ELSE}{IF not_readable}Not readable{ELSE}{IF readonly}Read only{ELSE}{IF binary}Binary file{ELSE}{IF too_large}File too large{ENDIF}{ENDIF}{ENDIF}{ENDIF}{ENDIF}">Edit</span>{ENDIF}{IF no_link} | <a href="{SCRIPT}?command=copy&amp;file={FILE}">Copy</a>{ENDIF}{IF dir_writeable} | <a href="{SCRIPT}?command=rename&amp;file={FILE}">Rename</a> | <a href="{SCRIPT}?command=remove&amp;file={FILE}">Delete</a>{ENDIF} |{IF users} <a href="{SCRIPT}?command=chprop&amp;file={FILE}">Chmod/Chgrp</a> |{ENDIF} <a href="{URL}" target="_blank">View in Browser</a>)</td>
 </tr>
 </tr>
index 5ec836ab2fc07d91ad749e2b80f6ac2771201ed3..5d14d4ac318af478c8a8af8fa846b6fdaf9ce7e5 100644 (file)
 
 <p>(equals <a href="{URL}" target="_blank">{URL}</a>)</p>
 
 
 <p>(equals <a href="{URL}" target="_blank">{URL}</a>)</p>
 
-<p><b style="color:#FF0000">Caution!</b> This file is locked for other users while you are editing it. To unlock it, click <i>Save and exit</i> or <i>Exit WITHOUT saving</i>. Please <b>don't</b> click the <i>Reload</i> button in your browser! This will confuse the editor.</p>
+<p><a href="{SCRIPT}?command=show&amp;file={DIR}">Back to {DIR}</a></p>{IF error}
 
 
-<form action="{SCRIPT}" method="get">
-<input type="hidden" name="command" value="canceledit">
-<input type="hidden" name="file" value="{FILE}">
-<p><input type="submit" value="Exit WITHOUT saving"></p>
-</form>
+<p>{ERROR}</p>{ENDIF}
 
 <form action="{SCRIPT}" method="post">
 <input type="hidden" name="command" value="endedit">
 <input type="hidden" name="file" value="{FILE}">
 
 <form action="{SCRIPT}" method="post">
 <input type="hidden" name="command" value="endedit">
 <input type="hidden" name="file" value="{FILE}">
+<input type="hidden" name="md5sum" value="{MD5SUM}">
+
+<p><textarea name="filecontent" rows="25" cols="120">{CONTENT}</textarea></p>
+
+<p><input type="checkbox" name="saveas" id="newfile" value="1"><label for="newfile"> Save as new file: {DIR} </label><input type="text" name="newfile" value="" onchange="if(this.form.newfile.value != '') this.form.saveas.checked = true; else this.form.saveas.checked = false;"></p>
 
 
-<table width="100%" border="1">
-<tr>
-<td width="50%" align="center">
-<input type="checkbox" name="saveas" id="newfile" value="1"><label for="newfile"> Save as new file: {DIR} </label><input type="text" name="newfile" value="" onchange="if(this.form.newfile.value != '') this.form.saveas.checked = true; else this.form.saveas.checked = false;"></td>
-<td width="50%" align="center"><input type="checkbox" name="encode_iso" id="encode_iso" value="1"><label for="encode_iso"> Encode ISO-8859-1 special chars</label></td>
-</tr>
-<tr>
-<td align="center"><input type="reset" value="Reset form"></td>
-<td align="center"><input type="submit" value="Save and exit"></td>
-</tr>
-</table>
-
-<textarea name="filecontent" rows="25" cols="120">{CONTENT}</textarea>
+<p><input type="submit" value="Save file"> <input type="reset" value="Discard changes"></p>
 </form>
 
 </body>
 </form>
 
 </body>
diff --git a/uselist b/uselist
deleted file mode 100644 (file)
index e69de29..0000000
diff --git a/uselist.lock b/uselist.lock
deleted file mode 100644 (file)
index e69de29..0000000

patrick-canterino.de