--- loncom/interface/selfenroll.pm 2009/02/05 12:27:21 1.15
+++ loncom/interface/selfenroll.pm 2021/12/14 12:53:12 1.27.2.8
@@ -1,7 +1,7 @@
# The LearningOnline Network
# Allow users to self-enroll in a course
#
-# $Id: selfenroll.pm,v 1.15 2009/02/05 12:27:21 raeburn Exp $
+# $Id: selfenroll.pm,v 1.27.2.8 2021/12/14 12:53:12 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -34,6 +34,8 @@ use Apache::lonnet;
use Apache::loncommon;
use Apache::lonlocal;
use Apache::createaccount;
+use Apache::loncoursequeueadmin;
+use Apache::lonuserutils;
use LONCAPA qw(:DEFAULT :match);
sub handler {
@@ -53,9 +55,11 @@ sub handler {
&Apache::lonlocal::get_language_handle($r);
&Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'},['courseid']);
my $js = &Apache::createaccount::catreturn_js();
- my ($coursechk,$courseid) = &validate_course_id($env{'form.courseid'});
- if ($coursechk ne 'ok') {
- &page_header($r,$courseid,$js);
+
+ my $courseid = Apache::lonnet::is_course($env{'form.courseid'});
+
+ unless ($courseid) {
+ &page_header($r,$env{'form.courseid'},$js);
$r->print('
'.&mt('Self-enrollment error').'
'.
''.
&mt('Invalid domain or course number').'');
@@ -80,7 +84,7 @@ sub handler {
$knownuser,$selfenroll_access_start,$selfenroll_access_end,
$selfenroll_section,$selfenroll_future,%curr_role,$cdomdesc,
$selfenroll_approval,$selfenroll_limit,$selfenroll_cap,
- $selfenroll_notifylist,$owner);
+ $selfenroll_notifylist,$owner,$crstype);
$selfenroll_types = $coursehash{'internal.selfenroll_types'};
$selfenroll_registered = $coursehash{'internal.selfenroll_registered'};
$selfenroll_section = $coursehash{'internal.selfenroll_section'};
@@ -91,6 +95,10 @@ sub handler {
$selfenroll_approval = $coursehash{'internal.selfenroll_approval'};
$selfenroll_notifylist = $coursehash{'internal.selfenroll_notifylist'};
$owner = $coursehash{'internal.courseowner'};
+ $crstype = $coursehash{'internal.type'};
+ if ($crstype eq '') {
+ $crstype = 'Course';
+ }
my $nospace;
if ($selfenroll_types ne '') {
my $start = $coursehash{'internal.selfenroll_start_date'};
@@ -213,7 +221,8 @@ sub handler {
if ($sso_url eq '') {
$sso_url = $login_path;
}
- $missing_formitem = &mt('The link to the requested page could not be followed.')."\\n".&mt('The placeholder for the courseID is absent.');
+ $missing_formitem = &mt('The link to the requested page could not be followed.')."\n".&mt('The placeholder for the courseID is absent.');
+ &js_escape(\$missing_formitem);
if ($knownuser) {
if (keys(%curr_role)) {
$r->print(''.&mt('Self-enrollment unavailable').'
'.
@@ -224,7 +233,7 @@ sub handler {
&process_self_enroll($r,$cdom,$cnum,$selfenroll_types,$selfenroll_registered,
$selfenroll_access_start,$selfenroll_access_end,
$selfenroll_section,$now,$selfenroll_approval,
- $selfenroll_notifylist,$owner);
+ $selfenroll_notifylist,$owner,$crstype,$lonhost,$handle);
} elsif ($env{'form.phase'} eq 'login') {
my $submit_text = &mt('Log in');
$r->print(''.&mt('Log-in to LON-CAPA').'
');
@@ -358,17 +367,6 @@ sub page_footer {
return;
}
-sub validate_course_id {
- my ($courseid) = @_;
- my ($cdom,$cnum) = ($env{'form.courseid'} =~ /^($match_domain)_($match_courseid)$/);
- if ($cdom ne '' && $cnum ne '') {
- if (&Apache::lonnet::is_course($cdom,$cnum)) {
- return ('ok',$courseid);
- }
- }
- return;
-}
-
sub user_is_known {
my $known = 0;
if ($env{'user.name'} ne '' && $env{'user.name'} ne 'public'
@@ -404,7 +402,7 @@ sub has_role {
my $output;
if ($curr_role{'status'} eq 'active') {
my $rolelink = &jump_to_role($curr_role{'role'});
- $output = &mt('You already have an active student role (section: "[_1]") in this course.',$curr_role{'section'}).'
'.$rolelink;
+ $output = &mt('You already have an active student role (section: "[_1]") in this course.',$curr_role{'section'}).'
'.$rolelink;
} elsif ($curr_role{'status'} eq 'future') {
$output = &mt('You have a student role (section: "[_1]") in this course which will become active [_2].',$curr_role{'section'},$curr_role{'start'});
}
@@ -414,7 +412,7 @@ sub has_role {
sub process_self_enroll {
my ($r,$cdom,$cnum,$selfenroll_types,$selfenroll_registered,
$selfenroll_access_start,$selfenroll_access_end,$selfenroll_section,
- $now,$selfenroll_approval,$selfenroll_notifylist,$owner) = @_;
+ $now,$selfenroll_approval,$selfenroll_notifylist,$owner,$crstype,$lonhost,$handle) = @_;
my $udom = $env{'user.domain'};
my $uname = $env{'user.name'};
my $selfenroll = 0;
@@ -441,11 +439,13 @@ sub process_self_enroll {
if ($selfenroll_section eq 'none') {
$usec = '';
}
+ my $instcid;
if ($selfenroll_registered) {
- my ($registered,$instsec,$message) = &check_registered($cdom,$cnum);
+ my ($registered,$instsec,$instcid,$message) = &check_registered($cdom,$cnum);
$usec = $instsec;
if (!$registered) {
- $r->print(''.&mt('Self-enrollment unavailable').'
'.&mt('Self-enrollment is restricted to students officially registered for this course.').'
');
+ $r->print(''.&mt('Self-enrollment unavailable').'
'.
+ &mt('Self-enrollment is restricted to students officially registered for this course.').'
');
if ($message) {
$r->print($message);
} else {
@@ -456,14 +456,15 @@ sub process_self_enroll {
}
if ($selfenroll_approval) {
my $outcome =
- &store_selfenroll_request($udom,$uname,$usec,$cdom,$cnum,
- $selfenroll_notifylist,$owner);
+ &store_selfenroll_request($r,$udom,$uname,$usec,$cdom,$cnum,
+ $selfenroll_notifylist,$owner,
+ $selfenroll_approval,$crstype,$lonhost,$handle);
$r->print($outcome);
} else {
my $enrollresult =
&Apache::lonnet::modify_student_enrollment($udom,$uname,undef,undef,undef,
undef,undef,$usec,$selfenroll_access_end,$selfenroll_access_start,
- 'selfenroll',undef,$cdom.'_'.$cnum,$selfenroll);
+ 'selfenroll',undef,$cdom.'_'.$cnum,$selfenroll,'selfenroll','',$instcid);
if ($enrollresult eq 'ok') {
my (%userroles,%newrole,%newgroups);
my $role = 'st';
@@ -475,7 +476,7 @@ sub process_self_enroll {
}
&Apache::lonnet::standard_roleprivs(\%newrole,$role,$cdom,$spec,$cnum,
$area);
- &Apache::lonnet::set_userprivs(\%userroles,\%newrole,%newgroups);
+ &Apache::lonnet::set_userprivs(\%userroles,\%newrole,\%newgroups);
$userroles{'user.role.'.$spec} = $selfenroll_access_start.'.'.$selfenroll_access_end;
&Apache::lonnet::appenv(\%userroles,[$role,'cm']);
$r->print(''.&mt('Enrollment process complete').'
');
@@ -535,37 +536,91 @@ sub user_can_selfenroll {
}
sub store_selfenroll_request {
- my ($udom,$uname,$usec,$cdom,$cnum,$selfenroll_notifylist,$owner) = @_;
+ my ($r,$udom,$uname,$usec,$cdom,$cnum,$selfenroll_notifylist,$owner,
+ $selfenroll_approval,$crstype,$lonhost,$handle) = @_;
my $namespace = 'selfenrollrequests';
my $output;
my $now = time;
my %existing =
&Apache::lonnet::get($namespace,[$uname.':'.$udom],$cdom,$cnum);
if ($existing{$uname.':'.$udom}) {
- my ($timestamp,$sec) = split(/:/,$existing{$uname.':'.$udom});
- $output = &mt('A self-enrollment request already exists for you for this course.').'
'.&mt('Your earlier request was submitted: [_1] and remains in a queue awaiting action by a Course Coordinator.',&Apache::lonlocal::locallocaltime($timestamp));
+ my $status;
+ $output = &mt('A self-enrollment request already exists for you for this course.').'
';
+ my %info = &Apache::lonnet::get($namespace,[$cdom.'_'.$cnum],$udom,$uname);
+ if (ref($info{$cdom.'_'.$cnum}) eq 'HASH') {
+ $status = $info{$cdom.'_'.$cnum}{'status'};
+ }
+ if ($status eq 'pending') {
+ my $token = $info{$cdom.'_'.$cnum}{'token'};
+ my ($statusupdate,$pendingform) = &pending_selfenrollment_form($r,$cdom,$cnum,$crstype,$token,$lonhost);
+ if ($statusupdate eq 'pending') {
+ $output .= $pendingform;
+ }
+ } else {
+ $output .= &mt('Your earlier request is in a queue awaiting action by a Course Coordinator.').
+ '
'.&Apache::loncoursequeueadmin::queued_selfenrollment();
+ }
} else {
my %selfenroll = (
$uname.':'.$udom => $now.':'.$usec,
);
my $putresult = &Apache::lonnet::put($namespace,\%selfenroll,$cdom,$cnum);
+ my $status = 'request';
+ if ($selfenroll_approval eq '2') {
+ $status = 'pending';
+ }
if ($putresult eq 'ok') {
- $output = &mt('Your request for self-enrollment has been recorded.').'
'.
- &mt('A message will be sent to your LON-CAPA account when the course coordinator takes action on your request').'
';
- my %emails = &Apache::loncommon::getemails($uname,$udom);
- if (($emails{'permanentemail'} ne '') || ($emails{'notification'} ne '')) {
- my $address = $emails{'permanentemail'};
- if ($address eq '') {
- $address = $emails{'notification'};
- }
- $output.= &mt('An e-mail will also be sent to: [_1] when this occurs.',$address);
- }
- if ($selfenroll_notifylist) {
- my $fullname = &Apache::loncommon::plainname($uname,$udom);
- my %courseinfo = &Apache::lonnet::coursedescription($cdom.'_'.$cnum);
- my $coursedesc = $courseinfo{'description'};
- &send_notification($selfenroll_notifylist,$fullname,$cdom.
- '_'.$cnum,$coursedesc,$now,'request',$owner);
+ my %userenroll = (
+ $cdom.'_'.$cnum => {
+ timestamp => $now,
+ section => $usec,
+ status => $status,
+ });
+ my $token;
+ if ($status eq 'pending') {
+ $token = &Apache::lonnet::tmpput(\%selfenroll,$lonhost);
+ $userenroll{$cdom.'_'.$cnum}{'token'} = $token;
+ $userenroll{$cdom.'_'.$cnum}{'lonhost'} = $lonhost;
+ $userenroll{$cdom.'_'.$cnum}{'handle'} = $handle;
+ }
+ my $warning;
+ my $userresult = &Apache::lonnet::put($namespace,\%userenroll,$udom,$uname);
+ if ($userresult ne 'ok') {
+ $warning = &mt('An error occurred saving a personal record of your request.');
+ }
+ $output = &mt('Your request for self-enrollment has been recorded.').'
';
+ if ($status eq 'pending') {
+ my ($statusupdate,$pendingform) = &pending_selfenrollment_form($r,$cdom,$cnum,$crstype,$token,$lonhost);
+ if ($statusupdate eq 'request') {
+ $status = $statusupdate;
+ } else {
+ $output .= $pendingform;
+ }
+ }
+ if ($status eq 'request') {
+ $output .= &mt('A message will be sent to your LON-CAPA account when the course coordinator takes action on your request.').'
'.
+ &mt('To access your LON-CAPA message, go to the Main Menu and click on "Send and Receive Messages".').'
';
+ my %emails = &Apache::loncommon::getemails($uname,$udom);
+ if (($emails{'permanentemail'} ne '') || ($emails{'notification'} ne '')) {
+ my $address = $emails{'permanentemail'};
+ if ($address eq '') {
+ $address = $emails{'notification'};
+ }
+ $output.= &mt('An e-mail will also be sent to: [_1] when this occurs.',$address).'
';
+ }
+ if ($warning) {
+ $output .= ''.$warning.'
';
+ }
+ $output .= &Apache::loncoursequeueadmin::queued_selfenrollment();
+
+ if ($selfenroll_notifylist) {
+ my $fullname = &Apache::loncommon::plainname($uname,$udom);
+ my %courseinfo = &Apache::lonnet::coursedescription($cdom.'_'.$cnum);
+ my $coursedesc = $courseinfo{'description'};
+ &Apache::loncoursequeueadmin::send_selfserve_notification(
+ $selfenroll_notifylist,$fullname,$cdom.'_'.$cnum,
+ $coursedesc,$now,'selfenrollreq',$owner);
+ }
}
} else {
$output = ''.&mt('An error occurred when recording your request.').'';
@@ -575,100 +630,60 @@ sub store_selfenroll_request {
return $output;
}
-sub send_notification {
- my ($notifylist,$textstr,$cid,$coursedesc,$timestamp,$context,$sender,
- $approvedlist,$rejectedlist) = @_;
-# FIXME locallocaltime needs to be able to take $sender_lh as an argument
-# so this can be localized to the recipients date display format/time zone
- $timestamp =&Apache::lonlocal::locallocaltime($timestamp);
- my $msgcc;
- my ($rawsubj,@rawmsg,$subject,$message,$namelink);
- $namelink = &Apache::loncommon::aboutmewrapper(
- &Apache::loncommon::plainname($env{'user.name'},$env{'user.domain'}));
- if ($context eq 'managers') {
- $rawsubj = 'Self-enrollment requests processed';
- push(@rawmsg,{
- mt => 'Enrollment requests in the following course: [_1] have been processed.',
- args => [$coursedesc],
- });
- } elsif ($context eq 'enroller') {
- $rawsubj = 'Enrollment request';
- push(@rawmsg,{
- mt => 'Your request for enrollment in the following course: [_1], requested on [_2], has been reviewed by a Course Coordinator.',
- args => [$coursedesc,$timestamp],
- });
- if (ref($textstr) eq 'ARRAY') {
- push(@rawmsg,@{$textstr});
- }
- } else {
- $rawsubj = 'Self-enrollment request';
- push(@rawmsg,{
- mt => 'Enrollment in the following course: [_1] was requested by [_2] on [_3].',
- args => [$coursedesc,$textstr,$timestamp],
- },
- {
- mt =>'As Course Coordinator, use Main Menu -> Manage Couse Users -> "Enrollment Requests" to display a list of pending enrollment requests which you can either approve or reject.'
- });
- }
- my @to_notify = split(/,/,$notifylist);
- my $numsent = 0;
- my @recusers;
- my @recudoms;
- foreach my $cc (@to_notify) {
- my ($ccname,$ccdom) = split(/:/,$cc);
- if (!exists($msgcc->{$ccname.':'.$ccdom})) {
- push(@recusers,$ccname);
- push(@recudoms,$ccdom);
- $msgcc->{$ccname.':'.$ccdom}='';
- $numsent ++;
- }
- }
- my %reciphash = (
- cc => $msgcc,
- );
- my ($uname,$udom);
- if ($sender =~ /:/) {
- ($uname,$udom) = split(/:/,$sender);
- } else {
- $uname = $sender;
- my %courseinfo = &Apache::lonnet::coursedescription($cid);
- $udom = $courseinfo{'num'};
- }
- my %sentmessage;
- my $stamp = time;
- my $msgcount = &Apache::lonmsg::get_uniq();
- my $sender_lh = &Apache::loncommon::user_lang($uname,$udom,$cid);
- $subject = &Apache::lonlocal::mt_user($sender_lh,$rawsubj);
- $message = '';
- foreach my $item (@rawmsg) {
- if (ref($item) eq 'HASH') {
- $message .= &Apache::lonlocal::mt_user($sender_lh,$item->{mt},@{$item->{args}})."\n";
- }
- }
- &Apache::lonmsg::process_sent_mail($subject,'',$numsent,$stamp,$uname,$udom,$msgcount,$cid,$$,$message,\@recusers,\@recudoms);
- my ($recipid,$recipstatus) =
- &Apache::lonmsg::store_recipients($subject,$uname,$udom,\%reciphash);
- foreach my $recip (sort(keys(%{$msgcc}))) {
- my ($ccname,$ccdom) = split(/:/,$recip);
- my $recip_lh = &Apache::loncommon::user_lang($ccname,$ccdom,$cid);
- my $subject = &Apache::lonlocal::mt_user($sender_lh,$rawsubj);
- my $message = '';
- foreach my $item (@rawmsg) {
- if (ref($item) eq 'HASH') {
- $message .= &Apache::lonlocal::mt_user($sender_lh,$item->{mt},
- @{$item->{args}})."\n";
- }
- }
- if ($context eq 'managers') {
- if ($approvedlist) {
- $message .= "\n\n".&Apache::lonlocal::mt_user($sender_lh,'Approved enrollments:')."\n".$approvedlist;
- }
- if ($rejectedlist) {
- $message .= "\n\n".&Apache::lonlocal::mt_user($sender_lh,'Rejected enrollments:')."\n".$rejectedlist;
+sub pending_selfenrollment_form {
+ my ($r,$cdom,$cnum,$crstype,$token,$lonhost) = @_;
+ my ($status,$output);
+ my $coursetype = &Apache::lonuserutils::get_extended_type($cdom,$cnum,$crstype);
+ my %postvalues = (
+ 'username' => $env{'user.name'},
+ 'domain' => $env{'user.domain'},
+ 'course' => $cdom.'_'.$cnum,
+ 'coursetype' => $coursetype,
+ );
+ my %domconfig = &Apache::lonnet::get_dom('configuration',['selfenrollment'],$cdom);
+
+ if (ref($domconfig{'selfenrollment'}) eq 'HASH') {
+ my ($url,$buttontext,$code,@fields);
+ if (ref($domconfig{'selfenrollment'}{'validation'}) eq 'HASH') {
+ my %courseinfo = &Apache::lonnet::coursedescription($cdom.'_'.$cnum,{ 'one_time' => 1});
+ $postvalues{'uniquecode'} = $courseinfo{'internal.uniquecode'};
+ $postvalues{'description'} = $courseinfo{'description'};
+ $url = $domconfig{'selfenrollment'}{'validation'}{'url'};
+ if (ref($domconfig{'selfenrollment'}{'validation'}{'fields'}) eq 'ARRAY') {
+ @fields = @{$domconfig{'selfenrollment'}{'validation'}{'fields'}};
+ }
+ $buttontext = $domconfig{'selfenrollment'}{'validation'}{'button'};
+
+ $output .= $domconfig{'selfenrollment'}{'validation'}{'markup'};
+ if (($url =~ m{^(https?\://|/)}) && (@fields > 0)) {
+ $output .= ''."\n";
+ $status = 'pending';
+ } else {
+ $status = 'request';
}
}
- my $status = &Apache::lonmsg::user_normal_msg($ccname,$ccdom,$subject,$message,undef,undef,undef,1,\%sentmessage,undef,undef,undef,1,$recipid);
+ } else {
+ $status = 'request';
}
+ return ($status,$output);
}
sub jump_to_role {
@@ -775,12 +790,12 @@ sub print_selfenroll_types {
sub check_registered {
my ($cdom,$cnum) = @_;
- my ($registered,$instsec,$message);
+ my ($registered,$instsec,$instcid,$message);
my %settings = &Apache::lonnet::get('environment',['internal.coursecode',
'internal.sectionnums',
'internal.crosslistings'],$cdom,$cnum);
my (@allcourses,%LC_code,%affiliates,%reply);
- &Apache::loncommon::get_institutional_codes(\%settings,\@allcourses,\%LC_code);
+ &Apache::loncommon::get_institutional_codes($cdom,$cnum,\%settings,\@allcourses,\%LC_code);
if (@allcourses > 0) {
@{$affiliates{$cnum}} = @allcourses;
my $outcome = &Apache::lonnet::fetch_enrollment_query('updatenow',\%affiliates,\%reply,$cdom,$cnum);
@@ -795,6 +810,7 @@ sub check_registered {
if (defined($enrolled{$env{'user.name'}})) {
$registered = 1;
$instsec = $LC_code{$class};
+ $instcid = $class;
last;
}
}
@@ -807,7 +823,7 @@ sub check_registered {
} else {
$message = &mt('As no institutional course sections are currently associated with this course, your registration status is undetermined.');
}
- return ($registered,$instsec,$message);
+ return ($registered,$instsec,$instcid,$message);
}
1;