| 1 | ################################################################################ |
1 | ################################################################################ |
| 2 | # WeBWorK Online Homework Delivery System |
2 | # WeBWorK Online Homework Delivery System |
| 3 | # Copyright © 2000-2006 The WeBWorK Project, http://openwebwork.sf.net/ |
3 | # Copyright © 2000-2006 The WeBWorK Project, http://openwebwork.sf.net/ |
| 4 | # $CVSHeader: webwork2/lib/WeBWorK/ContentGenerator/Instructor/PGProblemEditor.pm,v 1.66.2.6 2006/01/11 23:56:45 dpvc Exp $ |
4 | # $CVSHeader: webwork2/lib/WeBWorK/ContentGenerator/Instructor/PGProblemEditor.pm,v 1.66.2.7 2006/01/25 23:12:01 sh002i Exp $ |
| 5 | # |
5 | # |
| 6 | # This program is free software; you can redistribute it and/or modify it under |
6 | # This program is free software; you can redistribute it and/or modify it under |
| 7 | # the terms of either: (a) the GNU General Public License as published by the |
7 | # the terms of either: (a) the GNU General Public License as published by the |
| 8 | # Free Software Foundation; either version 2, or (at your option) any later |
8 | # Free Software Foundation; either version 2, or (at your option) any later |
| 9 | # version, or (b) the "Artistic License" which comes with this package. |
9 | # version, or (b) the "Artistic License" which comes with this package. |
| … | |
… | |
| 26 | =cut |
26 | =cut |
| 27 | |
27 | |
| 28 | use strict; |
28 | use strict; |
| 29 | use warnings; |
29 | use warnings; |
| 30 | use CGI qw(); |
30 | use CGI qw(); |
| 31 | use WeBWorK::Utils qw(readFile surePathToFile); |
31 | use WeBWorK::Utils qw(readFile surePathToFile path_is_subdir); |
| 32 | use Apache::Constants qw(:common REDIRECT); |
32 | use Apache::Constants qw(:common REDIRECT); |
| 33 | use HTML::Entities; |
33 | use HTML::Entities; |
| 34 | use URI::Escape; |
34 | use URI::Escape; |
| 35 | use WeBWorK::Utils; |
35 | use WeBWorK::Utils; |
| 36 | use WeBWorK::Utils::Tasks qw(fake_set fake_problem); |
36 | use WeBWorK::Utils::Tasks qw(fake_set fake_problem); |
| … | |
… | |
| 470 | |
470 | |
| 471 | my $problemContents = ${$self->{r_problemContents}}; |
471 | my $problemContents = ${$self->{r_problemContents}}; |
| 472 | |
472 | |
| 473 | unless ( $problemContents =~/\S/) { # non-empty contents |
473 | unless ( $problemContents =~/\S/) { # non-empty contents |
| 474 | if (-r $tempFilePath and not -d $tempFilePath) { |
474 | if (-r $tempFilePath and not -d $tempFilePath) { |
|
|
475 | die "tempFilePath is unsafe!" unless path_is_subdir($tempFilePath, $ce->{courseDirs}->{templates}, 1); # 1==path can be relative to dir |
| 475 | eval { $problemContents = WeBWorK::Utils::readFile($tempFilePath) }; |
476 | eval { $problemContents = WeBWorK::Utils::readFile($tempFilePath) }; |
| 476 | $problemContents = $@ if $@; |
477 | $problemContents = $@ if $@; |
| 477 | $inputFilePath = $tempFilePath; |
478 | $inputFilePath = $tempFilePath; |
| 478 | } elsif (-r $editFilePath and not -d $editFilePath) { |
479 | } elsif (-r $editFilePath and not -d $editFilePath) { |
|
|
480 | die "editFilePath is unsafe!" unless path_is_subdir($editFilePath, $ce->{courseDirs}->{templates}, 1); # 1==path can be relative to dir |
| 479 | eval { $problemContents = WeBWorK::Utils::readFile($editFilePath) }; |
481 | eval { $problemContents = WeBWorK::Utils::readFile($editFilePath) }; |
| 480 | $problemContents = $@ if $@; |
482 | $problemContents = $@ if $@; |
| 481 | $inputFilePath = $editFilePath; |
483 | $inputFilePath = $editFilePath; |
| 482 | } else { # file not existing is not an error |
484 | } else { # file not existing is not an error |
| 483 | #warn "No file exists"; |
485 | #warn "No file exists"; |
| … | |
… | |
| 950 | #$problemContents =~ s/\r/\n/g; |
952 | #$problemContents =~ s/\r/\n/g; |
| 951 | |
953 | |
| 952 | # make sure any missing directories are created |
954 | # make sure any missing directories are created |
| 953 | WeBWorK::Utils::surePathToFile($ce->{courseDirs}->{templates}, |
955 | WeBWorK::Utils::surePathToFile($ce->{courseDirs}->{templates}, |
| 954 | $outputFilePath); |
956 | $outputFilePath); |
|
|
957 | die "outputFilePath is unsafe!" unless path_is_subdir($outputFilePath, $ce->{courseDirs}->{templates}, 1); # 1==path can be relative to dir |
| 955 | |
958 | |
| 956 | eval { |
959 | eval { |
| 957 | local *OUTPUTFILE; |
960 | local *OUTPUTFILE; |
| 958 | open OUTPUTFILE, ">$outputFilePath" |
961 | open OUTPUTFILE, ">$outputFilePath" |
| 959 | or die "Failed to open $outputFilePath"; |
962 | or die "Failed to open $outputFilePath"; |
| … | |
… | |
| 999 | unless( $writeFileErrors or $do_not_save) { # everything worked! unlink and announce success! |
1002 | unless( $writeFileErrors or $do_not_save) { # everything worked! unlink and announce success! |
| 1000 | # unlink the temporary file if there are no errors and the save button has been pushed |
1003 | # unlink the temporary file if there are no errors and the save button has been pushed |
| 1001 | if (($action eq 'save' or $action eq 'save_as') and (-w $self->{tempFilePath}) ) { |
1004 | if (($action eq 'save' or $action eq 'save_as') and (-w $self->{tempFilePath}) ) { |
| 1002 | |
1005 | |
| 1003 | $self->addgoodmessage("Deleting temp file at " . $self->shortPath($self->{tempFilePath})); |
1006 | $self->addgoodmessage("Deleting temp file at " . $self->shortPath($self->{tempFilePath})); |
|
|
1007 | die "tempFilePath is unsafe!" unless path_is_subdir($self->{tempFilePath}, $ce->{courseDirs}->{templates}, 1); # 1==path can be relative to dir |
| 1004 | unlink($self->{tempFilePath}) ; |
1008 | unlink($self->{tempFilePath}) ; |
| 1005 | } |
1009 | } |
| 1006 | |
1010 | |
| 1007 | if ( defined($outputFilePath) and ! $self->{failure} and not $self->isTempEditFilePath($outputFilePath) ) { |
1011 | if ( defined($outputFilePath) and ! $self->{failure} and not $self->isTempEditFilePath($outputFilePath) ) { |
| 1008 | # don't announce saving of temporary editing files |
1012 | # don't announce saving of temporary editing files |
| … | |
… | |
| 1660 | return "Revert to ".$self->shortPath($editFilePath) ; |
1664 | return "Revert to ".$self->shortPath($editFilePath) ; |
| 1661 | |
1665 | |
| 1662 | } |
1666 | } |
| 1663 | sub revert_handler { |
1667 | sub revert_handler { |
| 1664 | my ($self, $genericParams, $actionParams, $tableParams) = @_; |
1668 | my ($self, $genericParams, $actionParams, $tableParams) = @_; |
|
|
1669 | my $ce = $self->ce; |
| 1665 | #$self->addgoodmessage("revert_handler called"); |
1670 | #$self->addgoodmessage("revert_handler called"); |
| 1666 | my $editFilePath = $self->{editFilePath}; |
1671 | my $editFilePath = $self->{editFilePath}; |
| 1667 | $self->{inputFilePath} = $editFilePath; |
1672 | $self->{inputFilePath} = $editFilePath; |
| 1668 | # unlink the temp files; |
1673 | # unlink the temp files; |
|
|
1674 | die "tempFilePath is unsafe!" unless path_is_subdir($self->{tempFilePath}, $ce->{courseDirs}->{templates}, 1); # 1==path can be relative to dir |
| 1669 | unlink($self->{tempFilePath}); |
1675 | unlink($self->{tempFilePath}); |
| 1670 | $self->addgoodmessage("Deleting temp file at " . $self->shortPath($self->{tempFilePath})); |
1676 | $self->addgoodmessage("Deleting temp file at " . $self->shortPath($self->{tempFilePath})); |
| 1671 | $self->{tempFilePath} = ''; |
1677 | $self->{tempFilePath} = ''; |
| 1672 | my $problemContents =''; |
1678 | my $problemContents =''; |
| 1673 | $self->{r_problemContents} = \$problemContents; |
1679 | $self->{r_problemContents} = \$problemContents; |