--- loncom/interface/domainprefs.pm 2023/06/01 18:09:59 1.424 +++ loncom/interface/domainprefs.pm 2024/02/27 15:48:01 1.436 @@ -1,7 +1,7 @@ # The LearningOnline Network with CAPA # Handler to set domain-wide configuration settings # -# $Id: domainprefs.pm,v 1.424 2023/06/01 18:09:59 raeburn Exp $ +# $Id: domainprefs.pm,v 1.436 2024/02/27 15:48:01 raeburn Exp $ # # Copyright Michigan State University Board of Trustees # @@ -95,8 +95,7 @@ about default quota sizes for portfolio institutional affiliation in the domain (e.g., Faculty, Staff, Student etc.), but is now also used to manage availability of user tools: i.e., blogs, aboutme page, and portfolios, and the course request tool, -used by course owners to request creation of a course, and to display/store -default quota sizes for Authoring Spaces. +used by course owners to request creation of a course. Outputs: 1 @@ -105,7 +104,7 @@ $datatable - HTML containing form eleme In the case of course requests, radio buttons are displayed for each institutional affiliate type (and also default, and _LC_adv) for each of the course types (official, unofficial, community, textbook, placement, and lti). -In each case the radio buttons allow the selection of one of four values: +In each case the radio buttons allow the selection of one of four values: 0, approval, validate, autolimit=N (where N is blank, or a positive integer). which have the following effects: @@ -223,7 +222,8 @@ sub handler { 'coursedefaults','usersessions','loadbalancing', 'requestauthor','selfenrollment','inststatus', 'ltitools','toolsec','ssl','trust','lti','ltisec', - 'privacy','passwords','proctoring','wafproxy','ipaccess'],$dom); + 'privacy','passwords','proctoring','wafproxy', + 'ipaccess','authordefaults'],$dom); my %encconfig = &Apache::lonnet::get_dom('encconfig',['ltitools','lti','proctoring','linkprot'],$dom,undef,1); my ($checked_is_home,$is_home); @@ -236,7 +236,7 @@ sub handler { $is_home = 1; } } - $checked_is_home = 1; + $checked_is_home = 1; foreach my $id (keys(%{$domconfig{'ltitools'}})) { if ((ref($domconfig{'ltitools'}{$id}) eq 'HASH') && (ref($encconfig{'ltitools'}{$id}) eq 'HASH')) { @@ -305,8 +305,8 @@ sub handler { 'contacts','privacy','usercreation','selfcreation', 'usermodification','scantron','requestcourses','requestauthor', 'coursecategories','serverstatuses','helpsettings','coursedefaults', - 'ltitools','proctoring','selfenrollment','usersessions','ssl', - 'trust','lti'); + 'authordefaults','ltitools','proctoring','selfenrollment', + 'usersessions','ssl','trust','lti'); my %existing; if (ref($domconfig{'loadbalancing'}) eq 'HASH') { %existing = %{$domconfig{'loadbalancing'}}; @@ -382,11 +382,11 @@ sub handler { modify => \&modify_passwords, }, 'quotas' => - { text => 'Blogs, personal pages/timezones, webDAV/quotas, portfolio', + { text => 'Blogs, personal pages/timezones, portfolio/quotas', help => 'Domain_Configuration_Quotas', header => [{col1 => 'User affiliation', col2 => 'Available tools', - col3 => 'Quotas, MB; (Authoring requires role)',}], + col3 => 'Portfolio quota (MB)',}], print => \&print_quotas, modify => \&modify_quotas, }, @@ -568,7 +568,7 @@ sub handler { modify => \&modify_selfenrollment, }, 'privacy' => - {text => 'Availability of User Information', + {text => 'Role assignments and user privacy', help => 'Domain_Configuration_User_Privacy', header => [{col1 => 'Role assigned in different domain', col2 => 'Approval options'}, @@ -604,7 +604,7 @@ sub handler { print => \&print_loadbalancing, modify => \&modify_loadbalancing, }, - 'ltitools' => + 'ltitools' => {text => 'External Tools (LTI)', help => 'Domain_Configuration_LTI_Tools', header => [{col1 => 'Encryption of shared secrets', @@ -662,13 +662,15 @@ sub handler { print => \&print_trust, modify => \&modify_trust, }, - 'lti' => + 'lti' => {text => 'LTI Link Protection and LTI Consumers', help => 'Domain_Configuration_LTI_Provider', header => [{col1 => 'Encryption of shared secrets', col2 => 'Settings'}, - {col1 => 'Rules for shared secrets', + {col1 => 'Rules for shared secrets', col2 => 'Settings'}, + {col1 => 'Link Protectors in Courses', + col2 => 'Values'}, {col1 => 'Link Protectors', col2 => 'Settings'}, {col1 => 'Consumers', @@ -676,7 +678,7 @@ sub handler { print => \&print_lti, modify => \&modify_lti, }, - 'ipaccess' => + 'ipaccess' => {text => 'IP-based access control', help => 'Domain_Configuration_IP_Access', header => [{col1 => 'Setting', @@ -684,6 +686,16 @@ sub handler { print => \&print_ipaccess, modify => \&modify_ipaccess, }, + 'authordefaults' => + {text => 'Authoring Space defaults', + help => 'Domain_Configuration_Author_Defaults', + header => [{col1 => 'Defaults which can be overridden by Author', + col2 => 'Settings',}, + {col1 => 'Defaults which can be overridden by a Dom. Coord.', + col2 => 'Settings',},], + print => \&print_authordefaults, + modify => \&modify_authordefaults, + }, ); if (keys(%servers) > 1) { $prefs{'login'} = { text => 'Log-in page options', @@ -882,13 +894,15 @@ sub process_changes { } elsif ($action eq 'lti') { $output = &modify_lti($r,$dom,$action,$lastactref,%domconfig); } elsif ($action eq 'privacy') { - $output = &modify_privacy($dom,%domconfig); + $output = &modify_privacy($dom,$lastactref,%domconfig); } elsif ($action eq 'passwords') { $output = &modify_passwords($r,$dom,$confname,$lastactref,%domconfig); } elsif ($action eq 'wafproxy') { $output = &modify_wafproxy($dom,$action,$lastactref,%domconfig); } elsif ($action eq 'ipaccess') { $output = &modify_ipaccess($dom,$lastactref,%domconfig); + } elsif ($action eq 'authordefaults') { + $output = &modify_authordefaults($dom,$lastactref,%domconfig); } return $output; } @@ -917,7 +931,7 @@ sub print_config_box { &Apache::lonuserutils::custom_role_privs(\%privs,\%full,\%levels,\%levelscurrent); my @templateroles = &Apache::lonuserutils::custom_template_roles($context,$crstype); $output = - &Apache::lonuserutils::custom_roledefs_js($context,$crstype,$formname,\%full, + &Apache::lonuserutils::custom_roledefs_js($context,$crstype,$formname,\%full, \@templateroles); } elsif ($action eq 'ltitools') { $output .= &Apache::lonconfigsettings::ltitools_javascript($settings); @@ -936,6 +950,8 @@ sub print_config_box { $output .= &saml_javascript(); } elsif ($action eq 'ipaccess') { $output .= &ipaccess_javascript($settings); + } elsif ($action eq 'authordefaults') { + $output .= &authordefaults_javascript(); } $output .= ' @@ -978,7 +994,7 @@ sub print_config_box { ($action eq 'selfenrollment') || ($action eq 'usersessions') || ($action eq 'ssl') || ($action eq 'directorysrch') || ($action eq 'trust') || ($action eq 'helpsettings') || ($action eq 'contacts') || ($action eq 'privacy') || ($action eq 'wafproxy') || - ($action eq 'lti') || ($action eq 'ltitools')) { + ($action eq 'lti') || ($action eq 'ltitools') || ($action eq 'authordefaults')) { $output .= $item->{'print'}->('top',$dom,$settings,\$rowtotal); } elsif ($action eq 'passwords') { $output .= $item->{'print'}->('top',$dom,$confname,$settings,\$rowtotal); @@ -1023,6 +1039,19 @@ sub print_config_box { $output .= $item->{'print'}->('shared',$dom,$settings,\$rowtotal); } elsif ($action eq 'passwords') { $output .= $item->{'print'}->('middle',$dom,$confname,$settings,\$rowtotal); + } elsif ($action eq 'lti') { + $output .= $item->{'print'}->('upper',$dom,$settings,\$rowtotal).' +
+ + + + + + + + + '."\n". + $item->{'print'}->('middle',$dom,$settings,\$rowtotal); } else { $output .= $item->{'print'}->('middle',$dom,$settings,\$rowtotal); } @@ -1055,6 +1084,10 @@ sub print_config_box { '. $item->{'print'}->('bottom',$dom,$settings,\$rowtotal); } else { + my $hdridx = 2; + if ($action eq 'lti') { + $hdridx = 3; + } $output .= '
'.&mt($item->{'header'}->[2]->{'col1'}).''.&mt($item->{'header'}->[2]->{'col2'}).'
'.&mt($item->{'header'}->[8]->{'col2'}).'
@@ -1063,8 +1096,8 @@ sub print_config_box { - - + + '."\n"; if ($action eq 'coursecategories') { $output .= &print_coursecategories('bottom',$dom,$item,$settings,\$rowtotal); @@ -1075,6 +1108,7 @@ sub print_config_box { } else { $output .= $item->{'print'}->('lower',$dom,$settings,\$rowtotal); } + $hdridx ++; $output .= '
'.&mt($item->{'header'}->[2]->{'col1'}).''.&mt($item->{'header'}->[2]->{'col2'}).''.&mt($item->{'header'}->[$hdridx]->{'col1'}).''.&mt($item->{'header'}->[$hdridx]->{'col2'}).'
@@ -1084,8 +1118,8 @@ sub print_config_box { - - '."\n"; + + '."\n"; if ($action eq 'passwords') { $output .= $item->{'print'}->('bottom',$dom,$confname,$settings,\$rowtotal); } else { @@ -1103,7 +1137,7 @@ sub print_config_box { $rowtotal ++; } elsif (($action eq 'usermodification') || ($action eq 'coursedefaults') || ($action eq 'directorysrch') || ($action eq 'helpsettings') || - ($action eq 'wafproxy')) { + ($action eq 'wafproxy') || ($action eq 'authordefaults')) { $output .= $item->{'print'}->('bottom',$dom,$settings,\$rowtotal); } elsif ($action eq 'scantron') { $output .= $item->{'print'}->($r,'bottom',$dom,$confname,$settings,\$rowtotal); @@ -2397,7 +2431,7 @@ sub print_quotas { } else { $context = $action; } - my ($datatable,$defaultquota,$authorquota,@usertools,@options,%validations); + my ($datatable,$defaultquota,@usertools,@options,%validations); my ($othertitle,$usertypes,$types) = &Apache::loncommon::sorted_inst_types($dom); my $typecount = 0; my ($css_class,%titles); @@ -2411,12 +2445,12 @@ sub print_quotas { @options = ('norequest','approval','automatic'); %titles = &authorrequest_titles(); } else { - @usertools = ('aboutme','blog','webdav','portfolio','timezone'); + @usertools = ('aboutme','blog','portfolio','portaccess','timezone'); %titles = &tool_titles(); } if (ref($types) eq 'ARRAY') { foreach my $type (@{$types}) { - my ($currdefquota,$currauthorquota); + my $currdefquota; unless (($context eq 'requestcourses') || ($context eq 'requestauthor')) { if (ref($settings) eq 'HASH') { @@ -2425,9 +2459,6 @@ sub print_quotas { } else { $currdefquota = $settings->{$type}; } - if (ref($settings->{authorquota}) eq 'HASH') { - $currauthorquota = $settings->{authorquota}->{$type}; - } } } if (defined($usertypes->{$type})) { @@ -2545,13 +2576,9 @@ sub print_quotas { ($context eq 'requestauthor')) { $datatable .= ''; } $datatable .= ''; @@ -2560,16 +2587,12 @@ sub print_quotas { } unless (($context eq 'requestcourses') || ($context eq 'requestauthor')) { $defaultquota = '20'; - $authorquota = '500'; if (ref($settings) eq 'HASH') { if (ref($settings->{'defaultquota'}) eq 'HASH') { $defaultquota = $settings->{'defaultquota'}->{'default'}; } elsif (defined($settings->{'default'})) { $defaultquota = $settings->{'default'}; } - if (ref($settings->{'authorquota'}) eq 'HASH') { - $authorquota = $settings->{'authorquota'}->{'default'}; - } } } $typecount ++; @@ -2681,12 +2704,9 @@ sub print_quotas { $datatable .= ''; unless (($context eq 'requestcourses') || ($context eq 'requestauthor')) { $datatable .= ''; + $defaultquota.'" size="5" />'; } $datatable .= ''; $typecount ++; @@ -3553,7 +3573,6 @@ sub lti_toggle_js { my %servers = &Apache::lonnet::get_servers($dom,'library'); my $primary = &Apache::lonnet::domain($dom,'primary'); my $course_servers = "'".join("','",keys(%servers))."'"; - return <<"ENDSCRIPT"; + +ENDSCRIPT +} + sub print_autoenroll { my ($dom,$settings,$rowtotal) = @_; my $autorun = &Apache::lonnet::auto_run(undef,$dom), @@ -4614,7 +4666,7 @@ sub print_contacts { map {$excluded{$_} = 1; } @{$lonstatus{'excluded'}}; } } - foreach my $item ('errorthreshold','errorsysmail') { + foreach my $item ('errorthreshold','errorsysmail') { $css_class = $rownum%2?' class="LC_odd_row"':''; $datatable .= ''. ''."\n"; + $$itemcount ++; } } - return $switchserver; + $css_class = $$itemcount%2?' class="LC_odd_row"':''; + $datatable .= ''."\n". + ''."\n"; + return $datatable; } sub print_coursedefaults { @@ -6808,6 +6903,7 @@ sub print_coursedefaults { my %choices = &Apache::lonlocal::texthash ( canuse_pdfforms => 'Course/Community users can create/upload PDF forms', uploadquota => 'Default quota for files uploaded directly to course/community using Course Editor (MB)', + coursequota => 'Default cumulative quota for all group portfolio spaces in course (MB)', anonsurvey_threshold => 'Responder count needed before showing submissions for anonymous surveys', coursecredits => 'Credits can be specified for courses', uselcmath => 'Math preview uses LON-CAPA previewer (javascript) in place of DragMath (Java)', @@ -6820,14 +6916,17 @@ sub print_coursedefaults { ltiauth => 'Student username in LTI launch of deep-linked URL can be accepted without re-authentication', domexttool => 'External Tools defined in the domain may be used in courses/communities (by type)', exttool => 'External Tools can be defined and configured in courses/communities (by type)', + crsauthor => 'Standard LON-CAPA problems can be created within a course/community (by type)', ); my %staticdefaults = ( anonsurvey_threshold => 10, uploadquota => 500, + coursequota => 20, postsubmit => 60, mysqltables => 172800, domexttool => 1, exttool => 0, + crsauthor => 1, ); if ($position eq 'top') { %defaultchecked = ( @@ -6941,12 +7040,14 @@ sub print_coursedefaults { $itemcount ++; } else { $css_class = $itemcount%2 ? ' class="LC_odd_row"' : ''; - my ($currdefresponder,%defcredits,%curruploadquota,%deftimeout,%currmysql); + my ($currdefresponder,%defcredits,%curruploadquota,%currcoursequota, + %deftimeout,%currmysql); my $currusecredits = 0; my $postsubmitclient = 1; my $ltiauth = 0; my %domexttool; my %exttool; + my %crsauthor; my @types = ('official','unofficial','community','textbook','placement'); if (ref($settings) eq 'HASH') { if ($settings->{'ltiauth'}) { @@ -6972,12 +7073,30 @@ sub print_coursedefaults { } } } + if (ref($settings->{'crsauthor'}) eq 'HASH') { + foreach my $type (@types) { + if ($settings->{'crsauthor'}->{$type}) { + $crsauthor{$type} = ' checked="checked"'; + } + } + } else { + foreach my $type (@types) { + if ($staticdefaults{'crsauthor'}) { + $crsauthor{$type} = ' checked="checked"'; + } + } + } $currdefresponder = $settings->{'anonsurvey_threshold'}; if (ref($settings->{'uploadquota'}) eq 'HASH') { foreach my $type (keys(%{$settings->{'uploadquota'}})) { $curruploadquota{$type} = $settings->{'uploadquota'}{$type}; } } + if (ref($settings->{'coursequota'}) eq 'HASH') { + foreach my $type (keys(%{$settings->{'coursequota'}})) { + $currcoursequota{$type} = $settings->{'coursequota'}{$type}; + } + } if (ref($settings->{'coursecredits'}) eq 'HASH') { foreach my $type (@types) { next if ($type eq 'community'); @@ -7026,6 +7145,9 @@ sub print_coursedefaults { if ($staticdefaults{'domexttool'}) { $domexttool{$type} = ' checked="checked"'; } + if ($staticdefaults{'crsauthor'}) { + $crsauthor{$type} = ' checked="checked"'; + } } } if (!$currdefresponder) { @@ -7037,6 +7159,9 @@ sub print_coursedefaults { if ($curruploadquota{$type} eq '') { $curruploadquota{$type} = $staticdefaults{'uploadquota'}; } + if ($currcoursequota{$type} eq '') { + $currcoursequota{$type} = $staticdefaults{'coursequota'}; + } } $datatable .= '
'.&mt($item->{'header'}->[3]->{'col1'}).''.&mt($item->{'header'}->[3]->{'col2'}).'
'.&mt($item->{'header'}->[$hdridx]->{'col1'}).''.&mt($item->{'header'}->[$hdridx]->{'col2'}).'
'. - ''.&mt('Portfolio').': '. + ''. ''.(' ' x 2). - ''.&mt('Authoring').': '. - '
'. - ''.&mt('Portfolio').': '. + ''. ''.(' ' x2). - ''.&mt('Authoring').': '. - '
'. @@ -4696,7 +4748,7 @@ sub print_contacts { $includeloc{'override_'.$key} = ''; $includestr{'override_'.$key} = ''; if ($settings->{'overrides'}{$key}{'include'} ne '') { - ($includeloc{'override_'.$key},$includestr{'override_'.$key}) = + ($includeloc{'override_'.$key},$includestr{'override_'.$key}) = split(/:/,$settings->{'overrides'}{$key}{'include'},2); $includestr{'override_'.$key} = &unescape($includestr{'override_'.$key}); } @@ -4708,7 +4760,6 @@ sub print_contacts { my $optionsprefix = 'LC_options_helpdesk_'; my $onclicktypes = "toggleHelpdeskRow(this.form,'overrides','$customclass','$optionsprefix');"; - $datatable .= &insttypes_row($settings,$types,$usertypes,$dom, $numinrow,$othertitle,'overrides', \$rownum,$onclicktypes,$customclass); @@ -4775,7 +4826,7 @@ sub overridden_helpdesk { } my $title; if (ref($short_titles) eq 'HASH') { - $title = $short_titles->{$item}; + $title = $short_titles->{$item}; } $output .= '
'."\n". + ''."\n". + '
'.$lt{'name'}.''."\n". + ''."\n". + '
'. + '
'.$lt{'info'}.''."\n". + ''. + '
'. + '
'."\n". + '
'."\n". + ''."\n". + ''.&mt('Add').''."\n". + '
'.$lt{'name'}.''."\n". + ''."\n". + '
'. + '
'.$lt{'info'}.''."\n". + ''. + '
'. + '
'."\n". + '
'. @@ -7060,6 +7185,19 @@ sub print_coursedefaults { } $datatable .= '
'."\n"; $itemcount ++; + $css_class = $itemcount%2 ? ' class="LC_odd_row"' : ''; + $datatable .= ''. + $choices{'coursequota'}. + ''. + ''. + ''; + foreach my $type (@types) { + $datatable .= ''; + } + $datatable .= '
'.&mt($type).'
'. + '
'."\n"; + $itemcount ++; my $onclick = "toggleDisplay(this.form,'credits');"; my $display = 'none'; if ($currusecredits) { @@ -7158,11 +7296,234 @@ sub print_coursedefaults { &mt($type).''."\n"; } $datatable .= ''."\n"; + $itemcount ++; + $css_class = $itemcount%2 ? ' class="LC_odd_row"' : ''; + $datatable .= ''. + $choices{'crsauthor'}. + ''. + ''. + ''; + foreach my $type (@types) { + $datatable .= ''."\n"; + } + $datatable .= '
'. + ''. + ''. + &mt($type).'
'."\n"; } $$rowtotal += $itemcount; return $datatable; } +sub print_authordefaults { + my ($position,$dom,$settings,$rowtotal) = @_; + my ($css_class,$datatable,%checkedon,%checkedoff); + my $itemcount = 1; + my %titles = &authordefaults_titles(); + if ($position eq 'top') { + my %defaultchecked = ( + 'nocodemirror' => 'off', + 'domcoordacc' => 'on', + ); + my @toggles = ('nocodemirror','domcoordacc'); + ($datatable,$itemcount) = &radiobutton_prefs($settings,\@toggles,\%defaultchecked, + \%titles,$itemcount); + my %staticdefaults = ( + 'copyright' => 'default', + 'sourceavail' => 'closed', + ); + $css_class = $itemcount%2?' class="LC_odd_row"':''; + my %currrights; + foreach my $item ('copyright','sourceavail') { + $currrights{$item} = $staticdefaults{$item}; + if (ref($settings) eq 'HASH') { + if (exists($settings->{$item})) { + $currrights{$item} = $settings->{$item}; + } + } + } + $datatable .= ''. + ''.$titles{'copyright'}. + ''. + &selectbox('copyright',$currrights{'copyright'},'', + \&Apache::loncommon::copyrightdescription, + (grep !/^priv|custom$/,(&Apache::loncommon::copyrightids))). + ''."\n"; + $itemcount ++; + $css_class = $itemcount%2?' class="LC_odd_row"':''; + $datatable .= ''. + ''.$titles{'sourceavail'}. + ''. + &selectbox('sourceavail',$currrights{'sourceavail'},'', + \&Apache::loncommon::source_copyrightdescription, + (&Apache::loncommon::source_copyrightids)). + ''."\n"; + } else { + $css_class = $itemcount%2 ? ' class="LC_odd_row"' : ''; + my $curreditors; + my %staticdefaults = ( + editors => ['edit','xml'], + authorquota => 500, + webdav => 0, + ); + my $curreditors = $staticdefaults{'editors'}; + if ((ref($settings) eq 'HASH') && + (ref($settings->{'editors'}) eq 'ARRAY')) { + $curreditors = $settings->{'editors'}; + } else { + $curreditors = $staticdefaults{'editors'}; + } + my @editors = ('edit','xml','daxe'); + $datatable = ''."\n". + ''.$titles{'editors'}.''."\n". + ''."\n". + ''; + foreach my $editor (@editors) { + my $checked; + if (grep(/^\Q$editor\E$/,@{$curreditors})) { + $checked = ' checked="checked"'; + } + $datatable .= ' '; + } + $datatable .= ''."\n".''."\n".''."\n"; + $itemcount ++; + $css_class = $itemcount%2?' class="LC_odd_row"':''; + my ($othertitle,$usertypes,$types) = &Apache::loncommon::sorted_inst_types($dom); + my @insttypes; + if (ref($types) eq 'ARRAY') { + @insttypes = @{$types}; + } + my $typecount = 0; + my %domconf = &Apache::lonnet::get_dom('configuration',['quotas'],$dom); + my @items = ('webdav','authorquota'); + my %quotas; + if (ref($domconf{'quotas'}) eq 'HASH') { + %quotas = %{$domconf{'quotas'}}; + foreach my $item (@items) { + if (ref($quotas{$item}) eq 'HASH') { + foreach my $type (@insttypes,'default') { + if ($item eq 'authorquota') { + if ($quotas{$item}{$type} !~ /^\d+$/) { + $quotas{$item}{$type} = $staticdefaults{$item}; + } + } elsif ($item eq 'webdav') { + if ($quotas{$item}{$type} !~ /^(0|1)$/) { + $quotas{$item}{$type} = $staticdefaults{$item}; + } + } + } + } else { + foreach my $type (@insttypes,'default') { + $quotas{$item}{$type} = $staticdefaults{$item}; + } + } + } + } else { + foreach my $item (@items) { + foreach my $type (@insttypes,'default') { + $quotas{$item}{$type} = $staticdefaults{$item}; + } + } + } + if (ref($usertypes) eq 'HASH') { + my $numinrow = 4; + my $onclick = ''; + $datatable .= &insttypes_row(\%quotas,$types,$usertypes,$dom, + $numinrow,$othertitle,'authorquota', + \$itemcount,$onclick); + $itemcount ++; + $datatable .= &insttypes_row(\%quotas,$types,$usertypes,$dom, + $numinrow,$othertitle,'webdav', + \$itemcount); + $itemcount ++; + } + my $checkedno = ' checked="checked"'; + my ($checkedon,$checkedoff); + if (ref($quotas{'webdav'}) eq 'HASH') { + if ($quotas{'webdav'}{'_LC_adv'} =~ /^0|1$/) { + if ($quotas{'webdav'}{'_LC_adv'}) { + $checkedon = $checkedno; + } else { + $checkedoff = $checkedno; + } + undef($checkedno); + } + } + $css_class = $itemcount%2?' class="LC_odd_row"':''; + $datatable .= ''. + ''.$titles{'webdav_LC_adv'}.'
'. + $titles{'webdav_LC_adv_over'}. + ''. + ''; + foreach my $option ('none','off','on') { + my ($text,$val,$checked); + if ($option eq 'none') { + $text = $titles{'none'}; + $val = ''; + $checked = $checkedno; + } elsif ($option eq 'off') { + $text = $titles{'overoff'}; + $val = 0; + $checked = $checkedoff; + } elsif ($option eq 'on') { + $text = $titles{'overon'}; + $val = 1; + $checked = $checkedon; + } + $datatable .= '  '; + } + $datatable .= ''; + $itemcount ++; + } + $$rowtotal += $itemcount; + return $datatable; +} + +sub authordefaults_titles { + return &Apache::lonlocal::texthash( + copyright => 'Copyright/Distribution', + sourceavail => ' Source Available', + editors => 'Available Editors', + webdav => 'WebDAV', + authorquota => 'Authoring Space quotas (MB)', + nocodemirror => 'Deactivate CodeMirror for EditXML editor', + domcoordacc => 'Dom. Coords. can enter Authoring Spaces in domain', + edit => 'Standard editor (Edit)', + xml => 'Text editor (EditXML)', + daxe => 'Daxe editor (Daxe)', + webdav_LC_adv => 'WebDAV access for LON-CAPA "advanced" users', + webdav_LC_adv_over => '(overrides access based on affiliation, if set)', + none => 'No override set', + overon => 'Override -- webDAV on', + overoff => 'Override -- webDAV off', + ); +} + +sub selectbox { + my ($name,$value,$readonly,$functionref,@idlist)=@_; + my $selout = ''; + return $selout; +} + sub print_selfenrollment { my ($position,$dom,$settings,$rowtotal) = @_; my ($css_class,$datatable); @@ -7929,7 +8290,7 @@ sub password_rules { if (ref($settings->{chars}) eq 'ARRAY') { map { $chars{$_} = 1; } (@{$settings->{chars}}); } - if ($prefix eq 'passwords') { + if ($prefix eq 'passwords') { if ($settings->{expire}) { $expire = $settings->{expire}; } @@ -8072,7 +8433,7 @@ sub print_wafproxy { my %config = &Apache::lonnet::get_dom('configuration',['wafproxy'],$domain); if (ref($config{'wafproxy'}) eq 'HASH') { $aliases{$domain} = $config{'wafproxy'}{'alias'}; - if (exists($config{'wafproxy'}{'saml'})) { + if (exists($config{'wafproxy'}{'saml'})) { $saml{$domain} = $config{'wafproxy'}{'saml'}; } foreach my $item ('remoteip','ipheader','trusted','vpnint','vpnext') { @@ -8089,8 +8450,10 @@ sub print_wafproxy { my $dom_in_effect; my $aliasrows = ''. ''. - &mt('Hostname').': '. - ''.&Apache::lonnet::hostname($server).' '; + &mt('Hostname').': '. + ''. + &Apache::lonnet::hostname($server). + ' '; if ($othercontrol{$server}) { $dom_in_effect = $othercontrol{$server}; my ($current,$forsaml); @@ -8137,10 +8500,10 @@ sub print_wafproxy { (' 'x2).''. &mt('Alias used for SSO Auth').':   '. - ''; + ''; } $aliasrows .= ''; $aliasinfo{$dom_in_effect} .= $aliasrows; @@ -9050,7 +9413,7 @@ sub print_loadbalancing { no => ' checked="checked"', ); my %balcookiechecked = ( - no => ' checked="checked"', + no => ' checked="checked"', ); foreach my $sparetype (@sparestypes) { my $targettable; @@ -9405,8 +9768,8 @@ sub tool_titles { my %titles = &Apache::lonlocal::texthash ( aboutme => 'Personal web page', blog => 'Blog', - webdav => 'WebDAV', portfolio => 'Portfolio', + portaccess => 'Share portfolio files', timezone => 'Can set time zone', official => 'Official courses (with institutional codes)', unofficial => 'Unofficial courses', @@ -9637,7 +10000,7 @@ sub print_selfcreation { ($datatable,$itemcount) = &radiobutton_prefs(\%radiohash,\@toggles,\%defaultchecked, \%choices,$itemcount,$onclick); $$rowtotal += $itemcount; - + if (ref($usertypes) eq 'HASH') { if (keys(%{$usertypes}) > 0) { $datatable .= &insttypes_row($createsettings,$types,$usertypes, @@ -9774,7 +10137,7 @@ sub print_selfcreation { my $currstyle = 'display:none'; if (grep(/^\Q$status\E$/,@ordered)) { $currstyle = $rowstyle; - $hidden = 0; + $hidden = 0; } $datatable .= &noninst_users($processing,$emailverified,$emailoptions,$emaildomain, $emailrules,$emailruleorder,$settings,$status,$rowid, @@ -9801,8 +10164,8 @@ sub print_selfcreation { foreach my $status (@posstypes) { my $rowid = $classprefix.$status; my $datarowstyle = 'display:none'; - if (grep(/^\Q$status\E$/,@ordered)) { - $datarowstyle = $rowstyle; + if (grep(/^\Q$status\E$/,@ordered)) { + $datarowstyle = $rowstyle; } $datatable .= &modifiable_userdata_row('cancreate','emailusername_'.$status,$settings, $numinrow,$$rowtotal,\%usertypeshash,$infofields, @@ -9904,7 +10267,7 @@ function toggleEmailOptions(form,radio,p document.getElementById(altprefix+'_inst_'+status).style.display = 'none'; document.getElementById(altprefix+'_noninst_'+status).style.display = 'none'; if (curr == 'custom') { - if (prefix) { + if (prefix) { document.getElementById(prefix+'_'+status).style.display = 'inline'; } } else if (curr == 'inst') { @@ -9927,10 +10290,10 @@ ENDSCRIPT sub noninst_users { my ($processing,$emailverified,$emailoptions,$emaildomain,$emailrules, - $emailruleorder,$settings,$type,$rowid,$typetitle,$css_class,$rowstyle,$intdom) = @_; + $emailruleorder,$settings,$type,$rowid,$typetitle,$css_class,$rowstyle,$intdom) = @_; my $class = 'LC_left_item'; if ($css_class) { - $css_class = ' class="'.$css_class.'"'; + $css_class = ' class="'.$css_class.'"'; } if ($rowid) { $rowid = ' id="'.$rowid.'"'; @@ -9945,10 +10308,10 @@ sub noninst_users { $description = &mt('Requests for: [_1] (status self-reported)',$typetitle); } $output = ''. - "$description\n". + "$description\n". ''. ''; - my %headers = &Apache::lonlocal::texthash( + my %headers = &Apache::lonlocal::texthash( approve => 'Processing', email => 'E-mail', username => 'Username', @@ -10073,7 +10436,7 @@ sub noninst_users { my $value; if (ref($emaildomain) eq 'HASH') { if (ref($emaildomain->{$type}) eq 'HASH') { - $value = $emaildomain->{$type}->{$option}; + $value = $emaildomain->{$type}->{$option}; } } if ($value eq '') { @@ -10391,7 +10754,7 @@ sub print_defaults { if ($defaults{$item.'_'.$field}) { $checkedon = $checkedoff; $checkedoff = ''; - } + } $datatable .= '
'. ''.$titles->{$field}.' '. ''. @@ -11220,7 +11583,7 @@ sub defaults_javascript { function portalExtras(caller) { var x = caller.value; var y = new Array('email','web'); - for (var i=0; i 0) { @@ -11324,7 +11687,7 @@ sub passwords_javascript { } &js_escape(\%intalert); my $defmin = $Apache::lonnet::passwdmin; - my $intauthjs; + my $intauthjs; if ($prefix eq 'passwords') { $intauthjs = <<"ENDSCRIPT"; function warnIntAuth(field) { @@ -11718,7 +12081,6 @@ sub modifiable_userdata_row { '
'; return $output; @@ -12196,7 +12601,7 @@ sub modify_login { if ($lang eq $env{'form.loginhelpurl_add_lang'}) { $formelem = 'loginhelpurl_add_file'; } - (my $result,$newurl{$lang}) = + (my $result,$newurl{$lang}) = &Apache::lonconfigsettings::publishlogo($r,'upload',$formelem,$dom,$confname, "help/$lang",'','',$newfile{$lang}, $modified); @@ -12273,7 +12678,7 @@ sub modify_login { my $modified = []; foreach my $lonhost (@newhosts) { my $formelem = 'loginheadtag_'.$lonhost; - (my $result,$newheadtagurls{$lonhost}) = + (my $result,$newheadtagurls{$lonhost}) = &Apache::lonconfigsettings::publishlogo($r,'upload',$formelem,$dom,$confname, "login/headtag/$lonhost",'','', $env{'form.loginheadtag_'.$lonhost.'.filename'}, @@ -12350,15 +12755,15 @@ sub modify_login { $currsaml{$lonhost}{$item} = $env{'form.saml_'.$item.'_'.$lonhost}; } } else { - if ($saml{$lonhost}) { + if ($saml{$lonhost}) { $changes{'saml'}{$lonhost} = 1; delete($currsaml{$lonhost}); } } } foreach my $posshost (keys(%currsaml)) { - unless (exists($domservers{$posshost})) { - delete($currsaml{$posshost}); + unless (exists($domservers{$posshost})) { + delete($currsaml{$posshost}); } } %{$loginhash{'login'}{'saml'}} = %currsaml; @@ -12372,7 +12777,7 @@ sub modify_login { my $modified = []; foreach my $lonhost (@newsamlimgs) { my $formelem = 'saml_img_'.$lonhost; - my ($result,$imgurl) = + my ($result,$imgurl) = &Apache::lonconfigsettings::publishlogo($r,'upload',$formelem,$dom,$confname, "login/saml/$lonhost",'','', $env{'form.saml_img_'.$lonhost.'.filename'}, @@ -12742,7 +13147,7 @@ sub modify_ipaccess { $possrange =~ s/,+/,/g; if ($possrange ne '') { my (@ok,$count); - $count = 0; + $count = 0; foreach my $poss (split(/\,/,$possrange)) { $count ++; $poss = &validate_ip_pattern($poss); @@ -12775,9 +13180,9 @@ sub modify_ipaccess { } } $confhash{$itemid}{'commblocks'} = {}; - + my %commblocks; - map { $commblocks{$_} = 1; } &Apache::loncommon::get_env_multiple('form.ipaccess_block_'.$idx); + map { $commblocks{$_} = 1; } &Apache::loncommon::get_env_multiple('form.ipaccess_block_'.$idx); foreach my $type (@{$typeorder}) { if ($commblocks{$type}) { $confhash{$itemid}{'commblocks'}{$type} = 'on'; @@ -12809,7 +13214,7 @@ sub modify_ipaccess { } $env{'form.ipaccess_cnum_'.$idx} =~ s/^\s+|\s+$//g; $env{'form.ipaccess_cdom_'.$idx} =~ s/^\s+|\s+$//g; - if (($env{'form.ipaccess_cnum_'.$idx} =~ /^$match_courseid$/) && + if (($env{'form.ipaccess_cnum_'.$idx} =~ /^$match_courseid$/) && ($env{'form.ipaccess_cdom_'.$idx} =~ /^$match_domain$/)) { if (&Apache::lonnet::homeserver($env{'form.ipaccess_cnum_'.$idx}, $env{'form.ipaccess_cdom_'.$idx}) eq 'no_host') { @@ -12889,7 +13294,7 @@ sub modify_ipaccess { if (keys(%{$confhash{$itemid}{'courses'}})) { my @courses; foreach my $cid (sort(keys(%{$confhash{$itemid}{'courses'}}))) { - my %courseinfo = &Apache::lonnet::coursedescription($cid,{'one_time' => 1}); + my %courseinfo = &Apache::lonnet::coursedescription($cid,{'one_time' => 1}); push(@courses,$courseinfo{'description'}.' ('.$cid.')'); } $resulttext .= '
  • '.&mt('Courses/Communities allowed').':
    • '. @@ -12957,6 +13362,239 @@ sub get_ipaccess_id { return ($id,$error); } +sub modify_authordefaults { + my ($dom,$lastactref,%domconfig) = @_; +# +# Retrieve current domain configuration for webDAV and Authoring Space quotas from $domconfig{'quotas'}. +# + my (%curr_quotas,%save_quotas,%confhash,%changes,%newvalues); + if (ref($domconfig{'quotas'}) eq 'HASH') { + foreach my $key (keys(%{$domconfig{'quotas'}})) { + if ($key =~ /^webdav|authorquota$/) { + $curr_quotas{$key} = $domconfig{'quotas'}{$key}; + } else { + $save_quotas{$key} = $domconfig{'quotas'}{$key}; + } + } + } + my %staticdefaults = ( + 'copyright' => 'default', + 'sourceavail' => 'closed', + 'nocodemirror' => 'off', + 'domcoordacc' => 'on', + 'editors' => ['edit','xml']. + 'authorquota' => 500, + 'webdav' => 0, + ); + my %titles = &authordefaults_titles(); + foreach my $item ('nocodemirror','domcoordacc') { + if ($env{'form.'.$item} =~ /^(0|1)$/) { + $confhash{$item} = $env{'form.'.$item}; + } + } + if ($env{'form.copyright'} =~ /^(default|domain|public)$/) { + $confhash{'copyright'} = $1; + } + if ($env{'form.sourceavail'} =~ /^(closed|open)$/) { + $confhash{'sourceavail'} = $1; + } + my @posseditors = &Apache::loncommon::get_env_multiple('form.author_editors'); + my @okeditors = ('edit','xml','daxe'); + my @editors; + foreach my $item (@posseditors) { + if (grep(/^\Q$item\E$/,@okeditors)) { + push(@editors,$item); + } + } + $confhash{'editors'} = \@editors; + + my ($othertitle,$usertypes,$types) = &Apache::loncommon::sorted_inst_types($dom); + my @insttypes; + if (ref($types) eq 'ARRAY') { + @insttypes = @{$types}; + } + my @webdavon = &Apache::loncommon::get_env_multiple('form.webdav'); + my %webdav; + map { $webdav{$_} = 1; } @webdavon; + foreach my $type (@insttypes,'default') { + my $possquota = $env{'form.authorquota_'.$type}; + if ($possquota =~ /^\d+$/) { + $save_quotas{'authorquota'}{$type} = $possquota; + } + if ($webdav{$type}) { + $save_quotas{'webdav'}{$type} = 1; + } else { + $save_quotas{'webdav'}{$type} = 0; + } + } + if ($env{'form.webdav_LC_adv'} =~ /^(0|1)$/) { + $save_quotas{'webdav'}{'_LC_adv'} = $env{'form.webdav_LC_adv'}; + } + if (ref($domconfig{'authordefaults'}) eq 'HASH') { + foreach my $item ('nocodemirror','domcoordacc','copyright','sourceavail') { + if ($domconfig{'authordefaults'}{$item} ne $confhash{$item}) { + $changes{$item} = 1; + } + } + if (ref($domconfig{'authordefaults'}{'editors'}) eq 'ARRAY') { + my @diffs = + &Apache::loncommon::compare_arrays($confhash{'editors'}, + $domconfig{'authordefaults'}{'editors'}); + unless (@diffs == 0) { + $changes{'editors'} = 1; + } + } else { + my @diffs = + &Apache::loncommon::compare_arrays($confhash{'editors'}, + $staticdefaults{'editors'}); + unless (@diffs == 0) { + $changes{'editors'} = 1; + } + } + } else { + my @offon = ('off','on'); + foreach my $item ('nocodemirror','domcoordacc') { + if ($offon[$confhash{$item}] ne $staticdefaults{$item}) { + $changes{$item} = 1; + } + } + foreach my $item ('copyright','sourceavail') { + if ($confhash{$item} ne $staticdefaults{$item}) { + $changes{$item} = 1; + } + } + } + foreach my $key ('authorquota','webdav') { + if (ref($curr_quotas{$key}) eq 'HASH') { + foreach my $type (@insttypes,'default') { + if (exists($save_quotas{$key}{$type})) { + if ($save_quotas{$key}{$type} ne $curr_quotas{$key}{$type}) { + $changes{$key}{$type} = 1; + } + } elsif (exists($curr_quotas{$key}{$type})) { + $save_quotas{$key}{$type} = $curr_quotas{$key}{$type}; + } else { + $save_quotas{$key}{$type} = $staticdefaults{$key}; + } + } + } else { + foreach my $type (@insttypes,'default') { + if (exists($save_quotas{$key}{$type})) { + unless ($save_quotas{$key}{$type} eq $staticdefaults{$key}) { + $changes{$key}{$type} = 1; + } + } else { + $save_quotas{$key}{$type} = $staticdefaults{$key}; + } + } + } + } + if (ref($curr_quotas{'webdav'}) eq 'HASH') { + if (exists($save_quotas{'webdav'}{'_LC_adv'})) { + if ($save_quotas{'webdav'}{'_LC_adv'} ne $curr_quotas{'webdav'}{'_LC_adv'}) { + $changes{'webdav_LC_adv'} = 1; + } + } elsif (exists($curr_quotas{'webdav'}{'_LC_adv'})) { + $changes{'webdav_LC_adv'} = 1; + } + } elsif (exists($save_quotas{'webdav'}{'_LC_adv'})) { + $changes{'webdav_LC_adv'} = 1; + } + my %confighash = ( + quotas => \%save_quotas, + authordefaults => \%confhash, + ); + my $putresult = &Apache::lonnet::put_dom('configuration',\%confighash, + $dom); + my $resulttext; + if ($putresult eq 'ok') { + if (keys(%changes)) { + my %domdefaults = &Apache::lonnet::get_domain_defaults($dom); + if ((exists($changes{'authorquota'})) || (exists($changes{'webdav'})) || + ($changes{'webdav_LC_adv'})) { + if ((exists($changes{'authorquota'})) && (ref($save_quotas{'authorquota'}) eq 'HASH')) { + $domdefaults{'authorquota'} = $save_quotas{'authorquota'}; + } + if (((exists($changes{'webdav'})) || ($changes{'webdav_LC_adv'})) && + (ref($save_quotas{'webdav'}) eq 'HASH')) { + $domdefaults{'webdav'} = $save_quotas{'webdav'}; + } + } + $resulttext = &mt('Changes made:').'
        '; + my $authoroverride; + foreach my $key ('nocodemirror','domcoordacc','copyright','sourceavail') { + if (exists($changes{$key})) { + $domdefaults{$key} = $confhash{$key}; + my $shown; + unless ($authoroverride) { + $resulttext .= '
      • '.&mt('Defaults which can be overridden by Author').'
          '; + $authoroverride = 1; + } + if (($key eq 'nocodemirror') || ($key eq 'domcoordacc')) { + $shown = ($confhash{$key} ? &mt('Yes') : &mt('No')); + } elsif ($key eq 'copyright') { + $shown = &Apache::loncommon::copyrightdescription($confhash{$key}); + } elsif ($key eq 'sourceavail') { + $shown = &Apache::loncommon::source_copyrightdescription($confhash{$key}); + } + $resulttext .= '
        • '.&mt('[_1] set to: [_2]',$titles{$key},$shown).'
        • '; + } + } + if ($authoroverride) { + $resulttext .= '
      • '; + } + my $domcoordoverride; + foreach my $key ('editors','authorquota','webdav','webdav_LC_adv') { + if (exists($changes{$key})) { + my $shown; + unless ($domcoordoverride) { + $resulttext .= '
      • '.&mt('Defaults which can be overridden by a Domain Coodinator').'
          '; + $domcoordoverride = 1; + } + if ($key eq 'editors') { + if (ref($confhash{'editors'}) eq 'ARRAY') { + $domdefaults{'editors'} = join(',',@{$confhash{'editors'}}); + if (@{$confhash{'editors'}}) { + $shown = join(', ', map { $titles{$_} } @{$confhash{'editors'}}); + } else { + $shown = &mt('None'); + } + } + } elsif ($key eq 'authorquota') { + foreach my $type (@insttypes) { + $shown .= $usertypes->{$type}.' -- '.$save_quotas{$key}{$type}.', '; + } + $shown .= $othertitle.' -- '.$save_quotas{$key}{'default'}; + } elsif ($key eq 'webdav') { + foreach my $type (@insttypes) { + $shown .= $usertypes->{$type}.' -- '. ($save_quotas{$key}{$type} ? &mt('Yes') : &mt('No')).', '; + } + $shown .= $othertitle.' -- '. ($save_quotas{$key}{'default'} ? &mt('Yes') : &mt('No')); + } elsif ($key eq 'webdav_LC_adv') { + if (exists($save_quotas{'webdav'}{'_LC_adv'})) { + $shown = ($save_quotas{'webdav'}{'_LC_adv'} ? $titles{'overon'} : $titles{'overoff'}); + } else { + $shown = $titles{'none'}; + } + } + $resulttext .= '
        • '.&mt('[_1] set to: [_2]',$titles{$key},$shown).'
        • '; + } + } + if ($domcoordoverride) { + $resulttext .= '
      • '; + } + my $cachetime = 24*60*60; + &Apache::lonnet::do_cache_new('domdefaults',$dom,\%domdefaults,$cachetime); + if (ref($lastactref) eq 'HASH') { + $lastactref->{'domdefaults'} = 1; + } + } else { + $resulttext = &mt('No changes made to Authoring Space defaults'); + } + } + return $resulttext; +} + sub modify_rolecolors { my ($r,$dom,$confname,$roles,$lastactref,%domconfig) = @_; my ($resulttext,%rolehash); @@ -13496,7 +14134,9 @@ sub check_switchserver { my @ids=&Apache::lonnet::current_machine_ids(); foreach my $id (@ids) { if ($id eq $home) { $allowed=1; } } if (!$allowed) { - $switchserver=''.&mt('Switch Server').''; + $switchserver=''.&mt('Switch Server').''; } return $switchserver; } @@ -13508,7 +14148,7 @@ sub modify_quotas { $author_ok,$switchserver,$errors,$validationitemsref,$validationnamesref, $validationfieldsref); if ($action eq 'quotas') { - $context = 'tools'; + $context = 'tools'; } else { $context = $action; } @@ -13528,7 +14168,7 @@ sub modify_quotas { @usertools = ('author'); %titles = &authorrequest_titles(); } else { - @usertools = ('aboutme','blog','webdav','portfolio','timezone'); + @usertools = ('aboutme','blog','portfolio','portaccess','timezone'); %titles = &tool_titles(); } my %domdefaults = &Apache::lonnet::get_domain_defaults($dom,1); @@ -13551,8 +14191,6 @@ sub modify_quotas { } else { if ($key =~ /^form\.quota_(.+)$/) { $confhash{'defaultquota'}{$1} = $env{$key}; - } elsif ($key =~ /^form\.authorquota_(.+)$/) { - $confhash{'authorquota'}{$1} = $env{$key}; } elsif ($key =~ /^form\.\Q$context\E_(.+)$/) { @{$toolshash{$1}} = &Apache::loncommon::get_env_multiple($key); } @@ -13846,7 +14484,6 @@ sub modify_quotas { } } else { $confhash{'defaultquota'}{'default'} = $env{'form.defaultquota'}; - $confhash{'authorquota'}{'default'} = $env{'form.authorquota'}; } foreach my $item (@usertools) { foreach my $type (@{$types},'default','_LC_adv') { @@ -13935,15 +14572,10 @@ sub modify_quotas { } } if (ref($domconfig{'quotas'}{'authorquota'}) eq 'HASH') { - foreach my $key (keys(%{$domconfig{'quotas'}{'authorquota'}})) { - if (exists($confhash{'authorquota'}{$key})) { - if ($confhash{'authorquota'}{$key} ne $domconfig{'quotas'}{'authorquota'}{$key}) { - $changes{'authorquota'}{$key} = 1; - } - } else { - $confhash{'authorquota'}{$key} = $domconfig{'quotas'}{'authorquota'}{$key}; - } - } + $confhash{'authorquota'} = $domconfig{'quotas'}{'authorquota'}; + } + if (ref($domconfig{'quotas'}{'webdav'}) eq 'HASH') { + $confhash{'webdav'} = $domconfig{'quotas'}{'webdav'}; } } if (ref($confhash{'defaultquota'}) eq 'HASH') { @@ -13963,21 +14595,6 @@ sub modify_quotas { } } } - if (ref($confhash{'authorquota'}) eq 'HASH') { - foreach my $key (keys(%{$confhash{'authorquota'}})) { - if (ref($domconfig{'quotas'}) eq 'HASH') { - if (ref($domconfig{'quotas'}{'authorquota'}) eq 'HASH') { - if (!exists($domconfig{'quotas'}{'authorquota'}{$key})) { - $changes{'authorquota'}{$key} = 1; - } - } else { - $changes{'authorquota'}{$key} = 1; - } - } else { - $changes{'authorquota'}{$key} = 1; - } - } - } } if ($context eq 'requestauthor') { @@ -14018,19 +14635,6 @@ sub modify_quotas { } $resulttext .= '
    • '; } - if (ref($changes{'authorquota'}) eq 'HASH') { - $resulttext .= '
    • '.&mt('Authoring Space default quotas').'
        '; - foreach my $type (@{$types},'default') { - if (defined($changes{'authorquota'}{$type})) { - my $typetitle = $usertypes->{$type}; - if ($type eq 'default') { - $typetitle = $othertitle; - } - $resulttext .= '
      • '.&mt('[_1] set to [_2] MB',$typetitle,$confhash{'authorquota'}{$type}).'
      • '; - } - } - $resulttext .= '
    • '; - } } my %newenv; foreach my $item (@usertools) { @@ -14493,7 +15097,6 @@ sub lti_security_results { off => &mt('Encryption of stored external tool secrets defined in domain disabled'), }, ); - } my @types= ('crs','dom'); if ($context eq 'lti') { @@ -14589,6 +15192,28 @@ sub lti_security_results { } } elsif ($item eq 'linkprot') { next; + } elsif ($item eq 'suggested') { + if ((ref($secchanges->{'suggested'}) eq 'HASH') && + (ref($newsec->{'suggested'}) eq 'HASH')) { + my $suggestions; + foreach my $id (sort { $a <=> $b } keys(%{$secchanges->{'suggested'}})) { + if (ref($newsec->{'suggested'}->{$id}) eq 'HASH') { + my $name = $newsec->{'suggested'}->{$id}->{'name'}; + my $info = $newsec->{'suggested'}->{$id}->{'info'}; + $suggestions .= '
    • '.&mt('Launcher: [_1]',$name).'
      '. + &mt('Recommend: [_1]','
      '.$info.'
      '). + '
    • '; + } else { + $suggestions .= '
    • '.&mt('Recommendations deleted for Launcher: [_1]', + $newsec->{'suggested'}->{$id}).'
    • '; + } + } + if ($suggestions) { + $output .= '
    • '.&mt('Hints in Courses for Link Protector Configuration'). + '
        '.$suggestions.'
      '. + '
    • '; + } + } } } if ($needs_update) { @@ -15193,7 +15818,7 @@ sub modify_lti { } } if (ref($currltisec{'linkprot'}) eq 'HASH') { - foreach my $id (%{$currltisec{'linkprot'}}) { + foreach my $id (keys(%{$currltisec{'linkprot'}})) { next if ($id !~ /^\d+$/); unless (exists($linkprotchg{$id})) { if (ref($currltisec{'linkprot'}{$id}) eq 'HASH') { @@ -15215,17 +15840,75 @@ sub modify_lti { if ($proterror) { $errors .= '
    • '.$proterror.'
    • '; } + + my (%delsuggested,%suggids,@suggested);; + if (ref($currltisec{'suggested'}) eq 'HASH') { + my $maxnum = $env{'form.linkprot_suggested_maxnum'}; + my @todelete = &Apache::loncommon::get_env_multiple('form.linkprot_suggested_del'); + for (my $i=0; $i<$maxnum; $i++) { + my $itemid = $env{'form.linkprot_suggested_id_'.$i}; + $itemid =~ s/\D+//g; + if ($itemid) { + if (ref($currltisec{'suggested'}->{$itemid}) eq 'HASH') { + push(@suggested,$i); + $suggids{$i} = $itemid; + if ((@todelete > 0) && (grep(/^$i$/,@todelete))) { + if (ref($currltisec{'suggested'}{$itemid}) eq 'HASH') { + $delsuggested{$itemid} = $currltisec{'suggested'}{$itemid}{'name'}; + } + } else { + if ($env{'form.linkprot_suggested_name_'.$i} eq '') { + $delsuggested{$itemid} = $currltisec{'suggested'}{$itemid}{'name'}; + } else { + $env{'form.linkprot_suggested_name_'.$i} =~ s/(`)/'/g; + $env{'form.linkprot_suggested_info_'.$i} =~ s/(`)/'/g; + $newltisec{'suggested'}{$itemid}{'name'} = $env{'form.linkprot_suggested_name_'.$i}; + $newltisec{'suggested'}{$itemid}{'info'} = $env{'form.linkprot_suggested_info_'.$i}; + if (($currltisec{'suggested'}{$itemid}{'name'} ne $newltisec{'suggested'}{$itemid}{'name'}) || + ($currltisec{'suggested'}{$itemid}{'info'} ne $newltisec{'suggested'}{$itemid}{'info'})) { + $secchanges{'suggested'}{$itemid} = 1; + } + } + } + } + } + } + } + foreach my $key (keys(%delsuggested)) { + $newltisec{'suggested'}{$key} = $delsuggested{$key}; + $secchanges{'suggested'}{$key} = 1; + } + if (($env{'form.linkprot_suggested_add'}) && + ($env{'form.linkprot_suggested_name_add'} ne '')) { + $env{'form.linkprot_suggested_name_add'} =~ s/(`)/'/g; + $env{'form.linkprot_suggested_info_add'} =~ s/(`)/'/g; + my ($newsuggid,$errormsg) = &get_lti_id($dom,$env{'form.linkprot_suggested_name_add'},'suggested'); + if ($newsuggid) { + $newltisec{'suggested'}{$newsuggid}{'name'} = $env{'form.linkprot_suggested_name_add'}; + $newltisec{'suggested'}{$newsuggid}{'info'} = $env{'form.linkprot_suggested_info_add'}; + $secchanges{'suggested'}{$newsuggid} = 1; + } else { + my $error = &mt('Failed to acquire unique ID for new Link Protectors in Courses Suggestion'); + if ($errormsg) { + $error .= ' ('.$errormsg.')'; + } + $errors .= '
    • '.$error.'
    • '; + } + } my (@items,%deletions,%itemids); if ($env{'form.lti_add'}) { my $consumer = $env{'form.lti_consumer_add'}; $consumer =~ s/(`)/'/g; - ($newid,my $error) = &get_lti_id($dom,$consumer); + ($newid,my $errormsg) = &get_lti_id($dom,$consumer,'lti'); if ($newid) { $itemids{'add'} = $newid; push(@items,'add'); $changes{$newid} = 1; } else { my $error = &mt('Failed to acquire unique ID for new LTI configuration'); + if ($errormsg) { + $error .= ' ('.$errormsg.')'; + } $errors .= '
    • '.$error.'
    • '; } } @@ -15819,7 +16502,8 @@ sub modify_lti { } $resulttext .= '
    '; if (ref($lastactref) eq 'HASH') { - if (($secchanges{'encrypt'}) || ($secchanges{'private'})) { + if (($secchanges{'encrypt'}) || ($secchanges{'private'}) || (exists($secchanges{'suggested'}))) { + &Apache::lonnet::get_domain_defaults($dom,1); $lastactref->{'domdefaults'} = 1; } } @@ -15858,23 +16542,26 @@ sub get_priv_creds { } sub get_lti_id { - my ($domain,$consumer) = @_; - # get lock on lti db + my ($domain,$consumer,$dbname) = @_; + unless (($dbname eq 'lti') || ($dbname eq 'suggested')) { + return ('','invalid db'); + } + # get lock on db my $lockhash = { lock => $env{'user.name'}. ':'.$env{'user.domain'}, }; my $tries = 0; - my $gotlock = &Apache::lonnet::newput_dom('lti',$lockhash,$domain); + my $gotlock = &Apache::lonnet::newput_dom($dbname,$lockhash,$domain); my ($id,$error); while (($gotlock ne 'ok') && ($tries<10)) { $tries ++; sleep (0.1); - $gotlock = &Apache::lonnet::newput_dom('lti',$lockhash,$domain); + $gotlock = &Apache::lonnet::newput_dom($dbname,$lockhash,$domain); } if ($gotlock eq 'ok') { - my %currids = &Apache::lonnet::dump_dom('lti',$domain); + my %currids = &Apache::lonnet::dump_dom($dbname,$domain); if ($currids{'lock'}) { delete($currids{'lock'}); if (keys(%currids)) { @@ -15886,14 +16573,14 @@ sub get_lti_id { $id = 1; } if ($id) { - unless (&Apache::lonnet::newput_dom('lti',{ $id => $consumer },$domain) eq 'ok') { + unless (&Apache::lonnet::newput_dom($dbname,{ $id => $consumer },$domain) eq 'ok') { $error = 'nostore'; } } else { $error = 'nonumber'; } } - my $dellockoutcome = &Apache::lonnet::del_dom('lti',['lock'],$domain); + my $dellockoutcome = &Apache::lonnet::del_dom($dbname,['lock'],$domain); } else { $error = 'nolock'; } @@ -16659,7 +17346,7 @@ sub modify_contacts { $contacts_hash{'contacts'}{'overrides'}{$type}{'include'} = $includeloc{$type}.':'.&escape($includestr{$type}); $newsetting{'override_'.$type}{'include'} = $contacts_hash{'contacts'}{'overrides'}{$type}{'include'}; } - } + } } } if (keys(%currsetting) > 0) { @@ -16717,12 +17404,12 @@ sub modify_contacts { } } if (@statuses) { - if (ref($currsetting{'overrides'}) eq 'HASH') { + if (ref($currsetting{'overrides'}) eq 'HASH') { foreach my $key (keys(%{$currsetting{'overrides'}})) { if (ref($currsetting{'overrides'}{$key}) eq 'HASH') { if (ref($newsetting{'override_'.$key}) eq 'HASH') { foreach my $item (@contacts,'bcc','others','include') { - if ($currsetting{'overrides'}{$key}{$item} ne $newsetting{'override_'.$key}{$item}) { + if ($currsetting{'overrides'}{$key}{$item} ne $newsetting{'override_'.$key}{$item}) { push(@{$changes{'overrides'}},$key); last; } @@ -16739,7 +17426,7 @@ sub modify_contacts { } } else { foreach my $key (@overrides) { - push(@{$changes{'overrides'}},$key); + push(@{$changes{'overrides'}},$key); } } } @@ -16921,7 +17608,7 @@ sub modify_contacts { $resulttext .= $bcctext.': '.$bcc{$type}.''; } elsif (!@text) { $resulttext .= &mt('No one'); - } + } if ($includestr{$type} ne '') { if ($includeloc{$type} eq 'b') { $resulttext .= '
    '.&mt('Text automatically added to e-mail body:').' '.$includestr{$type}; @@ -16945,14 +17632,14 @@ sub modify_contacts { if (ref($newsetting{'override_'.$type}) eq 'HASH') { my @text; foreach my $item (@contacts) { - if ($newsetting{'override_'.$type}{$item}) { + if ($newsetting{'override_'.$type}{$item}) { push(@text,$short_titles->{$item}); } } if ($newsetting{'override_'.$type}{'others'} ne '') { push(@text,$newsetting{'override_'.$type}{'others'}); } - + if (@text) { $resulttext .= &mt('Helpdesk e-mail sent to: [_1]', ''.join(', ',@text).''); @@ -17115,7 +17802,7 @@ sub modify_contacts { } sub modify_privacy { - my ($dom,%domconfig) = @_; + my ($dom,$lastactref,%domconfig) = @_; my ($resulttext,%current,%changes); if (ref($domconfig{'privacy'}) eq 'HASH') { %current = %{$domconfig{'privacy'}}; @@ -17351,6 +18038,28 @@ sub modify_privacy { } } $resulttext .= ''; + if ($changes{'approval'}) { + my %domdefaults = &Apache::lonnet::get_domain_defaults($dom); + delete($domdefaults{'userapprovals'}); + if (ref($privacyhash{'approval'}) eq 'HASH') { + foreach my $domtype ('instdom','extdom') { + if (ref($privacyhash{'approval'}{$domtype}) eq 'HASH') { + foreach my $roletype ('domain','author','course','community') { + if ($privacyhash{'approval'}{$domtype}{$roletype} eq 'user') { + $domdefaults{'userapprovals'} = 1; + last; + } + } + } + last if ($domdefaults{'userapprovals'}); + } + } + my $cachetime = 24*60*60; + &Apache::lonnet::do_cache_new('domdefaults',$dom,\%domdefaults,$cachetime); + if (ref($lastactref) eq 'HASH') { + $lastactref->{'domdefaults'} = 1; + } + } } else { $resulttext = &mt('No changes made to user information settings'); } @@ -17793,7 +18502,7 @@ sub modify_passwords { ); my $needed = '
    • '. join('
    • ',map {$rulenames{$_} } @{$confighash{'passwords'}{'chars'}}). - '
    '; + '
  • '; $resulttext .= '
  • '.&mt('[_1] set to: [_2]',$titles{'chars'},$needed).'
  • '; } else { $resulttext .= '
  • '.&mt('[_1] set to none',$titles{'chars'}).'
  • '; @@ -18276,7 +18985,7 @@ sub modify_selfcreation { if (($chosen eq 'inst') || ($chosen eq 'noninst')) { my $emaildom; if ($env{'form.cancreate_emaildomain_'.$chosen.'_'.$type} =~ /^\@[^\@]+$/) { - $emaildom = $env{'form.cancreate_emaildomain_'.$chosen.'_'.$type}; + $emaildom = $env{'form.cancreate_emaildomain_'.$chosen.'_'.$type}; $cancreate{'emaildomain'}{$type}{$chosen} = $emaildom; if (ref($curremaildom{$type}) eq 'HASH') { if (exists($curremaildom{$type}{$chosen})) { @@ -18288,7 +18997,7 @@ sub modify_selfcreation { } } elsif ($emaildom ne '') { push(@{$changes{'cancreate'}},'emaildomain'); - } + } } $cancreate{'emailoptions'}{$type} = $env{'form.cancreate_emailoptions_'.$type}; } elsif ($chosen eq 'custom') { @@ -18715,7 +19424,7 @@ sub modify_selfcreation { ); if (@types) { if (@statuses) { - $chgtext .= &mt('Processing of requests to create account with e-mail verification set as follows:'). + $chgtext .= &mt('Processing of requests to create account with e-mail verification set as follows:'). '
      '; foreach my $status (@statuses) { if ($status eq 'default') { @@ -18923,7 +19632,7 @@ sub modify_selfcreation { $typename = $othertitle; } else { $typename = $usertypes{$type}; - } + } $chgtext .= &mt('(Affiliation: [_1])',$typename); } if (@{$email_rule{$type}} > 0) { @@ -19268,7 +19977,7 @@ sub modify_defaults { } if ($item eq 'portal_def') { unless (grep(/^\Q$item\E$/,@errors)) { - if ($newvalues{$item} eq '') { + if ($newvalues{$item} eq '') { foreach my $field ('email','web') { if (exists($domdefaults{$item.'_'.$field})) { delete($domdefaults{$item.'_'.$field}); @@ -19453,7 +20162,7 @@ sub modify_defaults { $resulttext =~ s/, $//; $resulttext .= ''; } else { - $resulttext .= '
    • '.&mt('Institutional user status types deleted').'
    • '; + $resulttext .= '
    • '.&mt('Institutional user status types deleted').'
    • '; } } } elsif ($item eq 'unamemap_rule') { @@ -20488,15 +21197,19 @@ sub modify_coursedefaults { my @toggles = ('canuse_pdfforms','uselcmath','usejsme','inline_chem','ltiauth'); my @numbers = ('anonsurvey_threshold','uploadquota_official','uploadquota_unofficial', 'uploadquota_community','uploadquota_textbook','uploadquota_placement', - 'mysqltables_official','mysqltables_unofficial','mysqltables_community', - 'mysqltables_textbook','mysqltables_placement'); + 'coursequota_official','coursequota_unofficial','coursequota_community', + 'coursequota_textbook','coursequota_placement','mysqltables_official', + 'mysqltables_unofficial','mysqltables_community','mysqltables_textbook', + 'mysqltables_placement'); my @types = ('official','unofficial','community','textbook','placement'); my %staticdefaults = ( anonsurvey_threshold => 10, uploadquota => 500, + coursequota => 20, postsubmit => 60, mysqltables => 172800, domexttool => 1, + crsauthor => 1, ); my %texoptions = ( MathJax => 'MathJax', @@ -20541,7 +21254,7 @@ sub modify_coursedefaults { } $defaultshash{'coursedefaults'}{$item} = $newdef; } else { - my ($setting,$type) = ($item =~ /^(uploadquota|mysqltables)_(\w+)$/); + my ($setting,$type) = ($item =~ /^(uploadquota|coursequota|mysqltables)_(\w+)$/); if (ref($domconfig{'coursedefaults'}{$setting}) eq 'HASH') { $currdef = $domconfig{'coursedefaults'}{$setting}{$type}; } @@ -20553,7 +21266,7 @@ sub modify_coursedefaults { unless (($currdef eq '') && ($newdef == $staticdefaults{$item})) { $changes{$item} = 1; } - } elsif ($item =~ /^(uploadquota|mysqltables)_/) { + } elsif ($item =~ /^(uploadquota|coursequota|mysqltables)_/) { my $setting = $1; unless (($currdef eq '') && ($newdef == $staticdefaults{$setting})) { $changes{$setting} = 1; @@ -20688,9 +21401,10 @@ sub modify_coursedefaults { $changes{'postsubmit'} = 1; } } - my (%newdomexttool,%newexttool,%olddomexttool,%oldexttool); + my (%newdomexttool,%newexttool,%newcrsauthor,%olddomexttool,%oldexttool,%oldcrsauthor); map { $newdomexttool{$_} = 1; } &Apache::loncommon::get_env_multiple('form.domexttool'); - map { $newexttool{$_} = 1; } &Apache::loncommon::get_env_multiple('form.exttool'); + map { $newexttool{$_} = 1; } &Apache::loncommon::get_env_multiple('form.exttool'); + map { $newcrsauthor{$_} = 1; } &Apache::loncommon::get_env_multiple('form.crsauthor'); if (ref($domconfig{'coursedefaults'}{'domexttool'}) eq 'HASH') { %olddomexttool = %{$domconfig{'coursedefaults'}{'domexttool'}}; } else { @@ -20703,7 +21417,7 @@ sub modify_coursedefaults { } } if (ref($domconfig{'coursedefaults'}{'exttool'}) eq 'HASH') { - %oldexttool = %{$domconfig{'coursedefaults'}{'exttool'}}; + %oldexttool = %{$domconfig{'coursedefaults'}{'exttool'}}; } else { foreach my $type (@types) { if ($staticdefaults{'exttool'}) { @@ -20713,6 +21427,17 @@ sub modify_coursedefaults { } } } + if (ref($domconfig{'coursedefaults'}{'crsauthor'}) eq 'HASH') { + %oldcrsauthor = %{$domconfig{'coursedefaults'}{'crsauthor'}}; + } else { + foreach my $type (@types) { + if ($staticdefaults{'crsauthor'}) { + $oldcrsauthor{$type} = 1; + } else { + $oldcrsauthor{$type} = 0; + } + } + } foreach my $type (@types) { unless ($newdomexttool{$type}) { $newdomexttool{$type} = 0; @@ -20720,15 +21445,22 @@ sub modify_coursedefaults { unless ($newexttool{$type}) { $newexttool{$type} = 0; } + unless ($newcrsauthor{$type}) { + $newcrsauthor{$type} = 0; + } if ($newdomexttool{$type} != $olddomexttool{$type}) { $changes{'domexttool'} = 1; } if ($newexttool{$type} != $oldexttool{$type}) { $changes{'exttool'} = 1; } + if ($newcrsauthor{$type} != $oldcrsauthor{$type}) { + $changes{'crsauthor'} = 1; + } } $defaultshash{'coursedefaults'}{'domexttool'} = \%newdomexttool; $defaultshash{'coursedefaults'}{'exttool'} = \%newexttool; + $defaultshash{'coursedefaults'}{'crsauthor'} = \%newcrsauthor; } my $putresult = &Apache::lonnet::put_dom('configuration',\%defaultshash, $dom); @@ -20739,7 +21471,7 @@ sub modify_coursedefaults { ($changes{'coursecredits'}) || ($changes{'uselcmath'}) || ($changes{'usejsme'}) || ($changes{'canclone'}) || ($changes{'mysqltables'}) || ($changes{'texengine'}) || ($changes{'inline_chem'}) || ($changes{'ltiauth'}) || ($changes{'domexttool'}) || - ($changes{'exttool'}) ) { + ($changes{'exttool'}) || ($changes{'coursequota'}) || ($changes{'crsauthor'})) { foreach my $item ('canuse_pdfforms','uselcmath','usejsme','inline_chem','texengine', 'ltiauth') { if ($changes{$item}) { @@ -20772,6 +21504,13 @@ sub modify_coursedefaults { } } } + if ($changes{'coursequota'}) { + if (ref($defaultshash{'coursedefaults'}{'coursequota'}) eq 'HASH') { + foreach my $type (@types) { + $domdefaults{$type.'coursequota'}=$defaultshash{'coursedefaults'}{'coursequota'}{$type}; + } + } + } if ($changes{'canclone'}) { if (ref($defaultshash{'coursedefaults'}{'canclone'}) eq 'HASH') { if (ref($defaultshash{'coursedefaults'}{'canclone'}{'instcode'}) eq 'ARRAY') { @@ -20798,6 +21537,13 @@ sub modify_coursedefaults { } } } + if ($changes{'crsauthor'}) { + if (ref($defaultshash{'coursedefaults'}{'crsauthor'}) eq 'HASH') { + foreach my $type (@types) { + $domdefaults{$type.'crsauthor'}=$defaultshash{'coursedefaults'}{'crsauthor'}{$type}; + } + } + } my $cachetime = 24*60*60; &Apache::lonnet::do_cache_new('domdefaults',$dom,\%domdefaults,$cachetime); if (ref($lastactref) eq 'HASH') { @@ -20850,6 +21596,19 @@ sub modify_coursedefaults { } else { $resulttext .= '
    • '.&mt('Default quota for content uploaded via Course Editor remains default: [_1] MB',$staticdefaults{'uploadquota'}).'
    • '; } + } elsif ($item eq 'coursequota') { + if (ref($defaultshash{'coursedefaults'}{'coursequota'}) eq 'HASH') { + $resulttext .= '
    • '.&mt('Default cumulative quota for all group portfolio spaces in course set as follows:').'
        '. + '
      • '.&mt('Official courses: [_1] MB',''.$defaultshash{'coursedefaults'}{'coursequota'}{'official'}.'').'
      • '. + '
      • '.&mt('Unofficial courses: [_1] MB',''.$defaultshash{'coursedefaults'}{'coursequota'}{'unofficial'}.'').'
      • '. + '
      • '.&mt('Textbook courses: [_1] MB',''.$defaultshash{'coursedefaults'}{'coursequota'}{'textbook'}.'').'
      • '. + '
      • '.&mt('Placement tests: [_1] MB',''.$defaultshash{'coursedefaults'}{'coursequota'}{'placement'}.'').'
      • '. + '
      • '.&mt('Communities: [_1] MB',''.$defaultshash{'coursedefaults'}{'coursequota'}{'community'}.'').'
      • '. + '
      '. + '
    • '; + } else { + $resulttext .= '
    • '.&mt('Default cumulative quota for all group portfolio spaces in course remains default: [_1] MB',$staticdefaults{'coursequota'}).'
    • '; + } } elsif ($item eq 'mysqltables') { if (ref($defaultshash{'coursedefaults'}{'mysqltables'}) eq 'HASH') { $resulttext .= '
    • '.&mt('Lifetime of "Temporary" MySQL tables (student performance data) on homeserver').'
        '. @@ -20935,33 +21694,34 @@ sub modify_coursedefaults { } else { $resulttext .= '
      • '.&mt('LTI launch of deep-linked URL will require re-authentication').'
      • '; } - } elsif ($item eq 'domexttool') { - my @noyes = (&mt('no'),&mt('yes')); - if (ref($defaultshash{'coursedefaults'}{'domexttool'}) eq 'HASH') { - $resulttext .= '
      • '.&mt('External Tools defined in the domain may be used as follows:').'
          '. - '
        • '.&mt('Official courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'domexttool'}{'official'}].'').'
        • '. - '
        • '.&mt('Unofficial courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'domexttool'}{'unofficial'}].'').'
        • '. - '
        • '.&mt('Textbook courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'domexttool'}{'textbook'}].'').'
        • '. - '
        • '.&mt('Placement tests: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'domexttool'}{'placement'}].'').'
        • '. - '
        • '.&mt('Communities: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'domexttool'}{'community'}].'').'
        • '. - '
        '. - '
      • '; - } else { - $resulttext .= '
      • '.&mt('External Tools defined in the domain may be used in all course types, by default').'
      • '; - } - } elsif ($item eq 'exttool') { + } elsif (($item eq 'domexttool') || ($item eq 'exttool') || ($item eq 'crsauthor')) { my @noyes = (&mt('no'),&mt('yes')); - if (ref($defaultshash{'coursedefaults'}{'exttool'}) eq 'HASH') { - $resulttext .= '
      • '.&mt('External Tools can be defined and configured in course containers as follows:').'
          '. - '
        • '.&mt('Official courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'exttool'}{'official'}].'').'
        • '. - '
        • '.&mt('Unofficial courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'exttool'}{'unofficial'}].'').'
        • '. - '
        • '.&mt('Textbook courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'exttool'}{'textbook'}].'').'
        • '. - '
        • '.&mt('Placement tests: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'exttool'}{'placement'}].'').'
        • '. - '
        • '.&mt('Communities: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{'exttool'}{'community'}].'').'
        • '. + my %status = ( + domexttool => { + ishash => &mt('External Tools defined in the domain may be used as follows:'), + default => &mt('External Tools defined in the domain may be used in all course types, by default'), + }, + exttool => { + ishash => &mt('External Tools can be defined and configured in course containers as follows:'), + default => &mt('External Tools can not be defined in any course types, by default'), + }, + crsauthor => { + ishash => &mt('Standard Problems can be created within course containers as follows:'), + default => &mt('Standard Problems can be created within any course type, by default'), + }, + ); + + if (ref($defaultshash{'coursedefaults'}{$item}) eq 'HASH') { + $resulttext .= '
        • '.$status{$item}{'ishash'}.'
            '. + '
          • '.&mt('Official courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{$item}{'official'}].'').'
          • '. + '
          • '.&mt('Unofficial courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{$item}{'unofficial'}].'').'
          • '. + '
          • '.&mt('Textbook courses: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{$item}{'textbook'}].'').'
          • '. + '
          • '.&mt('Placement tests: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{$item}{'placement'}].'').'
          • '. + '
          • '.&mt('Communities: [_1]',''.$noyes[$defaultshash{'coursedefaults'}{$item}{'community'}].'').'
          • '. '
          '. '
        • '; } else { - $resulttext .= '
        • '.&mt('External Tools can not be defined in any course types, by default').'
        • '; + $resulttext .= '
        • '.$status{$item}{'default'}.'
        • '; } } } @@ -21356,7 +22116,7 @@ sub modify_wafproxy { } } elsif ($currvalue{$item}) { $changes{$item} = 1; - } + } } } else { if (keys(%curralias)) { @@ -21364,7 +22124,7 @@ sub modify_wafproxy { } if (keys(%currsaml)) { $changes{'saml'} = 1; - } + } if (keys(%currvalue)) { foreach my $key (keys(%currvalue)) { $changes{$key} = 1; @@ -21374,7 +22134,7 @@ sub modify_wafproxy { if (keys(%changes)) { my %defaultshash = ( wafproxy => \%wafproxy, - ); + ); my $putresult = &Apache::lonnet::put_dom('configuration',\%defaultshash, $dom); if ($putresult eq 'ok') { @@ -21390,7 +22150,7 @@ sub modify_wafproxy { $domdefaults{'waf_'.$item} = $wafproxy{$item}; } elsif (exists($domdefaults{'waf_'.$item})) { delete($domdefaults{'waf_'.$item}); - } + } } } if ($updatedomdefs) { @@ -21457,7 +22217,7 @@ sub modify_wafproxy { $output .= '
        • '.&mt('Aliases deleted for hostnames').'
        • '; } } elsif ($item eq 'saml') { - my $shown; + my $shown; if (ref($wafproxy{'saml'}) eq 'HASH') { if (keys(%{$wafproxy{'saml'}})) { $shown = join(', ',sort(keys(%{$wafproxy{'saml'}}))); @@ -21787,7 +22547,7 @@ sub modify_usersessions { if (($offload eq 'offloadoth') && (@okoffloadoth)) { $changes{'offloadoth'} = 1; } - } + } } } else { if (@okoffload) { @@ -22325,7 +23085,7 @@ sub modify_loadbalancing { } if ($env{'form.loadbalancing_cookie_'.$i}) { $defaultshash{'loadbalancing'}{$balancer}{'cookie'} = 1; - if (exists($currbalancer{$balancer})) { + if (exists($currbalancer{$balancer})) { unless ($currcookies{$balancer}) { $changes{'curr'}{$balancer}{'cookie'} = 1; } @@ -23011,7 +23771,6 @@ function balancerChange(balnum,baltotal, END } - sub new_spares_js { my @sparestypes = ('primary','default'); my $types = join("','",@sparestypes);
    '; my $rem; my %checks; - my %current; if (ref($settings) eq 'HASH') { my $hashref; if ($context eq 'lti') { @@ -11744,7 +12106,7 @@ sub modifiable_userdata_row { } } } - if (ref($hashref) eq 'HASH') { + if (ref($hashref) eq 'HASH') { foreach my $field (@fields) { if ($hashref->{$field}) { if ($role eq 'emailusername') { @@ -11756,7 +12118,6 @@ sub modifiable_userdata_row { } } } - my $total = scalar(@fields); for (my $i=0; $i<$total; $i++) { $rem = $i%($numinrow); @@ -11845,15 +12206,19 @@ sub insttypes_row { my ($settings,$types,$usertypes,$dom,$numinrow,$othertitle,$context,$rowtotal,$onclick, $customcss,$rowstyle) = @_; my %lt = &Apache::lonlocal::texthash ( - cansearch => 'Users allowed to search', + cansearch => 'Users allowed to search', statustocreate => 'Institutional affiliation(s) able to create own account (login/SSO)', - lockablenames => 'User preference to lock name', - selfassign => 'Self-reportable affiliations', - overrides => "Override domain's helpdesk settings based on requester's affiliation", + lockablenames => 'User preference to lock name', + selfassign => 'Self-reportable affiliations', + overrides => "Override domain's helpdesk settings based on requester's affiliation", + webdav => 'WebDAV access available', + authorquota => 'Authoring Space quota (MB)', ); - my $showdom; + my ($showdom,$defaultquota); if ($context eq 'cansearch') { $showdom = ' ('.$dom.')'; + } elsif ($context eq 'authorquota') { + $defaultquota = 500; } my $class = 'LC_left_item'; if ($context eq 'statustocreate') { @@ -11890,25 +12255,44 @@ sub insttypes_row { } $output .= ''; } - my $check = ' '; - if (ref($settings) eq 'HASH') { - if (ref($settings->{$context}) eq 'ARRAY') { - if (grep(/^\Q$types->[$i]\E$/,@{$settings->{$context}})) { - $check = ' checked="checked" '; - } - } elsif (ref($settings->{$context}) eq 'HASH') { - if (ref($settings->{$context}->{$types->[$i]}) eq 'HASH') { + if ($context eq 'authorquota') { + my $currquota; + if ($settings->{$context}->{$types->[$i]} =~ /^\d+$/) { + $currquota = $settings->{$context}->{$types->[$i]}; + } else { + $currquota = $defaultquota; + } + $output .= ''; + } else { + my $check = ' '; + if (ref($settings) eq 'HASH') { + if (ref($settings->{$context}) eq 'ARRAY') { + if (grep(/^\Q$types->[$i]\E$/,@{$settings->{$context}})) { + $check = ' checked="checked" '; + } + } elsif (ref($settings->{$context}) eq 'HASH') { + if (ref($settings->{$context}->{$types->[$i]}) eq 'HASH') { + $check = ' checked="checked" '; + } elsif ($context eq 'webdav') { + if ($settings->{$context}->{$types->[$i]}) { + $check = ' checked="checked" '; + } + } + } elsif ($context eq 'statustocreate') { $check = ' checked="checked" '; } - } elsif ($context eq 'statustocreate') { - $check = ' checked="checked" '; } + $output .= ''; } - $output .= ''; } } $rem = @{$types}%($numinrow); @@ -11920,7 +12304,7 @@ sub insttypes_row { } else { $output .= ''; @@ -11930,20 +12314,41 @@ sub insttypes_row { } else { $output .= '
    '."\n". + ''. + ''. - ''; } - $output .= ' '; + $output .= ' '; } else { if ($rem == 0) { $output .= '
    '; } - my $defcheck = ' '; - if (ref($settings) eq 'HASH') { - if (ref($settings->{$context}) eq 'ARRAY') { - if (grep(/^default$/,@{$settings->{$context}})) { + if ($context eq 'authorquota') { + my $currquota = 500; + if ((ref($settings) eq 'HASH') && (ref($settings->{$context}) eq 'HASH')) { + if ($settings->{$context}{'default'} =~ /^\d+$/) { + $currquota = $settings->{$context}{'default'}; + } + } + $output .= ''; + } else { + my $defcheck = ' '; + if (ref($settings) eq 'HASH') { + if (ref($settings->{$context}) eq 'ARRAY') { + if (grep(/^default$/,@{$settings->{$context}})) { + $defcheck = ' checked="checked" '; + } + } elsif (ref($settings->{$context}) eq 'HASH') { + if (ref($settings->{$context}->{'default'}) eq 'HASH') { + $defcheck = ' checked="checked" '; + } elsif ($context eq 'webdav') { + if ($settings->{$context}->{'default'}) { + $defcheck = ' checked="checked" '; + } + } + } elsif ($context eq 'statustocreate') { $defcheck = ' checked="checked" '; } - } elsif ($context eq 'statustocreate') { - $defcheck = ' checked="checked" '; } + $output .= ''; } - $output .= ''; } $output .= '