version 1.1027, 2011/11/02 23:05:07
|
version 1.1099, 2012/12/03 14:47:30
|
Line 70 use Apache::lonclonecourse();
|
Line 70 use Apache::lonclonecourse();
|
use LONCAPA qw(:DEFAULT :match); |
use LONCAPA qw(:DEFAULT :match); |
use DateTime::TimeZone; |
use DateTime::TimeZone; |
use DateTime::Locale::Catalog; |
use DateTime::Locale::Catalog; |
|
use Text::Aspell; |
|
use Authen::Captcha; |
|
use Captcha::reCAPTCHA; |
|
|
# ---------------------------------------------- Designs |
# ---------------------------------------------- Designs |
use vars qw(%defaultdesign); |
use vars qw(%defaultdesign); |
Line 154 sub ssi_with_retries {
|
Line 157 sub ssi_with_retries {
|
# ----------------------------------------------- Filetypes/Languages/Copyright |
# ----------------------------------------------- Filetypes/Languages/Copyright |
my %language; |
my %language; |
my %supported_language; |
my %supported_language; |
|
my %supported_codes; |
|
my %latex_language; # For choosing hyphenation in <transl..> |
|
my %latex_language_bykey; # for choosing hyphenation from metadata |
my %cprtag; |
my %cprtag; |
my %scprtag; |
my %scprtag; |
my %fe; my %fd; my %fm; |
my %fe; my %fd; my %fm; |
Line 186 BEGIN {
|
Line 192 BEGIN {
|
while (my $line = <$fh>) { |
while (my $line = <$fh>) { |
next if ($line=~/^\#/); |
next if ($line=~/^\#/); |
chomp($line); |
chomp($line); |
my ($key,$two,$country,$three,$enc,$val,$sup)=(split(/\t/,$line)); |
my ($key,$code,$country,$three,$enc,$val,$sup,$latex)=(split(/\t/,$line)); |
$language{$key}=$val.' - '.$enc; |
$language{$key}=$val.' - '.$enc; |
if ($sup) { |
if ($sup) { |
$supported_language{$key}=$sup; |
$supported_language{$key}=$sup; |
|
$supported_codes{$key} = $code; |
} |
} |
|
if ($latex) { |
|
$latex_language_bykey{$key} = $latex; |
|
$latex_language{$code} = $latex; |
|
} |
} |
} |
close($fh); |
close($fh); |
} |
} |
Line 651 if (!Array.prototype.indexOf) {
|
Line 662 if (!Array.prototype.indexOf) {
|
var n = 0; |
var n = 0; |
if (arguments.length > 0) { |
if (arguments.length > 0) { |
n = Number(arguments[1]); |
n = Number(arguments[1]); |
if (n !== n) { // shortcut for verifying if it's NaN |
if (n !== n) { // shortcut for verifying if it is NaN |
n = 0; |
n = 0; |
} else if (n !== 0 && n !== (1 / 0) && n !== -(1 / 0)) { |
} else if (n !== 0 && n !== (1 / 0) && n !== -(1 / 0)) { |
n = (n > 0 || -1) * Math.floor(Math.abs(n)); |
n = (n > 0 || -1) * Math.floor(Math.abs(n)); |
Line 879 sub check_uncheck_jscript {
|
Line 890 sub check_uncheck_jscript {
|
function checkAll(field) { |
function checkAll(field) { |
if (field.length > 0) { |
if (field.length > 0) { |
for (i = 0; i < field.length; i++) { |
for (i = 0; i < field.length; i++) { |
field[i].checked = true ; |
if (!field[i].disabled) { |
|
field[i].checked = true; |
|
} |
} |
} |
} else { |
} else { |
field.checked = true |
if (!field.disabled) { |
|
field.checked = true; |
|
} |
} |
} |
} |
} |
|
|
Line 989 sub select_language {
|
Line 1004 sub select_language {
|
|
|
=pod |
=pod |
|
|
|
|
|
=item * &list_languages() |
|
|
|
Returns an array reference that is suitable for use in language prompters. |
|
Each array element is itself a two element array. The first element |
|
is the language code. The second element a descsriptiuon of the |
|
language itself. This is suitable for use in e.g. |
|
&Apache::edit::select_arg (once dereferenced that is). |
|
|
|
=cut |
|
|
|
sub list_languages { |
|
my @lang_choices; |
|
|
|
foreach my $id (&languageids()) { |
|
my $code = &supportedlanguagecode($id); |
|
if ($code) { |
|
my $selector = $supported_codes{$id}; |
|
my $description = &plainlanguagedescription($id); |
|
push (@lang_choices, [$selector, $description]); |
|
} |
|
} |
|
return \@lang_choices; |
|
} |
|
|
|
=pod |
|
|
=item * &linked_select_forms(...) |
=item * &linked_select_forms(...) |
|
|
linked_select_forms returns a string containing a <script></script> block |
linked_select_forms returns a string containing a <script></script> block |
Line 1186 sub help_open_topic {
|
Line 1228 sub help_open_topic {
|
my ($topic, $text, $stayOnPage, $width, $height, $imgid) = @_; |
my ($topic, $text, $stayOnPage, $width, $height, $imgid) = @_; |
$text = "" if (not defined $text); |
$text = "" if (not defined $text); |
$stayOnPage = 0 if (not defined $stayOnPage); |
$stayOnPage = 0 if (not defined $stayOnPage); |
$width = 350 if (not defined $width); |
$width = 500 if (not defined $width); |
$height = 400 if (not defined $height); |
$height = 400 if (not defined $height); |
my $filename = $topic; |
my $filename = $topic; |
$filename =~ s/ /_/g; |
$filename =~ s/ /_/g; |
Line 1197 sub help_open_topic {
|
Line 1239 sub help_open_topic {
|
$topic=~s/\W/\_/g; |
$topic=~s/\W/\_/g; |
|
|
if (!$stayOnPage) { |
if (!$stayOnPage) { |
$link = "javascript:void(open('/adm/help/${filename}.hlp', 'Help_for_$topic', 'menubar=0,toolbar=1,scrollbars=1,width=$width,height=$height,resizable=yes'))"; |
$link = "javascript:openMyModal('/adm/help/${filename}.hlp',$width,$height,'yes');"; |
|
} elsif ($stayOnPage eq 'popup') { |
|
$link = "javascript:void(open('/adm/help/${filename}.hlp', 'Help_for_$topic', 'menubar=0,toolbar=1,scrollbars=1,width=$width,height=$height,resizable=yes'))"; |
} else { |
} else { |
$link = "/adm/help/${filename}.hlp"; |
$link = "/adm/help/${filename}.hlp"; |
} |
} |
Line 1230 sub help_open_topic {
|
Line 1274 sub help_open_topic {
|
# This is a quicky function for Latex cheatsheet editing, since it |
# This is a quicky function for Latex cheatsheet editing, since it |
# appears in at least four places |
# appears in at least four places |
sub helpLatexCheatsheet { |
sub helpLatexCheatsheet { |
my ($topic,$text,$not_author) = @_; |
my ($topic,$text,$not_author,$stayOnPage) = @_; |
my $out; |
my $out; |
my $addOther = ''; |
my $addOther = ''; |
if ($topic) { |
if ($topic) { |
$addOther = '<span>'.&Apache::loncommon::help_open_topic($topic,&mt($text), |
$addOther = '<span>'.&help_open_topic($topic,&mt($text),$stayOnPage, undef, 600).'</span> '; |
undef, undef, 600). |
|
'</span> '; |
|
} |
} |
$out = '<span>' # Start cheatsheet |
$out = '<span>' # Start cheatsheet |
.$addOther |
.$addOther |
.'<span>' |
.'<span>' |
.&Apache::loncommon::help_open_topic('Greek_Symbols',&mt('Greek Symbols'), |
.&help_open_topic('Greek_Symbols',&mt('Greek Symbols'),$stayOnPage,undef,600) |
undef,undef,600) |
|
.'</span> <span>' |
.'</span> <span>' |
.&Apache::loncommon::help_open_topic('Other_Symbols',&mt('Other Symbols'), |
.&help_open_topic('Other_Symbols',&mt('Other Symbols'),$stayOnPage,undef,600) |
undef,undef,600) |
|
.'</span>'; |
.'</span>'; |
unless ($not_author) { |
unless ($not_author) { |
$out .= ' <span>' |
$out .= ' <span>' |
.&Apache::loncommon::help_open_topic('Authoring_Output_Tags',&mt('Output Tags'), |
.&help_open_topic('Authoring_Output_Tags',&mt('Output Tags'),$stayOnPage,undef,600) |
undef,undef,600) |
|
.'</span>'; |
.'</span>'; |
} |
} |
$out .= '</span>'; # End cheatsheet |
$out .= '</span>'; # End cheatsheet |
Line 1371 function helpMenu(target) {
|
Line 1410 function helpMenu(target) {
|
return; |
return; |
} |
} |
function writeHelp(caller) { |
function writeHelp(caller) { |
caller.document.writeln('$start_page<frame name="bannerframe" src="'+banner_link+'" /><frame name="bodyframe" src="$details_link" /> $end_page') |
caller.document.writeln('$start_page\\n<frame name="bannerframe" src="'+banner_link+'" />\\n<frame name="bodyframe" src="$details_link" />\\n$end_page') |
caller.document.close() |
caller.document.close() |
caller.focus() |
caller.focus() |
} |
} |
Line 1745 Inputs: $workbook
|
Line 1784 Inputs: $workbook
|
|
|
Returns: $format, a hash reference. |
Returns: $format, a hash reference. |
|
|
|
|
=cut |
=cut |
|
|
############################################################### |
############################################################### |
Line 1977 sub select_form {
|
Line 2017 sub select_form {
|
# For display filters |
# For display filters |
|
|
sub display_filter { |
sub display_filter { |
|
my ($context) = @_; |
if (!$env{'form.show'}) { $env{'form.show'}=10; } |
if (!$env{'form.show'}) { $env{'form.show'}=10; } |
if (!$env{'form.displayfilter'}) { $env{'form.displayfilter'}='currentfolder'; } |
if (!$env{'form.displayfilter'}) { $env{'form.displayfilter'}='currentfolder'; } |
return '<span class="LC_nobreak"><label>'.&mt('Records [_1]', |
my $phraseinput = 'hidden'; |
|
my $includeinput = 'hidden'; |
|
my ($checked,$includetypestext); |
|
if ($env{'form.displayfilter'} eq 'containing') { |
|
$phraseinput = 'text'; |
|
if ($context eq 'parmslog') { |
|
$includeinput = 'checkbox'; |
|
if ($env{'form.includetypes'}) { |
|
$checked = ' checked="checked"'; |
|
} |
|
$includetypestext = &mt('Include parameter types'); |
|
} |
|
} else { |
|
$includetypestext = ' '; |
|
} |
|
my ($additional,$secondid,$thirdid); |
|
if ($context eq 'parmslog') { |
|
$additional = |
|
'<label><input type="'.$includeinput.'" name="includetypes"'. |
|
$checked.' name="includetypes" value="1" id="includetypes" />'. |
|
' <span id="includetypestext">'.$includetypestext.'</span>'. |
|
'</label>'; |
|
$secondid = 'includetypes'; |
|
$thirdid = 'includetypestext'; |
|
} |
|
my $onchange = "javascript:toggleHistoryOptions(this,'containingphrase','$context', |
|
'$secondid','$thirdid')"; |
|
return '<span class="LC_nobreak"><label>'.&mt('Records: [_1]', |
&Apache::lonmeta::selectbox('show',$env{'form.show'},undef, |
&Apache::lonmeta::selectbox('show',$env{'form.show'},undef, |
(&mt('all'),10,20,50,100,1000,10000))). |
(&mt('all'),10,20,50,100,1000,10000))). |
'</label></span> <span class="LC_nobreak">'. |
'</label></span> <span class="LC_nobreak">'. |
&mt('Filter [_1]', |
&mt('Filter: [_1]', |
&select_form($env{'form.displayfilter'}, |
&select_form($env{'form.displayfilter'}, |
'displayfilter', |
'displayfilter', |
{'currentfolder' => 'Current folder/page', |
{'currentfolder' => 'Current folder/page', |
'containing' => 'Containing phrase', |
'containing' => 'Containing phrase', |
'none' => 'None'})). |
'none' => 'None'},$onchange)).' '. |
'<input type="text" name="containingphrase" size="30" value="'.&HTML::Entities::encode($env{'form.containingphrase'}).'" /></span>'; |
'<input type="'.$phraseinput.'" name="containingphrase" id="containingphrase" size="30" value="'. |
|
&HTML::Entities::encode($env{'form.containingphrase'}). |
|
'" />'.$additional; |
|
} |
|
|
|
sub display_filter_js { |
|
my $includetext = &mt('Include parameter types'); |
|
return <<"ENDJS"; |
|
|
|
function toggleHistoryOptions(setter,firstid,context,secondid,thirdid) { |
|
var firstType = 'hidden'; |
|
if (setter.options[setter.selectedIndex].value == 'containing') { |
|
firstType = 'text'; |
|
} |
|
firstObject = document.getElementById(firstid); |
|
if (typeof(firstObject) == 'object') { |
|
if (firstObject.type != firstType) { |
|
changeInputType(firstObject,firstType); |
|
} |
|
} |
|
if (context == 'parmslog') { |
|
var secondType = 'hidden'; |
|
if (firstType == 'text') { |
|
secondType = 'checkbox'; |
|
} |
|
secondObject = document.getElementById(secondid); |
|
if (typeof(secondObject) == 'object') { |
|
if (secondObject.type != secondType) { |
|
changeInputType(secondObject,secondType); |
|
} |
|
} |
|
var textItem = document.getElementById(thirdid); |
|
var currtext = textItem.innerHTML; |
|
var newtext; |
|
if (firstType == 'text') { |
|
newtext = '$includetext'; |
|
} else { |
|
newtext = ' '; |
|
} |
|
if (currtext != newtext) { |
|
textItem.innerHTML = newtext; |
|
} |
|
} |
|
return; |
|
} |
|
|
|
function changeInputType(oldObject,newType) { |
|
var newObject = document.createElement('input'); |
|
newObject.type = newType; |
|
if (oldObject.size) { |
|
newObject.size = oldObject.size; |
|
} |
|
if (oldObject.value) { |
|
newObject.value = oldObject.value; |
|
} |
|
if (oldObject.name) { |
|
newObject.name = oldObject.name; |
|
} |
|
if (oldObject.id) { |
|
newObject.id = oldObject.id; |
|
} |
|
oldObject.parentNode.replaceChild(newObject,oldObject); |
|
return; |
|
} |
|
|
|
ENDJS |
} |
} |
|
|
sub gradeleveldescription { |
sub gradeleveldescription { |
Line 2853 database which holds them.
|
Line 2986 database which holds them.
|
|
|
Uses global $thesaurus_db_file. |
Uses global $thesaurus_db_file. |
|
|
|
|
=cut |
=cut |
|
|
############################################################### |
############################################################### |
Line 2888 sub get_related_words {
|
Line 3022 sub get_related_words {
|
untie %thesaurus_db; |
untie %thesaurus_db; |
return @Words; |
return @Words; |
} |
} |
|
############################################################### |
|
# |
|
# Spell checking |
|
# |
|
|
|
=pod |
|
|
|
=head1 Spell checking |
|
|
|
=over 4 |
|
|
|
=item * &check_spelling($wordlist $language) |
|
|
|
Takes a string containing words and feeds it to an external |
|
spellcheck program via a pipeline. Returns a string containing |
|
them mis-spelled words. |
|
|
|
Parameters: |
|
|
|
=over 4 |
|
|
|
=item - $wordlist |
|
|
|
String that will be fed into the spellcheck program. |
|
|
|
=item - $language |
|
|
|
Language string that specifies the language for which the spell |
|
check will be performed. |
|
|
|
=back |
|
|
|
=back |
|
|
|
Note: This sub assumes that aspell is installed. |
|
|
|
|
|
=cut |
|
|
|
|
=pod |
=pod |
|
|
Line 2895 sub get_related_words {
|
Line 3068 sub get_related_words {
|
|
|
=cut |
=cut |
|
|
|
sub check_spelling { |
|
my ($wordlist, $language) = @_; |
|
my @misspellings; |
|
|
|
# Generate the speller and set the langauge. |
|
# if explicitly selected: |
|
|
|
my $speller = Text::Aspell->new; |
|
if ($language) { |
|
$speller->set_option('lang', $language); |
|
} |
|
|
|
# Turn the word list into an array of words by splittingon whitespace |
|
|
|
my @words = split(/\s+/, $wordlist); |
|
|
|
foreach my $word (@words) { |
|
if(! $speller->check($word)) { |
|
push(@misspellings, $word); |
|
} |
|
} |
|
return join(' ', @misspellings); |
|
|
|
} |
|
|
# -------------------------------------------------------------- Plaintext name |
# -------------------------------------------------------------- Plaintext name |
=pod |
=pod |
|
|
Line 3124 sub noteswrapper {
|
Line 3322 sub noteswrapper {
|
# ------------------------------------------------------------- Aboutme Wrapper |
# ------------------------------------------------------------- Aboutme Wrapper |
|
|
sub aboutmewrapper { |
sub aboutmewrapper { |
my ($link,$username,$domain,$target)=@_; |
my ($link,$username,$domain,$target,$class)=@_; |
if (!defined($username) && !defined($domain)) { |
if (!defined($username) && !defined($domain)) { |
return; |
return; |
} |
} |
return '<a href="/adm/'.$domain.'/'.$username.'/aboutme?forcestudent=1"'. |
return '<a href="/adm/'.$domain.'/'.$username.'/aboutme"'. |
($target?' target="$target"':'').' title="'.&mt("View this user's personal information page").'">'.$link.'</a>'; |
($target?' target="'.$target.'"':'').($class?' class="'.$class.'"':'').' title="'.&mt("View this user's personal information page").'">'.$link.'</a>'; |
} |
} |
|
|
# ------------------------------------------------------------ Syllabus Wrapper |
# ------------------------------------------------------------ Syllabus Wrapper |
Line 3230 sub languagedescription {
|
Line 3428 sub languagedescription {
|
($supported_language{$code}?' ('.&mt('interface available').')':''); |
($supported_language{$code}?' ('.&mt('interface available').')':''); |
} |
} |
|
|
|
=pod |
|
|
|
=item * &plainlanguagedescription |
|
|
|
Returns both the plain language description (e.g. 'Creoles and Pidgins, English-based (Other)') |
|
and the language character encoding (e.g. ISO) separated by a ' - ' string. |
|
|
|
=cut |
|
|
sub plainlanguagedescription { |
sub plainlanguagedescription { |
my $code=shift; |
my $code=shift; |
return $language{$code}; |
return $language{$code}; |
} |
} |
|
|
|
=pod |
|
|
|
=item * &supportedlanguagecode |
|
|
|
Returns the supported language code (e.g. sptutf maps to pt) given a language |
|
code. |
|
|
|
=cut |
|
|
sub supportedlanguagecode { |
sub supportedlanguagecode { |
my $code=shift; |
my $code=shift; |
return $supported_language{$code}; |
return $supported_language{$code}; |
Line 3242 sub supportedlanguagecode {
|
Line 3458 sub supportedlanguagecode {
|
|
|
=pod |
=pod |
|
|
|
=item * &latexlanguage() |
|
|
|
Given a language key code returns the correspondnig language to use |
|
to select the correct hyphenation on LaTeX printouts. This is undef if there |
|
is no supported hyphenation for the language code. |
|
|
|
=cut |
|
|
|
sub latexlanguage { |
|
my $code = shift; |
|
return $latex_language{$code}; |
|
} |
|
|
|
=pod |
|
|
|
=item * &latexhyphenation() |
|
|
|
Same as above but what's supplied is the language as it might be stored |
|
in the metadata. |
|
|
|
=cut |
|
|
|
sub latexhyphenation { |
|
my $key = shift; |
|
return $latex_language_bykey{$key}; |
|
} |
|
|
|
=pod |
|
|
=item * ©rightids() |
=item * ©rightids() |
|
|
returns list of all copyrights |
returns list of all copyrights |
Line 3938 sub findallcourses {
|
Line 4183 sub findallcourses {
|
$udom = $env{'user.domain'}; |
$udom = $env{'user.domain'}; |
} |
} |
if (($uname ne $env{'user.name'}) || ($udom ne $env{'user.domain'})) { |
if (($uname ne $env{'user.name'}) || ($udom ne $env{'user.domain'})) { |
my $extra = &Apache::lonnet::freeze_escape({'skipcheck' => 1}); |
my %roleshash = &Apache::lonnet::dump('roles',$udom,$uname); |
my %roleshash = &Apache::lonnet::dump('roles',$udom,$uname,'.',undef, |
|
$extra); |
|
if (!%roles) { |
if (!%roles) { |
%roles = ( |
%roles = ( |
cc => 1, |
cc => 1, |
Line 3965 sub findallcourses {
|
Line 4208 sub findallcourses {
|
if ($tstart) { |
if ($tstart) { |
next if ($tstart > $now); |
next if ($tstart > $now); |
} |
} |
my ($cdom,$cnum,$sec,$cnumpart,$secpart,$role,$realsec); |
my ($cdom,$cnum,$sec,$cnumpart,$secpart,$role); |
(undef,$cdom,$cnumpart,$secpart) = split(/\//,$entry); |
(undef,$cdom,$cnumpart,$secpart) = split(/\//,$entry); |
|
my $value = $trole.'/'.$cdom.'/'; |
if ($secpart eq '') { |
if ($secpart eq '') { |
($cnum,$role) = split(/_/,$cnumpart); |
($cnum,$role) = split(/_/,$cnumpart); |
$sec = 'none'; |
$sec = 'none'; |
$realsec = ''; |
$value .= $cnum.'/'; |
} else { |
} else { |
$cnum = $cnumpart; |
$cnum = $cnumpart; |
($sec,$role) = split(/_/,$secpart); |
($sec,$role) = split(/_/,$secpart); |
$realsec = $sec; |
$value .= $cnum.'/'.$sec; |
|
} |
|
if (ref($courses{$cdom.'_'.$cnum}{$sec}) eq 'ARRAY') { |
|
unless (grep(/^\Q$value\E$/,@{$courses{$cdom.'_'.$cnum}{$sec}})) { |
|
push(@{$courses{$cdom.'_'.$cnum}{$sec}},$value); |
|
} |
|
} else { |
|
@{$courses{$cdom.'_'.$cnum}{$sec}} = ($value); |
} |
} |
$courses{$cdom.'_'.$cnum}{$sec} = $trole.'/'.$cdom.'/'.$cnum.'/'.$realsec; |
|
} |
} |
} else { |
} else { |
foreach my $key (keys(%env)) { |
foreach my $key (keys(%env)) { |
Line 3994 sub findallcourses {
|
Line 4244 sub findallcourses {
|
if ($now>$endtime) { $active=0; } |
if ($now>$endtime) { $active=0; } |
} |
} |
if ($active) { |
if ($active) { |
|
my $value = $role.'/'.$cdom.'/'.$cnum.'/'; |
if ($sec eq '') { |
if ($sec eq '') { |
$sec = 'none'; |
$sec = 'none'; |
|
} else { |
|
$value .= $sec; |
|
} |
|
if (ref($courses{$cdom.'_'.$cnum}{$sec}) eq 'ARRAY') { |
|
unless (grep(/^\Q$value\E$/,@{$courses{$cdom.'_'.$cnum}{$sec}})) { |
|
push(@{$courses{$cdom.'_'.$cnum}{$sec}},$value); |
|
} |
|
} else { |
|
@{$courses{$cdom.'_'.$cnum}{$sec}} = ($value); |
} |
} |
$courses{$cdom.'_'.$cnum}{$sec} = |
|
$role.'/'.$cdom.'/'.$cnum.'/'.$sec; |
|
} |
} |
} |
} |
} |
} |
Line 4009 sub findallcourses {
|
Line 4267 sub findallcourses {
|
############################################### |
############################################### |
|
|
sub blockcheck { |
sub blockcheck { |
my ($setters,$activity,$uname,$udom) = @_; |
my ($setters,$activity,$uname,$udom,$url) = @_; |
|
|
if (!defined($udom)) { |
if (!defined($udom)) { |
$udom = $env{'user.domain'}; |
$udom = $env{'user.domain'}; |
Line 4021 sub blockcheck {
|
Line 4279 sub blockcheck {
|
# If uname and udom are for a course, check for blocks in the course. |
# If uname and udom are for a course, check for blocks in the course. |
|
|
if (&Apache::lonnet::is_course($udom,$uname)) { |
if (&Apache::lonnet::is_course($udom,$uname)) { |
my %records = &Apache::lonnet::dump('comm_block',$udom,$uname); |
my ($startblock,$endblock,$triggerblock) = |
my ($startblock,$endblock)=&get_blocks($setters,$activity,$udom,$uname); |
&get_blocks($setters,$activity,$udom,$uname,$url); |
return ($startblock,$endblock); |
return ($startblock,$endblock,$triggerblock); |
} |
} |
|
|
my $startblock = 0; |
my $startblock = 0; |
my $endblock = 0; |
my $endblock = 0; |
|
my $triggerblock = ''; |
my %live_courses = &findallcourses(undef,$uname,$udom); |
my %live_courses = &findallcourses(undef,$uname,$udom); |
|
|
# If uname is for a user, and activity is course-specific, i.e., |
# If uname is for a user, and activity is course-specific, i.e., |
Line 4091 sub blockcheck {
|
Line 4350 sub blockcheck {
|
if ($otheruser) { |
if ($otheruser) { |
# Resource belongs to user other than current user. |
# Resource belongs to user other than current user. |
# Assemble privs for that user, and check for 'evb' priv. |
# Assemble privs for that user, and check for 'evb' priv. |
my ($trole,$tdom,$tnum,$tsec); |
my (%allroles,%userroles); |
my $entry = $live_courses{$course}{$sec}; |
if (ref($live_courses{$course}{$sec}) eq 'ARRAY') { |
if ($entry =~ /^cr/) { |
foreach my $entry (@{$live_courses{$course}{$sec}}) { |
($trole,$tdom,$tnum,$tsec) = |
my ($trole,$tdom,$tnum,$tsec); |
($entry =~ m|^(cr/$match_domain/$match_username/\w+)\./($match_domain)/($match_username)/?(\w*)$|); |
if ($entry =~ /^cr/) { |
} else { |
($trole,$tdom,$tnum,$tsec) = |
($trole,$tdom,$tnum,$tsec) = split(/\//,$entry); |
($entry =~ m|^(cr/$match_domain/$match_username/\w+)\./($match_domain)/($match_username)/?(\w*)$|); |
} |
} else { |
my ($spec,$area,$trest,%allroles,%userroles); |
($trole,$tdom,$tnum,$tsec) = split(/\//,$entry); |
$area = '/'.$tdom.'/'.$tnum; |
} |
$trest = $tnum; |
my ($spec,$area,$trest); |
if ($tsec ne '') { |
$area = '/'.$tdom.'/'.$tnum; |
$area .= '/'.$tsec; |
$trest = $tnum; |
$trest .= '/'.$tsec; |
if ($tsec ne '') { |
} |
$area .= '/'.$tsec; |
$spec = $trole.'.'.$area; |
$trest .= '/'.$tsec; |
if ($trole =~ /^cr/) { |
} |
&Apache::lonnet::custom_roleprivs(\%allroles,$trole, |
$spec = $trole.'.'.$area; |
$tdom,$spec,$trest,$area); |
if ($trole =~ /^cr/) { |
} else { |
&Apache::lonnet::custom_roleprivs(\%allroles,$trole, |
&Apache::lonnet::standard_roleprivs(\%allroles,$trole, |
$tdom,$spec,$trest,$area); |
$tdom,$spec,$trest,$area); |
} else { |
} |
&Apache::lonnet::standard_roleprivs(\%allroles,$trole, |
my ($author,$adv) = &Apache::lonnet::set_userprivs(\%userroles,\%allroles); |
$tdom,$spec,$trest,$area); |
if ($userroles{'user.priv.'.$checkrole} =~ /evb\&([^\:]*)/) { |
} |
if ($1) { |
} |
$no_userblock = 1; |
my ($author,$adv) = &Apache::lonnet::set_userprivs(\%userroles,\%allroles); |
last; |
if ($userroles{'user.priv.'.$checkrole} =~ /evb\&([^\:]*)/) { |
|
if ($1) { |
|
$no_userblock = 1; |
|
last; |
|
} |
} |
} |
} |
} |
} else { |
} else { |
Line 4138 sub blockcheck {
|
Line 4401 sub blockcheck {
|
# Retrieve blocking times and identity of locker for course |
# Retrieve blocking times and identity of locker for course |
# of specified user, unless user has 'evb' privilege. |
# of specified user, unless user has 'evb' privilege. |
|
|
my ($start,$end)=&get_blocks($setters,$activity,$cdom,$cnum); |
my ($start,$end,$trigger) = |
|
&get_blocks($setters,$activity,$cdom,$cnum,$url); |
if (($start != 0) && |
if (($start != 0) && |
(($startblock == 0) || ($startblock > $start))) { |
(($startblock == 0) || ($startblock > $start))) { |
$startblock = $start; |
$startblock = $start; |
|
if ($trigger ne '') { |
|
$triggerblock = $trigger; |
|
} |
} |
} |
if (($end != 0) && |
if (($end != 0) && |
(($endblock == 0) || ($endblock < $end))) { |
(($endblock == 0) || ($endblock < $end))) { |
$endblock = $end; |
$endblock = $end; |
|
if ($trigger ne '') { |
|
$triggerblock = $trigger; |
|
} |
} |
} |
} |
} |
return ($startblock,$endblock); |
return ($startblock,$endblock,$triggerblock); |
} |
} |
|
|
sub get_blocks { |
sub get_blocks { |
my ($setters,$activity,$cdom,$cnum) = @_; |
my ($setters,$activity,$cdom,$cnum,$url) = @_; |
my $startblock = 0; |
my $startblock = 0; |
my $endblock = 0; |
my $endblock = 0; |
|
my $triggerblock = ''; |
my $course = $cdom.'_'.$cnum; |
my $course = $cdom.'_'.$cnum; |
$setters->{$course} = {}; |
$setters->{$course} = {}; |
$setters->{$course}{'staff'} = []; |
$setters->{$course}{'staff'} = []; |
$setters->{$course}{'times'} = []; |
$setters->{$course}{'times'} = []; |
my %records = &Apache::lonnet::dump('comm_block',$cdom,$cnum); |
$setters->{$course}{'triggers'} = []; |
foreach my $record (keys(%records)) { |
my (@blockers,%triggered); |
my ($start,$end) = ($record =~ m/^(\d+)____(\d+)$/); |
my $now = time; |
if ($start <= time && $end >= time) { |
my %commblocks = &Apache::lonnet::get_comm_blocks($cdom,$cnum); |
my ($staff_name,$staff_dom,$title,$blocks) = |
if ($activity eq 'docs') { |
&parse_block_record($records{$record}); |
@blockers = &Apache::lonnet::has_comm_blocking('bre',undef,$url,\%commblocks); |
if ($blocks->{$activity} eq 'on') { |
foreach my $block (@blockers) { |
push(@{$$setters{$course}{'staff'}},[$staff_name,$staff_dom]); |
if ($block =~ /^firstaccess____(.+)$/) { |
push(@{$$setters{$course}{'times'}}, [$start,$end]); |
my $item = $1; |
if ( ($startblock == 0) || ($startblock > $start) ) { |
my $type = 'map'; |
$startblock = $start; |
my $timersymb = $item; |
|
if ($item eq 'course') { |
|
$type = 'course'; |
|
} elsif ($item =~ /___\d+___/) { |
|
$type = 'resource'; |
|
} else { |
|
$timersymb = &Apache::lonnet::symbread($item); |
|
} |
|
my $start = $env{'course.'.$cdom.'_'.$cnum.'.firstaccess.'.$timersymb}; |
|
my $end = $start + $env{'course.'.$cdom.'_'.$cnum.'.timerinterval.'.$timersymb}; |
|
$triggered{$block} = { |
|
start => $start, |
|
end => $end, |
|
type => $type, |
|
}; |
|
} |
|
} |
|
} else { |
|
foreach my $block (keys(%commblocks)) { |
|
if ($block =~ m/^(\d+)____(\d+)$/) { |
|
my ($start,$end) = ($1,$2); |
|
if ($start <= time && $end >= time) { |
|
if (ref($commblocks{$block}) eq 'HASH') { |
|
if (ref($commblocks{$block}{'blocks'}) eq 'HASH') { |
|
if ($commblocks{$block}{'blocks'}{$activity} eq 'on') { |
|
unless(grep(/^\Q$block\E$/,@blockers)) { |
|
push(@blockers,$block); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
} elsif ($block =~ /^firstaccess____(.+)$/) { |
|
my $item = $1; |
|
my $timersymb = $item; |
|
my $type = 'map'; |
|
if ($item eq 'course') { |
|
$type = 'course'; |
|
} elsif ($item =~ /___\d+___/) { |
|
$type = 'resource'; |
|
} else { |
|
$timersymb = &Apache::lonnet::symbread($item); |
|
} |
|
my $start = $env{'course.'.$cdom.'_'.$cnum.'.firstaccess.'.$timersymb}; |
|
my $end = $start + $env{'course.'.$cdom.'_'.$cnum.'.timerinterval.'.$timersymb}; |
|
if ($start && $end) { |
|
if (($start <= time) && ($end >= time)) { |
|
unless (grep(/^\Q$block\E$/,@blockers)) { |
|
push(@blockers,$block); |
|
$triggered{$block} = { |
|
start => $start, |
|
end => $end, |
|
type => $type, |
|
}; |
|
} |
|
} |
} |
} |
if ( ($endblock == 0) || ($endblock < $end) ) { |
} |
$endblock = $end; |
} |
|
} |
|
foreach my $blocker (@blockers) { |
|
my ($staff_name,$staff_dom,$title,$blocks) = |
|
&parse_block_record($commblocks{$blocker}); |
|
push(@{$$setters{$course}{'staff'}},[$staff_name,$staff_dom]); |
|
my ($start,$end,$triggertype); |
|
if ($blocker =~ m/^(\d+)____(\d+)$/) { |
|
($start,$end) = ($1,$2); |
|
} elsif (ref($triggered{$blocker}) eq 'HASH') { |
|
$start = $triggered{$blocker}{'start'}; |
|
$end = $triggered{$blocker}{'end'}; |
|
$triggertype = $triggered{$blocker}{'type'}; |
|
} |
|
if ($start) { |
|
push(@{$$setters{$course}{'times'}}, [$start,$end]); |
|
if ($triggertype) { |
|
push(@{$$setters{$course}{'triggers'}},$triggertype); |
|
} else { |
|
push(@{$$setters{$course}{'triggers'}},0); |
|
} |
|
if ( ($startblock == 0) || ($startblock > $start) ) { |
|
$startblock = $start; |
|
if ($triggertype) { |
|
$triggerblock = $blocker; |
} |
} |
} |
} |
|
if ( ($endblock == 0) || ($endblock < $end) ) { |
|
$endblock = $end; |
|
if ($triggertype) { |
|
$triggerblock = $blocker; |
|
} |
|
} |
} |
} |
} |
} |
return ($startblock,$endblock); |
return ($startblock,$endblock,$triggerblock); |
} |
} |
|
|
sub parse_block_record { |
sub parse_block_record { |
Line 4201 sub parse_block_record {
|
Line 4557 sub parse_block_record {
|
} |
} |
|
|
sub blocking_status { |
sub blocking_status { |
my ($activity,$uname,$udom) = @_; |
my ($activity,$uname,$udom,$url) = @_; |
my %setters; |
my %setters; |
|
|
# check for active blocking |
# check for active blocking |
my ($startblock,$endblock)=&blockcheck(\%setters,$activity,$uname,$udom); |
my ($startblock,$endblock,$triggerblock) = |
|
&blockcheck(\%setters,$activity,$uname,$udom,$url); |
my $blocked = $startblock && $endblock ? 1 : 0; |
my $blocked = 0; |
|
if ($startblock && $endblock) { |
# caller just wants to know whether a block is active |
$blocked = 1; |
if (!wantarray) { return $blocked; } |
} |
|
|
# build a link to a popup window containing the details |
# caller just wants to know whether a block is active |
my $querystring = "?activity=$activity"; |
if (!wantarray) { return $blocked; } |
# $uname and $udom decide whose portfolio the user is trying to look at |
|
$querystring .= "&udom=$udom" if $udom; |
# build a link to a popup window containing the details |
$querystring .= "&uname=$uname" if $uname; |
my $querystring = "?activity=$activity"; |
|
# $uname and $udom decide whose portfolio the user is trying to look at |
my $output .= <<'END_MYBLOCK'; |
if ($activity eq 'port') { |
function openWindow(url, wdwName, w, h, toolbar,scrollbar) { |
$querystring .= "&udom=$udom" if $udom; |
var options = "width=" + w + ",height=" + h + ","; |
$querystring .= "&uname=$uname" if $uname; |
options += "resizable=yes,scrollbars="+scrollbar+",status=no,"; |
} elsif ($activity eq 'docs') { |
options += "menubar=no,toolbar="+toolbar+",location=no,directories=no"; |
$querystring .= '&url='.&HTML::Entities::encode($url,'&"'); |
var newWin = window.open(url, wdwName, options); |
} |
newWin.focus(); |
|
} |
my $output .= <<'END_MYBLOCK'; |
|
function openWindow(url, wdwName, w, h, toolbar,scrollbar) { |
|
var options = "width=" + w + ",height=" + h + ","; |
|
options += "resizable=yes,scrollbars="+scrollbar+",status=no,"; |
|
options += "menubar=no,toolbar="+toolbar+",location=no,directories=no"; |
|
var newWin = window.open(url, wdwName, options); |
|
newWin.focus(); |
|
} |
END_MYBLOCK |
END_MYBLOCK |
|
|
$output = Apache::lonhtmlcommon::scripttag($output); |
$output = Apache::lonhtmlcommon::scripttag($output); |
|
|
my $popupUrl = "/adm/blockingstatus/$querystring"; |
my $popupUrl = "/adm/blockingstatus/$querystring"; |
my $text = mt('Communication Blocked'); |
my $text = &mt('Communication Blocked'); |
|
if ($activity eq 'docs') { |
$output .= <<"END_BLOCK"; |
$text = &mt('Content Access Blocked'); |
|
} elsif ($activity eq 'printout') { |
|
$text = &mt('Printing Blocked'); |
|
} |
|
$output .= <<"END_BLOCK"; |
<div class='LC_comblock'> |
<div class='LC_comblock'> |
<a onclick='openWindow("$popupUrl","Blocking Table",600,300,"no","no");return false;' href='/adm/blockingstatus/$querystring' |
<a onclick='openWindow("$popupUrl","Blocking Table",600,300,"no","no");return false;' href='/adm/blockingstatus/$querystring' |
title='$text'> |
title='$text'> |
Line 4244 END_MYBLOCK
|
Line 4611 END_MYBLOCK
|
|
|
END_BLOCK |
END_BLOCK |
|
|
return ($blocked, $output); |
return ($blocked, $output); |
} |
} |
|
|
############################################### |
############################################### |
Line 4532 sub designparm {
|
Line 4899 sub designparm {
|
|
|
=item * &authorspace() |
=item * &authorspace() |
|
|
Inputs: ./. |
Inputs: $url (usually will be undef). |
|
|
Returns: Path to the Construction Space of the current user's |
Returns: Path to Construction Space containing the resource or |
accessed author space |
directory being viewed (or for which action is being taken). |
The author space will be that of the current user |
If $url is provided, and begins /priv/<domain>/<uname> |
when accessing the own author space |
the path will be that portion of the $context argument. |
and that of the co-author/assistent co-author |
Otherwise the path will be for the author space of the current |
when accessing the co-author's/assistent co-author's |
user when the current role is author, or for that of the |
space |
co-author/assistant co-author space when the current role |
|
is co-author or assistant co-author. |
|
|
=cut |
=cut |
|
|
sub authorspace { |
sub authorspace { |
|
my ($url) = @_; |
|
if ($url ne '') { |
|
if ($url =~ m{^(/priv/$match_domain/$match_username/)}) { |
|
return $1; |
|
} |
|
} |
my $caname = ''; |
my $caname = ''; |
my $cadom = ''; |
my $cadom = ''; |
if ($env{'request.role'} =~ /^ca|^aa/) { |
if ($env{'request.role'} =~ /^(?:ca|aa)/) { |
($cadom,$caname) = |
($cadom,$caname) = |
($env{'request.role'}=~/($match_domain)\/($match_username)$/); |
($env{'request.role'}=~/($match_domain)\/($match_username)$/); |
} else { |
} elsif ($env{'request.role'} =~ m{^au\./($match_domain)/}) { |
$caname = $env{'user.name'}; |
$caname = $env{'user.name'}; |
$cadom = $env{'user.domain'}; |
$cadom = $env{'user.domain'}; |
} |
} |
return '/priv/'.$cadom.'/'.$caname.'/'; |
if (($caname ne '') && ($cadom ne '')) { |
|
return "/priv/$cadom/$caname/"; |
|
} |
|
return; |
} |
} |
|
|
############################################## |
############################################## |
Line 4683 Inputs:
|
Line 5060 Inputs:
|
should it have jsmath forced on by the |
should it have jsmath forced on by the |
current page |
current page |
|
|
|
=item * $advtoolsref, optional argument, ref to an array containing |
|
inlineremote items to be added in "Functions" menu below |
|
breadcrumbs. |
|
|
=back |
=back |
|
|
Returns: A uniform header for LON-CAPA web pages. |
Returns: A uniform header for LON-CAPA web pages. |
Line 4694 other decorations will be returned.
|
Line 5075 other decorations will be returned.
|
|
|
sub bodytag { |
sub bodytag { |
my ($title,$function,$addentries,$bodyonly,$domain,$forcereg, |
my ($title,$function,$addentries,$bodyonly,$domain,$forcereg, |
$no_nav_bar,$bgcolor,$args)=@_; |
$no_nav_bar,$bgcolor,$args,$advtoolsref)=@_; |
|
|
my $public; |
my $public; |
if ((($env{'user.name'} eq 'public') && ($env{'user.domain'} eq 'public')) |
if ((($env{'user.name'} eq 'public') && ($env{'user.domain'} eq 'public')) |
Line 4751 sub bodytag {
|
Line 5132 sub bodytag {
|
if ($public) { |
if ($public) { |
undef($role); |
undef($role); |
} else { |
} else { |
$name = &aboutmewrapper($name,$env{'user.name'},$env{'user.domain'}); |
$name = &aboutmewrapper($name,$env{'user.name'},$env{'user.domain'}, |
|
undef,'LC_menubuttons_link'); |
} |
} |
|
|
my $titleinfo = '<h1>'.$title.'</h1>'; |
my $titleinfo = '<h1>'.$title.'</h1>'; |
Line 4812 sub bodytag {
|
Line 5194 sub bodytag {
|
if ($env{'request.state'} eq 'construct') { |
if ($env{'request.state'} eq 'construct') { |
$bodytag .= &Apache::lonmenu::innerregister($forcereg, |
$bodytag .= &Apache::lonmenu::innerregister($forcereg, |
$args->{'bread_crumbs'}); |
$args->{'bread_crumbs'}); |
} elsif ($forcereg) { |
} elsif ($forcereg) { |
$bodytag .= &Apache::lonmenu::innerregister($forcereg); |
$bodytag .= &Apache::lonmenu::innerregister($forcereg,undef, |
|
$args->{'group'}); |
|
} else { |
|
$bodytag .= |
|
&Apache::lonmenu::prepare_functions($env{'request.noversionuri'}, |
|
$forcereg,$args->{'group'}, |
|
$args->{'bread_crumbs'}, |
|
$advtoolsref); |
} |
} |
}else{ |
}else{ |
# this is to seperate menu from content when there's no secondary |
# this is to seperate menu from content when there's no secondary |
Line 4828 sub bodytag {
|
Line 5217 sub bodytag {
|
sub dc_courseid_toggle { |
sub dc_courseid_toggle { |
my ($dc_info) = @_; |
my ($dc_info) = @_; |
return ' <span id="dccidtext" class="LC_cusr_subheading LC_nobreak">'. |
return ' <span id="dccidtext" class="LC_cusr_subheading LC_nobreak">'. |
'<a href="javascript:showCourseID();">'. |
'<a href="javascript:showCourseID();" class="LC_menubuttons_link">'. |
&mt('(More ...)').'</a></span>'. |
&mt('(More ...)').'</a></span>'. |
'<div id="dccid" class="LC_dccid">'.$dc_info.'</div>'; |
'<div id="dccid" class="LC_dccid">'.$dc_info.'</div>'; |
} |
} |
Line 4885 i.e., $env{'internal.head.redirect'} exi
|
Line 5274 i.e., $env{'internal.head.redirect'} exi
|
|
|
sub endbodytag { |
sub endbodytag { |
my ($args) = @_; |
my ($args) = @_; |
my $endbodytag='</body>'; |
my $endbodytag; |
|
unless ((ref($args) eq 'HASH') && ($args->{'notbody'})) { |
|
$endbodytag='</body>'; |
|
} |
$endbodytag=&Apache::lontexconvert::jsMath_process()."\n".$endbodytag; |
$endbodytag=&Apache::lontexconvert::jsMath_process()."\n".$endbodytag; |
if ( exists( $env{'internal.head.redirect'} ) ) { |
if ( exists( $env{'internal.head.redirect'} ) ) { |
if (!(ref($args) eq 'HASH' && $args->{'noredirectlink'})) { |
if (!(ref($args) eq 'HASH' && $args->{'noredirectlink'})) { |
Line 4933 sub standard_css {
|
Line 5325 sub standard_css {
|
my $mono = 'monospace'; |
my $mono = 'monospace'; |
my $data_table_head = $sidebg; |
my $data_table_head = $sidebg; |
my $data_table_light = '#FAFAFA'; |
my $data_table_light = '#FAFAFA'; |
my $data_table_dark = '#F0F0F0'; |
my $data_table_dark = '#E0E0E0'; |
my $data_table_darker = '#CCCCCC'; |
my $data_table_darker = '#CCCCCC'; |
my $data_table_highlight = '#FFFF00'; |
my $data_table_highlight = '#FFFF00'; |
my $mail_new = '#FFBB77'; |
my $mail_new = '#FFBB77'; |
Line 4973 body {
|
Line 5365 body {
|
a:focus, |
a:focus, |
a:focus img { |
a:focus img { |
color: red; |
color: red; |
background: yellow; |
|
} |
} |
|
|
form, .inline { |
form, .inline { |
Line 5026 form, .inline {
|
Line 5417 form, .inline {
|
|
|
.LC_error { |
.LC_error { |
color: red; |
color: red; |
font-size: larger; |
|
} |
} |
|
|
.LC_warning, |
.LC_warning { |
|
color: darkorange; |
|
} |
|
|
.LC_diff_removed { |
.LC_diff_removed { |
color: red; |
color: red; |
} |
} |
Line 5068 div.LC_confirm_box .LC_success img {
|
Line 5461 div.LC_confirm_box .LC_success img {
|
} |
} |
|
|
.LC_discussion { |
.LC_discussion { |
background: $tabbg; |
background: $data_table_dark; |
border: 1px solid black; |
border: 1px solid black; |
margin: 2px; |
margin: 2px; |
} |
} |
|
|
.LC_disc_action_links_bar { |
|
background: $tabbg; |
|
border: none; |
|
margin: 4px; |
|
} |
|
|
|
.LC_disc_action_left { |
.LC_disc_action_left { |
|
background: $sidebg; |
text-align: left; |
text-align: left; |
|
padding: 4px; |
|
margin: 2px; |
} |
} |
|
|
.LC_disc_action_right { |
.LC_disc_action_right { |
|
background: $sidebg; |
text-align: right; |
text-align: right; |
|
padding: 4px; |
|
margin: 2px; |
} |
} |
|
|
.LC_disc_new_item { |
.LC_disc_new_item { |
background: white; |
background: white; |
border: 2px solid red; |
border: 2px solid red; |
margin: 2px; |
margin: 4px; |
|
padding: 4px; |
} |
} |
|
|
.LC_disc_old_item { |
.LC_disc_old_item { |
background: white; |
background: white; |
border: 1px solid black; |
margin: 4px; |
margin: 2px; |
padding: 4px; |
} |
} |
|
|
table.LC_pastsubmission { |
table.LC_pastsubmission { |
Line 5191 td.LC_table_cell_checkbox {
|
Line 5585 td.LC_table_cell_checkbox {
|
text-align: left; |
text-align: left; |
} |
} |
|
|
.LC_head_subbox { |
.LC_head_subbox, .LC_actionbox { |
clear:both; |
clear:both; |
background: #F8F8F8; /* $sidebg; */ |
background: #F8F8F8; /* $sidebg; */ |
border: 1px solid $sidebg; |
border: 1px solid $sidebg; |
margin: 0 0 10px 0; |
margin: 0 0 10px 0; |
padding: 3px; |
padding: 3px; |
text-align: left; |
text-align: left; |
} |
} |
Line 5218 td.LC_table_cell_checkbox {
|
Line 5612 td.LC_table_cell_checkbox {
|
vertical-align: middle; |
vertical-align: middle; |
} |
} |
|
|
li.LC_menubuttons_inline_text img,a { |
li.LC_menubuttons_inline_text img { |
cursor:pointer; |
cursor:pointer; |
text-decoration: none; |
text-decoration: none; |
} |
} |
Line 5514 span.LC_current_location {
|
Line 5908 span.LC_current_location {
|
background: $pgbg; |
background: $pgbg; |
} |
} |
|
|
|
span.LC_current_nav_location { |
|
font-weight:bold; |
|
background: $sidebg; |
|
} |
|
|
span.LC_parm_menu_item { |
span.LC_parm_menu_item { |
font-size: larger; |
font-size: larger; |
} |
} |
Line 5885 div.LC_docs_entry_move {
|
Line 6284 div.LC_docs_entry_move {
|
|
|
table.LC_data_table tr > td.LC_docs_entry_commands, |
table.LC_data_table tr > td.LC_docs_entry_commands, |
table.LC_data_table tr > td.LC_docs_entry_parameter { |
table.LC_data_table tr > td.LC_docs_entry_parameter { |
background: #DDDDDD; |
|
font-size: x-small; |
font-size: x-small; |
} |
} |
|
|
Line 6015 div.LC_edit_problem_footer {
|
Line 6413 div.LC_edit_problem_footer {
|
font-weight: normal; |
font-weight: normal; |
font-size: medium; |
font-size: medium; |
margin: 2px; |
margin: 2px; |
|
background-color: $sidebg; |
} |
} |
|
|
div.LC_edit_problem_header, |
div.LC_edit_problem_header, |
Line 6031 div.LC_edit_problem_header_title {
|
Line 6430 div.LC_edit_problem_header_title {
|
font-size: larger; |
font-size: larger; |
background: $tabbg; |
background: $tabbg; |
padding: 3px; |
padding: 3px; |
|
margin: 0 0 5px 0; |
} |
} |
|
|
table.LC_edit_problem_header_title { |
table.LC_edit_problem_header_title { |
Line 6068 div.LC_createcourse {
|
Line 6468 div.LC_createcourse {
|
display:none; |
display:none; |
} |
} |
|
|
a:hover, |
|
ol.LC_primary_menu a:hover, |
ol.LC_primary_menu a:hover, |
ol#LC_MenuBreadcrumbs a:hover, |
ol#LC_MenuBreadcrumbs a:hover, |
ol#LC_PathBreadcrumbs a:hover, |
ol#LC_PathBreadcrumbs a:hover, |
Line 6162 fieldset > legend {
|
Line 6561 fieldset > legend {
|
ol.LC_primary_menu { |
ol.LC_primary_menu { |
float: right; |
float: right; |
margin: 0; |
margin: 0; |
|
padding: 0; |
background-color: $pgbg_or_bgcolor; |
background-color: $pgbg_or_bgcolor; |
} |
} |
|
|
Line 6170 ol#LC_PathBreadcrumbs {
|
Line 6570 ol#LC_PathBreadcrumbs {
|
} |
} |
|
|
ol.LC_primary_menu li { |
ol.LC_primary_menu li { |
display: inline; |
color: RGB(80, 80, 80); |
padding: 5px 5px 0 10px; |
vertical-align: middle; |
|
text-align: left; |
|
list-style: none; |
|
float: left; |
|
} |
|
|
|
ol.LC_primary_menu li a { |
|
display: block; |
|
margin: 0; |
|
padding: 0 5px 0 10px; |
|
text-decoration: none; |
|
} |
|
|
|
ol.LC_primary_menu li ul { |
|
display: none; |
|
width: 10em; |
|
background-color: $data_table_light; |
|
} |
|
|
|
ol.LC_primary_menu li:hover ul, ol.LC_primary_menu li.hover ul { |
|
display: block; |
|
position: absolute; |
|
margin: 0; |
|
padding: 0; |
|
z-index: 2; |
|
} |
|
|
|
ol.LC_primary_menu li:hover li, ol.LC_primary_menu li.hover li { |
|
font-size: 90%; |
vertical-align: top; |
vertical-align: top; |
|
float: none; |
|
border-left: 1px solid black; |
|
border-right: 1px solid black; |
|
} |
|
|
|
ol.LC_primary_menu li:hover li a, ol.LC_primary_menu li.hover li a { |
|
background-color:$data_table_light; |
|
} |
|
|
|
ol.LC_primary_menu li li a:hover { |
|
color:$button_hover; |
|
background-color:$data_table_dark; |
} |
} |
|
|
ol.LC_primary_menu li img { |
ol.LC_primary_menu li img { |
vertical-align: bottom; |
vertical-align: bottom; |
height: 1.1em; |
height: 1.1em; |
|
margin: 0.2em 0 0 0; |
} |
} |
|
|
ol.LC_primary_menu a { |
ol.LC_primary_menu a { |
Line 6302 ul.LC_TabContent li.active a {
|
Line 6743 ul.LC_TabContent li.active a {
|
background:#FFFFFF; |
background:#FFFFFF; |
outline: none; |
outline: none; |
} |
} |
|
|
|
ul.LC_TabContent li.goback { |
|
float: left; |
|
border-left: none; |
|
} |
|
|
#maincoursedoc { |
#maincoursedoc { |
clear:both; |
clear:both; |
} |
} |
Line 6551 a#LC_content_toolbar_changefolder_toggle
|
Line 6998 a#LC_content_toolbar_changefolder_toggle
|
background-image:url(/res/adm/pages/open-all-folders.gif); |
background-image:url(/res/adm/pages/open-all-folders.gif); |
} |
} |
|
|
|
a#LC_content_toolbar_edittoplevel { |
|
background-image:url(/res/adm/pages/edittoplevel.gif); |
|
} |
|
|
ul#LC_toolbar li a:hover { |
ul#LC_toolbar li a:hover { |
background-position: bottom center; |
background-position: bottom center; |
} |
} |
Line 6561 ul#LC_toolbar {
|
Line 7012 ul#LC_toolbar {
|
list-style:none; |
list-style:none; |
position:relative; |
position:relative; |
background-color:white; |
background-color:white; |
|
overflow: auto; |
} |
} |
|
|
ul#LC_toolbar li { |
ul#LC_toolbar li { |
Line 6570 ul#LC_toolbar li {
|
Line 7022 ul#LC_toolbar li {
|
float: left; |
float: left; |
display:inline; |
display:inline; |
vertical-align:middle; |
vertical-align:middle; |
|
white-space: nowrap; |
} |
} |
|
|
|
|
Line 6619 ul.LC_funclist li {
|
Line 7072 ul.LC_funclist li {
|
display: none; |
display: none; |
} |
} |
|
|
|
.LCmodal-overlay { |
|
position:fixed; |
|
top:0; |
|
right:0; |
|
bottom:0; |
|
left:0; |
|
height:100%; |
|
width:100%; |
|
margin:0; |
|
padding:0; |
|
background:#999; |
|
opacity:.75; |
|
filter: alpha(opacity=75); |
|
-moz-opacity: 0.75; |
|
z-index:101; |
|
} |
|
|
|
* html .LCmodal-overlay { |
|
position: absolute; |
|
height: expression(document.body.scrollHeight > document.body.offsetHeight ? document.body.scrollHeight : document.body.offsetHeight + 'px'); |
|
} |
|
|
|
.LCmodal-window { |
|
position:fixed; |
|
top:50%; |
|
left:50%; |
|
margin:0; |
|
padding:0; |
|
z-index:102; |
|
} |
|
|
|
* html .LCmodal-window { |
|
position:absolute; |
|
} |
|
|
|
.LCclose-window { |
|
position:absolute; |
|
width:32px; |
|
height:32px; |
|
right:8px; |
|
top:8px; |
|
background:transparent url('/res/adm/pages/process-stop.png') no-repeat scroll right top; |
|
text-indent:-99999px; |
|
overflow:hidden; |
|
cursor:pointer; |
|
} |
|
|
END |
END |
} |
} |
|
|
Line 6667 sub headtag {
|
Line 7167 sub headtag {
|
'<head>'. |
'<head>'. |
&font_settings(); |
&font_settings(); |
|
|
|
my $inhibitprint = &print_suppression(); |
|
|
if (!$args->{'frameset'}) { |
if (!$args->{'frameset'}) { |
$result .= &Apache::lonhtmlcommon::htmlareaheaders(); |
$result .= &Apache::lonhtmlcommon::htmlareaheaders(); |
} |
} |
Line 6677 sub headtag {
|
Line 7179 sub headtag {
|
&& !$args->{'only_body'} |
&& !$args->{'only_body'} |
&& !$args->{'frameset'}) { |
&& !$args->{'frameset'}) { |
$result .= &help_menu_js(); |
$result .= &help_menu_js(); |
|
$result.=&modal_window(); |
|
$result.=&togglebox_script(); |
|
$result.=&wishlist_window(); |
|
$result.=&LCprogressbarUpdate_script(); |
|
} else { |
|
if ($args->{'add_modal'}) { |
|
$result.=&modal_window(); |
|
} |
|
if ($args->{'add_wishlist'}) { |
|
$result.=&wishlist_window(); |
|
} |
|
if ($args->{'add_togglebox'}) { |
|
$result.=&togglebox_script(); |
|
} |
|
if ($args->{'add_progressbar'}) { |
|
$result.=&LCprogressbarUpdate_script(); |
|
} |
} |
} |
|
|
if (ref($args->{'redirect'})) { |
if (ref($args->{'redirect'})) { |
my ($time,$url,$inhibit_continue) = @{$args->{'redirect'}}; |
my ($time,$url,$inhibit_continue) = @{$args->{'redirect'}}; |
$url = &Apache::lonenc::check_encrypt($url); |
$url = &Apache::lonenc::check_encrypt($url); |
Line 6696 ADDMETA
|
Line 7214 ADDMETA
|
if (!$args->{'no_auto_mt_title'}) { $title = &mt($title); } |
if (!$args->{'no_auto_mt_title'}) { $title = &mt($title); } |
$result .= '<title> LON-CAPA '.$title.'</title>' |
$result .= '<title> LON-CAPA '.$title.'</title>' |
.'<link rel="stylesheet" type="text/css" href="'.$url.'" />' |
.'<link rel="stylesheet" type="text/css" href="'.$url.'" />' |
|
.$inhibitprint |
.$head_extra; |
.$head_extra; |
return $result.'</head>'; |
return $result.'</head>'; |
} |
} |
Line 6721 sub font_settings {
|
Line 7240 sub font_settings {
|
|
|
=pod |
=pod |
|
|
|
=item * &print_suppression() |
|
|
|
In course context returns css which causes the body to be blank when media="print", |
|
if printout generation is unavailable for the current resource. |
|
|
|
This could be because: |
|
|
|
(a) printstartdate is in the future |
|
|
|
(b) printenddate is in the past |
|
|
|
(c) there is an active exam block with "printout" |
|
functionality blocked |
|
|
|
Users with pav, pfo or evb privileges are exempt. |
|
|
|
Inputs: none |
|
|
|
=cut |
|
|
|
|
|
sub print_suppression { |
|
my $noprint; |
|
if ($env{'request.course.id'}) { |
|
my $scope = $env{'request.course.id'}; |
|
if ((&Apache::lonnet::allowed('pav',$scope)) || |
|
(&Apache::lonnet::allowed('pfo',$scope))) { |
|
return; |
|
} |
|
if ($env{'request.course.sec'} ne '') { |
|
$scope .= "/$env{'request.course.sec'}"; |
|
if ((&Apache::lonnet::allowed('pav',$scope)) || |
|
(&Apache::lonnet::allowed('pfo',$scope))) { |
|
return; |
|
} |
|
} |
|
my $cdom = $env{'course.'.$env{'request.course.id'}.'.domain'}; |
|
my $cnum = $env{'course.'.$env{'request.course.id'}.'.num'}; |
|
my $blocked = &blocking_status('printout',$cnum,$cdom); |
|
if ($blocked) { |
|
my $checkrole = "cm./$cdom/$cnum"; |
|
if ($env{'request.course.sec'} ne '') { |
|
$checkrole .= "/$env{'request.course.sec'}"; |
|
} |
|
unless ((&Apache::lonnet::allowed('evb',undef,undef,$checkrole)) && |
|
($env{'request.role'} !~ m{^st\./$cdom/$cnum})) { |
|
$noprint = 1; |
|
} |
|
} |
|
unless ($noprint) { |
|
my $symb = &Apache::lonnet::symbread(); |
|
if ($symb ne '') { |
|
my $navmap = Apache::lonnavmaps::navmap->new(); |
|
if (ref($navmap)) { |
|
my $res = $navmap->getBySymb($symb); |
|
if (ref($res)) { |
|
if (!$res->resprintable()) { |
|
$noprint = 1; |
|
} |
|
} |
|
} |
|
} |
|
} |
|
if ($noprint) { |
|
return <<"ENDSTYLE"; |
|
<style type="text/css" media="print"> |
|
body { display:none } |
|
</style> |
|
ENDSTYLE |
|
} |
|
} |
|
return; |
|
} |
|
|
|
=pod |
|
|
=item * &xml_begin() |
=item * &xml_begin() |
|
|
Returns the needed doctype and <html> |
Returns the needed doctype and <html> |
Line 6793 $args - additional optional args support
|
Line 7388 $args - additional optional args support
|
current page |
current page |
bread_crumbs -> Array containing breadcrumbs |
bread_crumbs -> Array containing breadcrumbs |
bread_crumbs_component -> if exists show it as headline else show only the breadcrumbs |
bread_crumbs_component -> if exists show it as headline else show only the breadcrumbs |
|
group -> includes the current group, if page is for a |
|
specific group |
|
|
=back |
=back |
|
|
Line 6803 $args - additional optional args support
|
Line 7400 $args - additional optional args support
|
sub start_page { |
sub start_page { |
my ($title,$head_extra,$args) = @_; |
my ($title,$head_extra,$args) = @_; |
#&Apache::lonnet::logthis("start_page ".join(':',caller(0))); |
#&Apache::lonnet::logthis("start_page ".join(':',caller(0))); |
#SD |
|
#I don't see why we copy certain elements of %$args to %head_args |
|
#head args is passed to headtag() and this routine only reads those |
|
#keys that are needed. There doesn't happen any writes or any processing |
|
#of other keys. |
|
#proposal: just pass $args to headtag instead of \%head_args and delete |
|
#marked lines |
|
#<- MARK |
|
my %head_args; |
|
foreach my $arg ('redirect','force_register','domain','function', |
|
'bgcolor','frameset','no_nav_bar','only_body', |
|
'no_auto_mt_title') { |
|
if (defined($args->{$arg})) { |
|
$head_args{$arg} = $args->{$arg}; |
|
} |
|
} |
|
#MARK -> |
|
|
|
$env{'internal.start_page'}++; |
$env{'internal.start_page'}++; |
my $result; |
my ($result,@advtools); |
|
|
if (! exists($args->{'skip_phases'}{'head'}) ) { |
if (! exists($args->{'skip_phases'}{'head'}) ) { |
$result .= |
$result .= &xml_begin() . &headtag($title, $head_extra, $args); |
&xml_begin() . &headtag($title,$head_extra,\%head_args); |
|
#replace prev line by |
|
# &xml_begin() . &headtag($title, $head_extra, $args); |
|
} |
} |
|
|
if (! exists($args->{'skip_phases'}{'body'}) ) { |
if (! exists($args->{'skip_phases'}{'body'}) ) { |
Line 6842 sub start_page {
|
Line 7419 sub start_page {
|
$args->{'function'}, $args->{'add_entries'}, |
$args->{'function'}, $args->{'add_entries'}, |
$args->{'only_body'}, $args->{'domain'}, |
$args->{'only_body'}, $args->{'domain'}, |
$args->{'force_register'}, $args->{'no_nav_bar'}, |
$args->{'force_register'}, $args->{'no_nav_bar'}, |
$args->{'bgcolor'}, $args); |
$args->{'bgcolor'}, $args, |
|
\@advtools); |
} |
} |
} |
} |
|
|
Line 6871 sub start_page {
|
Line 7449 sub start_page {
|
&Apache::lonhtmlcommon::add_breadcrumb($crumb); |
&Apache::lonhtmlcommon::add_breadcrumb($crumb); |
} |
} |
} |
} |
|
# if @advtools array contains items add then to the breadcrumbs |
|
if (@advtools > 0) { |
|
&Apache::lonmenu::advtools_crumbs(@advtools); |
|
} |
|
|
#if bread_crumbs_component exists show it as headline else show only the breadcrumbs |
#if bread_crumbs_component exists show it as headline else show only the breadcrumbs |
if(exists($args->{'bread_crumbs_component'})){ |
if(exists($args->{'bread_crumbs_component'})){ |
Line 6894 sub end_page {
|
Line 7476 sub end_page {
|
} |
} |
$result .= &Apache::lonxml::xmlend($target,$parser); |
$result .= &Apache::lonxml::xmlend($target,$parser); |
} |
} |
|
|
if ($args->{'frameset'}) { |
if ($args->{'frameset'}) { |
$result .= '</frameset>'; |
$result .= '</frameset>'; |
} else { |
} else { |
$result .= &endbodytag($args); |
$result .= &endbodytag($args); |
} |
} |
$result .= "\n</html>"; |
unless ($args->{'notbody'}) { |
|
$result .= "\n</html>"; |
|
} |
|
|
if ($args->{'js_ready'}) { |
if ($args->{'js_ready'}) { |
$result = &js_ready($result); |
$result = &js_ready($result); |
Line 6913 sub end_page {
|
Line 7496 sub end_page {
|
return $result; |
return $result; |
} |
} |
|
|
|
sub wishlist_window { |
|
return(<<'ENDWISHLIST'); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
// <!-- BEGIN LON-CAPA Internal |
|
function set_wishlistlink(title, path) { |
|
if (!title) { |
|
title = document.title; |
|
title = title.replace(/^LON-CAPA /,''); |
|
} |
|
if (!path) { |
|
path = location.pathname; |
|
} |
|
Win = window.open('/adm/wishlist?mode=newLink&setTitle='+title+'&setPath='+path, |
|
'wishlistNewLink','width=560,height=350,scrollbars=0'); |
|
} |
|
// END LON-CAPA Internal --> |
|
// ]]> |
|
</script> |
|
ENDWISHLIST |
|
} |
|
|
|
sub modal_window { |
|
return(<<'ENDMODAL'); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
// <!-- BEGIN LON-CAPA Internal |
|
var modalWindow = { |
|
parent:"body", |
|
windowId:null, |
|
content:null, |
|
width:null, |
|
height:null, |
|
close:function() |
|
{ |
|
$(".LCmodal-window").remove(); |
|
$(".LCmodal-overlay").remove(); |
|
}, |
|
open:function() |
|
{ |
|
var modal = ""; |
|
modal += "<div class=\"LCmodal-overlay\"></div>"; |
|
modal += "<div id=\"" + this.windowId + "\" class=\"LCmodal-window\" style=\"width:" + this.width + "px; height:" + this.height + "px; margin-top:-" + (this.height / 2) + "px; margin-left:-" + (this.width / 2) + "px;\">"; |
|
modal += this.content; |
|
modal += "</div>"; |
|
|
|
$(this.parent).append(modal); |
|
|
|
$(".LCmodal-window").append("<a class=\"LCclose-window\"></a>"); |
|
$(".LCclose-window").click(function(){modalWindow.close();}); |
|
$(".LCmodal-overlay").click(function(){modalWindow.close();}); |
|
} |
|
}; |
|
var openMyModal = function(source,width,height,scrolling) |
|
{ |
|
modalWindow.windowId = "myModal"; |
|
modalWindow.width = width; |
|
modalWindow.height = height; |
|
modalWindow.content = "<iframe width='"+width+"' height='"+height+"' frameborder='0' scrolling='"+scrolling+"' allowtransparency='true' src='" + source + "'></iframe>"; |
|
modalWindow.open(); |
|
}; |
|
// END LON-CAPA Internal --> |
|
// ]]> |
|
</script> |
|
ENDMODAL |
|
} |
|
|
|
sub modal_link { |
|
my ($link,$linktext,$width,$height,$target,$scrolling,$title)=@_; |
|
unless ($width) { $width=480; } |
|
unless ($height) { $height=400; } |
|
unless ($scrolling) { $scrolling='yes'; } |
|
my $target_attr; |
|
if (defined($target)) { |
|
$target_attr = 'target="'.$target.'"'; |
|
} |
|
return <<"ENDLINK"; |
|
<a href="$link" $target_attr title="$title" onclick="javascript:openMyModal('$link',$width,$height,'$scrolling'); return false;"> |
|
$linktext</a> |
|
ENDLINK |
|
} |
|
|
|
sub modal_adhoc_script { |
|
my ($funcname,$width,$height,$content)=@_; |
|
return (<<ENDADHOC); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
var $funcname = function() |
|
{ |
|
modalWindow.windowId = "myModal"; |
|
modalWindow.width = $width; |
|
modalWindow.height = $height; |
|
modalWindow.content = '$content'; |
|
modalWindow.open(); |
|
}; |
|
// ]]> |
|
</script> |
|
ENDADHOC |
|
} |
|
|
|
sub modal_adhoc_inner { |
|
my ($funcname,$width,$height,$content)=@_; |
|
my $innerwidth=$width-20; |
|
$content=&js_ready( |
|
&start_page('Dialog',undef,{'only_body'=>1,'bgcolor'=>'#FFFFFF'}). |
|
&start_scrollbox($width.'px',$innerwidth.'px',$height.'px'). |
|
$content. |
|
&end_scrollbox(). |
|
&end_page() |
|
); |
|
return &modal_adhoc_script($funcname,$width,$height,$content); |
|
} |
|
|
|
sub modal_adhoc_window { |
|
my ($funcname,$width,$height,$content,$linktext)=@_; |
|
return &modal_adhoc_inner($funcname,$width,$height,$content). |
|
"<a href=\"javascript:$funcname();void(0);\">".$linktext."</a>"; |
|
} |
|
|
|
sub modal_adhoc_launch { |
|
my ($funcname,$width,$height,$content)=@_; |
|
return &modal_adhoc_inner($funcname,$width,$height,$content).(<<ENDLAUNCH); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
$funcname(); |
|
// ]]> |
|
</script> |
|
ENDLAUNCH |
|
} |
|
|
|
sub modal_adhoc_close { |
|
return (<<ENDCLOSE); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
modalWindow.close(); |
|
// ]]> |
|
</script> |
|
ENDCLOSE |
|
} |
|
|
|
sub togglebox_script { |
|
return(<<ENDTOGGLE); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
function LCtoggleDisplay(id,hidetext,showtext) { |
|
link = document.getElementById(id + "link").childNodes[0]; |
|
with (document.getElementById(id).style) { |
|
if (display == "none" ) { |
|
display = "inline"; |
|
link.nodeValue = hidetext; |
|
} else { |
|
display = "none"; |
|
link.nodeValue = showtext; |
|
} |
|
} |
|
} |
|
// ]]> |
|
</script> |
|
ENDTOGGLE |
|
} |
|
|
|
sub start_togglebox { |
|
my ($id,$heading,$headerbg,$hidetext,$showtext)=@_; |
|
unless ($heading) { $heading=''; } else { $heading.=' '; } |
|
unless ($showtext) { $showtext=&mt('show'); } |
|
unless ($hidetext) { $hidetext=&mt('hide'); } |
|
unless ($headerbg) { $headerbg='#FFFFFF'; } |
|
return &start_data_table(). |
|
&start_data_table_header_row(). |
|
'<td bgcolor="'.$headerbg.'">'.$heading. |
|
'[<a id="'.$id.'link" href="javascript:LCtoggleDisplay(\''.$id.'\',\''.$hidetext.'\',\''. |
|
$showtext.'\')">'.$showtext.'</a>]</td>'. |
|
&end_data_table_header_row(). |
|
'<tr id="'.$id.'" style="display:none""><td>'; |
|
} |
|
|
|
sub end_togglebox { |
|
return '</td></tr>'.&end_data_table(); |
|
} |
|
|
|
sub LCprogressbar_script { |
|
my ($id)=@_; |
|
return(<<ENDPROGRESS); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
\$('#progressbar$id').progressbar({ |
|
value: 0, |
|
change: function(event, ui) { |
|
var newVal = \$(this).progressbar('option', 'value'); |
|
\$('.pblabel', this).text(LCprogressTxt); |
|
} |
|
}); |
|
// ]]> |
|
</script> |
|
ENDPROGRESS |
|
} |
|
|
|
sub LCprogressbarUpdate_script { |
|
return(<<ENDPROGRESSUPDATE); |
|
<style type="text/css"> |
|
.ui-progressbar { position:relative; } |
|
.pblabel { position: absolute; width: 100%; text-align: center; line-height: 1.9em; } |
|
</style> |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
var LCprogressTxt='---'; |
|
|
|
function LCupdateProgress(percent,progresstext,id) { |
|
LCprogressTxt=progresstext; |
|
\$('#progressbar'+id).progressbar('value',percent); |
|
} |
|
// ]]> |
|
</script> |
|
ENDPROGRESSUPDATE |
|
} |
|
|
|
my $LClastpercent; |
|
my $LCidcnt; |
|
my $LCcurrentid; |
|
|
|
sub LCprogressbar { |
|
my ($r)=(@_); |
|
$LClastpercent=0; |
|
$LCidcnt++; |
|
$LCcurrentid=$$.'_'.$LCidcnt; |
|
my $starting=&mt('Starting'); |
|
my $content=(<<ENDPROGBAR); |
|
<p> |
|
<div id="progressbar$LCcurrentid"> |
|
<span class="pblabel">$starting</span> |
|
</div> |
|
</p> |
|
ENDPROGBAR |
|
&r_print($r,$content.&LCprogressbar_script($LCcurrentid)); |
|
} |
|
|
|
sub LCprogressbarUpdate { |
|
my ($r,$val,$text)=@_; |
|
unless ($val) { |
|
if ($LClastpercent) { |
|
$val=$LClastpercent; |
|
} else { |
|
$val=0; |
|
} |
|
} |
|
if ($val<0) { $val=0; } |
|
if ($val>100) { $val=0; } |
|
$LClastpercent=$val; |
|
unless ($text) { $text=$val.'%'; } |
|
$text=&js_ready($text); |
|
&r_print($r,<<ENDUPDATE); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
LCupdateProgress($val,'$text','$LCcurrentid'); |
|
// ]]> |
|
</script> |
|
ENDUPDATE |
|
} |
|
|
|
sub LCprogressbarClose { |
|
my ($r)=@_; |
|
$LClastpercent=0; |
|
&r_print($r,<<ENDCLOSE); |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
\$("#progressbar$LCcurrentid").hide('slow'); |
|
// ]]> |
|
</script> |
|
ENDCLOSE |
|
} |
|
|
|
sub r_print { |
|
my ($r,$to_print)=@_; |
|
if ($r) { |
|
$r->print($to_print); |
|
$r->rflush(); |
|
} else { |
|
print($to_print); |
|
} |
|
} |
|
|
sub html_encode { |
sub html_encode { |
my ($result) = @_; |
my ($result) = @_; |
|
|
Line 6920 sub html_encode {
|
Line 7784 sub html_encode {
|
|
|
return $result; |
return $result; |
} |
} |
|
|
sub js_ready { |
sub js_ready { |
my ($result) = @_; |
my ($result) = @_; |
|
|
Line 6958 sub validate_page {
|
Line 7823 sub validate_page {
|
|
|
|
|
sub start_scrollbox { |
sub start_scrollbox { |
my ($outerwidth,$width,$height,$id)=@_; |
my ($outerwidth,$width,$height,$id,$bgcolor)=@_; |
unless ($outerwidth) { $outerwidth='520px'; } |
unless ($outerwidth) { $outerwidth='520px'; } |
unless ($width) { $width='500px'; } |
unless ($width) { $width='500px'; } |
unless ($height) { $height='200px'; } |
unless ($height) { $height='200px'; } |
my ($table_id,$div_id); |
my ($table_id,$div_id,$tdcol); |
if ($id ne '') { |
if ($id ne '') { |
$table_id = " id='table_$id'"; |
$table_id = " id='table_$id'"; |
$div_id = " id='div_$id'"; |
$div_id = " id='div_$id'"; |
} |
} |
return "<table style='width: $outerwidth; border: 1px solid none;'$table_id><tr><td style='width: $width;' bgcolor='#FFFFFF'><div style='overflow:auto; width:$width; height: $height;'$div_id>"; |
if ($bgcolor ne '') { |
|
$tdcol = "background-color: $bgcolor;"; |
|
} |
|
return <<"END"; |
|
<table style="width: $outerwidth; border: 1px solid none;"$table_id><tr><td style="width: $width;$tdcol"><div style="overflow:auto; width:$width; height: $height;"$div_id> |
|
END |
} |
} |
|
|
sub end_scrollbox { |
sub end_scrollbox { |
return '</td></tr></table>'; |
return '</div></td></tr></table>'; |
} |
} |
|
|
sub simple_error_page { |
sub simple_error_page { |
my ($r,$title,$msg) = @_; |
my ($r,$title,$msg) = @_; |
my $page = |
my $page = |
&Apache::loncommon::start_page($title). |
&Apache::loncommon::start_page($title). |
&mt($msg). |
'<p class="LC_error">'.&mt($msg).'</p>'. |
&Apache::loncommon::end_page(); |
&Apache::loncommon::end_page(); |
if (ref($r)) { |
if (ref($r)) { |
$r->print($page); |
$r->print($page); |
Line 7193 role status: active, previous or future.
|
Line 8063 role status: active, previous or future.
|
|
|
sub check_user_status { |
sub check_user_status { |
my ($udom,$uname,$cdom,$crs,$role,$sec) = @_; |
my ($udom,$uname,$cdom,$crs,$role,$sec) = @_; |
my $extra = &Apache::lonnet::freeze_escape({'skipcheck' => 1}); |
my %userinfo = &Apache::lonnet::dump('roles',$udom,$uname); |
my %userinfo = &Apache::lonnet::dump('roles',$udom,$uname,'.',undef,$extra); |
|
my @uroles = keys %userinfo; |
my @uroles = keys %userinfo; |
my $srchstr; |
my $srchstr; |
my $active_chk = 'none'; |
my $active_chk = 'none'; |
Line 8250 sub get_standard_codeitems {
|
Line 9119 sub get_standard_codeitems {
|
|
|
=item * sorted_slots() |
=item * sorted_slots() |
|
|
Sorts an array of slot names in order of slot start time (earliest first). |
Sorts an array of slot names in order of an optional sort key, |
|
default sort is by slot start time (earliest first). |
|
|
Inputs: |
Inputs: |
|
|
Line 8260 slotsarr - Reference to array of unsort
|
Line 9130 slotsarr - Reference to array of unsort
|
|
|
slots - Reference to hash of hash, where outer hash keys are slot names. |
slots - Reference to hash of hash, where outer hash keys are slot names. |
|
|
|
sortkey - Name of key in inner hash to be sorted on (e.g., starttime). |
|
|
=back |
=back |
|
|
Returns: |
Returns: |
|
|
=over 4 |
=over 4 |
|
|
sorted - An array of slot names sorted by the start time of the slot. |
sorted - An array of slot names sorted by a specified sort key |
|
(default sort key is start time of the slot). |
=back |
|
|
|
=back |
=back |
|
|
Line 8276 sorted - An array of slot names sorted
|
Line 9147 sorted - An array of slot names sorted
|
|
|
|
|
sub sorted_slots { |
sub sorted_slots { |
my ($slotsarr,$slots) = @_; |
my ($slotsarr,$slots,$sortkey) = @_; |
|
if ($sortkey eq '') { |
|
$sortkey = 'starttime'; |
|
} |
my @sorted; |
my @sorted; |
if ((ref($slotsarr) eq 'ARRAY') && (ref($slots) eq 'HASH')) { |
if ((ref($slotsarr) eq 'ARRAY') && (ref($slots) eq 'HASH')) { |
@sorted = |
@sorted = |
sort { |
sort { |
if (ref($slots->{$a}) && ref($slots->{$b})) { |
if (ref($slots->{$a}) && ref($slots->{$b})) { |
return $slots->{$a}{'starttime'} <=> $slots->{$b}{'starttime'} |
return $slots->{$a}{$sortkey} <=> $slots->{$b}{$sortkey} |
} |
} |
if (ref($slots->{$a})) { return -1;} |
if (ref($slots->{$a})) { return -1;} |
if (ref($slots->{$b})) { return 1;} |
if (ref($slots->{$b})) { return 1;} |
Line 8292 sub sorted_slots {
|
Line 9166 sub sorted_slots {
|
return @sorted; |
return @sorted; |
} |
} |
|
|
|
=pod |
|
|
|
=item * get_future_slots() |
|
|
|
Inputs: |
|
|
|
=over 4 |
|
|
|
cnum - course number |
|
|
|
cdom - course domain |
|
|
|
now - current UNIX time |
|
|
|
symb - optional symb |
|
|
|
=back |
|
|
|
Returns: |
|
|
|
=over 4 |
|
|
|
sorted_reservable - ref to array of student_schedulable slots currently |
|
reservable, ordered by end date of reservation period. |
|
|
|
reservable_now - ref to hash of student_schedulable slots currently |
|
reservable. |
|
|
|
Keys in inner hash are: |
|
(a) symb: either blank or symb to which slot use is restricted. |
|
(b) endreserve: end date of reservation period. |
|
|
|
sorted_future - ref to array of student_schedulable slots reservable in |
|
the future, ordered by start date of reservation period. |
|
|
|
future_reservable - ref to hash of student_schedulable slots reservable |
|
in the future. |
|
|
|
Keys in inner hash are: |
|
(a) symb: either blank or symb to which slot use is restricted. |
|
(b) startreserve: start date of reservation period. |
|
|
|
=back |
|
|
|
=cut |
|
|
|
sub get_future_slots { |
|
my ($cnum,$cdom,$now,$symb) = @_; |
|
my (%reservable_now,%future_reservable,@sorted_reservable,@sorted_future); |
|
my %slots = &Apache::lonnet::get_course_slots($cnum,$cdom); |
|
foreach my $slot (keys(%slots)) { |
|
next unless($slots{$slot}->{'type'} eq 'schedulable_student'); |
|
if ($symb) { |
|
next if (($slots{$slot}->{'symb'} ne '') && |
|
($slots{$slot}->{'symb'} ne $symb)); |
|
} |
|
if (($slots{$slot}->{'starttime'} > $now) && |
|
($slots{$slot}->{'endtime'} > $now)) { |
|
if (($slots{$slot}->{'allowedsections'}) || ($slots{$slot}->{'allowedusers'})) { |
|
my $userallowed = 0; |
|
if ($slots{$slot}->{'allowedsections'}) { |
|
my @allowed_sec = split(',',$slots{$slot}->{'allowedsections'}); |
|
if (!defined($env{'request.role.sec'}) |
|
&& grep(/^No section assigned$/,@allowed_sec)) { |
|
$userallowed=1; |
|
} else { |
|
if (grep(/^\Q$env{'request.role.sec'}\E$/,@allowed_sec)) { |
|
$userallowed=1; |
|
} |
|
} |
|
unless ($userallowed) { |
|
if (defined($env{'request.course.groups'})) { |
|
my @groups = split(/:/,$env{'request.course.groups'}); |
|
foreach my $group (@groups) { |
|
if (grep(/^\Q$group\E$/,@allowed_sec)) { |
|
$userallowed=1; |
|
last; |
|
} |
|
} |
|
} |
|
} |
|
} |
|
if ($slots{$slot}->{'allowedusers'}) { |
|
my @allowed_users = split(',',$slots{$slot}->{'allowedusers'}); |
|
my $user = $env{'user.name'}.':'.$env{'user.domain'}; |
|
if (grep(/^\Q$user\E$/,@allowed_users)) { |
|
$userallowed = 1; |
|
} |
|
} |
|
next unless($userallowed); |
|
} |
|
my $startreserve = $slots{$slot}->{'startreserve'}; |
|
my $endreserve = $slots{$slot}->{'endreserve'}; |
|
my $symb = $slots{$slot}->{'symb'}; |
|
if (($startreserve < $now) && |
|
(!$endreserve || $endreserve > $now)) { |
|
my $lastres = $endreserve; |
|
if (!$lastres) { |
|
$lastres = $slots{$slot}->{'starttime'}; |
|
} |
|
$reservable_now{$slot} = { |
|
symb => $symb, |
|
endreserve => $lastres |
|
}; |
|
} elsif (($startreserve > $now) && |
|
(!$endreserve || $endreserve > $startreserve)) { |
|
$future_reservable{$slot} = { |
|
symb => $symb, |
|
startreserve => $startreserve |
|
}; |
|
} |
|
} |
|
} |
|
my @unsorted_reservable = keys(%reservable_now); |
|
if (@unsorted_reservable > 0) { |
|
@sorted_reservable = |
|
&sorted_slots(\@unsorted_reservable,\%reservable_now,'endreserve'); |
|
} |
|
my @unsorted_future = keys(%future_reservable); |
|
if (@unsorted_future > 0) { |
|
@sorted_future = |
|
&sorted_slots(\@unsorted_future,\%future_reservable,'startreserve'); |
|
} |
|
return (\@sorted_reservable,\%reservable_now,\@sorted_future,\%future_reservable); |
|
} |
|
|
=pod |
=pod |
|
|
|
=back |
|
|
=head1 HTTP Helpers |
=head1 HTTP Helpers |
|
|
=over 4 |
=over 4 |
Line 8433 sub get_env_multiple {
|
Line 9434 sub get_env_multiple {
|
|
|
sub ask_for_embedded_content { |
sub ask_for_embedded_content { |
my ($actionurl,$state,$allfiles,$codebase,$args)=@_; |
my ($actionurl,$state,$allfiles,$codebase,$args)=@_; |
my (%subdependencies,%dependencies,%mapping,%existing,%newfiles,%pathchanges); |
my (%subdependencies,%dependencies,%mapping,%existing,%newfiles,%pathchanges, |
my $num = 0; |
%currsubfile,%unused,$rem); |
|
my $counter = 0; |
|
my $numnew = 0; |
my $numremref = 0; |
my $numremref = 0; |
my $numinvalid = 0; |
my $numinvalid = 0; |
my $numpathchg = 0; |
my $numpathchg = 0; |
my $numexisting = 0; |
my $numexisting = 0; |
my ($output,$upload_output,$toplevel,$url,$udom,$uname,$getpropath); |
my $numunused = 0; |
|
my ($output,$upload_output,$toplevel,$url,$udom,$uname,$getpropath,$cdom,$cnum, |
|
$fileloc,$filename,$delete_output,$modify_output,$title,$symb,$path); |
|
my $heading = &mt('Upload embedded files'); |
|
my $buttontext = &mt('Upload'); |
|
|
|
my $navmap; |
|
if ($env{'request.course.id'}) { |
|
$navmap = Apache::lonnavmaps::navmap->new(); |
|
} |
if (($actionurl eq '/adm/portfolio') || ($actionurl eq '/adm/coursegrp_portfolio')) { |
if (($actionurl eq '/adm/portfolio') || ($actionurl eq '/adm/coursegrp_portfolio')) { |
my $current_path='/'; |
my $current_path='/'; |
if ($env{'form.currentpath'}) { |
if ($env{'form.currentpath'}) { |
Line 8467 sub ask_for_embedded_content {
|
Line 9479 sub ask_for_embedded_content {
|
} |
} |
} elsif ($actionurl eq '/adm/coursedocs') { |
} elsif ($actionurl eq '/adm/coursedocs') { |
if (ref($args) eq 'HASH') { |
if (ref($args) eq 'HASH') { |
$url = $args->{'docs_url'}; |
$url = $args->{'docs_url'}; |
$toplevel = $url; |
$toplevel = $url; |
|
if ($args->{'context'} eq 'paste') { |
|
($cdom,$cnum) = ($url =~ m{^\Q/uploaded/\E($match_domain)/($match_courseid)/}); |
|
($path) = |
|
($toplevel =~ m{^(\Q/uploaded/$cdom/$cnum/\E(?:docs|supplemental)/(?:default|\d+)/\d+)/}); |
|
$fileloc = &Apache::lonnet::filelocation('',$toplevel); |
|
$fileloc =~ s{^/}{}; |
|
} |
|
} |
|
} elsif ($actionurl eq '/adm/dependencies') { |
|
if ($env{'request.course.id'} ne '') { |
|
$cdom = $env{'course.'.$env{'request.course.id'}.'.domain'}; |
|
$cnum = $env{'course.'.$env{'request.course.id'}.'.num'}; |
|
if (ref($args) eq 'HASH') { |
|
$url = $args->{'docs_url'}; |
|
$title = $args->{'docs_title'}; |
|
$toplevel = "/$url"; |
|
($rem) = ($toplevel =~ m{^(.+/)[^/]+$}); |
|
($path) = |
|
($toplevel =~ m{^(\Q/uploaded/$cdom/$cnum/\E(?:docs|supplemental)/(?:default|\d+)/\d+)/}); |
|
$fileloc = &Apache::lonnet::filelocation('',$toplevel); |
|
$fileloc =~ s{^/}{}; |
|
($filename) = ($fileloc =~ m{.+/([^/]+)$}); |
|
$heading = &mt('Status of dependencies in [_1]',"$title ($filename)"); |
|
} |
} |
} |
} |
} |
my $now = time(); |
my $now = time(); |
Line 8507 sub ask_for_embedded_content {
|
Line 9543 sub ask_for_embedded_content {
|
} |
} |
} |
} |
} |
} |
|
my $dirptr = 16384; |
foreach my $path (keys(%subdependencies)) { |
foreach my $path (keys(%subdependencies)) { |
my %currsubfile; |
$currsubfile{$path} = {}; |
if (($actionurl eq '/adm/portfolio') || ($actionurl eq '/adm/coursegrp_portfolio')) { |
if (($actionurl eq '/adm/portfolio') || ($actionurl eq '/adm/coursegrp_portfolio')) { |
my ($sublistref,$listerror) = |
my ($sublistref,$listerror) = |
&Apache::lonnet::dirlist($url.$path,$udom,$uname,$getpropath); |
&Apache::lonnet::dirlist($url.$path,$udom,$uname,$getpropath); |
if (ref($sublistref) eq 'ARRAY') { |
if (ref($sublistref) eq 'ARRAY') { |
foreach my $line (@{$sublistref}) { |
foreach my $line (@{$sublistref}) { |
my ($file_name,$rest) = split(/\&/,$line,2); |
my ($file_name,$rest) = split(/\&/,$line,2); |
$currsubfile{$file_name} = 1; |
$currsubfile{$path}{$file_name} = 1; |
} |
} |
} |
} |
} elsif (($actionurl eq '/adm/upload') || ($actionurl eq '/adm/testbank')) { |
} elsif (($actionurl eq '/adm/upload') || ($actionurl eq '/adm/testbank')) { |
if (opendir(my $dir,$url.'/'.$path)) { |
if (opendir(my $dir,$url.'/'.$path)) { |
my @subdir_list = grep(!/^\./,readdir($dir)); |
my @subdir_list = grep(!/^\./,readdir($dir)); |
map {$currsubfile{$_} = 1;} @subdir_list; |
map {$currsubfile{$path}{$_} = 1;} @subdir_list; |
|
} |
|
} elsif (($actionurl eq '/adm/dependencies') || |
|
(($actionurl eq '/adm/coursedocs') && (ref($args) eq 'HASH') && |
|
($args->{'context'} eq 'paste'))) { |
|
if ($env{'request.course.id'} ne '') { |
|
my ($dir) = ($fileloc =~ m{^(.+/)[^/]+$}); |
|
if ($dir ne '') { |
|
my ($sublistref,$listerror) = |
|
&Apache::lonnet::dirlist($dir.$path,$cdom,$cnum,$getpropath,undef,'/'); |
|
if (ref($sublistref) eq 'ARRAY') { |
|
foreach my $line (@{$sublistref}) { |
|
my ($file_name,$dom,undef,$testdir,undef,undef,undef,undef,$size, |
|
undef,$mtime)=split(/\&/,$line,12); |
|
unless (($testdir&$dirptr) || |
|
($file_name =~ /^\.\.?$/)) { |
|
$currsubfile{$path}{$file_name} = [$size,$mtime]; |
|
} |
|
} |
|
} |
|
} |
} |
} |
} |
} |
foreach my $file (keys(%{$subdependencies{$path}})) { |
foreach my $file (keys(%{$subdependencies{$path}})) { |
if ($currsubfile{$file}) { |
if (exists($currsubfile{$path}{$file})) { |
my $item = $path.'/'.$file; |
my $item = $path.'/'.$file; |
unless ($mapping{$item} eq $item) { |
unless ($mapping{$item} eq $item) { |
$pathchanges{$item} = 1; |
$pathchanges{$item} = 1; |
Line 8536 sub ask_for_embedded_content {
|
Line 9593 sub ask_for_embedded_content {
|
$newfiles{$path.'/'.$file} = 1; |
$newfiles{$path.'/'.$file} = 1; |
} |
} |
} |
} |
|
if ($actionurl eq '/adm/dependencies') { |
|
foreach my $path (keys(%currsubfile)) { |
|
if (ref($currsubfile{$path}) eq 'HASH') { |
|
foreach my $file (keys(%{$currsubfile{$path}})) { |
|
unless ($subdependencies{$path}{$file}) { |
|
next if (($rem ne '') && |
|
(($env{"httpref.$rem"."$path/$file"} ne '') || |
|
(ref($navmap) && |
|
(($navmap->getResourceByUrl($rem."$path/$file") ne '') || |
|
(($file =~ /^(.*\.s?html?)\.bak$/i) && |
|
($navmap->getResourceByUrl($rem."$path/$1"))))))); |
|
$unused{$path.'/'.$file} = 1; |
|
} |
|
} |
|
} |
|
} |
|
} |
} |
} |
my %currfile; |
my %currfile; |
if (($actionurl eq '/adm/portfolio') || ($actionurl eq '/adm/coursegrp_portfolio')) { |
if (($actionurl eq '/adm/portfolio') || ($actionurl eq '/adm/coursegrp_portfolio')) { |
Line 8552 sub ask_for_embedded_content {
|
Line 9626 sub ask_for_embedded_content {
|
my @dir_list = grep(!/^\./,readdir($dir)); |
my @dir_list = grep(!/^\./,readdir($dir)); |
map {$currfile{$_} = 1;} @dir_list; |
map {$currfile{$_} = 1;} @dir_list; |
} |
} |
|
} elsif (($actionurl eq '/adm/dependencies') || |
|
(($actionurl eq '/adm/coursedocs') && (ref($args) eq 'HASH') && |
|
($args->{'context'} eq 'paste'))) { |
|
if ($env{'request.course.id'} ne '') { |
|
my ($dir) = ($fileloc =~ m{^(.+/)[^/]+$}); |
|
if ($dir ne '') { |
|
my ($dirlistref,$listerror) = |
|
&Apache::lonnet::dirlist($dir,$cdom,$cnum,$getpropath,undef,'/'); |
|
if (ref($dirlistref) eq 'ARRAY') { |
|
foreach my $line (@{$dirlistref}) { |
|
my ($file_name,$dom,undef,$testdir,undef,undef,undef,undef, |
|
$size,undef,$mtime)=split(/\&/,$line,12); |
|
unless (($testdir&$dirptr) || |
|
($file_name =~ /^\.\.?$/)) { |
|
$currfile{$file_name} = [$size,$mtime]; |
|
} |
|
} |
|
} |
|
} |
|
} |
} |
} |
foreach my $file (keys(%dependencies)) { |
foreach my $file (keys(%dependencies)) { |
if ($currfile{$file}) { |
if (exists($currfile{$file})) { |
unless ($mapping{$file} eq $file) { |
unless ($mapping{$file} eq $file) { |
$pathchanges{$file} = 1; |
$pathchanges{$file} = 1; |
} |
} |
Line 8564 sub ask_for_embedded_content {
|
Line 9658 sub ask_for_embedded_content {
|
$newfiles{$file} = 1; |
$newfiles{$file} = 1; |
} |
} |
} |
} |
|
foreach my $file (keys(%currfile)) { |
|
unless (($file eq $filename) || |
|
($file eq $filename.'.bak') || |
|
($dependencies{$file})) { |
|
if ($actionurl eq '/adm/dependencies') { |
|
next if (($rem ne '') && |
|
(($env{"httpref.$rem".$file} ne '') || |
|
(ref($navmap) && |
|
(($navmap->getResourceByUrl($rem.$file) ne '') || |
|
(($file =~ /^(.*\.s?html?)\.bak$/i) && |
|
($navmap->getResourceByUrl($rem.$1))))))); |
|
} |
|
$unused{$file} = 1; |
|
} |
|
} |
|
if (($actionurl eq '/adm/coursedocs') && (ref($args) eq 'HASH') && |
|
($args->{'context'} eq 'paste')) { |
|
$counter = scalar(keys(%existing)); |
|
$numpathchg = scalar(keys(%pathchanges)); |
|
return ($output,$counter,$numpathchg,\%existing); |
|
} |
foreach my $embed_file (sort {lc($a) cmp lc($b)} keys(%newfiles)) { |
foreach my $embed_file (sort {lc($a) cmp lc($b)} keys(%newfiles)) { |
|
if ($actionurl eq '/adm/dependencies') { |
|
next if ($embed_file =~ m{^\w+://}); |
|
} |
$upload_output .= &start_data_table_row(). |
$upload_output .= &start_data_table_row(). |
'<td><span class="LC_filename">'.$embed_file.'</span>'; |
'<td><img src="'.&icon($embed_file).'" /> '. |
|
'<span class="LC_filename">'.$embed_file.'</span>'; |
unless ($mapping{$embed_file} eq $embed_file) { |
unless ($mapping{$embed_file} eq $embed_file) { |
$upload_output .= '<br /><span class="LC_info" style="font-size:smaller;">'.&mt('changed from: [_1]',$mapping{$embed_file}).'</span>'; |
$upload_output .= '<br /><span class="LC_info" style="font-size:smaller;">'.&mt('changed from: [_1]',$mapping{$embed_file}).'</span>'; |
} |
} |
$upload_output .= '</td><td>'; |
$upload_output .= '</td><td>'; |
if ($args->{'ignore_remote_references'} |
if ($args->{'ignore_remote_references'} && $embed_file =~ m{^\w+://}) { |
&& $embed_file =~ m{^\w+://}) { |
|
$upload_output.='<span class="LC_warning">'.&mt("URL points to other server.").'</span>'; |
$upload_output.='<span class="LC_warning">'.&mt("URL points to other server.").'</span>'; |
$numremref++; |
$numremref++; |
} elsif ($args->{'error_on_invalid_names'} |
} elsif ($args->{'error_on_invalid_names'} |
&& $embed_file ne &Apache::lonnet::clean_filename($embed_file,{'keep_path' => 1,})) { |
&& $embed_file ne &Apache::lonnet::clean_filename($embed_file,{'keep_path' => 1,})) { |
|
|
$upload_output.='<span class="LC_warning">'.&mt('Invalid characters').'</span>'; |
$upload_output.='<span class="LC_warning">'.&mt('Invalid characters').'</span>'; |
$numinvalid++; |
$numinvalid++; |
} else { |
} else { |
$upload_output .= &embedded_file_element('upload_embedded',$num, |
$upload_output .= &embedded_file_element('upload_embedded',$counter, |
$embed_file,\%mapping, |
$embed_file,\%mapping, |
$allfiles,$codebase); |
$allfiles,$codebase,'upload'); |
$num++; |
$counter ++; |
|
$numnew ++; |
} |
} |
$upload_output .= '</td>'.&Apache::loncommon::end_data_table_row()."\n"; |
$upload_output .= '</td>'.&Apache::loncommon::end_data_table_row()."\n"; |
} |
} |
foreach my $embed_file (sort {lc($a) cmp lc($b)} keys(%existing)) { |
foreach my $embed_file (sort {lc($a) cmp lc($b)} keys(%existing)) { |
$upload_output .= &start_data_table_row(). |
if ($actionurl eq '/adm/dependencies') { |
'<td><span class="LC_filename">'.$embed_file.'</span></td>'. |
my ($size,$mtime) = &get_dependency_details(\%currfile,\%currsubfile,$embed_file); |
'<td><span class="LC_warning">'.&mt('Already exists').'</span></td>'. |
$modify_output .= &start_data_table_row(). |
&Apache::loncommon::end_data_table_row()."\n"; |
'<td><a href="'.$path.'/'.$embed_file.'" style="text-decoration:none;">'. |
|
'<img src="'.&icon($embed_file).'" border="0" />'. |
|
' <span class="LC_filename">'.$embed_file.'</span></a></td>'. |
|
'<td>'.$size.'</td>'. |
|
'<td>'.$mtime.'</td>'. |
|
'<td><label><input type="checkbox" name="mod_upload_dep" '. |
|
'onclick="toggleBrowse('."'$counter'".')" id="mod_upload_dep_'. |
|
$counter.'" value="'.$counter.'" />'.&mt('Yes').'</label>'. |
|
'<div id="moduploaddep_'.$counter.'" style="display:none;">'. |
|
&embedded_file_element('upload_embedded',$counter, |
|
$embed_file,\%mapping, |
|
$allfiles,$codebase,'modify'). |
|
'</div></td>'. |
|
&end_data_table_row()."\n"; |
|
$counter ++; |
|
} else { |
|
$upload_output .= &start_data_table_row(). |
|
'<td><span class="LC_filename">'.$embed_file.'</span></td>'; |
|
'<td><span class="LC_warning">'.&mt('Already exists').'</span></td>'. |
|
&Apache::loncommon::end_data_table_row()."\n"; |
|
} |
|
} |
|
my $delidx = $counter; |
|
foreach my $oldfile (sort {lc($a) cmp lc($b)} keys(%unused)) { |
|
my ($size,$mtime) = &get_dependency_details(\%currfile,\%currsubfile,$oldfile); |
|
$delete_output .= &start_data_table_row(). |
|
'<td><img src="'.&icon($oldfile).'" />'. |
|
' <span class="LC_filename">'.$oldfile.'</span></td>'. |
|
'<td>'.$size.'</td>'. |
|
'<td>'.$mtime.'</td>'. |
|
'<td><label><input type="checkbox" name="del_upload_dep" '. |
|
' value="'.$delidx.'" />'.&mt('Yes').'</label>'. |
|
&embedded_file_element('upload_embedded',$delidx, |
|
$oldfile,\%mapping,$allfiles, |
|
$codebase,'delete').'</td>'. |
|
&end_data_table_row()."\n"; |
|
$numunused ++; |
|
$delidx ++; |
} |
} |
if ($upload_output) { |
if ($upload_output) { |
$upload_output = &start_data_table(). |
$upload_output = &start_data_table(). |
$upload_output. |
$upload_output. |
&end_data_table()."\n"; |
&end_data_table()."\n"; |
} |
} |
|
if ($modify_output) { |
|
$modify_output = &start_data_table(). |
|
&start_data_table_header_row(). |
|
'<th>'.&mt('File').'</th>'. |
|
'<th>'.&mt('Size (KB)').'</th>'. |
|
'<th>'.&mt('Modified').'</th>'. |
|
'<th>'.&mt('Upload replacement?').'</th>'. |
|
&end_data_table_header_row(). |
|
$modify_output. |
|
&end_data_table()."\n"; |
|
} |
|
if ($delete_output) { |
|
$delete_output = &start_data_table(). |
|
&start_data_table_header_row(). |
|
'<th>'.&mt('File').'</th>'. |
|
'<th>'.&mt('Size (KB)').'</th>'. |
|
'<th>'.&mt('Modified').'</th>'. |
|
'<th>'.&mt('Delete?').'</th>'. |
|
&end_data_table_header_row(). |
|
$delete_output. |
|
&end_data_table()."\n"; |
|
} |
my $applies = 0; |
my $applies = 0; |
if ($numremref) { |
if ($numremref) { |
$applies ++; |
$applies ++; |
Line 8609 sub ask_for_embedded_content {
|
Line 9786 sub ask_for_embedded_content {
|
if ($numexisting) { |
if ($numexisting) { |
$applies ++; |
$applies ++; |
} |
} |
if ($num) { |
if ($counter || $numunused) { |
$output = '<form name="upload_embedded" action="'.$actionurl.'"'. |
$output = '<form name="upload_embedded" action="'.$actionurl.'"'. |
' method="post" enctype="multipart/form-data">'."\n". |
' method="post" enctype="multipart/form-data">'."\n". |
$state. |
$state.'<h3>'.$heading.'</h3>'; |
'<h3>'.&mt('Upload embedded files'). |
if ($actionurl eq '/adm/dependencies') { |
':</h3>'.$upload_output.'<br />'."\n". |
if ($numnew) { |
'<input type ="hidden" name="number_embedded_items" value="'. |
$output .= '<h4>'.&mt('Missing dependencies').'</h4>'. |
$num.'" />'."\n"; |
'<p>'.&mt('The following files need to be uploaded.').'</p>'."\n". |
if ($actionurl eq '') { |
$upload_output.'<br />'."\n"; |
|
} |
|
if ($numexisting) { |
|
$output .= '<h4>'.&mt('Uploaded dependencies (in use)').'</h4>'. |
|
'<p>'.&mt('Upload a new file to replace the one currently in use.').'</p>'."\n". |
|
$modify_output.'<br />'."\n"; |
|
$buttontext = &mt('Save changes'); |
|
} |
|
if ($numunused) { |
|
$output .= '<h4>'.&mt('Unused files').'</h4>'. |
|
'<p>'.&mt('The following uploaded files are no longer used.').'</p>'."\n". |
|
$delete_output.'<br />'."\n"; |
|
$buttontext = &mt('Save changes'); |
|
} |
|
} else { |
|
$output .= $upload_output.'<br />'."\n"; |
|
} |
|
$output .= '<input type ="hidden" name="number_embedded_items" value="'. |
|
$counter.'" />'."\n"; |
|
if ($actionurl eq '/adm/dependencies') { |
|
$output .= '<input type ="hidden" name="number_newemb_items" value="'. |
|
$numnew.'" />'."\n"; |
|
} elsif ($actionurl eq '') { |
$output .= '<input type="hidden" name="phase" value="three" />'; |
$output .= '<input type="hidden" name="phase" value="three" />'; |
} |
} |
} elsif ($applies) { |
} elsif ($applies) { |
Line 8645 sub ask_for_embedded_content {
|
Line 9844 sub ask_for_embedded_content {
|
$output .= $upload_output.'<br />'; |
$output .= $upload_output.'<br />'; |
} |
} |
my ($pathchange_output,$chgcount); |
my ($pathchange_output,$chgcount); |
$chgcount = $num; |
$chgcount = $counter; |
if (keys(%pathchanges) > 0) { |
if (keys(%pathchanges) > 0) { |
foreach my $embed_file (sort {lc($a) cmp lc($b)} keys(%pathchanges)) { |
foreach my $embed_file (sort {lc($a) cmp lc($b)} keys(%pathchanges)) { |
if ($num) { |
if ($counter) { |
$output .= &embedded_file_element('pathchange',$chgcount, |
$output .= &embedded_file_element('pathchange',$chgcount, |
$embed_file,\%mapping, |
$embed_file,\%mapping, |
$allfiles,$codebase); |
$allfiles,$codebase,'change'); |
} else { |
} else { |
$pathchange_output .= |
$pathchange_output .= |
&start_data_table_row(). |
&start_data_table_row(). |
Line 8660 sub ask_for_embedded_content {
|
Line 9859 sub ask_for_embedded_content {
|
'<td>'.$mapping{$embed_file}.'</td>'. |
'<td>'.$mapping{$embed_file}.'</td>'. |
'<td>'.$embed_file. |
'<td>'.$embed_file. |
&embedded_file_element('pathchange',$numpathchg,$embed_file, |
&embedded_file_element('pathchange',$numpathchg,$embed_file, |
\%mapping,$allfiles,$codebase). |
\%mapping,$allfiles,$codebase,'change'). |
'</td>'.&end_data_table_row(); |
'</td>'.&end_data_table_row(); |
} |
} |
$numpathchg ++; |
$numpathchg ++; |
$chgcount ++; |
$chgcount ++; |
} |
} |
} |
} |
if ($num) { |
if ($counter) { |
if ($numpathchg) { |
if ($numpathchg) { |
$output .= '<input type ="hidden" name="number_pathchange_items" value="'. |
$output .= '<input type ="hidden" name="number_pathchange_items" value="'. |
$numpathchg.'" />'."\n"; |
$numpathchg.'" />'."\n"; |
Line 8677 sub ask_for_embedded_content {
|
Line 9876 sub ask_for_embedded_content {
|
$output .= '<input type="hidden" name="phase" value="three" />'."\n"; |
$output .= '<input type="hidden" name="phase" value="three" />'."\n"; |
} elsif ($actionurl eq '/adm/portfolio' || $actionurl eq '/adm/coursegrp_portfolio') { |
} elsif ($actionurl eq '/adm/portfolio' || $actionurl eq '/adm/coursegrp_portfolio') { |
$output .= '<input type="hidden" name="action" value="upload_embedded" />'; |
$output .= '<input type="hidden" name="action" value="upload_embedded" />'; |
|
} elsif ($actionurl eq '/adm/dependencies') { |
|
$output .= '<input type="hidden" name="action" value="process_changes" />'; |
} |
} |
$output .= '<input type ="submit" value="'.&mt('Upload Listed Files').'" />'."\n". |
$output .= '<input type ="submit" value="'.$buttontext.'" />'."\n".'</form>'."\n"; |
&mt('(only files for which a location has been provided will be uploaded)').'</form>'."\n"; |
|
} elsif ($numpathchg) { |
} elsif ($numpathchg) { |
my %pathchange = (); |
my %pathchange = (); |
$output .= &modify_html_form('pathchange',$actionurl,$state,\%pathchange,$pathchange_output); |
$output .= &modify_html_form('pathchange',$actionurl,$state,\%pathchange,$pathchange_output); |
Line 8687 sub ask_for_embedded_content {
|
Line 9887 sub ask_for_embedded_content {
|
$output .= '<p>'.&mt('or').'</p>'; |
$output .= '<p>'.&mt('or').'</p>'; |
} |
} |
} |
} |
return ($output,$num,$numpathchg); |
return ($output,$counter,$numpathchg); |
} |
} |
|
|
sub embedded_file_element { |
sub embedded_file_element { |
my ($context,$num,$embed_file,$mapping,$allfiles,$codebase) = @_; |
my ($context,$num,$embed_file,$mapping,$allfiles,$codebase,$type) = @_; |
return unless ((ref($mapping) eq 'HASH') && (ref($allfiles) eq 'HASH') && |
return unless ((ref($mapping) eq 'HASH') && (ref($allfiles) eq 'HASH') && |
(ref($codebase) eq 'HASH')); |
(ref($codebase) eq 'HASH')); |
my $output; |
my $output; |
if ($context eq 'upload_embedded') { |
if (($context eq 'upload_embedded') && ($type ne 'delete')) { |
$output = '<input name="embedded_item_'.$num.'" type="file" value="" />'."\n"; |
$output = '<input name="embedded_item_'.$num.'" type="file" value="" />'."\n"; |
} |
} |
$output .= '<input name="embedded_orig_'.$num.'" type="hidden" value="'. |
$output .= '<input name="embedded_orig_'.$num.'" type="hidden" value="'. |
Line 8722 sub embedded_file_element {
|
Line 9922 sub embedded_file_element {
|
return $output; |
return $output; |
} |
} |
|
|
|
sub get_dependency_details { |
|
my ($currfile,$currsubfile,$embed_file) = @_; |
|
my ($size,$mtime,$showsize,$showmtime); |
|
if ((ref($currfile) eq 'HASH') && (ref($currsubfile))) { |
|
if ($embed_file =~ m{/}) { |
|
my ($path,$fname) = split(/\//,$embed_file); |
|
if (ref($currsubfile->{$path}{$fname}) eq 'ARRAY') { |
|
($size,$mtime) = @{$currsubfile->{$path}{$fname}}; |
|
} |
|
} else { |
|
if (ref($currfile->{$embed_file}) eq 'ARRAY') { |
|
($size,$mtime) = @{$currfile->{$embed_file}}; |
|
} |
|
} |
|
$showsize = $size/1024.0; |
|
$showsize = sprintf("%.1f",$showsize); |
|
if ($mtime > 0) { |
|
$showmtime = &Apache::lonlocal::locallocaltime($mtime); |
|
} |
|
} |
|
return ($showsize,$showmtime); |
|
} |
|
|
|
sub ask_embedded_js { |
|
return <<"END"; |
|
<script type="text/javascript""> |
|
// <![CDATA[ |
|
function toggleBrowse(counter) { |
|
var chkboxid = document.getElementById('mod_upload_dep_'+counter); |
|
var fileid = document.getElementById('embedded_item_'+counter); |
|
var uploaddivid = document.getElementById('moduploaddep_'+counter); |
|
if (chkboxid.checked == true) { |
|
uploaddivid.style.display='block'; |
|
} else { |
|
uploaddivid.style.display='none'; |
|
fileid.value = ''; |
|
} |
|
} |
|
// ]]> |
|
</script> |
|
|
|
END |
|
} |
|
|
sub upload_embedded { |
sub upload_embedded { |
my ($context,$dirpath,$uname,$udom,$dir_root,$url_root,$group,$disk_quota, |
my ($context,$dirpath,$uname,$udom,$dir_root,$url_root,$group,$disk_quota, |
$current_disk_usage,$hiddenstate,$actionurl) = @_; |
$current_disk_usage,$hiddenstate,$actionurl) = @_; |
Line 8780 sub upload_embedded {
|
Line 10024 sub upload_embedded {
|
$output .= &mt('File name not allowed - rename the file to remove the number immediately before the file extension([_1]) and re-upload.',$2).'<br />'; |
$output .= &mt('File name not allowed - rename the file to remove the number immediately before the file extension([_1]) and re-upload.',$2).'<br />'; |
next; |
next; |
} |
} |
|
|
$env{'form.embedded_item_'.$i.'.filename'}=$fname; |
$env{'form.embedded_item_'.$i.'.filename'}=$fname; |
if ($context eq 'portfolio') { |
if ($context eq 'portfolio') { |
my $result; |
my $result; |
Line 8837 sub upload_embedded {
|
Line 10080 sub upload_embedded {
|
if (!open($fh,'>'.$dest)) { |
if (!open($fh,'>'.$dest)) { |
&Apache::lonnet::logthis('Failed to create '.$dest); |
&Apache::lonnet::logthis('Failed to create '.$dest); |
$output .= '<span class="LC_error">'. |
$output .= '<span class="LC_error">'. |
&mt('An error occurred while trying to upload [_1] for embedded element [_2].',$orig_uploaded_filename,$env{'form.embedded_orig_'.$i}). |
&mt('An error occurred while trying to upload [_1] for embedded element [_2].', |
|
$orig_uploaded_filename,$env{'form.embedded_orig_'.$i}). |
'</span><br />'; |
'</span><br />'; |
} else { |
} else { |
if (!print $fh $env{'form.embedded_item_'.$i}) { |
if (!print $fh $env{'form.embedded_item_'.$i}) { |
&Apache::lonnet::logthis('Failed to write to '.$dest); |
&Apache::lonnet::logthis('Failed to write to '.$dest); |
$output .= '<span class="LC_error">'. |
$output .= '<span class="LC_error">'. |
&mt('An error occurred while writing the file [_1] for embedded element [_2].',$orig_uploaded_filename,$env{'form.embedded_orig_'.$i}). |
&mt('An error occurred while writing the file [_1] for embedded element [_2].', |
|
$orig_uploaded_filename,$env{'form.embedded_orig_'.$i}). |
'</span><br />'; |
'</span><br />'; |
} else { |
} else { |
$output .= &mt('Uploaded [_1]','<span class="LC_filename">'. |
$output .= &mt('Uploaded [_1]','<span class="LC_filename">'. |
Line 8865 sub upload_embedded {
|
Line 10110 sub upload_embedded {
|
} |
} |
$output .= &modify_html_form('upload_embedded',$actionurl,$hiddenstate,\%pathchange); |
$output .= &modify_html_form('upload_embedded',$actionurl,$hiddenstate,\%pathchange); |
$returnflag = 'ok'; |
$returnflag = 'ok'; |
if (keys(%pathchange) > 0) { |
my $numpathchgs = scalar(keys(%pathchange)); |
|
if ($numpathchgs > 0) { |
if ($context eq 'portfolio') { |
if ($context eq 'portfolio') { |
$output .= '<p>'.&mt('or').'</p>'; |
$output .= '<p>'.&mt('or').'</p>'; |
} elsif ($context eq 'testbank') { |
} elsif ($context eq 'testbank') { |
$output .= '<p>'.&mt('Or [_1]continue[_2] the testbank import without modifying the reference(s).','<a href="javascript:document.testbankForm.submit();">','</a>').'</p>'; |
$output .= '<p>'.&mt('Or [_1]continue[_2] the testbank import without modifying the reference(s).', |
|
'<a href="javascript:document.testbankForm.submit();">','</a>').'</p>'; |
$returnflag = 'modify_orightml'; |
$returnflag = 'modify_orightml'; |
} |
} |
} |
} |
return ($output.$footer,$returnflag); |
return ($output.$footer,$returnflag,$numpathchgs); |
} |
} |
|
|
sub modify_html_form { |
sub modify_html_form { |
Line 8908 sub modify_html_form {
|
Line 10155 sub modify_html_form {
|
'<input type="hidden" name="embedded_orig_'.$i.'" value="'. |
'<input type="hidden" name="embedded_orig_'.$i.'" value="'. |
&escape($env{'form.embedded_orig_'.$i}).'" /></td>'. |
&escape($env{'form.embedded_orig_'.$i}).'" /></td>'. |
&end_data_table_row(); |
&end_data_table_row(); |
} |
} |
} |
} |
} else { |
} else { |
$modifyform = $pathchgtable; |
$modifyform = $pathchgtable; |
Line 8919 sub modify_html_form {
|
Line 10166 sub modify_html_form {
|
} |
} |
} |
} |
if ($modifyform) { |
if ($modifyform) { |
|
if ($actionurl eq '/adm/dependencies') { |
|
$hiddenstate .= '<input type="hidden" name="action" value="modifyhrefs" />'; |
|
} |
return '<h3>'.&mt('Changes in content of HTML file required').'</h3>'."\n". |
return '<h3>'.&mt('Changes in content of HTML file required').'</h3>'."\n". |
'<p>'.&mt('Changes need to be made to the reference(s) used for one or more of the dependencies, if your HTML file is to work correctly:').'<ol>'."\n". |
'<p>'.&mt('Changes need to be made to the reference(s) used for one or more of the dependencies, if your HTML file is to work correctly:').'<ol>'."\n". |
'<li>'.&mt('For consistency between the reference(s) and the location of the corresponding stored file within LON-CAPA.').'</li>'."\n". |
'<li>'.&mt('For consistency between the reference(s) and the location of the corresponding stored file within LON-CAPA.').'</li>'."\n". |
Line 8947 sub modify_html_refs {
|
Line 10197 sub modify_html_refs {
|
$container = $env{'form.container'}; |
$container = $env{'form.container'}; |
} elsif ($context eq 'coursedoc') { |
} elsif ($context eq 'coursedoc') { |
$container = $env{'form.primaryurl'}; |
$container = $env{'form.primaryurl'}; |
|
} elsif ($context eq 'manage_dependencies') { |
|
(undef,undef,$container) = &Apache::lonnet::decode_symb($env{'form.symb'}); |
|
$container = "/$container"; |
} else { |
} else { |
$container = $Apache::lonnet::perlvar{'lonDocRoot'}.$env{'form.filename'}; |
$container = $Apache::lonnet::perlvar{'lonDocRoot'}.$env{'form.filename'}; |
} |
} |
my (%allfiles,%codebase,$output,$content); |
my (%allfiles,%codebase,$output,$content); |
my @changes = &get_env_multiple('form.namechange'); |
my @changes = &get_env_multiple('form.namechange'); |
return unless (@changes > 0); |
unless (@changes > 0) { |
if (($context eq 'portfolio') || ($context eq 'coursedoc')) { |
if (wantarray) { |
return unless ($container =~ m{^/uploaded/\Q$udom\E/\Q$uname\E/}); |
return ('',0,0); |
|
} else { |
|
return; |
|
} |
|
} |
|
if (($context eq 'portfolio') || ($context eq 'coursedoc') || |
|
($context eq 'manage_dependencies')) { |
|
unless ($container =~ m{^/uploaded/\Q$udom\E/\Q$uname\E/}) { |
|
if (wantarray) { |
|
return ('',0,0); |
|
} else { |
|
return; |
|
} |
|
} |
$content = &Apache::lonnet::getfile($container); |
$content = &Apache::lonnet::getfile($container); |
return if ($content eq '-1'); |
if ($content eq '-1') { |
|
if (wantarray) { |
|
return ('',0,0); |
|
} else { |
|
return; |
|
} |
|
} |
} else { |
} else { |
return unless ($container =~ /^\Q$dir_root\E/); |
unless ($container =~ /^\Q$dir_root\E/) { |
|
if (wantarray) { |
|
return ('',0,0); |
|
} else { |
|
return; |
|
} |
|
} |
if (open(my $fh,"<$container")) { |
if (open(my $fh,"<$container")) { |
$content = join('', <$fh>); |
$content = join('', <$fh>); |
close($fh); |
close($fh); |
} else { |
} else { |
return; |
if (wantarray) { |
|
return ('',0,0); |
|
} else { |
|
return; |
|
} |
} |
} |
} |
} |
my ($count,$codebasecount) = (0,0); |
my ($count,$codebasecount) = (0,0); |
Line 8997 sub modify_html_refs {
|
Line 10279 sub modify_html_refs {
|
} |
} |
if ($count || $codebasecount) { |
if ($count || $codebasecount) { |
my $saveresult; |
my $saveresult; |
if ($context eq 'portfolio' || $context eq 'coursedoc') { |
if (($context eq 'portfolio') || ($context eq 'coursedoc') || |
|
($context eq 'manage_dependencies')) { |
my $url = &Apache::lonnet::store_edited_file($container,$content,$udom,$uname,\$saveresult); |
my $url = &Apache::lonnet::store_edited_file($container,$content,$udom,$uname,\$saveresult); |
if ($url eq $container) { |
if ($url eq $container) { |
my ($fname) = ($container =~ m{/([^/]+)$}); |
my ($fname) = ($container =~ m{/([^/]+)$}); |
$output = '<p>'.&mt('Updated [quant,_1,reference] in [_2].', |
$output = '<p>'.&mt('Updated [quant,_1,reference] in [_2].', |
$count,'<span class="LC_filename">'. |
$count,'<span class="LC_filename">'. |
$fname.'</span>').'</p>'; |
$fname.'</span>').'</p>'; |
} else { |
} else { |
$output = '<p class="LC_error">'. |
$output = '<p class="LC_error">'. |
&mt('Error: update failed for: [_1].', |
&mt('Error: update failed for: [_1].', |
Line 9030 sub modify_html_refs {
|
Line 10313 sub modify_html_refs {
|
' to modify references: '.$parse_result); |
' to modify references: '.$parse_result); |
} |
} |
} |
} |
return $output; |
if (wantarray) { |
|
return ($output,$count,$codebasecount); |
|
} else { |
|
return $output; |
|
} |
} |
} |
|
|
sub check_for_existing { |
sub check_for_existing { |
Line 9186 sub check_for_traversal {
|
Line 10473 sub check_for_traversal {
|
return $cleanpath; |
return $cleanpath; |
} |
} |
|
|
|
sub is_archive_file { |
|
my ($mimetype) = @_; |
|
if (($mimetype eq 'application/octet-stream') || |
|
($mimetype eq 'application/x-stuffit') || |
|
($mimetype =~ m{^application/(x\-)?(compressed|tar|zip|tgz|gz|gtar|gzip|gunzip|bz|bz2|bzip2)})) { |
|
return 1; |
|
} |
|
return; |
|
} |
|
|
|
sub decompress_form { |
|
my ($mimetype,$archiveurl,$action,$noextract,$hiddenelements,$dirlist) = @_; |
|
my %lt = &Apache::lonlocal::texthash ( |
|
this => 'This file is an archive file.', |
|
camt => 'This file is a Camtasia archive file.', |
|
itsc => 'Its contents are as follows:', |
|
youm => 'You may wish to extract its contents.', |
|
extr => 'Extract contents', |
|
auto => 'LON-CAPA can process the files automatically, or you can decide how each should be handled.', |
|
proa => 'Process automatically?', |
|
yes => 'Yes', |
|
no => 'No', |
|
fold => 'Title for folder containing movie', |
|
movi => 'Title for page containing embedded movie', |
|
); |
|
my $fileloc = &Apache::lonnet::filelocation(undef,$archiveurl); |
|
my ($is_camtasia,$topdir,%toplevel,@paths); |
|
my $info = &list_archive_contents($fileloc,\@paths); |
|
if (@paths) { |
|
foreach my $path (@paths) { |
|
$path =~ s{^/}{}; |
|
if ($path =~ m{^([^/]+)/$}) { |
|
$topdir = $1; |
|
} |
|
if ($path =~ m{^([^/]+)/}) { |
|
$toplevel{$1} = $path; |
|
} else { |
|
$toplevel{$path} = $path; |
|
} |
|
} |
|
} |
|
if ($mimetype =~ m{^application/(x\-)?(compressed|zip)}) { |
|
my @camtasia = ("$topdir/","$topdir/index.html", |
|
"$topdir/media/", |
|
"$topdir/media/$topdir.mp4", |
|
"$topdir/media/FirstFrame.png", |
|
"$topdir/media/player.swf", |
|
"$topdir/media/swfobject.js", |
|
"$topdir/media/expressInstall.swf"); |
|
my @diffs = &compare_arrays(\@paths,\@camtasia); |
|
if (@diffs == 0) { |
|
$is_camtasia = 1; |
|
} |
|
} |
|
my $output; |
|
if ($is_camtasia) { |
|
$output = <<"ENDCAM"; |
|
<script type="text/javascript" language="Javascript"> |
|
// <![CDATA[ |
|
|
|
function camtasiaToggle() { |
|
for (var i=0; i<document.uploaded_decompress.autoextract_camtasia.length; i++) { |
|
if (document.uploaded_decompress.autoextract_camtasia[i].checked) { |
|
if (document.uploaded_decompress.autoextract_camtasia[i].value == 1) { |
|
|
|
document.getElementById('camtasia_titles').style.display='block'; |
|
} else { |
|
document.getElementById('camtasia_titles').style.display='none'; |
|
} |
|
} |
|
} |
|
return; |
|
} |
|
|
|
// ]]> |
|
</script> |
|
<p>$lt{'camt'}</p> |
|
ENDCAM |
|
} else { |
|
$output = '<p>'.$lt{'this'}; |
|
if ($info eq '') { |
|
$output .= ' '.$lt{'youm'}.'</p>'."\n"; |
|
} else { |
|
$output .= ' '.$lt{'itsc'}.'</p>'."\n". |
|
'<div><pre>'.$info.'</pre></div>'; |
|
} |
|
} |
|
$output .= '<form name="uploaded_decompress" action="'.$action.'" method="post">'."\n"; |
|
my $duplicates; |
|
my $num = 0; |
|
if (ref($dirlist) eq 'ARRAY') { |
|
foreach my $item (@{$dirlist}) { |
|
if (ref($item) eq 'ARRAY') { |
|
if (exists($toplevel{$item->[0]})) { |
|
$duplicates .= |
|
&start_data_table_row(). |
|
'<td><label><input type="radio" name="archive_overwrite_'.$num.'" '. |
|
'value="0" checked="checked" />'.&mt('No').'</label>'. |
|
' <label><input type="radio" name="archive_overwrite_'.$num.'" '. |
|
'value="1" />'.&mt('Yes').'</label>'. |
|
'<input type="hidden" name="archive_overwrite_name_'.$num.'" value="'.$item->[0].'" /></td>'."\n". |
|
'<td>'.$item->[0].'</td>'; |
|
if ($item->[2]) { |
|
$duplicates .= '<td>'.&mt('Directory').'</td>'; |
|
} else { |
|
$duplicates .= '<td>'.&mt('File').'</td>'; |
|
} |
|
$duplicates .= '<td>'.$item->[3].'</td>'. |
|
'<td>'. |
|
&Apache::lonlocal::locallocaltime($item->[4]). |
|
'</td>'. |
|
&end_data_table_row(); |
|
$num ++; |
|
} |
|
} |
|
} |
|
} |
|
my $itemcount; |
|
if (@paths > 0) { |
|
$itemcount = scalar(@paths); |
|
} else { |
|
$itemcount = 1; |
|
} |
|
if ($is_camtasia) { |
|
$output .= $lt{'auto'}.'<br />'. |
|
'<span class="LC_nobreak">'.$lt{'proa'}.'<label>'. |
|
'<input type="radio" name="autoextract_camtasia" value="1" onclick="javascript:camtasiaToggle();" checked="checked" />'. |
|
$lt{'yes'}.'</label> <label>'. |
|
'<input type="radio" name="autoextract_camtasia" value="0" onclick="javascript:camtasiaToggle();" />'. |
|
$lt{'no'}.'</label></span><br />'. |
|
'<div id="camtasia_titles" style="display:block">'. |
|
&Apache::lonhtmlcommon::start_pick_box(). |
|
&Apache::lonhtmlcommon::row_title($lt{'fold'}). |
|
'<input type="textbox" name="camtasia_foldername" value="'.$env{'form.comment'}.'" />'."\n". |
|
&Apache::lonhtmlcommon::row_closure(). |
|
&Apache::lonhtmlcommon::row_title($lt{'movi'}). |
|
'<input type="textbox" name="camtasia_moviename" value="" />'."\n". |
|
&Apache::lonhtmlcommon::row_closure(1). |
|
&Apache::lonhtmlcommon::end_pick_box(). |
|
'</div>'; |
|
} |
|
$output .= |
|
'<input type="hidden" name="archive_overwrite_total" value="'.$num.'" />'. |
|
'<input type="hidden" name="archive_itemcount" value="'.$itemcount.'" />'. |
|
"\n"; |
|
if ($duplicates ne '') { |
|
$output .= '<p><span class="LC_warning">'. |
|
&mt('Warning: decompression of the archive will overwrite the following items which already exist:').'</span><br />'. |
|
&start_data_table(). |
|
&start_data_table_header_row(). |
|
'<th>'.&mt('Overwrite?').'</th>'. |
|
'<th>'.&mt('Name').'</th>'. |
|
'<th>'.&mt('Type').'</th>'. |
|
'<th>'.&mt('Size').'</th>'. |
|
'<th>'.&mt('Last modified').'</th>'. |
|
&end_data_table_header_row(). |
|
$duplicates. |
|
&end_data_table(). |
|
'</p>'; |
|
} |
|
$output .= '<input type="hidden" name="archiveurl" value="'.$archiveurl.'" />'."\n"; |
|
if (ref($hiddenelements) eq 'HASH') { |
|
foreach my $hidden (sort(keys(%{$hiddenelements}))) { |
|
$output .= '<input type="hidden" name="'.$hidden.'" value="'.$hiddenelements->{$hidden}.'" />'."\n"; |
|
} |
|
} |
|
$output .= <<"END"; |
|
<br /> |
|
<input type="submit" name="decompress" value="$lt{'extr'}" /> |
|
</form> |
|
$noextract |
|
END |
|
return $output; |
|
} |
|
|
|
sub decompression_utility { |
|
my ($program) = @_; |
|
my @utilities = ('tar','gunzip','bunzip2','unzip'); |
|
my $location; |
|
if (grep(/^\Q$program\E$/,@utilities)) { |
|
foreach my $dir ('/bin/','/usr/bin/','/usr/local/bin/','/sbin/', |
|
'/usr/sbin/') { |
|
if (-x $dir.$program) { |
|
$location = $dir.$program; |
|
last; |
|
} |
|
} |
|
} |
|
return $location; |
|
} |
|
|
|
sub list_archive_contents { |
|
my ($file,$pathsref) = @_; |
|
my (@cmd,$output); |
|
my $needsregexp; |
|
if ($file =~ /\.zip$/) { |
|
@cmd = (&decompression_utility('unzip'),"-l"); |
|
$needsregexp = 1; |
|
} elsif (($file =~ m/\.tar\.gz$/) || |
|
($file =~ /\.tgz$/)) { |
|
@cmd = (&decompression_utility('tar'),"-ztf"); |
|
} elsif ($file =~ /\.tar\.bz2$/) { |
|
@cmd = (&decompression_utility('tar'),"-jtf"); |
|
} elsif ($file =~ m|\.tar$|) { |
|
@cmd = (&decompression_utility('tar'),"-tf"); |
|
} |
|
if (@cmd) { |
|
undef($!); |
|
undef($@); |
|
if (open(my $fh,"-|", @cmd, $file)) { |
|
while (my $line = <$fh>) { |
|
$output .= $line; |
|
chomp($line); |
|
my $item; |
|
if ($needsregexp) { |
|
($item) = ($line =~ /^\s*\d+\s+[\d\-]+\s+[\d:]+\s*(.+)$/); |
|
} else { |
|
$item = $line; |
|
} |
|
if ($item ne '') { |
|
unless (grep(/^\Q$item\E$/,@{$pathsref})) { |
|
push(@{$pathsref},$item); |
|
} |
|
} |
|
} |
|
close($fh); |
|
} |
|
} |
|
return $output; |
|
} |
|
|
|
sub decompress_uploaded_file { |
|
my ($file,$dir) = @_; |
|
&Apache::lonnet::appenv({'cgi.file' => $file}); |
|
&Apache::lonnet::appenv({'cgi.dir' => $dir}); |
|
my $result = &Apache::lonnet::ssi_body('/cgi-bin/decompress.pl'); |
|
my ($handle) = ($env{'user.environment'} =~m{/([^/]+)\.id$}); |
|
my $lonidsdir = $Apache::lonnet::perlvar{'lonIDsDir'}; |
|
&Apache::lonnet::transfer_profile_to_env($lonidsdir,$handle,1); |
|
my $decompressed = $env{'cgi.decompressed'}; |
|
&Apache::lonnet::delenv('cgi.file'); |
|
&Apache::lonnet::delenv('cgi.dir'); |
|
&Apache::lonnet::delenv('cgi.decompressed'); |
|
return ($decompressed,$result); |
|
} |
|
|
|
sub process_decompression { |
|
my ($docudom,$docuname,$file,$destination,$dir_root,$hiddenelem) = @_; |
|
my ($dir,$error,$warning,$output); |
|
if ($file !~ /\.(zip|tar|bz2|gz|tar.gz|tar.bz2|tgz)$/) { |
|
$error = &mt('File name not a supported archive file type.'). |
|
'<br />'.&mt('File name should end with one of: [_1].', |
|
'.zip, .tar, .bz2, .gz, .tar.gz, .tar.bz2, .tgz'); |
|
} else { |
|
my $docuhome = &Apache::lonnet::homeserver($docuname,$docudom); |
|
if ($docuhome eq 'no_host') { |
|
$error = &mt('Could not determine home server for course.'); |
|
} else { |
|
my @ids=&Apache::lonnet::current_machine_ids(); |
|
my $currdir = "$dir_root/$destination"; |
|
if (grep(/^\Q$docuhome\E$/,@ids)) { |
|
$dir = &LONCAPA::propath($docudom,$docuname). |
|
"$dir_root/$destination"; |
|
} else { |
|
$dir = $Apache::lonnet::perlvar{'lonDocRoot'}. |
|
"$dir_root/$docudom/$docuname/$destination"; |
|
unless (&Apache::lonnet::repcopy_userfile("$dir/$file") eq 'ok') { |
|
$error = &mt('Archive file not found.'); |
|
} |
|
} |
|
my (@to_overwrite,@to_skip); |
|
if ($env{'form.archive_overwrite_total'} > 0) { |
|
my $total = $env{'form.archive_overwrite_total'}; |
|
for (my $i=0; $i<$total; $i++) { |
|
if ($env{'form.archive_overwrite_'.$i} == 1) { |
|
push(@to_overwrite,$env{'form.archive_overwrite_name_'.$i}); |
|
} elsif ($env{'form.archive_overwrite_'.$i} == 0) { |
|
push(@to_skip,$env{'form.archive_overwrite_name_'.$i}); |
|
} |
|
} |
|
} |
|
my $numskip = scalar(@to_skip); |
|
if (($numskip > 0) && |
|
($numskip == $env{'form.archive_itemcount'})) { |
|
$warning = &mt('All items in the archive file already exist, and no overwriting of existing files has been requested.'); |
|
} elsif ($dir eq '') { |
|
$error = &mt('Directory containing archive file unavailable.'); |
|
} elsif (!$error) { |
|
my ($decompressed,$display); |
|
if ($numskip > 0) { |
|
my $tempdir = time.'_'.$$.int(rand(10000)); |
|
mkdir("$dir/$tempdir",0755); |
|
system("mv $dir/$file $dir/$tempdir/$file"); |
|
($decompressed,$display) = |
|
&decompress_uploaded_file($file,"$dir/$tempdir"); |
|
foreach my $item (@to_skip) { |
|
if (($item ne '') && ($item !~ /\.\./)) { |
|
if (-f "$dir/$tempdir/$item") { |
|
unlink("$dir/$tempdir/$item"); |
|
} elsif (-d "$dir/$tempdir/$item") { |
|
system("rm -rf $dir/$tempdir/$item"); |
|
} |
|
} |
|
} |
|
system("mv $dir/$tempdir/* $dir"); |
|
rmdir("$dir/$tempdir"); |
|
} else { |
|
($decompressed,$display) = |
|
&decompress_uploaded_file($file,$dir); |
|
} |
|
if ($decompressed eq 'ok') { |
|
$output = '<p class="LC_info">'. |
|
&mt('Files extracted successfully from archive.'). |
|
'</p>'."\n"; |
|
my ($warning,$result,@contents); |
|
my ($newdirlistref,$newlisterror) = |
|
&Apache::lonnet::dirlist($currdir,$docudom, |
|
$docuname,1); |
|
my (%is_dir,%changes,@newitems); |
|
my $dirptr = 16384; |
|
if (ref($newdirlistref) eq 'ARRAY') { |
|
foreach my $dir_line (@{$newdirlistref}) { |
|
my ($item,undef,undef,$testdir)=split(/\&/,$dir_line,5); |
|
unless (($item =~ /^\.+$/) || ($item eq $file) || |
|
((@to_skip > 0) && (grep(/^\Q$item\E$/,@to_skip)))) { |
|
push(@newitems,$item); |
|
if ($dirptr&$testdir) { |
|
$is_dir{$item} = 1; |
|
} |
|
$changes{$item} = 1; |
|
} |
|
} |
|
} |
|
if (keys(%changes) > 0) { |
|
foreach my $item (sort(@newitems)) { |
|
if ($changes{$item}) { |
|
push(@contents,$item); |
|
} |
|
} |
|
} |
|
if (@contents > 0) { |
|
my $wantform; |
|
unless ($env{'form.autoextract_camtasia'}) { |
|
$wantform = 1; |
|
} |
|
my (%children,%parent,%dirorder,%titles); |
|
my ($count,$datatable) = &get_extracted($docudom,$docuname, |
|
$currdir,\%is_dir, |
|
\%children,\%parent, |
|
\@contents,\%dirorder, |
|
\%titles,$wantform); |
|
if ($datatable ne '') { |
|
$output .= &archive_options_form('decompressed',$datatable, |
|
$count,$hiddenelem); |
|
my $startcount = 6; |
|
$output .= &archive_javascript($startcount,$count, |
|
\%titles,\%children); |
|
} |
|
if ($env{'form.autoextract_camtasia'}) { |
|
my %displayed; |
|
my $total = 1; |
|
$env{'form.archive_directory'} = []; |
|
foreach my $i (sort { $a <=> $b } keys(%dirorder)) { |
|
my $path = join('/',map { $titles{$_}; } @{$dirorder{$i}}); |
|
$path =~ s{/$}{}; |
|
my $item; |
|
if ($path ne '') { |
|
$item = "$path/$titles{$i}"; |
|
} else { |
|
$item = $titles{$i}; |
|
} |
|
$env{'form.archive_content_'.$i} = "$dir_root/$destination/$item"; |
|
if ($item eq $contents[0]) { |
|
push(@{$env{'form.archive_directory'}},$i); |
|
$env{'form.archive_'.$i} = 'display'; |
|
$env{'form.archive_title_'.$i} = $env{'form.camtasia_foldername'}; |
|
$displayed{'folder'} = $i; |
|
} elsif ($item eq "$contents[0]/index.html") { |
|
$env{'form.archive_'.$i} = 'display'; |
|
$env{'form.archive_title_'.$i} = $env{'form.camtasia_moviename'}; |
|
$displayed{'web'} = $i; |
|
} else { |
|
if ($item eq "$contents[0]/media") { |
|
push(@{$env{'form.archive_directory'}},$i); |
|
} |
|
$env{'form.archive_'.$i} = 'dependency'; |
|
} |
|
$total ++; |
|
} |
|
for (my $i=1; $i<$total; $i++) { |
|
next if ($i == $displayed{'web'}); |
|
next if ($i == $displayed{'folder'}); |
|
$env{'form.archive_dependent_on_'.$i} = $displayed{'web'}; |
|
} |
|
$env{'form.phase'} = 'decompress_cleanup'; |
|
$env{'form.archivedelete'} = 1; |
|
$env{'form.archive_count'} = $total-1; |
|
$output .= |
|
&process_extracted_files('coursedocs',$docudom, |
|
$docuname,$destination, |
|
$dir_root,$hiddenelem); |
|
} |
|
} else { |
|
$warning = &mt('No new items extracted from archive file.'); |
|
} |
|
} else { |
|
$output = $display; |
|
$error = &mt('An error occurred during extraction from the archive file.'); |
|
} |
|
} |
|
} |
|
} |
|
if ($error) { |
|
$output .= '<p class="LC_error">'.&mt('Not extracted.').'<br />'. |
|
$error.'</p>'."\n"; |
|
} |
|
if ($warning) { |
|
$output .= '<p class="LC_warning">'.$warning.'</p>'."\n"; |
|
} |
|
return $output; |
|
} |
|
|
|
sub get_extracted { |
|
my ($docudom,$docuname,$currdir,$is_dir,$children,$parent,$contents,$dirorder, |
|
$titles,$wantform) = @_; |
|
my $count = 0; |
|
my $depth = 0; |
|
my $datatable; |
|
my @hierarchy; |
|
return unless ((ref($is_dir) eq 'HASH') && (ref($children) eq 'HASH') && |
|
(ref($parent) eq 'HASH') && (ref($contents) eq 'ARRAY') && |
|
(ref($dirorder) eq 'HASH') && (ref($titles) eq 'HASH')); |
|
foreach my $item (@{$contents}) { |
|
$count ++; |
|
@{$dirorder->{$count}} = @hierarchy; |
|
$titles->{$count} = $item; |
|
&archive_hierarchy($depth,$count,$parent,$children); |
|
if ($wantform) { |
|
$datatable .= &archive_row($is_dir->{$item},$item, |
|
$currdir,$depth,$count); |
|
} |
|
if ($is_dir->{$item}) { |
|
$depth ++; |
|
push(@hierarchy,$count); |
|
$parent->{$depth} = $count; |
|
$datatable .= |
|
&recurse_extracted_archive("$currdir/$item",$docudom,$docuname, |
|
\$depth,\$count,\@hierarchy,$dirorder, |
|
$children,$parent,$titles,$wantform); |
|
$depth --; |
|
pop(@hierarchy); |
|
} |
|
} |
|
return ($count,$datatable); |
|
} |
|
|
|
sub recurse_extracted_archive { |
|
my ($currdir,$docudom,$docuname,$depth,$count,$hierarchy,$dirorder, |
|
$children,$parent,$titles,$wantform) = @_; |
|
my $result=''; |
|
unless ((ref($depth)) && (ref($count)) && (ref($hierarchy) eq 'ARRAY') && |
|
(ref($children) eq 'HASH') && (ref($parent) eq 'HASH') && |
|
(ref($dirorder) eq 'HASH')) { |
|
return $result; |
|
} |
|
my $dirptr = 16384; |
|
my ($newdirlistref,$newlisterror) = |
|
&Apache::lonnet::dirlist($currdir,$docudom,$docuname,1); |
|
if (ref($newdirlistref) eq 'ARRAY') { |
|
foreach my $dir_line (@{$newdirlistref}) { |
|
my ($item,undef,undef,$testdir)=split(/\&/,$dir_line,5); |
|
unless ($item =~ /^\.+$/) { |
|
$$count ++; |
|
@{$dirorder->{$$count}} = @{$hierarchy}; |
|
$titles->{$$count} = $item; |
|
&archive_hierarchy($$depth,$$count,$parent,$children); |
|
|
|
my $is_dir; |
|
if ($dirptr&$testdir) { |
|
$is_dir = 1; |
|
} |
|
if ($wantform) { |
|
$result .= &archive_row($is_dir,$item,$currdir,$$depth,$$count); |
|
} |
|
if ($is_dir) { |
|
$$depth ++; |
|
push(@{$hierarchy},$$count); |
|
$parent->{$$depth} = $$count; |
|
$result .= |
|
&recurse_extracted_archive("$currdir/$item",$docudom, |
|
$docuname,$depth,$count, |
|
$hierarchy,$dirorder,$children, |
|
$parent,$titles,$wantform); |
|
$$depth --; |
|
pop(@{$hierarchy}); |
|
} |
|
} |
|
} |
|
} |
|
return $result; |
|
} |
|
|
|
sub archive_hierarchy { |
|
my ($depth,$count,$parent,$children) =@_; |
|
if ((ref($parent) eq 'HASH') && (ref($children) eq 'HASH')) { |
|
if (exists($parent->{$depth})) { |
|
$children->{$parent->{$depth}} .= $count.':'; |
|
} |
|
} |
|
return; |
|
} |
|
|
|
sub archive_row { |
|
my ($is_dir,$item,$currdir,$depth,$count) = @_; |
|
my ($name) = ($item =~ m{([^/]+)$}); |
|
my %choices = &Apache::lonlocal::texthash ( |
|
'display' => 'Add as file', |
|
'dependency' => 'Include as dependency', |
|
'discard' => 'Discard', |
|
); |
|
if ($is_dir) { |
|
$choices{'display'} = &mt('Add as folder'); |
|
} |
|
my $output = &start_data_table_row().'<td align="right">'.$count.'</td>'."\n"; |
|
my $offset = 0; |
|
foreach my $action ('display','dependency','discard') { |
|
$offset ++; |
|
if ($action ne 'display') { |
|
$offset ++; |
|
} |
|
$output .= '<td><span class="LC_nobreak">'. |
|
'<label><input type="radio" name="archive_'.$count. |
|
'" id="archive_'.$action.'_'.$count.'" value="'.$action.'"'; |
|
my $text = $choices{$action}; |
|
if ($is_dir) { |
|
$output .= ' onclick="javascript:propagateCheck(this.form,'."'$count'".');"'; |
|
if ($action eq 'display') { |
|
$text = &mt('Add as folder'); |
|
} |
|
} else { |
|
$output .= ' onclick="javascript:dependencyCheck(this.form,'."$count,$offset".');"'; |
|
|
|
} |
|
$output .= ' /> '.$choices{$action}.'</label></span>'; |
|
if ($action eq 'dependency') { |
|
$output .= '<div id="arc_depon_'.$count.'" style="display:none;">'."\n". |
|
&mt('Used by:').' <select name="archive_dependent_on_'.$count.'" '. |
|
'onchange="propagateSelect(this.form,'."$count,$offset".')">'."\n". |
|
'<option value=""></option>'."\n". |
|
'</select>'."\n". |
|
'</div>'; |
|
} elsif ($action eq 'display') { |
|
$output .= '<div id="arc_title_'.$count.'" style="display:none;">'."\n". |
|
&mt('Title:').' <input type="text" name="archive_title_'.$count.'" id="archive_title_'.$count.'" />'."\n". |
|
'</div>'; |
|
} |
|
$output .= '</td>'; |
|
} |
|
$output .= '<td><input type="hidden" name="archive_content_'.$count.'" value="'. |
|
&HTML::Entities::encode("$currdir/$item",'"<>&').'" />'.(' ' x 2); |
|
for (my $i=0; $i<$depth; $i++) { |
|
$output .= ('<img src="/adm/lonIcons/whitespace1.gif" class="LC_docs_spacer" alt="" />' x2)."\n"; |
|
} |
|
if ($is_dir) { |
|
$output .= '<img src="/adm/lonIcons/navmap.folder.open.gif" alt="" /> '."\n". |
|
'<input type="hidden" name="archive_directory" value="'.$count.'" />'."\n"; |
|
} else { |
|
$output .= '<input type="hidden" name="archive_file" value="'.$count.'" />'."\n"; |
|
} |
|
$output .= ' '.$name.'</td>'."\n". |
|
&end_data_table_row(); |
|
return $output; |
|
} |
|
|
|
sub archive_options_form { |
|
my ($form,$display,$count,$hiddenelem) = @_; |
|
my %lt = &Apache::lonlocal::texthash( |
|
perm => 'Permanently remove archive file?', |
|
hows => 'How should each extracted item be incorporated in the course?', |
|
cont => 'Content actions for all', |
|
addf => 'Add as folder/file', |
|
incd => 'Include as dependency for a displayed file', |
|
disc => 'Discard', |
|
no => 'No', |
|
yes => 'Yes', |
|
save => 'Save', |
|
); |
|
my $output = <<"END"; |
|
<form name="$form" method="post" action=""> |
|
<p><span class="LC_nobreak">$lt{'perm'} |
|
<label> |
|
<input type="radio" name="archivedelete" value="0" checked="checked" />$lt{'no'} |
|
</label> |
|
|
|
<label> |
|
<input type="radio" name="archivedelete" value="1" />$lt{'yes'}</label> |
|
</span> |
|
</p> |
|
<input type="hidden" name="phase" value="decompress_cleanup" /> |
|
<br />$lt{'hows'} |
|
<div class="LC_columnSection"> |
|
<fieldset> |
|
<legend>$lt{'cont'}</legend> |
|
<input type="button" value="$lt{'addf'}" onclick="javascript:checkAll(document.$form,'display');" /> |
|
<input type="button" value="$lt{'incd'}" onclick="javascript:checkAll(document.$form,'dependency');" /> |
|
<input type="button" value="$lt{'disc'}" onclick="javascript:checkAll(document.$form,'discard');" /> |
|
</fieldset> |
|
</div> |
|
END |
|
return $output. |
|
&start_data_table()."\n". |
|
$display."\n". |
|
&end_data_table()."\n". |
|
'<input type="hidden" name="archive_count" value="'.$count.'" />'. |
|
$hiddenelem. |
|
'<br /><input type="submit" name="archive_submit" value="'.$lt{'save'}.'" />'. |
|
'</form>'; |
|
} |
|
|
|
sub archive_javascript { |
|
my ($startcount,$numitems,$titles,$children) = @_; |
|
return unless ((ref($titles) eq 'HASH') && (ref($children) eq 'HASH')); |
|
my $maintitle = $env{'form.comment'}; |
|
my $scripttag = <<START; |
|
<script type="text/javascript"> |
|
// <![CDATA[ |
|
|
|
function checkAll(form,prefix) { |
|
var idstr = new RegExp("^archive_"+prefix+"_\\\\d+\$"); |
|
for (var i=0; i < form.elements.length; i++) { |
|
var id = form.elements[i].id; |
|
if ((id != '') && (id != undefined)) { |
|
if (idstr.test(id)) { |
|
if (form.elements[i].type == 'radio') { |
|
form.elements[i].checked = true; |
|
var nostart = i-$startcount; |
|
var offset = nostart%7; |
|
var count = (nostart-offset)/7; |
|
dependencyCheck(form,count,offset); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
|
|
function propagateCheck(form,count) { |
|
if (count > 0) { |
|
var startelement = $startcount + ((count-1) * 7); |
|
for (var j=1; j<6; j++) { |
|
if ((j != 2) && (j != 4)) { |
|
var item = startelement + j; |
|
if (form.elements[item].type == 'radio') { |
|
if (form.elements[item].checked) { |
|
containerCheck(form,count,j); |
|
break; |
|
} |
|
} |
|
} |
|
} |
|
} |
|
} |
|
|
|
numitems = $numitems |
|
var titles = new Array(numitems); |
|
var parents = new Array(numitems); |
|
for (var i=0; i<numitems; i++) { |
|
parents[i] = new Array; |
|
} |
|
var maintitle = '$maintitle'; |
|
|
|
START |
|
|
|
foreach my $container (sort { $a <=> $b } (keys(%{$children}))) { |
|
my @contents = split(/:/,$children->{$container}); |
|
for (my $i=0; $i<@contents; $i ++) { |
|
$scripttag .= 'parents['.$container.']['.$i.'] = '.$contents[$i]."\n"; |
|
} |
|
} |
|
|
|
foreach my $key (sort { $a <=> $b } (keys(%{$titles}))) { |
|
$scripttag .= "titles[$key] = '".$titles->{$key}."';\n"; |
|
} |
|
|
|
$scripttag .= <<END; |
|
|
|
function containerCheck(form,count,offset) { |
|
if (count > 0) { |
|
dependencyCheck(form,count,offset); |
|
var item = (offset+$startcount)+7*(count-1); |
|
form.elements[item].checked = true; |
|
if(Object.prototype.toString.call(parents[count]) === '[object Array]') { |
|
if (parents[count].length > 0) { |
|
for (var j=0; j<parents[count].length; j++) { |
|
containerCheck(form,parents[count][j],offset); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
|
|
function dependencyCheck(form,count,offset) { |
|
if (count > 0) { |
|
var chosen = (offset+$startcount)+7*(count-1); |
|
var depitem = $startcount + ((count-1) * 7) + 4; |
|
var currtype = form.elements[depitem].type; |
|
if (form.elements[chosen].value == 'dependency') { |
|
document.getElementById('arc_depon_'+count).style.display='block'; |
|
form.elements[depitem].options.length = 0; |
|
form.elements[depitem].options[0] = new Option('Select','',true,true); |
|
for (var i=1; i<=numitems; i++) { |
|
if (i == count) { |
|
continue; |
|
} |
|
var startelement = $startcount + (i-1) * 7; |
|
for (var j=1; j<6; j++) { |
|
if ((j != 2) && (j!= 4)) { |
|
var item = startelement + j; |
|
if (form.elements[item].type == 'radio') { |
|
if (form.elements[item].checked) { |
|
if (form.elements[item].value == 'display') { |
|
var n = form.elements[depitem].options.length; |
|
form.elements[depitem].options[n] = new Option(titles[i],i,false,false); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
} |
|
} else { |
|
document.getElementById('arc_depon_'+count).style.display='none'; |
|
form.elements[depitem].options.length = 0; |
|
form.elements[depitem].options[0] = new Option('Select','',true,true); |
|
} |
|
titleCheck(form,count,offset); |
|
} |
|
} |
|
|
|
function propagateSelect(form,count,offset) { |
|
if (count > 0) { |
|
var item = (1+offset+$startcount)+7*(count-1); |
|
var picked = form.elements[item].options[form.elements[item].selectedIndex].value; |
|
if (Object.prototype.toString.call(parents[count]) === '[object Array]') { |
|
if (parents[count].length > 0) { |
|
for (var j=0; j<parents[count].length; j++) { |
|
containerSelect(form,parents[count][j],offset,picked); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
|
|
function containerSelect(form,count,offset,picked) { |
|
if (count > 0) { |
|
var item = (offset+$startcount)+7*(count-1); |
|
if (form.elements[item].type == 'radio') { |
|
if (form.elements[item].value == 'dependency') { |
|
if (form.elements[item+1].type == 'select-one') { |
|
for (var i=0; i<form.elements[item+1].options.length; i++) { |
|
if (form.elements[item+1].options[i].value == picked) { |
|
form.elements[item+1].selectedIndex = i; |
|
break; |
|
} |
|
} |
|
} |
|
if (Object.prototype.toString.call(parents[count]) === '[object Array]') { |
|
if (parents[count].length > 0) { |
|
for (var j=0; j<parents[count].length; j++) { |
|
containerSelect(form,parents[count][j],offset,picked); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
} |
|
} |
|
|
|
function titleCheck(form,count,offset) { |
|
if (count > 0) { |
|
var chosen = (offset+$startcount)+7*(count-1); |
|
var depitem = $startcount + ((count-1) * 7) + 2; |
|
var currtype = form.elements[depitem].type; |
|
if (form.elements[chosen].value == 'display') { |
|
document.getElementById('arc_title_'+count).style.display='block'; |
|
if ((count==1) && ((parents[count].length > 0) || (numitems == 1))) { |
|
document.getElementById('archive_title_'+count).value=maintitle; |
|
} |
|
} else { |
|
document.getElementById('arc_title_'+count).style.display='none'; |
|
if (currtype == 'text') { |
|
document.getElementById('archive_title_'+count).value=''; |
|
} |
|
} |
|
} |
|
return; |
|
} |
|
|
|
// ]]> |
|
</script> |
|
END |
|
return $scripttag; |
|
} |
|
|
|
sub process_extracted_files { |
|
my ($context,$docudom,$docuname,$destination,$dir_root,$hiddenelem) = @_; |
|
my $numitems = $env{'form.archive_count'}; |
|
return unless ($numitems); |
|
my @ids=&Apache::lonnet::current_machine_ids(); |
|
my ($prefix,$pathtocheck,$dir,$ishome,$error,$warning,%toplevelitems,%is_dir, |
|
%folders,%containers,%mapinner,%prompttofetch); |
|
my $docuhome = &Apache::lonnet::homeserver($docuname,$docudom); |
|
if (grep(/^\Q$docuhome\E$/,@ids)) { |
|
$prefix = &LONCAPA::propath($docudom,$docuname); |
|
$pathtocheck = "$dir_root/$destination"; |
|
$dir = $dir_root; |
|
$ishome = 1; |
|
} else { |
|
$prefix = $Apache::lonnet::perlvar{'lonDocRoot'}; |
|
$pathtocheck = "$dir_root/$docudom/$docuname/$destination"; |
|
$dir = "$dir_root/$docudom/$docuname"; |
|
} |
|
my $currdir = "$dir_root/$destination"; |
|
(my $docstype,$mapinner{'0'}) = ($destination =~ m{^(docs|supplemental)/(\w+)/}); |
|
if ($env{'form.folderpath'}) { |
|
my @items = split('&',$env{'form.folderpath'}); |
|
$folders{'0'} = $items[-2]; |
|
if ($env{'form.folderpath'} =~ /\:1$/) { |
|
$containers{'0'}='page'; |
|
} else { |
|
$containers{'0'}='sequence'; |
|
} |
|
} |
|
my @archdirs = &get_env_multiple('form.archive_directory'); |
|
if ($numitems) { |
|
for (my $i=1; $i<=$numitems; $i++) { |
|
my $path = $env{'form.archive_content_'.$i}; |
|
if ($path =~ m{^\Q$pathtocheck\E/([^/]+)$}) { |
|
my $item = $1; |
|
$toplevelitems{$item} = $i; |
|
if (grep(/^\Q$i\E$/,@archdirs)) { |
|
$is_dir{$item} = 1; |
|
} |
|
} |
|
} |
|
} |
|
my ($output,%children,%parent,%titles,%dirorder,$result); |
|
if (keys(%toplevelitems) > 0) { |
|
my @contents = sort(keys(%toplevelitems)); |
|
(my $count,undef) = &get_extracted($docudom,$docuname,$currdir,\%is_dir,\%children, |
|
\%parent,\@contents,\%dirorder,\%titles); |
|
} |
|
my (%referrer,%orphaned,%todelete,%todeletedir,%newdest,%newseqid); |
|
if ($numitems) { |
|
for (my $i=1; $i<=$numitems; $i++) { |
|
next if ($env{'form.archive_'.$i} eq 'dependency'); |
|
my $path = $env{'form.archive_content_'.$i}; |
|
if ($path =~ /^\Q$pathtocheck\E/) { |
|
if ($env{'form.archive_'.$i} eq 'discard') { |
|
if ($prefix ne '' && $path ne '') { |
|
if (-e $prefix.$path) { |
|
if ((@archdirs > 0) && |
|
(grep(/^\Q$i\E$/,@archdirs))) { |
|
$todeletedir{$prefix.$path} = 1; |
|
} else { |
|
$todelete{$prefix.$path} = 1; |
|
} |
|
} |
|
} |
|
} elsif ($env{'form.archive_'.$i} eq 'display') { |
|
my ($docstitle,$title,$url,$outer); |
|
($title) = ($path =~ m{/([^/]+)$}); |
|
$docstitle = $env{'form.archive_title_'.$i}; |
|
if ($docstitle eq '') { |
|
$docstitle = $title; |
|
} |
|
$outer = 0; |
|
if (ref($dirorder{$i}) eq 'ARRAY') { |
|
if (@{$dirorder{$i}} > 0) { |
|
foreach my $item (reverse(@{$dirorder{$i}})) { |
|
if ($env{'form.archive_'.$item} eq 'display') { |
|
$outer = $item; |
|
last; |
|
} |
|
} |
|
} |
|
} |
|
my ($errtext,$fatal) = |
|
&LONCAPA::map::mapread('/uploaded/'.$docudom.'/'.$docuname. |
|
'/'.$folders{$outer}.'.'. |
|
$containers{$outer}); |
|
next if ($fatal); |
|
if ((@archdirs > 0) && (grep(/^\Q$i\E$/,@archdirs))) { |
|
if ($context eq 'coursedocs') { |
|
$mapinner{$i} = time; |
|
$folders{$i} = 'default_'.$mapinner{$i}; |
|
$containers{$i} = 'sequence'; |
|
my $url = '/uploaded/'.$docudom.'/'.$docuname.'/'. |
|
$folders{$i}.'.'.$containers{$i}; |
|
my $newidx = &LONCAPA::map::getresidx(); |
|
$LONCAPA::map::resources[$newidx]= |
|
$docstitle.':'.$url.':false:normal:res'; |
|
push(@LONCAPA::map::order,$newidx); |
|
my ($outtext,$errtext) = |
|
&LONCAPA::map::storemap('/uploaded/'.$docudom.'/'. |
|
$docuname.'/'.$folders{$outer}. |
|
'.'.$containers{$outer},1,1); |
|
$newseqid{$i} = $newidx; |
|
unless ($errtext) { |
|
$result .= '<li>'.&mt('Folder: [_1] added to course',$docstitle).'</li>'."\n"; |
|
} |
|
} |
|
} else { |
|
if ($context eq 'coursedocs') { |
|
my $newidx=&LONCAPA::map::getresidx(); |
|
my $url = '/uploaded/'.$docudom.'/'.$docuname.'/'. |
|
$docstype.'/'.$mapinner{$outer}.'/'.$newidx.'/'. |
|
$title; |
|
if (!-e "$prefix$dir/$docstype/$mapinner{$outer}") { |
|
mkdir("$prefix$dir/$docstype/$mapinner{$outer}",0755); |
|
} |
|
if (!-e "$prefix$dir/$docstype/$mapinner{$outer}/$newidx") { |
|
mkdir("$prefix$dir/$docstype/$mapinner{$outer}/$newidx"); |
|
} |
|
if (-e "$prefix$dir/$docstype/$mapinner{$outer}/$newidx") { |
|
system("mv $prefix$path $prefix$dir/$docstype/$mapinner{$outer}/$newidx/$title"); |
|
$newdest{$i} = "$prefix$dir/$docstype/$mapinner{$outer}/$newidx"; |
|
unless ($ishome) { |
|
my $fetch = "$newdest{$i}/$title"; |
|
$fetch =~ s/^\Q$prefix$dir\E//; |
|
$prompttofetch{$fetch} = 1; |
|
} |
|
} |
|
$LONCAPA::map::resources[$newidx]= |
|
$docstitle.':'.$url.':false:normal:res'; |
|
push(@LONCAPA::map::order, $newidx); |
|
my ($outtext,$errtext)= |
|
&LONCAPA::map::storemap('/uploaded/'.$docudom.'/'. |
|
$docuname.'/'.$folders{$outer}. |
|
'.'.$containers{$outer},1,1); |
|
unless ($errtext) { |
|
if (-e "$prefix$dir/$docstype/$mapinner{$outer}/$newidx/$title") { |
|
$result .= '<li>'.&mt('File: [_1] added to course',$docstitle).'</li>'."\n"; |
|
} |
|
} |
|
} |
|
} |
|
} |
|
} else { |
|
$warning .= &mt('Item extracted from archive: [_1] has unexpected path.',$path).'<br />'; |
|
} |
|
} |
|
for (my $i=1; $i<=$numitems; $i++) { |
|
next unless ($env{'form.archive_'.$i} eq 'dependency'); |
|
my $path = $env{'form.archive_content_'.$i}; |
|
if ($path =~ /^\Q$pathtocheck\E/) { |
|
my ($title) = ($path =~ m{/([^/]+)$}); |
|
$referrer{$i} = $env{'form.archive_dependent_on_'.$i}; |
|
if ($env{'form.archive_'.$referrer{$i}} eq 'display') { |
|
if (ref($dirorder{$i}) eq 'ARRAY') { |
|
my ($itemidx,$fullpath,$relpath); |
|
if (ref($dirorder{$referrer{$i}}) eq 'ARRAY') { |
|
my $container = $dirorder{$referrer{$i}}->[-1]; |
|
for (my $j=0; $j<@{$dirorder{$i}}; $j++) { |
|
if ($dirorder{$i}->[$j] eq $container) { |
|
$itemidx = $j; |
|
} |
|
} |
|
} |
|
if ($itemidx eq '') { |
|
$itemidx = 0; |
|
} |
|
if (grep(/^\Q$referrer{$i}\E$/,@archdirs)) { |
|
if ($mapinner{$referrer{$i}}) { |
|
$fullpath = "$prefix$dir/$docstype/$mapinner{$referrer{$i}}"; |
|
for (my $j=$itemidx; $j<@{$dirorder{$i}}; $j++) { |
|
if (grep(/^\Q$dirorder{$i}->[$j]\E$/,@archdirs)) { |
|
unless (defined($newseqid{$dirorder{$i}->[$j]})) { |
|
$fullpath .= '/'.$titles{$dirorder{$i}->[$j]}; |
|
$relpath .= '/'.$titles{$dirorder{$i}->[$j]}; |
|
if (!-e $fullpath) { |
|
mkdir($fullpath,0755); |
|
} |
|
} |
|
} else { |
|
last; |
|
} |
|
} |
|
} |
|
} elsif ($newdest{$referrer{$i}}) { |
|
$fullpath = $newdest{$referrer{$i}}; |
|
for (my $j=$itemidx; $j<@{$dirorder{$i}}; $j++) { |
|
if ($env{'form.archive_'.$dirorder{$i}->[$j]} eq 'discard') { |
|
$orphaned{$i} = $env{'form.archive_'.$dirorder{$i}->[$j]}; |
|
last; |
|
} elsif (grep(/^\Q$dirorder{$i}->[$j]\E$/,@archdirs)) { |
|
unless (defined($newseqid{$dirorder{$i}->[$j]})) { |
|
$fullpath .= '/'.$titles{$dirorder{$i}->[$j]}; |
|
$relpath .= '/'.$titles{$dirorder{$i}->[$j]}; |
|
if (!-e $fullpath) { |
|
mkdir($fullpath,0755); |
|
} |
|
} |
|
} else { |
|
last; |
|
} |
|
} |
|
} |
|
if ($fullpath ne '') { |
|
if (-e "$prefix$path") { |
|
system("mv $prefix$path $fullpath/$title"); |
|
} |
|
if (-e "$fullpath/$title") { |
|
my $showpath; |
|
if ($relpath ne '') { |
|
$showpath = "$relpath/$title"; |
|
} else { |
|
$showpath = "/$title"; |
|
} |
|
$result .= '<li>'.&mt('[_1] included as a dependency',$showpath).'</li>'."\n"; |
|
} |
|
unless ($ishome) { |
|
my $fetch = "$fullpath/$title"; |
|
$fetch =~ s/^\Q$prefix$dir\E//; |
|
$prompttofetch{$fetch} = 1; |
|
} |
|
} |
|
} |
|
} elsif ($env{'form.archive_'.$referrer{$i}} eq 'discard') { |
|
$warning .= &mt('[_1] is a dependency of [_2], which was discarded.', |
|
$path,$env{'form.archive_content_'.$referrer{$i}}).'<br />'; |
|
} |
|
} else { |
|
$warning .= &mt('Item extracted from archive: [_1] has unexpected path.',$path).'<br />'; |
|
} |
|
} |
|
if (keys(%todelete)) { |
|
foreach my $key (keys(%todelete)) { |
|
unlink($key); |
|
} |
|
} |
|
if (keys(%todeletedir)) { |
|
foreach my $key (keys(%todeletedir)) { |
|
rmdir($key); |
|
} |
|
} |
|
foreach my $dir (sort(keys(%is_dir))) { |
|
if (($pathtocheck ne '') && ($dir ne '')) { |
|
&cleanup_empty_dirs($prefix."$pathtocheck/$dir"); |
|
} |
|
} |
|
if ($result ne '') { |
|
$output .= '<ul>'."\n". |
|
$result."\n". |
|
'</ul>'; |
|
} |
|
unless ($ishome) { |
|
my $replicationfail; |
|
foreach my $item (keys(%prompttofetch)) { |
|
my $fetchresult= &Apache::lonnet::reply('fetchuserfile:'.$item,$docuhome); |
|
unless ($fetchresult eq 'ok') { |
|
$replicationfail .= '<li>'.$item.'</li>'."\n"; |
|
} |
|
} |
|
if ($replicationfail) { |
|
$output .= '<p class="LC_error">'. |
|
&mt('Course home server failed to retrieve:').'<ul>'. |
|
$replicationfail. |
|
'</ul></p>'; |
|
} |
|
} |
|
} else { |
|
$warning = &mt('No items found in archive.'); |
|
} |
|
if ($error) { |
|
$output .= '<p class="LC_error">'.&mt('Not extracted.').'<br />'. |
|
$error.'</p>'."\n"; |
|
} |
|
if ($warning) { |
|
$output .= '<p class="LC_warning">'.$warning.'</p>'."\n"; |
|
} |
|
return $output; |
|
} |
|
|
|
sub cleanup_empty_dirs { |
|
my ($path) = @_; |
|
if (($path ne '') && (-d $path)) { |
|
if (opendir(my $dirh,$path)) { |
|
my @dircontents = grep(!/^\./,readdir($dirh)); |
|
my $numitems = 0; |
|
foreach my $item (@dircontents) { |
|
if (-d "$path/$item") { |
|
&recurse_dirs("$path/$item"); |
|
if (-e "$path/$item") { |
|
$numitems ++; |
|
} |
|
} else { |
|
$numitems ++; |
|
} |
|
} |
|
if ($numitems == 0) { |
|
rmdir($path); |
|
} |
|
closedir($dirh); |
|
} |
|
} |
|
return; |
|
} |
|
|
|
=pod |
|
|
|
=item &get_folder_hierarchy() |
|
|
|
Provides hierarchy of names of folders/sub-folders containing the current |
|
item, |
|
|
|
Inputs: 3 |
|
- $navmap - navmaps object |
|
|
|
- $map - url for map (either the trigger itself, or map containing |
|
the resource, which is the trigger). |
|
|
|
- $showitem - 1 => show title for map itself; 0 => do not show. |
|
|
|
Outputs: 1 @pathitems - array of folder/subfolder names. |
|
|
|
=cut |
|
|
|
sub get_folder_hierarchy { |
|
my ($navmap,$map,$showitem) = @_; |
|
my @pathitems; |
|
if (ref($navmap)) { |
|
my $mapres = $navmap->getResourceByUrl($map); |
|
if (ref($mapres)) { |
|
my $pcslist = $mapres->map_hierarchy(); |
|
if ($pcslist ne '') { |
|
my @pcs = split(/,/,$pcslist); |
|
foreach my $pc (@pcs) { |
|
if ($pc == 1) { |
|
push(@pathitems,&mt('Main Course Documents')); |
|
} else { |
|
my $res = $navmap->getByMapPc($pc); |
|
if (ref($res)) { |
|
my $title = $res->compTitle(); |
|
$title =~ s/\W+/_/g; |
|
if ($title ne '') { |
|
push(@pathitems,$title); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
if ($showitem) { |
|
if ($mapres->{ID} eq '0.0') { |
|
push(@pathitems,&mt('Main Course Documents')); |
|
} else { |
|
my $maptitle = $mapres->compTitle(); |
|
$maptitle =~ s/\W+/_/g; |
|
if ($maptitle ne '') { |
|
push(@pathitems,$maptitle); |
|
} |
|
} |
|
} |
|
} |
|
} |
|
return @pathitems; |
|
} |
|
|
=pod |
=pod |
|
|
=item * &get_turnedin_filepath() |
=item * &get_turnedin_filepath() |
Line 11331 sub init_user_environment {
|
Line 13784 sub init_user_environment {
|
|
|
# See if old ID present, if so, remove |
# See if old ID present, if so, remove |
|
|
my ($filename,$cookie,$userroles); |
my ($filename,$cookie,$userroles,$firstaccenv,$timerintenv); |
my $now=time; |
my $now=time; |
|
|
if ($public) { |
if ($public) { |
Line 11369 sub init_user_environment {
|
Line 13822 sub init_user_environment {
|
|
|
# Initialize roles |
# Initialize roles |
|
|
$userroles=&Apache::lonnet::rolesinit($domain,$username,$authhost); |
($userroles,$firstaccenv,$timerintenv) = |
|
&Apache::lonnet::rolesinit($domain,$username,$authhost); |
} |
} |
# ------------------------------------ Check browser type and MathML capability |
# ------------------------------------ Check browser type and MathML capability |
|
|
Line 11430 sub init_user_environment {
|
Line 13884 sub init_user_environment {
|
%domdef = &Apache::lonnet::get_domain_defaults($domain); |
%domdef = &Apache::lonnet::get_domain_defaults($domain); |
} |
} |
|
|
foreach my $tool ('aboutme','blog','portfolio') { |
foreach my $tool ('aboutme','blog','webdav','portfolio') { |
$userenv{'availabletools.'.$tool} = |
$userenv{'availabletools.'.$tool} = |
&Apache::lonnet::usertools_access($username,$domain,$tool,'reload', |
&Apache::lonnet::usertools_access($username,$domain,$tool,'reload', |
undef,\%userenv,\%domdef,\%is_adv); |
undef,\%userenv,\%domdef,\%is_adv); |
Line 11443 sub init_user_environment {
|
Line 13897 sub init_user_environment {
|
\%userenv,\%domdef,\%is_adv); |
\%userenv,\%domdef,\%is_adv); |
} |
} |
|
|
|
$userenv{'canrequest.author'} = |
|
&Apache::lonnet::usertools_access($username,$domain,'requestauthor', |
|
'reload','requestauthor', |
|
\%userenv,\%domdef,\%is_adv); |
|
my %reqauthor = &Apache::lonnet::get('requestauthor',['author_status','author'], |
|
$domain,$username); |
|
my $reqstatus = $reqauthor{'author_status'}; |
|
if ($reqstatus eq 'approval' || $reqstatus eq 'approved') { |
|
if (ref($reqauthor{'author'}) eq 'HASH') { |
|
$userenv{'requestauthorqueued'} = $reqstatus.':'. |
|
$reqauthor{'author'}{'timestamp'}; |
|
} |
|
} |
|
|
$env{'user.environment'} = "$lonids/$cookie.id"; |
$env{'user.environment'} = "$lonids/$cookie.id"; |
|
|
if (tie(my %disk_env,'GDBM_File',"$lonids/$cookie.id", |
if (tie(my %disk_env,'GDBM_File',"$lonids/$cookie.id", |
&GDBM_WRCREAT(),0640)) { |
&GDBM_WRCREAT(),0640)) { |
&_add_to_env(\%disk_env,\%initial_env); |
&_add_to_env(\%disk_env,\%initial_env); |
&_add_to_env(\%disk_env,\%userenv,'environment.'); |
&_add_to_env(\%disk_env,\%userenv,'environment.'); |
&_add_to_env(\%disk_env,$userroles); |
&_add_to_env(\%disk_env,$userroles); |
|
if (ref($firstaccenv) eq 'HASH') { |
|
&_add_to_env(\%disk_env,$firstaccenv); |
|
} |
|
if (ref($timerintenv) eq 'HASH') { |
|
&_add_to_env(\%disk_env,$timerintenv); |
|
} |
if (ref($args->{'extra_env'})) { |
if (ref($args->{'extra_env'})) { |
&_add_to_env(\%disk_env,$args->{'extra_env'}); |
&_add_to_env(\%disk_env,$args->{'extra_env'}); |
} |
} |
Line 11485 sub get_symb {
|
Line 13959 sub get_symb {
|
my $symb=($env{'form.symb'} ne '' ? $env{'form.symb'} : (&Apache::lonnet::symbread($url))); |
my $symb=($env{'form.symb'} ne '' ? $env{'form.symb'} : (&Apache::lonnet::symbread($url))); |
if ($symb eq '') { |
if ($symb eq '') { |
if (!$silent) { |
if (!$silent) { |
$request->print("Unable to handle ambiguous references:$url:."); |
if (ref($request)) { |
|
$request->print("Unable to handle ambiguous references:$url:."); |
|
} |
return (); |
return (); |
} |
} |
} |
} |
Line 11549 sub build_release_hashes {
|
Line 14025 sub build_release_hashes {
|
return; |
return; |
} |
} |
|
|
|
sub update_content_constraints { |
|
my ($cdom,$cnum,$chome,$cid) = @_; |
|
my %curr_reqd_hash = &Apache::lonnet::userenvironment($cdom,$cnum,'internal.releaserequired'); |
|
my ($reqdmajor,$reqdminor) = split(/\./,$curr_reqd_hash{'internal.releaserequired'}); |
|
my %checkresponsetypes; |
|
foreach my $key (keys(%Apache::lonnet::needsrelease)) { |
|
my ($item,$name,$value) = split(/:/,$key); |
|
if ($item eq 'resourcetag') { |
|
if ($name eq 'responsetype') { |
|
$checkresponsetypes{$value} = $Apache::lonnet::needsrelease{$key} |
|
} |
|
} |
|
} |
|
my $navmap = Apache::lonnavmaps::navmap->new(); |
|
if (defined($navmap)) { |
|
my %allresponses; |
|
foreach my $res ($navmap->retrieveResources(undef,sub { $_[0]->is_problem() },1,0)) { |
|
my %responses = $res->responseTypes(); |
|
foreach my $key (keys(%responses)) { |
|
next unless(exists($checkresponsetypes{$key})); |
|
$allresponses{$key} += $responses{$key}; |
|
} |
|
} |
|
foreach my $key (keys(%allresponses)) { |
|
my ($major,$minor) = split(/\./,$checkresponsetypes{$key}); |
|
if (($major > $reqdmajor) || ($major == $reqdmajor && $minor > $reqdminor)) { |
|
($reqdmajor,$reqdminor) = ($major,$minor); |
|
} |
|
} |
|
undef($navmap); |
|
} |
|
unless (($reqdmajor eq '') && ($reqdminor eq '')) { |
|
&Apache::lonnet::update_released_required($reqdmajor.'.'.$reqdminor,$cdom,$cnum,$chome,$cid); |
|
} |
|
return; |
|
} |
|
|
|
sub parse_supplemental_title { |
|
my ($title) = @_; |
|
|
|
my ($foldertitle,$renametitle); |
|
if ($title =~ /&&&/) { |
|
$title = &HTML::Entites::decode($title); |
|
} |
|
if ($title =~ m/^(\d+)___&&&___($match_username)___&&&___($match_domain)___&&&___(.*)$/) { |
|
$renametitle=$4; |
|
my ($time,$uname,$udom) = ($1,$2,$3); |
|
$foldertitle=&Apache::lontexconvert::msgtexconverted($4); |
|
my $name = &plainname($uname,$udom); |
|
$name = &HTML::Entities::encode($name,'"<>&\''); |
|
$renametitle = &HTML::Entities::encode($renametitle,'"<>&\''); |
|
$title='<i>'.&Apache::lonlocal::locallocaltime($time).'</i> '. |
|
$name.': <br />'.$foldertitle; |
|
} |
|
if (wantarray) { |
|
return ($title,$foldertitle,$renametitle); |
|
} |
|
return $title; |
|
} |
|
|
|
sub captcha_display { |
|
my ($context,$lonhost) = @_; |
|
my ($output,$error); |
|
my ($captcha,$pubkey,$privkey) = &get_captcha_config($context,$lonhost); |
|
if ($captcha eq 'original') { |
|
$output = &create_captcha(); |
|
unless ($output) { |
|
$error = 'captcha'; |
|
} |
|
} elsif ($captcha eq 'recaptcha') { |
|
$output = &create_recaptcha($pubkey); |
|
unless ($output) { |
|
$error = 'recaptcha'; |
|
} |
|
} |
|
return ($output,$error); |
|
} |
|
|
|
sub captcha_response { |
|
my ($context,$lonhost) = @_; |
|
my ($captcha_chk,$captcha_error); |
|
my ($captcha,$pubkey,$privkey) = &get_captcha_config($context,$lonhost); |
|
if ($captcha eq 'original') { |
|
($captcha_chk,$captcha_error) = &check_captcha(); |
|
} elsif ($captcha eq 'recaptcha') { |
|
$captcha_chk = &check_recaptcha($privkey); |
|
} else { |
|
$captcha_chk = 1; |
|
} |
|
return ($captcha_chk,$captcha_error); |
|
} |
|
|
|
sub get_captcha_config { |
|
my ($context,$lonhost) = @_; |
|
my ($captcha,$pubkey,$privkey,$hashtocheck); |
|
my $hostname = &Apache::lonnet::hostname($lonhost); |
|
my $serverhomeID = &Apache::lonnet::get_server_homeID($hostname); |
|
my $serverhomedom = &Apache::lonnet::host_domain($serverhomeID); |
|
if ($context eq 'usercreation') { |
|
my %domconfig = &Apache::lonnet::get_dom('configuration',[$context],$serverhomedom); |
|
if (ref($domconfig{$context}) eq 'HASH') { |
|
$hashtocheck = $domconfig{$context}{'cancreate'}; |
|
if (ref($hashtocheck) eq 'HASH') { |
|
if ($hashtocheck->{'captcha'} eq 'recaptcha') { |
|
if (ref($hashtocheck->{'recaptchakeys'}) eq 'HASH') { |
|
$pubkey = $hashtocheck->{'recaptchakeys'}{'public'}; |
|
$privkey = $hashtocheck->{'recaptchakeys'}{'private'}; |
|
} |
|
if ($privkey && $pubkey) { |
|
$captcha = 'recaptcha'; |
|
} else { |
|
$captcha = 'original'; |
|
} |
|
} elsif ($hashtocheck->{'captcha'} ne 'notused') { |
|
$captcha = 'original'; |
|
} |
|
} |
|
} else { |
|
$captcha = 'captcha'; |
|
} |
|
} elsif ($context eq 'login') { |
|
my %domconfhash = &Apache::loncommon::get_domainconf($serverhomedom); |
|
if ($domconfhash{$serverhomedom.'.login.captcha'} eq 'recaptcha') { |
|
$pubkey = $domconfhash{$serverhomedom.'.login.recaptchakeys_public'}; |
|
$privkey = $domconfhash{$serverhomedom.'.login.recaptchakeys_private'}; |
|
if ($privkey && $pubkey) { |
|
$captcha = 'recaptcha'; |
|
} else { |
|
$captcha = 'original'; |
|
} |
|
} elsif ($domconfhash{$serverhomedom.'.login.captcha'} eq 'original') { |
|
$captcha = 'original'; |
|
} |
|
} |
|
return ($captcha,$pubkey,$privkey); |
|
} |
|
|
|
sub create_captcha { |
|
my %captcha_params = &captcha_settings(); |
|
my ($output,$maxtries,$tries) = ('',10,0); |
|
while ($tries < $maxtries) { |
|
$tries ++; |
|
my $captcha = Authen::Captcha->new ( |
|
output_folder => $captcha_params{'output_dir'}, |
|
data_folder => $captcha_params{'db_dir'}, |
|
); |
|
my $md5sum = $captcha->generate_code($captcha_params{'numchars'}); |
|
|
|
if (-e $Apache::lonnet::perlvar{'lonCaptchaDir'}.'/'.$md5sum.'.png') { |
|
$output = '<input type="hidden" name="crypt" value="'.$md5sum.'" />'."\n". |
|
&mt('Type in the letters/numbers shown below').' '. |
|
'<input type="text" size="5" name="code" value="" /><br />'. |
|
'<img src="'.$captcha_params{'www_output_dir'}.'/'.$md5sum.'.png" />'; |
|
last; |
|
} |
|
} |
|
return $output; |
|
} |
|
|
|
sub captcha_settings { |
|
my %captcha_params = ( |
|
output_dir => $Apache::lonnet::perlvar{'lonCaptchaDir'}, |
|
www_output_dir => "/captchaspool", |
|
db_dir => $Apache::lonnet::perlvar{'lonCaptchaDb'}, |
|
numchars => '5', |
|
); |
|
return %captcha_params; |
|
} |
|
|
|
sub check_captcha { |
|
my ($captcha_chk,$captcha_error); |
|
my $code = $env{'form.code'}; |
|
my $md5sum = $env{'form.crypt'}; |
|
my %captcha_params = &captcha_settings(); |
|
my $captcha = Authen::Captcha->new( |
|
output_folder => $captcha_params{'output_dir'}, |
|
data_folder => $captcha_params{'db_dir'}, |
|
); |
|
my $captcha_chk = $captcha->check_code($code,$md5sum); |
|
my %captcha_hash = ( |
|
0 => 'Code not checked (file error)', |
|
-1 => 'Failed: code expired', |
|
-2 => 'Failed: invalid code (not in database)', |
|
-3 => 'Failed: invalid code (code does not match crypt)', |
|
); |
|
if ($captcha_chk != 1) { |
|
$captcha_error = $captcha_hash{$captcha_chk} |
|
} |
|
return ($captcha_chk,$captcha_error); |
|
} |
|
|
|
sub create_recaptcha { |
|
my ($pubkey) = @_; |
|
my $captcha = Captcha::reCAPTCHA->new; |
|
return $captcha->get_options_setter({theme => 'white'})."\n". |
|
$captcha->get_html($pubkey). |
|
&mt('If either word is hard to read, [_1] will replace them.', |
|
'<image src="/res/adm/pages/refresh.gif" alt="reCAPTCHA refresh" />'). |
|
'<br /><br />'; |
|
} |
|
|
|
sub check_recaptcha { |
|
my ($privkey) = @_; |
|
my $captcha_chk; |
|
my $captcha = Captcha::reCAPTCHA->new; |
|
my $captcha_result = |
|
$captcha->check_answer( |
|
$privkey, |
|
$ENV{'REMOTE_ADDR'}, |
|
$env{'form.recaptcha_challenge_field'}, |
|
$env{'form.recaptcha_response_field'}, |
|
); |
|
if ($captcha_result->{is_valid}) { |
|
$captcha_chk = 1; |
|
} |
|
return $captcha_chk; |
|
} |
|
|
=pod |
=pod |
|
|
=back |
=back |