--- loncom/auth/lonroles.pm 2010/08/01 18:34:19 1.256
+++ loncom/auth/lonroles.pm 2014/04/05 12:25:19 1.269.2.17
@@ -1,7 +1,7 @@
# The LearningOnline Network with CAPA
# User Roles Screen
#
-# $Id: lonroles.pm,v 1.256 2010/08/01 18:34:19 raeburn Exp $
+# $Id: lonroles.pm,v 1.269.2.17 2014/04/05 12:25:19 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -138,6 +138,8 @@ use Apache::lonlocal;
use Apache::lonpageflip();
use Apache::lonnavdisplay();
use Apache::loncoursequeueadmin;
+use Apache::longroup;
+use Apache::lonrss;
use GDBM_File;
use LONCAPA qw(:DEFAULT :match);
use HTML::Entities;
@@ -149,6 +151,7 @@ sub redirect_user {
&Apache::loncommon::content_type($r,'text/html');
&Apache::loncommon::no_cache($r);
$r->send_http_header;
+ my $swinfo=&Apache::lonmenu::rawconfig();
# Breadcrumbs
my $brcrum = [{'href' => $url,
@@ -163,6 +166,11 @@ sub redirect_user {
$url=~s/ /\%20/g;
$r->print(<
+//
+
$msg
$end_page
ENDREDIR
@@ -203,13 +211,48 @@ sub handler {
my $now=time;
my $then=$env{'user.login.time'};
my $refresh=$env{'user.refresh.time'};
+ my $update=$env{'user.update.time'};
if (!$refresh) {
$refresh = $then;
}
+ if (!$update) {
+ $update = $then;
+ }
+
+ &Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'});
+
+# -------------------------------------------------- Check if setting hot list
+ my $hotlist;
+ if ($env{'form.action'} eq 'verify_and_change_rolespref') {
+ $hotlist = &Apache::lonpreferences::verify_and_change_rolespref($r);
+ }
+
+# -------------------------------------------------------- Check for new roles
+ my $updateresult;
+ if ($env{'form.state'} eq 'doupdate') {
+ my $show_course=&Apache::loncommon::show_course();
+ my $checkingtxt;
+ if ($show_course) {
+ $checkingtxt = &mt('Checking for new courses ...');
+ } else {
+ $checkingtxt = &mt('Checking for new roles ...');
+ }
+ $updateresult = $checkingtxt;
+ $updateresult .= &update_session_roles();
+ &Apache::lonnet::appenv({'user.update.time' => $now});
+ $update = $now;
+ &Apache::loncoursequeueadmin::reqauthor_check();
+ }
+
+# -------------------------------------------------- Check for author requests
+ my $reqauthor;
+ if ($env{'form.state'} eq 'requestauthor') {
+ $reqauthor = &Apache::loncoursequeueadmin::process_reqauthor(\$update);
+ }
+
my $envkey;
my %dcroles = ();
- my $numdc = &check_fordc(\%dcroles,$then);
- &Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'});
+ my $numdc = &check_fordc(\%dcroles,$update,$then);
my $loncaparev = $Apache::lonnet::perlvar{'lonVersion'};
# ================================================================== Roles Init
@@ -228,13 +271,13 @@ sub handler {
if (defined($env{'user.role.'.$env{'form.switchrole'}})) {
my ($start,$end) = split(/\./,$env{'user.role.'.$env{'form.switchrole'}});
if (!$end || $end > $now) {
- if (!$start || $start < $refresh) {
+ if (!$start || $start < $update) {
$switch_is_active = 1;
}
}
}
unless ($switch_is_active) {
- &adhoc_course_role($refresh,$then);
+ &adhoc_course_role($refresh,$update,$then);
}
}
my %temp=('logout_'.$env{'request.course.id'} => time);
@@ -245,18 +288,21 @@ sub handler {
"request.course.fn" => '',
"request.course.uri" => '',
"request.course.sec" => '',
+ "request.course.tied" => '',
"request.role" => 'cm',
"request.role.adv" => $env{'user.adv'},
"request.role.domain" => $env{'user.domain'}});
# Check if user is a DC trying to enter a course or author space and needs privs to be created
if ($numdc > 0) {
- foreach my $envkey (keys %env) {
+ foreach my $envkey (keys(%env)) {
# Is this an ad-hoc Coordinator role?
if (my ($ccrole,$domain,$coursenum) =
($envkey =~ m-^form\.(cc|co)\./($match_domain)/($match_courseid)$-)) {
if ($dcroles{$domain}) {
- &Apache::lonnet::check_adhoc_privs($domain,$coursenum,
- $then,$refresh,$now,$ccrole);
+ if (&Apache::lonnet::check_adhoc_privs($domain,$coursenum,
+ $update,$refresh,$now,$ccrole)) {
+ &Apache::lonnet::appenv({"environment.internal.$domain.$coursenum.$ccrole.adhoc" => time});
+ }
}
last;
}
@@ -271,6 +317,7 @@ sub handler {
my $trolecode = 'au./'.$domain.'/';
my $switchserver = '/adm/switchserver?otherserver='.$home.'&role='.$trolecode;
$r->internal_redirect($switchserver);
+ return OK;
}
last;
}
@@ -282,6 +329,7 @@ sub handler {
my $trolecode = 'ca./'.$domain.'/'.$user;
my $switchserver = '/adm/switchserver?otherserver='.$home.'&role='.$trolecode;
$r->internal_redirect($switchserver);
+ return OK;
}
last;
}
@@ -296,13 +344,14 @@ sub handler {
if ($dcroles{$domain}) {
my ($server_status,$home) = &check_author_homeserver($user,$domain);
if (($server_status eq 'ok') || ($server_status eq 'switchserver')) {
- &Apache::lonnet::check_adhoc_privs($domain,$user,$then,
+ &Apache::lonnet::check_adhoc_privs($domain,$user,$update,
$refresh,$now,'ca');
if ($server_status eq 'switchserver') {
my $trolecode = 'ca./'.$domain.'/'.$user;
my $switchserver = '/adm/switchserver?'
.'otherserver='.$home.'&role='.$trolecode;
$r->internal_redirect($switchserver);
+ return OK;
}
} else {
delete($env{$envkey});
@@ -315,10 +364,10 @@ sub handler {
}
}
- foreach $envkey (keys %env) {
+ foreach $envkey (keys(%env)) {
next if ($envkey!~/^user\.role\./);
my ($where,$trolecode,$role,$tstatus,$tend,$tstart);
- &Apache::lonnet::role_status($envkey,$then,$refresh,$now,\$role,\$where,
+ &Apache::lonnet::role_status($envkey,$update,$refresh,$now,\$role,\$where,
\$trolecode,\$tstatus,\$tstart,\$tend);
if ($env{'form.'.$trolecode}) {
if ($tstatus eq 'is') {
@@ -477,16 +526,39 @@ ENDENTERKEY
if (($cnum) && ($role ne 'ca') && ($role ne 'aa')) {
my $msg;
- my ($furl,$ferr)=
- &Apache::lonuserstate::readmap($cdom.'/'.$cnum);
+ my ($furl,$ferr)=
+ &Apache::lonuserstate::readmap($cdom.'/'.$cnum);
+ unless ($ferr) {
+ unless (($env{'form.switchrole'}) ||
+ ($env{"environment.internal.$cdom.$cnum.$role.adhoc"})) {
+ &Apache::lonnet::put('nohist_crslastlogin',
+ {$env{'user.name'}.':'.$env{'user.domain'}.
+ ':'.$csec.':'.$role => $now},$cdom,$cnum);
+ }
+ my ($feeds,$syllabus_time);
+ &Apache::lonrss::advertisefeeds($cnum,$cdom,undef,\$feeds);
+ &Apache::lonnet::appenv({'request.course.feeds' => $feeds});
+ &Apache::lonnet::get_numsuppfiles($cnum,$cdom,1);
+ unless ($env{'course.'.$cdom.'_'.$cnum.'.updatedsyllabus'}) {
+ unless (($env{'course.'.$cdom.'_'.$cnum.'.externalsyllabus'}) ||
+ ($env{'course.'.$cdom.'_'.$cnum.'.uploadedsyllabus'})) {
+ my %syllabus=&Apache::lonnet::dump('syllabus',$cdom,$cnum);
+ $syllabus_time = $syllabus{'uploaded.lastmodified'};
+ if ($syllabus_time) {
+ &Apache::lonnet::appenv({'request.course.syllabustime' => $syllabus_time});
+ }
+ }
+ }
+ }
if (($env{'form.orgurl'}) &&
- ($env{'form.orgurl'}!~/^\/adm\/flip/)) {
+ ($env{'form.orgurl'}!~/^\/adm\/flip/) &&
+ ($env{'form.orgurl'} ne '/adm/roles')) {
my $dest=$env{'form.orgurl'};
if ($env{'form.symb'}) {
if ($dest =~ /\?/) {
$dest .= '&';
} else {
- $dest .= '?'
+ $dest .= '?';
}
$dest .= 'symb='.$env{'form.symb'};
}
@@ -498,7 +570,8 @@ ENDENTERKEY
if ($dest =~ m{^/adm/coursedocs\?folderpath}) {
if ($env{'request.course.id'} eq $cdom.'_'.$cnum) {
my $chome = &Apache::lonnet::homeserver($cnum,$cdom);
- &update_content_constraints($cdom,$cnum,$chome,$cdom.'_'.$cnum);
+ &Apache::loncommon::update_content_constraints($cdom,$cnum,$chome,
+ $cdom.'_'.$cnum);
}
}
$r->internal_redirect($dest);
@@ -524,24 +597,60 @@ ENDENTERKEY
} else {
# Check to see if the user is a CC entering a course
# for the first time
- my (undef, undef, $role, $courseid) = split(/\./, $envkey);
- if (substr($courseid, 0, 1) eq '/') {
- $courseid = substr($courseid, 1);
- }
- $courseid =~ s/\//_/;
if ((($role eq 'cc') || ($role eq 'co'))
- && ($env{'course.' . $courseid .'.course.helper.not.run'})) {
+ && ($env{'course.' .$cdom.'_'.$cnum.'.course.helper.not.run'})) {
$furl = "/adm/helper/course.initialization.helper";
# Send the user to the course they selected
} elsif ($env{'request.course.id'}) {
- if ($env{'form.destinationurl'}) {
- my $dest = $env{'form.destinationurl'};
- if ($env{'form.destsymb'} ne '') {
- my $esc_symb = &HTML::Entities::encode($env{'form.destsymb'},'"<>&');
- $dest .= '?symb='.$esc_symb;
+ my ($dest,$destsymb,$checkenc);
+ $dest = $env{'form.destinationurl'};
+ $destsymb = $env{'form.destsymb'};
+ if ($dest ne '') {
+ if ($env{'form.switchrole'}) {
+ if ($destsymb ne '') {
+ if ($destsymb !~ m{^/enc/}) {
+ unless ($env{'request.role.adv'}) {
+ $checkenc = 1;
+ }
+ }
+ }
+ if ($dest =~ m{^/enc/}) {
+ if ($env{'request.role.adv'}) {
+ $dest = &Apache::lonenc::unencrypted($dest);
+ if ($destsymb eq '') {
+ ($destsymb) = ($dest =~ /(?:\?|\&)symb=([^\&]*)/);
+ $destsymb = &unescape($destsymb);
+ }
+ }
+ } else {
+ if ($destsymb eq '') {
+ ($destsymb) = ($dest =~ /(?:\?|\&)symb=([^\&]+)/);
+ $destsymb = &unescape($destsymb);
+ }
+ unless ($env{'request.role.adv'}) {
+ $checkenc = 1;
+ }
+ }
+ if (($checkenc) && ($destsymb ne '')) {
+ my ($encstate,$unencsymb,$res);
+ $unencsymb = &Apache::lonnet::symbclean($destsymb);
+ (undef,undef,$res) = &Apache::lonnet::decode_symb($unencsymb);
+ &Apache::lonnet::symbverify($unencsymb,$res,\$encstate);
+ if ($encstate) {
+ if (($dest ne '') && ($dest !~ m{^/enc/})) {
+ $dest=&Apache::lonenc::encrypted($dest);
+ }
+ }
+ }
+ }
+ unless (($dest =~ m{^/enc/}) || ($dest =~ /(\?|\&)symb=.+___\d+___.+/)) {
+ if (($destsymb ne '') && ($destsymb !~ m{^/enc/})) {
+ my $esc_symb = &escape($destsymb);
+ $dest .= '?symb='.$esc_symb;
+ }
}
&redirect_user($r, &mt('Entering [_1]',
- $env{'course.'.$courseid.'.description'}),
+ $env{'course.'.$env{'request.course.id'}.'.description'}),
$dest, $msg);
return OK;
}
@@ -551,25 +660,36 @@ ENDENTERKEY
$env{'request.course.id'}.'/'
.$env{'request.course.sec'})
) {
- my $startpage = &courseloadpage($courseid);
+ my $startpage = &courseloadpage($env{'request.course.id'});
unless ($startpage eq 'firstres') {
$msg = &mt('Entering [_1] ...',
- $env{'course.'.$courseid.'.description'});
+ $env{'course.'.$env{'request.course.id'}.'.description'});
&redirect_user($r, &mt('New in course'),
'/adm/whatsnew?refpage=start', $msg);
return OK;
}
}
}
-# Are we allowed to look at the first resource?
- if ($furl !~ m|^/adm/|) {
-# Guess not ...
- $furl=&Apache::lonpageflip::first_accessible_resource();
- }
+ # Are we allowed to look at the first resource?
+ if ($furl =~ m{^(/adm/wrapper|)/ext/}) {
+ # If it's an external resource,
+ # strip off the symb argument and possible query
+ my ($exturl,$symb) = ($furl =~ m{^(.+)(?:\?|\&)symb=(.+)$});
+ # Unencode $symb
+ $symb = &unescape($symb);
+ # Then check for permission
+ if (!&Apache::lonnet::allowed('bre',$exturl,$symb)) {
+ $furl = &Apache::lonpageflip::first_accessible_resource();
+ }
+ # For other resources just check for permission
+ } elsif (!&Apache::lonnet::allowed('bre',$furl)) {
+ $furl = &Apache::lonpageflip::first_accessible_resource();
+ }
+
$msg = &mt('Entering [_1] ...',
- $env{'course.'.$courseid.'.description'});
+ $env{'course.'.$cdom.'_'.$cnum.'.description'});
&redirect_user($r, &mt('Entering [_1]',
- $env{'course.'.$courseid.'.description'}),
+ $env{'course.'.$cdom.'_'.$cnum.'.description'}),
$furl, $msg);
}
return OK;
@@ -580,13 +700,12 @@ ENDENTERKEY
if ($role =~ /^(au|ca|aa)$/) {
my $redirect_url = '/priv/';
if ($role eq 'au') {
- $redirect_url.=$env{'user.name'};
+ $redirect_url.=$env{'user.domain'}.'/'.$env{'user.name'};
} else {
- $where =~ /\/(.*)$/;
- $redirect_url .= $1;
+ $redirect_url .= $where;
}
$redirect_url .= '/';
- &redirect_user($r,&mt('Entering Construction Space'),
+ &redirect_user($r,&mt('Entering Authoring Space'),
$redirect_url);
return OK;
}
@@ -618,22 +737,28 @@ ENDENTERKEY
my $crumbtext = 'User Roles';
my $pagetitle = 'My Roles';
my $recent = &mt('Recent Roles');
+ my $standby = &mt('Role selected. Please stand by.');
my $show_course=&Apache::loncommon::show_course();
if ($show_course) {
$crumbtext = 'Courses';
$pagetitle = 'My Courses';
$recent = &mt('Recent Courses');
+ $standby = &mt('Course selected. Please stand by.');
}
my $brcrum =[{href=>"/adm/roles",text=>$crumbtext}];
+
+ my %roles_in_env;
+ my $showcount = &roles_from_env(\%roles_in_env,$update);
+
my $swinfo=&Apache::lonmenu::rawconfig();
my $start_page=&Apache::loncommon::start_page($pagetitle,undef,{bread_crumbs=>$brcrum});
- my $standby=&mt('Role selected. Please stand by.');
+ my $funcs = &get_roles_functions($showcount);
$standby=~s/\n/\\n/g;
- my $noscript=''.&mt('Use of LON-CAPA requires Javascript to be enabled in your web browser.').' '.&mt('As this is not the case, most functionality in the system will be unavailable.').' ';
+ my $noscript=''.&mt('Use of LON-CAPA requires Javascript to be enabled in your web browser.').' '.&mt('As this is not the case, most functionality in the system will be unavailable.').' ';
$r->print(<
+$funcs
$noscript
@@ -653,8 +778,22 @@ function enterrole (thisform,rolecode,bu
thisform.submit();
} else {
alert('$standby');
- }
+ }
}
+
+function rolesView (caller) {
+ if ((caller == 'showall') || (caller == 'noshowall')) {
+ document.rolechoice.display.value = caller;
+ } else {
+ if ((caller == 'doupdate') || (caller == 'requestauthor') ||
+ (caller == 'queued')) {
+ document.rolechoice.state.value = caller;
+ }
+ }
+ document.rolechoice.selectrole.value='';
+ document.rolechoice.submit();
+}
+
// ]]>
ENDHEADER
@@ -715,47 +854,60 @@ ENDHEADER
}
}
}
-# -------------------------------------------------------- Choice or no choice?
if ($nochoose) {
$r->print("".&mt('Sorry ...')." \n".
&mt('This action is currently not authorized.').' '.
&Apache::loncommon::end_page());
return OK;
} else {
+ if ($updateresult || $reqauthor || $hotlist) {
+ my $showresult = '';
+ if ($updateresult) {
+ $showresult .= &Apache::lonhtmlcommon::confirm_success($updateresult);
+ }
+ if ($reqauthor) {
+ $showresult .= &Apache::lonhtmlcommon::confirm_success($reqauthor);
+ }
+ if ($hotlist) {
+ $showresult .= $hotlist;
+ }
+ $showresult .= '
';
+ $r->print($showresult);
+ } elsif ($env{'form.state'} eq 'queued') {
+ $r->print(&get_queued());
+ }
if (($ENV{'REDIRECT_QUERY_STRING'}) && ($fn)) {
$fn.='?'.$ENV{'REDIRECT_QUERY_STRING'};
}
+ my $display = ($env{'form.display'} =~ /^(showall)$/);
$r->print('
';
+ }
+ } elsif ($currrole_expired) {
+ $msg .= '';
+ if (&Apache::loncommon::show_course()) {
+ $msg .= &mt('Your role in the current course has expired.');
+ } else {
+ $msg .= &mt('Your current role has expired.');
+ }
+ $msg .= ' '.&mt('However you can continue to use this role until you logout, click the "Re-Select" button, or your session has been idle for more than 24 hours.').'
';
+ }
+ &Apache::lonnet::set_userprivs(\%userroles,\%allroles,\%allgroups,\%groups_roles);
+ my ($curr_is_adv,$curr_role_adv,$curr_author,$curr_role_author);
+ $curr_author = $env{'user.author'};
+ if (($env{'request.role'} =~/^au/) || ($env{'request.role'} =~/^ca/) ||
+ ($env{'request.role'} =~/^aa/)) {
+ $curr_role_author=1;
+ }
+ $curr_is_adv = $env{'user.adv'};
+ $curr_role_adv = $env{'request.role.adv'};
+ if (keys(%userroles) > 0) {
+ foreach my $role (@changed_roles) {
+ unless(grep(/^\Q$role\E$/,@rolecodes)) {
+ push(@rolecodes,$role);
+ }
+ }
+ unless(grep(/^\Qcm\E$/,@rolecodes)) {
+ push(@rolecodes,'cm');
+ }
+ &Apache::lonnet::appenv(\%userroles,\@rolecodes);
+ }
+ my %newenv;
+ if (&Apache::lonnet::is_advanced_user($env{'user.domain'},$env{'user.name'})) {
+ unless ($curr_is_adv) {
+ $newenv{'user.adv'} = 1;
+ }
+ } elsif ($curr_is_adv && !$curr_role_adv) {
+ &Apache::lonnet::delenv('user.adv');
+ }
+ my %authorroleshash =
+ &Apache::lonnet::get_my_roles('','','userroles',['active'],['au','ca','aa']);
+ if (keys(%authorroleshash)) {
+ unless ($curr_author) {
+ $newenv{'user.author'} = 1;
+ }
+ } elsif ($curr_author && !$curr_role_author) {
+ &Apache::lonnet::delenv('user.author');
+ }
+ if ($env{'request.course.id'}) {
+ my $cdom = $env{'course.'.$env{'request.course.id'}.'.domain'};
+ my $cnum = $env{'course.'.$env{'request.course.id'}.'.num'};
+ my (@activecrsgroups,$crsgroupschanged);
+ if ($env{'request.course.groups'}) {
+ @activecrsgroups = split(/:/,$env{'request.course.groups'});
+ foreach my $item (keys(%deletedroles)) {
+ if ($item =~ m{^gr\./\Q$cdom\E/\Q$cnum\E/(\w+)$}) {
+ if (grep(/^\Q$1\E$/,@activecrsgroups)) {
+ $crsgroupschanged = 1;
+ last;
+ }
+ }
+ }
+ }
+ unless ($crsgroupschanged) {
+ foreach my $item (keys(%newgroup)) {
+ if ($item =~ m{^gr\./\Q$cdom\E/\Q$cnum\E/(\w+)$}) {
+ if ($newgroup{$item} eq 'active') {
+ $crsgroupschanged = 1;
+ last;
+ }
+ }
+ }
+ }
+ if ((ref($changed_groups{$env{'request.course.id'}}) eq 'HASH') ||
+ (ref($groupchange{"/$cdom/$cnum"}) eq 'HASH') ||
+ ($crsgroupschanged)) {
+ my %grouproles = &Apache::lonnet::get_my_roles('','','userroles',
+ ['active'],['gr'],[$cdom],1);
+ my @activegroups;
+ foreach my $item (keys(%grouproles)) {
+ next unless($item =~ /^\Q$cnum\E:\Q$cdom\E/);
+ my $group;
+ my ($crsn,$crsd,$role,$remainder) = split(/:/,$item,4);
+ if ($remainder =~ /:/) {
+ (my $other,$group) = ($remainder =~ /^([\w:]+):([^:]+)$/);
+ } else {
+ $group = $remainder;
+ }
+ if ($group ne '') {
+ push(@activegroups,$group);
+ }
+ }
+ $newenv{'request.course.groups'} = join(':',@activegroups);
+ }
+ }
+ if (keys(%newenv)) {
+ &Apache::lonnet::appenv(\%newenv);
+ }
+ if (!@changed_roles || !(keys(%changed_groups))) {
+ my ($rolesmsg,$groupsmsg);
+ if (!@changed_roles) {
+ if (&Apache::loncommon::show_course()) {
+ $rolesmsg = &mt('No new courses or communities');
+ } else {
+ $rolesmsg = &mt('No role changes');
+ }
+ }
+ if ($hasgroups && !(keys(%changed_groups)) && !(grep(/gr/,@changed_roles))) {
+ $groupsmsg = &mt('No changes in course/community groups');
+ }
+ if (!@changed_roles && !(keys(%changed_groups))) {
+ if (($msg ne '') || ($groupsmsg ne '')) {
+ $msg .= '';
+ if ($rolesmsg) {
+ $msg .= ''.$rolesmsg.' ';
+ }
+ if ($groupsmsg) {
+ $msg .= ''.$groupsmsg.' ';
+ }
+ $msg .= ' ';
+ } else {
+ $msg = ' '.$rolesmsg.' ';
+ }
+ return $msg;
+ }
+ }
+ my $changemsg;
+ if (@changed_roles > 0) {
+ if (keys(%newgroup) > 0) {
+ my $groupmsg;
+ my (%curr_groups,%groupdescs,$currcrs);
+ foreach my $item (sort(keys(%newgroup))) {
+ if (&is_active_course($item,$refresh,$update,\%roleshash)) {
+ if ($item =~ m{^gr\./($match_domain/$match_courseid)/(\w+)$}) {
+ my ($cdom,$cnum) = split(/\//,$1);
+ my $group = $2;
+ if ($currcrs ne $cdom.'_'.$cnum) {
+ if ($currcrs) {
+ $groupmsg .= '';
+ }
+ $groupmsg .= ' '.
+ $env{'course.'.$cdom.'_'.$cnum.'.description'}.' ';
+ $currcrs = $cdom.'_'.$cnum;
+ }
+ my $groupdesc;
+ unless (ref($curr_groups{$cdom.'_'.$cnum}) eq 'HASH') {
+ %{$curr_groups{$cdom.'_'.$cnum}} =
+ &Apache::longroup::coursegroups($cdom,$cnum);
+ }
+ unless ((ref($groupdescs{$cdom.'_'.$cnum}) eq 'HASH') &&
+ ($groupdescs{$cdom.'_'.$cnum}{$group})) {
+
+ my %groupinfo =
+ &Apache::longroup::get_group_settings($curr_groups{$cdom.'_'.$cnum}{$group});
+ $groupdescs{$cdom.'_'.$cnum}{$group} =
+ &unescape($groupinfo{'description'});
+ }
+ $groupdesc = $groupdescs{$cdom.'_'.$cnum}{$group};
+ if ($groupdesc) {
+ $groupmsg .= ''.
+ &mt('[_1] with status: [_2].',
+ ''.$groupdesc.' ',$newgroup{$item}).' ';
+ }
+ }
+ }
+ if ($groupmsg) {
+ $groupmsg .= ' ';
+ }
+ }
+ if ($groupmsg) {
+ $changemsg .= ''.
+ &mt('Courses with new groups').' '.
+ '';
+ }
+ }
+ if (keys(%newrole) > 0) {
+ my $newmsg;
+ foreach my $item (sort(keys(%newrole))) {
+ my $desc = &role_desc($item,$update,$refresh,$now);
+ if ($desc) {
+ $newmsg .= ''.
+ &mt('[_1] with status: [_2].',
+ $desc,$newrole{$item}).' ';
+ }
+ }
+ if ($newmsg) {
+ $changemsg .= ''.&mt('New roles').
+ ''.
+ ' ';
+ }
+ }
+ if (keys(%customprivchg) > 0) {
+ my $privmsg;
+ foreach my $item (sort(keys(%customprivchg))) {
+ my $desc = &role_desc($item,$update,$refresh,$now);
+ if ($desc) {
+ $privmsg .= ''.$desc.' ';
+ }
+ }
+ if ($privmsg) {
+ $changemsg .= ''.
+ &mt('Custom roles with privilege changes').
+ ''.
+ ' ';
+ }
+ }
+ if (keys(%rolechange) > 0) {
+ my $rolemsg;
+ foreach my $item (sort(keys(%rolechange))) {
+ my $desc = &role_desc($item,$update,$refresh,$now);
+ if ($desc) {
+ $rolemsg .= ''.
+ &mt('[_1] status now: [_2].',$desc,
+ $rolechange{$item}).' ';
+ }
+ }
+ if ($rolemsg) {
+ $changemsg .= ''.
+ &mt('Existing roles with status changes').' '.
+ ''.
+ '';
+ }
+ }
+ if (keys(%deletedroles) > 0) {
+ my $delmsg;
+ foreach my $item (sort(keys(%deletedroles))) {
+ my $desc = &role_desc($item,$update,$refresh,$now);
+ if ($desc) {
+ $delmsg .= ''.$desc.' ';
+ }
+ }
+ if ($delmsg) {
+ $changemsg .= ''.
+ &mt('Existing roles now expired').' '.
+ ''.
+ '';
+ }
+ }
+ }
+ if ((keys(%changed_groups) > 0) || (keys(%groupchange) > 0)) {
+ my $groupchgmsg;
+ foreach my $key (sort(keys(%changed_groups))) {
+ my $crs = 'gr/'.$key;
+ $crs =~ s/_/\//;
+ if (&is_active_course($crs,$refresh,$update,\%roleshash)) {
+ if (ref($changed_groups{$key}) eq 'HASH') {
+ my @showgroups;
+ foreach my $group (sort(keys(%{$changed_groups{$key}}))) {
+ if ($changed_groups{$key}{$group} eq 'active') {
+ push(@showgroups,$group);
+ }
+ }
+ if (@showgroups > 0) {
+ $groupchgmsg .= ''.
+ &mt('Course: [_1], groups: [_2].',$key,
+ join(', ',@showgroups)).
+ ' ';
+ }
+ }
+ }
+ }
+ if (keys(%groupchange) > 0) {
+ $groupchgmsg .= ''.
+ &mt('Existing course/community groups with status changes').' '.
+ '';
+ foreach my $crs (sort(keys(%groupchange))) {
+ my $cid = $crs;
+ $cid=~s{^/}{};
+ $cid=~s{/}{_};
+ my $crsdesc = $env{'course.'.$cid.'.description'};
+ my $cdom = $env{'course.'.$cid.'.domain'};
+ my $cnum = $env{'course.'.$cid.'.num'};
+ my %curr_groups = &Apache::longroup::coursegroups($cdom,$cnum);
+ my %groupdesc;
+ if (ref($groupchange{$crs}) eq 'HASH') {
+ $groupchgmsg .= ''.&mt('Course/Community: [_1]',''.$crsdesc.' ');
+ foreach my $group (sort(keys(%{$groupchange{$crs}}))) {
+ unless ($groupdesc{$group}) {
+ my %groupinfo = &Apache::longroup::get_group_settings($curr_groups{$group});
+ $groupdesc{$group} = &unescape($groupinfo{'description'});
+ }
+ $groupchgmsg .= ''.&mt('Group: [_1] status now: [_2].',''.$groupdesc{$group}.' ',$groupchange{$crs}{$group}).' ';
+ }
+ $groupchgmsg .= ' ';
+ }
+ }
+ $groupchgmsg .= ' ';
+ }
+ if ($groupchgmsg) {
+ $changemsg .= ''.
+ &mt('Courses with changes in groups').' '.
+ '';
+ }
+ }
+ if ($changemsg) {
+ $msg .= '';
+ } else {
+ if (&Apache::loncommon::show_course()) {
+ $msg = &mt('No new courses or communities');
+ } else {
+ $msg = &mt('No role changes');
+ }
+ }
+ return $msg;
+}
+
+sub role_desc {
+ my ($item,$update,$refresh,$now) = @_;
+ my ($where,$trolecode,$role,$tstatus,$tend,$tstart,$twhere,
+ $trole,$tremark);
+ &Apache::lonnet::role_status('user.role.'.$item,$update,$refresh,
+ $now,\$role,\$where,\$trolecode,
+ \$tstatus,\$tstart,\$tend);
+ return unless ($role);
+ if ($role =~ /^cr\//) {
+ my ($rdummy,$rdomain,$rauthor,$rrole)=split(/\//,$role);
+ $tremark = &mt('Custom role defined by [_1].',$rauthor.':'.$rdomain);
+ }
+ $trole=Apache::lonnet::plaintext($role);
+ my ($tdom,$trest,$tsection)=
+ split(/\//,Apache::lonnet::declutter($where));
+ if (($role eq 'ca') || ($role eq 'aa')) {
+ my $home = &Apache::lonnet::homeserver($trest,$tdom);
+ $home = &Apache::lonnet::hostname($home);
+ $twhere=&mt('User').': '.$trest.' '.&mt('Domain').
+ ': '.$tdom.' '.&mt('Server').': '.$home;
+ } elsif ($role eq 'au') {
+ my $home = &Apache::lonnet::homeserver
+ ($env{'user.name'},$env{'user.domain'});
+ $home = &Apache::lonnet::hostname($home);
+ $twhere=&mt('Domain').': '.$tdom.' '.&mt('Server').
+ ': '.$home;
+ } elsif ($trest) {
+ my $tcourseid=$tdom.'_'.$trest;
+ my $crstype = &Apache::loncommon::course_type($tcourseid);
+ $trole = &Apache::lonnet::plaintext($role,$crstype,$tcourseid);
+ if ($env{'course.'.$tcourseid.'.description'}) {
+ $twhere=$env{'course.'.$tcourseid.'.description'};
+ } else {
+ my %newhash=&Apache::lonnet::coursedescription($tcourseid);
+ if (%newhash) {
+ $twhere=$newhash{'description'};
+ } else {
+ $twhere=&mt('Currently not available');
+ }
+ }
+ if ($tsection) {
+ $twhere.= ' '.&mt('Section').': '.$tsection;
+ }
+ if ($role ne 'st') {
+ $twhere.= ' '.&mt('Domain').': '.$tdom;
+ }
+ } elsif ($tdom) {
+ $twhere = &mt('Domain').': '.$tdom;
+ }
+ my $output;
+ if ($trole) {
+ $output = $trole;
+ if ($twhere) {
+ $output .= " -- $twhere";
+ }
+ if ($tremark) {
+ $output .= ' '.$tremark;
+ }
+ }
+ return $output;
+}
+
+sub curr_role_status {
+ my ($start,$end,$refresh,$update) = @_;
+ if (($start) && ($start<0)) { return 'deleted' };
+ my $status = 'active';
+ if (($end) && ($end<=$update)) {
+ $status = 'previous';
+ }
+ if (($start) && ($refresh<$start)) {
+ $status = 'future';
+ }
+ return $status;
+}
+
+sub gather_roleprivs {
+ my ($allroles,$allgroups,$userroles,$area,$role,$tstart,$tend,$status) = @_;
+ return unless ((ref($allroles) eq 'HASH') && (ref($allgroups) eq 'HASH') && (ref($userroles) eq 'HASH'));
+ if (($area ne '') && ($role ne '')) {
+ &Apache::lonnet::userrolelog($role,$env{'user.name'},$env{'user.domain'},
+ $area,$tstart,$tend);
+ my $spec=$role.'.'.$area;
+ $userroles->{'user.role.'.$spec} = $tstart.'.'.$tend;
+ my ($tdummy,$tdomain,$trest)=split(/\//,$area);
+ if ($status eq 'active') {
+ if ($role =~ /^cr\//) {
+ &Apache::lonnet::custom_roleprivs($allroles,$role,$tdomain,$trest,$spec,$area);
+ } elsif ($role eq 'gr') {
+ my %rolehash = &Apache::lonnet::get('roles',[$area.'_'.$role],
+ $env{'user.domain'},
+ $env{'user.name'});
+ my ($trole) = split(/_/,$rolehash{$area.'_'.$role},2);
+ (undef,my $group_privs) = split(/\//,$trole);
+ $group_privs = &unescape($group_privs);
+ &Apache::lonnet::group_roleprivs($allgroups,$area,$group_privs,$tend,$tstart);
+ } else {
+ &Apache::lonnet::standard_roleprivs($allroles,$role,$tdomain,$spec,$trest,$area);
+ }
+ }
+ }
+ return;
+}
+
+sub is_active_course {
+ my ($rolekey,$refresh,$update,$roleshashref) = @_;
+ return unless(ref($roleshashref) eq 'HASH');
+ my ($role,$cdom,$cnum) = split(/\//,$rolekey);
+ my $is_active;
+ foreach my $key (keys(%{$roleshashref})) {
+ if ($key =~ /^\Q$cnum\E:\Q$cdom\E:/) {
+ my ($tstart,$tend) = split(/:/,$roleshashref->{$key});
+ my $status = &curr_role_status($tstart,$tend,$refresh,$update);
+ if ($status eq 'active') {
+ $is_active = 1;
+ last;
+ }
+ }
+ }
+ return $is_active;
+}
+
+sub get_roles_functions {
+ my ($rolescount) = @_;
+ my @links;
+ push(@links,["javascript:rolesView('doupdate');",'start-here-22x22',&mt('Check for changes')]);
+ if ($env{'environment.canrequest.author'}) {
+ unless (&Apache::loncoursequeueadmin::is_active_author()) {
+ push(@links,["javascript:rolesView('requestauthor');",'list-add-22x22',&mt('Request author role')]);
+ }
+ }
+ if (($rolescount > 3) || ($env{'environment.recentroles'})) {
+ push(@links,['/adm/preferences?action=changerolespref&returnurl=/adm/roles','role_hotlist-22x22',&mt('Hotlist')]);
+ }
+ if (&Apache::lonmenu::check_for_rcrs()) {
+ push(@links,['/adm/requestcourse','rcrs-22x22',&mt('Request course')]);
+ }
+ if ($env{'form.state'} eq 'queued') {
+ push(@links,["javascript:rolesView('noqueued');",'selfenrl-queue-22x22',&mt('Hide queued')]);
+ } else {
+ push(@links,["javascript:rolesView('queued');",'selfenrl-queue-22x22',&mt('Show queued')]);
+ }
+ if ($env{'user.adv'}) {
+ if ($env{'form.display'} eq 'showall') {
+ push(@links,["javascript:rolesView('noshowall');",'edit-redo-22x22',&mt('Exclude expired')]);
+ } else {
+ push(@links,["javascript:rolesView('showall');",'edit-undo-22x22',&mt('Include expired')]);
+ }
+ }
+ if (&Apache::loncommon::designparm('login.coursecatalog',$env{'user.domain'})) {
+ push(@links,['/adm/coursecatalog','ccat-22x22',&mt('Course catalog')]);
+ }
+ my $funcs = &Apache::lonhtmlcommon::start_funclist();
+ foreach my $link (@links) {
+ $funcs .= &Apache::lonhtmlcommon::add_item_funclist(
+ '');
+ }
+ $funcs .= &Apache::lonhtmlcommon::end_funclist();
+ return &Apache::loncommon::head_subbox($funcs);
+}
+
+sub get_queued {
+ my ($output,%reqcrs);
+ my ($types,$typenames) = &Apache::loncommon::course_types();
+ my %statusinfo = &Apache::lonnet::dump('courserequests',$env{'user.domain'},
+ $env{'user.name'},'^status:');
+ foreach my $key (keys(%statusinfo)) {
+ next unless (($statusinfo{$key} eq 'approval') || ($statusinfo{$key} eq 'pending'));
+ (undef,my($cdom,$cnum)) = split(/:/,$key);
+ my $requestkey = $cdom.'_'.$cnum;
+ if ($requestkey =~ /^($match_domain)_($match_courseid)$/) {
+ my %history = &Apache::lonnet::restore($requestkey,'courserequests',
+ $env{'user.domain'},$env{'user.name'});
+ next if ((exists($history{'status'})) && ($history{'status'} eq 'created'));
+ my $reqtime = $history{'reqtime'};
+ my $lastupdate = $history{'timestamp'};
+ my $showtype = $history{'crstype'};
+ if (defined($typenames->{$history{'crstype'}})) {
+ $showtype = $typenames->{$history{'crstype'}};
+ }
+ my $description;
+ if (ref($history{'details'}) eq 'HASH') {
+ $description = $history{details}{'cdescr'};
+ }
+ @{$reqcrs{$reqtime}} = ($description,$showtype);
+ }
+ }
+ my @sortedtimes = sort {$a <=> $b} (keys(%reqcrs));
+ if (@sortedtimes > 0) {
+ $output .= ''.&mt('Course/Community requests').' '.
+ &Apache::loncommon::start_data_table().
+ &Apache::loncommon::start_data_table_header_row().
+ '
'.&mt('Date requested').' '.
+ ''.&mt('Course title').' '.
+ ''.&mt('Course type').' ';
+ &Apache::loncommon::end_data_table_header_row();
+ foreach my $reqtime (@sortedtimes) {
+ next unless (ref($reqcrs{$reqtime}) eq 'ARRAY');
+ $output .= &Apache::loncommon::start_data_table_row().
+ ''.&Apache::lonlocal::locallocaltime($reqtime).' '.
+ ''.join(' ',@{$reqcrs{$reqtime}}).' '.
+ &Apache::loncommon::end_data_table_row();
+ }
+ $output .= &Apache::loncommon::end_data_table().
+ ' ';
+ }
+ my $queuedselfenroll = &Apache::loncoursequeueadmin::queued_selfenrollment(1);
+ if ($queuedselfenroll) {
+ $output .= ''.&mt('Enrollment requests').' '.
+ $queuedselfenroll.'
';
+ }
+ if ($env{'environment.canrequest.author'}) {
+ unless (&Apache::loncoursequeueadmin::is_active_author()) {
+ my $requestauthor;
+ my ($status,$timestamp) = split(/:/,$env{'environment.requestauthorqueued'});
+ if (($status eq 'approval') || ($status eq 'approved')) {
+ $output .= ''.&mt('Author role request').' ';
+ if ($status eq 'approval') {
+ $output .= &mt('A request for authoring space submitted on [_1] is awaiting approval',
+ &Apache::lonlocal::locallocaltime($timestamp));
+ } elsif ($status eq 'approved') {
+ my %roleshash =
+ &Apache::lonnet::get_my_roles($env{'user.name'},$env{'user.domain'},'userroles',
+ ['active'],['au'],[$env{'user.domain'}]);
+ if (keys(%roleshash)) {
+ $output .= ''.
+ &mt('Your request for an author role has been approved.').' '.
+ &mt('Use the "Check for changes" link to update your list of roles.').
+ ' ';
+ }
+ }
+ $output .= '
';
+ }
+ }
+ }
+ unless ($output) {
+ if ($env{'environment.canrequest.author'} || $env{'environment.canrequest.official'} ||
+ $env{'environment.canrequest.unofficial'} || $env{'environment.canrequest.community'}) {
+ $output = &mt('No requests for courses, communities or authoring currently queued');
+ } else {
+ $output = &mt('No enrollment requests currently queued awaiting approval');
+ }
+ }
+ return '
'.&mt('Queued requests').' '.
+ $output.' ';
+}
+
1;
__END__