--- loncom/interface/lonfeedback.pm 2006/11/29 03:23:02 1.220 +++ loncom/interface/lonfeedback.pm 2009/12/08 13:33:12 1.282 @@ -1,7 +1,7 @@ # The LearningOnline Network # Feedback # -# $Id: lonfeedback.pm,v 1.220 2006/11/29 03:23:02 raeburn Exp $ +# $Id: lonfeedback.pm,v 1.282 2009/12/08 13:33:12 wenzelju Exp $ # # Copyright Michigan State University Board of Trustees # @@ -44,7 +44,6 @@ use HTML::LCParser(); use Apache::lonspeller(); use Apache::longroup; use Cwd; -use lib '/home/httpd/lib/perl/'; use LONCAPA; sub discussion_open { @@ -75,6 +74,9 @@ sub discussion_visible { sub list_discussion { my ($mode,$status,$ressymb,$imsextras,$group)=@_; + unless ($ressymb) { $ressymb=&Apache::lonnet::symbread(); } + unless ($ressymb) { return ''; } + $ressymb=&wrap_symb($ressymb); my $outputtarget=$env{'form.grade_target'}; if (defined($env{'form.export'})) { if($env{'form.export'}) { @@ -86,14 +88,32 @@ sub list_discussion { $outputtarget = 'export'; } } - if (not &discussion_visible($status)) { return ''; } + if (not &discussion_visible($status)) { + if ($mode ne 'board') { + &Apache::lonenc::check_encrypt(\$ressymb); + return '
"; + } + } if ($group ne '' && $mode eq 'board') { if (&check_group_priv($group,'vgb') ne 'ok') { return ''; } } - my @bgcols = ("#cccccc","#eeeeee"); + my ($blocked,$blocktext) = + &Apache::loncommon::blocking_status('boards'); + if ($blocked) { + $blocktext = '
'; + }else{ + $blocktext.=""; + } + return $blocktext; + } + + my @bgcols = ("LC_disc_old_item","LC_disc_new_item"); my $discussiononly=0; if ($mode eq 'board') { $discussiononly=1; } unless ($env{'request.course.id'}) { return ''; } @@ -103,9 +123,6 @@ sub list_discussion { $crs.='_'.$env{'request.course.sec'}; } $crs=~s/\_/\//g; - unless ($ressymb) { $ressymb=&Apache::lonnet::symbread(); } - unless ($ressymb) { return ''; } - $ressymb=&wrap_symb($ressymb); my $encsymb=&Apache::lonenc::check_encrypt($ressymb); my $viewgrades=(&Apache::lonnet::allowed('vgr',$crs) && ($ressymb=~/\.(problem|exam|quiz|assess|survey|form|task)$/)); @@ -133,7 +150,7 @@ sub list_discussion { my $previous = 0; my $visit = 0; my $newpostsflag = 0; - my @posters = split/\&/,$dischash{$userpickkey}; + my @posters = split(/\&/,$dischash{$userpickkey}); # Retain identification of "NEW" posts identified in last display, if continuing 'previous' browsing of posts. &Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'},['previous','sortposts','rolefilter','statusfilter','sectionpick','grouppick','totposters']); @@ -155,6 +172,7 @@ sub list_discussion { my $cdom = $env{'course.'.$cid.'.domain'}; my $cnum = $env{'course.'.$cid.'.num'}; + my $crstype = &Apache::loncommon::course_type(); # Get information about students and non-students in course for filtering display of posts my %roleshash = (); @@ -162,19 +180,19 @@ sub list_discussion { my ($classgroups,$studentgroups); if ($env{'form.rolefilter'}) { %roleshash = &Apache::lonnet::dump('nohist_userroles',$cdom,$cnum); - foreach (keys %roleshash) { - my ($role,$uname,$udom,$sec) = split/:/,$_; + foreach my $rolekey (keys(%roleshash)) { + my ($role,$uname,$udom,$sec) = split(/:/,$rolekey); if ($role =~ /^cr/) { $role = 'cr'; } - my ($end,$start) = split/:/,$roleshash{$_}; + my ($end,$start) = split(/:/,$roleshash{$rolekey}); my $now = time; my $status = 'Active'; if (($now < $start) || ($end > 0 && $now > $end)) { $status = 'Expired'; } if ($uname && $udom) { - push @{$roleinfo{$uname.':'.$udom}}, $role.':'.$sec.':'.$status; + push(@{$roleinfo{$uname.':'.$udom}}, $role.':'.$sec.':'.$status); } } my ($classlist,$keylist) = @@ -184,7 +202,7 @@ sub list_discussion { while (my ($student,$data) = each %$classlist) { my ($section,$status) = ($data->[$sec_index], $data->[$status_index]); - push @{$roleinfo{$student}}, 'st:'.$section.':'.$status; + push(@{$roleinfo{$student}}, 'st:'.$section.':'.$status); } ($classgroups,$studentgroups) = &Apache::loncoursedata::get_group_memberships($classlist,$keylist, @@ -338,10 +356,10 @@ sub list_discussion { $togglink = 'toggoff'; } - $chglink .= '&changes='.$displinkA.'_'.$displinkB.'_'.$marklink.'_'.$togglink; + $chglink .= '&changes='.$displinkA.'_'.$displinkB.'_'.$marklink.'_'.$togglink; if ($newpostsflag) { - $chglink .= '&previous='.$prevread; + $chglink .= '&previous='.$prevread; } $chglink.=&group_args($group); @@ -398,13 +416,13 @@ imscp_v1p1.xsd http://www.imsglobal.org/ } } else { my $colspan=$maxdepth+1; - $discussion.= qq| - - |; - $discussion.='
'; - $discussion .=''; - + |); + $discussion.=''. + "\n".'
'. - ''; - my $escsymb=&escape($ressymb); - if ($visible>2) { - $discussion.=''; - if ($newpostsflag) { - if (!$markondisp) { - $discussion .=''; - } - } else { - $discussion .= ''; - } - $discussion .= '
'. - ''.&mt('Threaded View').'  '. - ''.&mt('Chronological View').'   - '.&mt('Sorting/Filtering options').'  '; - } else { - $discussion .= ''; - } - $discussion .=''.&mt('Export').'?  '. - &mt('Preferences on what is marked as NEW'). - '
'.&mt('Mark NEW posts no longer new').''; - } else { - $discussion .= '
  
'; + $discussion .= &action_links_bar($colspan,$ressymb,$visible, + $newpostsflag,$group, + $prevread,$markondisp); + my $escsymb=&escape($ressymb); my $numhidden = keys(%notshown); if ($numhidden > 0) { my $colspan = $maxdepth+1; $discussion.="\n".'"; } - my $thisdepth=$depth[$alldiscussion{$_}]; + my $thisdepth=$depth[$alldiscussion{$post}]; if ($outputtarget ne 'tex' && $outputtarget ne 'export') { for (1..$thisdepth) { $discussion.=''; @@ -534,52 +507,52 @@ imscp_v1p1.xsd http://www.imsglobal.org/ my $colspan=$maxdepth-$thisdepth+1; if ($outputtarget eq 'tex') { #cleanup block - $discussionitems[$alldiscussion{$_}]=~s/]*)>/
'. ''.&mt('Show all posts').' '.&mt('to display').' '. @@ -493,39 +466,39 @@ imscp_v1p1.xsd http://www.imsglobal.org/ # Choose sort mechanism my @showposts = (); if ($sortposts eq 'descdate') { - @showposts = (sort { $b <=> $a } keys %alldiscussion); + @showposts = (sort { $b <=> $a } keys(%alldiscussion)); } elsif ($sortposts eq 'thread') { - @showposts = (sort { $a <=> $b } keys %alldiscussion); + @showposts = (sort { $a <=> $b } keys(%alldiscussion)); } elsif ($sortposts eq 'subject') { - foreach (sort keys %subjectsort) { - push @showposts, @{$subjectsort{$_}}; + foreach my $key (sort(keys(%subjectsort))) { + push(@showposts, @{$subjectsort{$key}}); } } elsif ($sortposts eq 'username') { - foreach my $domain (sort keys %usernamesort) { - foreach (sort keys %{$usernamesort{$domain}}) { - push @showposts, @{$usernamesort{$domain}{$_}}; + foreach my $domain (sort(keys(%usernamesort))) { + foreach my $key (sort(keys(%{$usernamesort{$domain}}))) { + push(@showposts, @{$usernamesort{$domain}{$key}}); } } } elsif ($sortposts eq 'lastfirst') { - foreach my $last (sort keys %namesort) { - foreach (sort keys %{$namesort{$last}}) { - push @showposts, @{$namesort{$last}{$_}}; + foreach my $last (sort(keys(%namesort))) { + foreach my $key (sort(keys(%{$namesort{$last}}))) { + push(@showposts, @{$namesort{$last}{$key}}); } } } else { - @showposts = (sort { $a <=> $b } keys %alldiscussion); + @showposts = (sort { $a <=> $b } keys(%alldiscussion)); } my $currdepth = 0; my $firstidx = $alldiscussion{$showposts[0]}; - foreach (@showposts) { + foreach my $post (@showposts) { unless (($sortposts eq 'thread') || (($sortposts eq '') && ($env{'environment.threadeddiscussion'})) || ($outputtarget eq 'export')) { - $alldiscussion{$_} = $_; + $alldiscussion{$post} = $post; } - unless ( ($notshown{$alldiscussion{$_}} eq '1') || ($shown{$alldiscussion{$_}} == 0) ) { + unless ( ($notshown{$alldiscussion{$post}} eq '1') || ($shown{$alldiscussion{$post}} == 0) ) { if ($outputtarget ne 'tex' && $outputtarget ne 'export') { $discussion.="\n
   
/; - $discussionitems[$alldiscussion{$_}]=~s/]*)>]*)>/ - END $r->print(&Apache::loncommon::end_data_table_row()); @@ -1903,8 +1968,9 @@ END $r->print(<$lt{'dotm'} - + END + my $save = &mt('Save'); $r->print(&Apache::loncommon::end_data_table_row()); $r->print(&Apache::loncommon::end_data_table()); $r->print(< - - - + + + - + END if (exists($env{'form.group'})) { $r->print(''); @@ -1947,7 +2013,14 @@ sub print_sortfilter_options { my $group_sel = ''; my $numgroupvis = 5; my %sectioncount = &Apache::loncommon::get_sections(); - + my @courseroles = qw(st ad ep ta in); + my $crstype = &Apache::loncommon::course_type(); + my $ccrole = 'cc'; + if ($crstype eq 'Community') { + $ccrole = 'co'; + } + push(@courseroles,$ccrole); + if ($env{'request.course.sec'} !~ /^\s*$/) { #Restrict section choice to current section @sections = ('all',$env{'request.course.sec'}); $numvisible = 2; @@ -2004,13 +2077,13 @@ sub print_sortfilter_options { 'spgr' => 'Specific groups', 'psub' => 'Pick specific users (by name)', 'shal' => 'Show a list of current posters', - 'stor' => 'Store changes', + 'stor' => 'Save changes', ); my %sort_types = (); my %role_types = (); my %status_types = (); - &sort_filter_names(\%sort_types,\%role_types,\%status_types); + &sort_filter_names(\%sort_types,\%role_types,\%status_types,$crstype); my $js = < @@ -2057,22 +2130,22 @@ END $r->print(< + $lt{'diso'}
$lt{'prca'}

/; + $discussionitems[$alldiscussion{$post}]=~s/]*)>//; + $discussionitems[$alldiscussion{$post}]=~s/]*)>]*)>/'; } } @@ -588,14 +561,14 @@ imscp_v1p1.xsd http://www.imsglobal.org/ my $colspan=$maxdepth+1; $discussion .= < - '; return $discussion; } sub postingform_display { my ($mode,$ressymb,$now,$subject,$comment,$outputtarget,$attachnum, - $currnewattach,$currdelold,$group) = @_; + $currnewattach,$currdelold,$group,$crstype) = @_; my $newattachmsg; my %lt = &Apache::lonlocal::texthash( 'note' => 'Note: in anonymous discussion, your name is visible only to course faculty', @@ -790,6 +836,9 @@ sub postingform_display { 'poan' => 'Post Anonymous Discussion', 'newa' => 'New attachments', ); + if ($crstype eq 'Community') { + $lt{'note'} = &mt('Note: in anonymous discussion, your name is visible only to community facilitators'); + } my $postingform = (< @@ -798,7 +847,7 @@ sub postingform_display {
$lt{'note'}
$lt{'title'}: 

- + ENDDISCUSS if ($env{'form.origpage'}) { $postingform .= ''; } + my $blockblog = &Apache::loncommon::blocking_status('blogs'); + if (!$blockblog) { + $postingform .= &add_blog_checkbox($crstype); + } $postingform .= "\n"; if ($outputtarget ne 'tex') { $postingform .= &generate_attachments_button('',$attachnum,$ressymb, $now,$currnewattach, - $currdelold,'',$mode); + $currdelold,'',$mode, + $blockblog); if ((ref($currnewattach) eq 'ARRAY') && (@{$currnewattach} > 0)) { $newattachmsg = '
'.$lt{'newa'}.'
'; if (@{$currnewattach} > 1) { @@ -851,6 +905,9 @@ sub build_posting_display { $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}); + my $see_anonymous = + &Apache::lonnet::allowed('rin',$env{'request.course.id'}.($env{'request.course.sec'}?'/'.$env{'request.course.sec'}:'')); + if ((@{$grouppick} == 0) || (grep(/^all$/,@{$grouppick}))) { $skip_group_check = 1; } @@ -901,7 +958,7 @@ sub build_posting_display { $$visible++; if ($contrib{$idx.':history'}) { if ($contrib{$idx.':history'} =~ /:/) { - my @oldversions = split/:/,$contrib{$idx.':history'}; + my @oldversions = split(/:/,$contrib{$idx.':history'}); $numoldver = @oldversions; } else { $numoldver = 1; @@ -940,35 +997,37 @@ sub build_posting_display { if ($subject eq '') { if (defined($$subjectsort{'__No subject'})) { - push @{$$subjectsort{'__No subject'}}, $idx; + push(@{$$subjectsort{'__No subject'}}, $idx); } else { @{$$subjectsort{'__No subject'}} = ("$idx"); } } else { if (defined($$subjectsort{$subject})) { - push @{$$subjectsort{$subject}}, $idx; + push(@{$$subjectsort{$subject}}, $idx); } else { @{$$subjectsort{$subject}} = ("$idx"); } } - if ((!$contrib{$idx.':anonymous'}) || (&Apache::lonnet::allowed('rin',$env{'request.course.id'}.($env{'request.course.sec'}?'/'.$env{'request.course.sec'}:'')))) { + if (!$contrib{$idx.':anonymous'} || $see_anonymous) { $sender=&Apache::loncommon::aboutmewrapper( $plainname, $contrib{$idx.':sendername'}, $contrib{$idx.':senderdomain'}).' ('. - $contrib{$idx.':sendername'}.' at '. + $contrib{$idx.':sendername'}.':'. $contrib{$idx.':senderdomain'}.')'; if ($contrib{$idx.':anonymous'}) { $sender.=' ['.$$anonhash{$key}.'] '. $screenname; } - + if ($see_anonymous) { + $sender.=&Apache::loncommon::student_image_tag($contrib{$idx.':senderdomain'},$contrib{$idx.':sendername'}); + } # Set up for sorting by domain, then username unless (defined($$usernamesort{$contrib{$idx.':senderdomain'}})) { %{$$usernamesort{$contrib{$idx.':senderdomain'}}} = (); } if (defined($$usernamesort{$contrib{$idx.':senderdomain'}}{$contrib{$idx.':sendername'}})) { - push @{$$usernamesort{$contrib{$idx.':senderdomain'}}{$contrib{$idx.':sendername'}}}, $idx; + push(@{$$usernamesort{$contrib{$idx.':senderdomain'}}{$contrib{$idx.':sendername'}}}, $idx); } else { @{$$usernamesort{$contrib{$idx.':senderdomain'}}{$contrib{$idx.':sendername'}}} = ("$idx"); } @@ -988,7 +1047,7 @@ sub build_posting_display { %{$$namesort{$lastname}} = (); } if (defined($$namesort{$lastname}{$firstname})) { - push @{$$namesort{$lastname}{$firstname}}, $idx; + push(@{$$namesort{$lastname}{$firstname}}, $idx); } else { @{$$namesort{$lastname}{$firstname}} = ("$idx"); } @@ -997,7 +1056,7 @@ sub build_posting_display { $sender.=' '.&mt('Edit').''; @@ -1015,7 +1074,7 @@ sub build_posting_display { $sender.=' '.&mt('Make Visible').''; } @@ -1023,7 +1082,7 @@ sub build_posting_display { $sender.=' '.&mt('Hide').''; @@ -1044,7 +1103,7 @@ sub build_posting_display { %{$$usernamesort{'__anon'}} = (); } if (defined($$usernamesort{'__anon'}{'__anon'})) { - push @{$$usernamesort{'__anon'}{'__anon'}}, $idx; + push(@{$$usernamesort{'__anon'}{'__anon'}}, $idx); } else { @{$$usernamesort{'__anon'}{'__anon'}} = ("$idx"); } @@ -1053,7 +1112,7 @@ sub build_posting_display { %{$$namesort{'__anon'}} = (); } if (defined($$namesort{'__anon'}{'__anon'})) { - push @{$$namesort{'__anon'}{'__anon'}}, $idx; + push(@{$$namesort{'__anon'}{'__anon'}}, $idx); } else { @{$$namesort{'__anon'}{'__anon'}} = ("$idx"); } @@ -1064,7 +1123,7 @@ sub build_posting_display { $sender.=' '.&mt('Reply').''; @@ -1075,7 +1134,7 @@ sub build_posting_display { $sender.=' '.&mt('Reply').''; } @@ -1112,7 +1171,7 @@ sub build_posting_display { $$imsitems{$idx}{'attach'}=$attachtxt{$numoldver}; $$imsitems{$idx}{'timestamp'}=$contrib{$idx.':timestamp'}; $$imsitems{$idx}{'sender'}=$plainname.' ('. - $contrib{$idx.':sendername'}.' at '. + $contrib{$idx.':sendername'}.':'. $contrib{$idx.':senderdomain'}.')'; $$imsitems{$idx}{'isanonymous'}='false'; if ($contrib{$idx.':anonymous'}) { @@ -1185,24 +1244,24 @@ sub build_posting_display { if ($prevread > 0 && $prevread <= $posttime) { $$newitem{$idx} = 1; $$discussionitems[$idx] .= ' -

/; my $threadinsert=''; if ($thisdepth > 0) { $threadinsert='
Reply: '.$thisdepth.''; } - $discussionitems[$alldiscussion{$_}]=~s/<\/td>]*)>/$threadinsert<\/td>
/; - $discussionitems[$alldiscussion{$_}]=~s/]+)>(Edit|Hide|Delete|Reply|Submissions)<\/a>//g; - $discussionitems[$alldiscussion{$_}]=~s/(|<\/b>|<\/a>|]+)>)//g; + $discussionitems[$alldiscussion{$post}]=~s/<\/td>]*)>/$threadinsert<\/td>/; + $discussionitems[$alldiscussion{$post}]=~s/]+)>(Edit|Hide|Delete|Reply|Submissions)<\/a>//g; + $discussionitems[$alldiscussion{$post}]=~s/(|<\/b>|<\/a>|]+)>)//g; - $discussionitems[$alldiscussion{$_}]='\vskip 0 mm\noindent\makebox[2 cm][b]{\hrulefill}'.$discussionitems[$alldiscussion{$_}]; - $discussion.=$discussionitems[$alldiscussion{$_}]; + $discussionitems[$alldiscussion{$post}]='\vskip 0 mm\noindent\makebox[2 cm][b]{\hrulefill}'.$discussionitems[$alldiscussion{$post}]; + $discussion.=$discussionitems[$alldiscussion{$post}]; } elsif ($outputtarget eq 'export') { - my $postfilename = $alldiscussion{$_}.'-'.$imsitems{$alldiscussion{$_}}{'timestamp'}.'.html'; + my $postfilename = $alldiscussion{$post}.'-'.$imsitems{$alldiscussion{$post}}{'timestamp'}.'.html'; if ($manifestok) { - if (($depth[$alldiscussion{$_}] <= $currdepth) && ($alldiscussion{$_} != $firstidx)) { + if (($depth[$alldiscussion{$post}] <= $currdepth) && ($alldiscussion{$post} != $firstidx)) { print $manifestfile ' '."\n"; } - $currdepth = $depth[$alldiscussion{$_}]; + $currdepth = $depth[$alldiscussion{$post}]; print $manifestfile "\n". - ''. - ''.$imsitems{$alldiscussion{$_}}{'title'}.''; + ''. + ''.$imsitems{$alldiscussion{$post}}{'title'}.''; $imsresources .= "\n". - ''."\n". + ''."\n". ''."\n". - $imsfiles{$alldiscussion{$_}}{$imsitems{$alldiscussion{$_}}{'currversion'}}."\n". + $imsfiles{$alldiscussion{$post}}{$imsitems{$alldiscussion{$post}}{'currversion'}}."\n". ''; } my $postingfile; my $postingfilename = $tempexport.'/'.$postfilename; if ($postingfile = Apache::File->new('>'.$postingfilename)) { print $postingfile 'Discussion Post'. - $imsitems{$alldiscussion{$_}}{'title'}.' '. - $imsitems{$alldiscussion{$_}}{'sender'}. - $imsitems{$alldiscussion{$_}}{'timestamp'}.'

'. - $imsitems{$alldiscussion{$_}}{'message'}.'
'. - $imsitems{$alldiscussion{$_}}{'attach'}.''."\n"; + $imsitems{$alldiscussion{$post}}{'title'}.' '. + $imsitems{$alldiscussion{$post}}{'sender'}. + $imsitems{$alldiscussion{$post}}{'timestamp'}.'

'. + $imsitems{$alldiscussion{$post}}{'message'}.'
'. + $imsitems{$alldiscussion{$post}}{'attach'}.''."\n"; close($postingfile); } else { - $discussion .= $lt{'aerr'}.' '.$alldiscussion{$_}.'
'; + $discussion .= $lt{'aerr'}.' '.$alldiscussion{$post}.'
'; } - $copyresult.=&replicate_attachments($imsitems{$alldiscussion{$_}}{'allattachments'},$tempexport); + $copyresult.=&replicate_attachments($imsitems{$alldiscussion{$post}}{'allattachments'},$tempexport); } else { - $discussion.='
'. $discussionitems[$alldiscussion{$_}]. + $discussion.=''. $discussionitems[$alldiscussion{$post}]. '
- +
+

\n"; } if ($outputtarget eq 'export') { if ($manifestok) { @@ -749,39 +726,108 @@ END &postingform_display($mode,$ressymb,$now,$subject, $comment,$outputtarget,$attachnum, $currnewattach,$currdelold, - $group); + $group,$crstype); } } else { $discussion.= &postingform_display($mode,$ressymb,$now,$subject, $comment,$outputtarget,$attachnum, - $currnewattach,$currdelold); + $currnewattach,$currdelold,'',$crstype); } } } else { - $discussion.='
'; + $discussion.='
'; + if ($outputtarget ne 'tex') { + $discussion.= &send_message_link($ressymb); + } + $discussion.=''; + } + return $discussion; +} + +sub send_feedback_link { + my ($ressymb,$target) = @_; + my $output = ''. + ' '. + ''.&mt('Post Discussion').''; + return $output; +} + +sub send_message_link { + my ($ressymb) = @_; + my $output = ''. + ' '.&mt('Send Feedback').''; + return $output; +} + +sub action_links_bar { + my ($colspan,$ressymb,$visible,$newpostsflag,$group,$prevread,$markondisp) = @_; + my $discussion = '
- '; +
NEW
+ '; } else { $$newitem{$idx} = 0; $$discussionitems[$idx] .= ' -

'.&mt('NEW').'
+
'; } - $$discussionitems[$idx] .= ''; if ($$dischash{$toggkey}) { $$discussionitems[$idx].=''; } $$discussionitems[$idx].= '
   '. + $$discussionitems[$idx] .= '  '. ''.$subject.'  '. - $sender.' '.$vgrlink.' ('. + ''.$sender.' '.$vgrlink.' ('. &Apache::lonlocal::locallocaltime($posttime).')  '. $ctlink.'
'. - $message.'

'; + $message.''; if ($contrib{$idx.':history'}) { my @postversions = (); $$discussionitems[$idx] .= &mt('This post has been edited by the author.'); @@ -1213,7 +1272,7 @@ sub build_posting_display { } $$discussionitems[$idx].='
'.&mt('Earlier version(s) were posted on: '); if ($contrib{$idx.':history'} =~ m/:/) { - @postversions = split/:/,$contrib{$idx.':history'}; + @postversions = split(/:/,$contrib{$idx.':history'}); } else { @postversions = ("$contrib{$idx.':history'}"); } @@ -1236,9 +1295,9 @@ sub filter_regexp { my $skiptest = 1; if (@{$rolefilter} > 0) { my @okrolefilter = (); - foreach (@{$rolefilter}) { - unless ($_ eq '') { - push @okrolefilter, $_; + foreach my $role (@{$rolefilter}) { + unless ($role eq '') { + push(@okrolefilter, $role); } } if (@okrolefilter > 0) { @@ -1256,9 +1315,9 @@ sub filter_regexp { } if (@{$sectionpick} > 0) { my @oksectionpick = (); - foreach (@{$sectionpick}) { - unless ($_ eq '') { - push @oksectionpick, $_; + foreach my $sec (@{$sectionpick}) { + unless ($sec eq '') { + push(@oksectionpick, $sec); } } if ((@oksectionpick > 0) && (!grep/^all$/,@oksectionpick)) { @@ -1309,7 +1368,7 @@ sub get_post_contents { $$plainname, $$contrib{$idx.':sendername'}, $$contrib{$idx.':senderdomain'}).' ('. - $$contrib{$idx.':sendername'}.' at '. + $$contrib{$idx.':sendername'}.':'. $$contrib{$idx.':senderdomain'}.')'; my $attachmenturls = $$contrib{$idx.':attachmenturl'}; my @postversions = (); @@ -1320,7 +1379,7 @@ sub get_post_contents { } &get_post_versions($messages,$$contrib{$idx.':message'},1); &get_post_versions($subjects,$$contrib{$idx.':subject'},1); - push @postversions,$$contrib{$idx.':timestamp'}; + push(@postversions,$$contrib{$idx.':timestamp'}); $end = @postversions; } else { &get_post_versions($messages,$$contrib{$idx.':message'},1,$numver); @@ -1348,8 +1407,8 @@ sub get_post_contents { $$imsfiles{$idx}{$i} = ''; if ($attachmsg) { $$attachtxt{$i} = '
'.&mt('Attachments').':
'; - foreach (sort keys %currattach) { - if ($$allattachments{$_}{'filename'} =~ m-^/uploaded/([^/]+/[^/]+)(/feedback)?(/?\d*)/([^/]+)$-) { + foreach my $key (sort(keys(%currattach))) { + if ($$allattachments{$key}{'filename'} =~ m-^/uploaded/([^/]+/[^/]+)(/feedback)?(/?\d*)/([^/]+)$-) { my $fname = $1.$3.'/'.$4; $$imsfiles{$idx}{$i} .= ''."\n"; $$attachtxt{$i}.= ''.$4.'
'; @@ -1382,11 +1441,11 @@ END sub replicate_attachments { my ($attachrefs,$tempexport) = @_; my $response; - foreach my $id (keys %{$attachrefs}) { + foreach my $id (keys(%{$attachrefs})) { if ($$attachrefs{$id}{'filename'} =~ m-^/uploaded/([^/]+)/([^/]+)(/feedback)?(/?\d*)/([^/]+)$-) { my $path = $tempexport; my $tail = $1.'/'.$2.$4; - my @extras = split/\//,$tail; + my @extras = split(/\//,$tail); my $destination = $tempexport.'/'.$1.'/'.$2.$4.'/'.$5; if (!-e $destination) { my $i= 0; @@ -1418,20 +1477,18 @@ sub replicate_attachments { } sub mail_screen { - my ($r,$feedurl,$options) = @_; + my ($r,$feedurl,$options,$caller_symb,$attachmaxtext) = @_; if (exists($env{'form.origpage'})) { &Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'},['subject','comment','currnewattach','addnewattach','deloldattach','delnewattach','timestamp','idx','anondiscuss','discuss','blog','group','ref']); } my %lt = &Apache::lonlocal::texthash( - 'plch' => 'Please check at least one of the following feedback types:', 'myqu' => 'My question/comment/feedback:', 'title' => 'Title', 'reta' => 'Retained attachments', - 'atta' => 'Attachment (128 KB max size)', - ); - my $title=&Apache::lonnet::gettitle($feedurl); - if (!$title) { $title = $feedurl; } + 'atta' => 'Attachment', + ); + my $restitle = &get_resource_title($caller_symb,$feedurl); my $quote=''; my $subject = ''; my $comment = ''; @@ -1497,7 +1554,7 @@ END unless (($contrib{'hidden'}=~/\.$idx\./) || ($contrib{'deleted'}=~/\.$idx\./)) { if ($contrib{$idx.':history'}) { if ($contrib{$idx.':history'} =~ /:/) { - my @oldversions = split/:/,$contrib{$idx.':history'}; + my @oldversions = split(/:/,$contrib{$idx.':history'}); $numoldver = @oldversions; } else { $numoldver = 1; @@ -1506,7 +1563,7 @@ END if ($env{'form.replydisc'}) { if ($contrib{$idx.':history'}) { if ($contrib{$idx.':history'} =~ /:/) { - my @oldversions = split/:/,$contrib{$idx.':history'}; + my @oldversions = split(/:/,$contrib{$idx.':history'}); $numoldver = @oldversions; } else { $numoldver = 1; @@ -1520,7 +1577,7 @@ END if ($idx > 0) { my %subversions = (); &get_post_versions(\%subversions,$contrib{$idx.':subject'},1,$numoldver); - $subject = &mt('Re: ')..$subversions{$numoldver}; + $subject = &mt('Re: ').$subversions{$numoldver}; } $subject = &HTML::Entities::encode($subject,'<>&"'); } else { @@ -1565,7 +1622,7 @@ END $comment = &unescape($env{'form.comment'}); &process_attachments(\@currnewattach,\@currdelold,\@keepold); } - my $latexHelp=&Apache::loncommon::helpLatexCheatsheet(); + my $latexHelp=&Apache::loncommon::helpLatexCheatsheet(undef,undef,1); my $send=&mt('Send'); my $alert = &mt('Please select a feedback type.'); my $js= < END + # Breadcrumbs + my $brcrum = [{'href' => '', + 'text' => 'Resource Feedback and Discussion'}]; + my %onload = ('onload' => 'window.focus();setposttype();'); my $start_page= &Apache::loncommon::start_page('Resource Feedback and Discussion',$js, - {'add_entries' => \%onload}); + {'add_entries' => \%onload, + 'bread_crumbs' => $brcrum,}); if ($quote ne '') { &newline_to_br(\$quote); @@ -1619,7 +1681,7 @@ END $r->print(<$title +

$restitle

$prevtag @@ -1631,44 +1693,45 @@ END END } elsif ($env{'form.editdisc'}) { $r->print(< - + + END } $r->print(< $quote

$lt{'myqu'}

$latexHelp +

+

$lt{'title'}:

-

END if ( ($env{'form.editdisc'}) || ($env{'form.replydisc'}) ) { if ($env{'form.origpage'}) { - foreach (@currnewattach) { - $r->print(''."\n"); + foreach my $attach (@currnewattach) { + $r->print(''."\n"); } - foreach (@currdelold) { - $r->print(''."\n"); + foreach my $oldatt (@currdelold) { + $r->print(''."\n"); } } if ($env{'form.editdisc'}) { if ($attachmenturls) { &extract_attachments($attachmenturls,$idx,$numoldver,\$attachmsg,\%attachments,\%currattach,\@currdelold); - $attachnum = scalar(keys %currattach); - foreach (keys %currattach) { - $r->print(''."\n"); + $attachnum = scalar(keys(%currattach)); + foreach my $key (keys(%currattach)) { + $r->print(''."\n"); } } } } else { $r->print(< +$lt{'atta'} $attachmaxtext:

END } @@ -1681,13 +1744,14 @@ END $r->print(< - +

END if ($env{'form.editdisc'} || $env{'form.replydisc'}) { my $now = time; my $ressymb = $symb; + &Apache::lonenc::check_encrypt(\$ressymb); my $postidx = ''; if ($env{'form.editdisc'}) { $postidx = $idx; @@ -1695,7 +1759,8 @@ END if (@currnewattach > 0) { $attachnum += @currnewattach; } - $r->print(&generate_attachments_button($postidx,$attachnum,$ressymb,$now,\@currnewattach,\@currdelold,$numoldver)); + my $blockblog = &Apache::loncommon::blocking_status('blogs'); + $r->print(&generate_attachments_button($postidx,$attachnum,$ressymb,$now,\@currnewattach,\@currdelold,$numoldver,'',$blockblog)); if ($attachnum > 0) { if (@currnewattach > 0) { $newattachmsg .= '
'.&mt('New attachments').'
'; @@ -1740,14 +1805,14 @@ sub print_display_options { 'actn' => 'Action', 'deff' => 'Default for all discussions', 'prca' => 'Preferences can be set for this discussion that determine ....', - 'whpo' => 'Which posts are displayed when you display this bulletin board or resource, and', + 'whpo' => 'Which posts are displayed when you display this discussion board or resource, and', 'unwh' => 'Under what circumstances posts are identified as "NEW", and', 'wipa' => 'Whether individual posts can be marked as read/unread', 'allposts' => 'All posts', 'unread' => 'New posts only', 'unmark' => 'Posts not marked read', 'ondisp' => 'Once displayed', - 'onmark' => 'Once marked not NEW ', + 'onmark' => 'Once marked not NEW', 'toggon' => 'Shown', 'toggoff' => 'Not shown', 'disa' => 'Posts displayed?', @@ -1870,7 +1935,7 @@ END &Apache::loncommon::end_page(); $r->print(< +
$lt{'sdpf'}
$lt{'prca'}
  1. $lt{'whpo'}
  2. $lt{'unwh'}
  3. $lt{'wipa'}

END @@ -1886,9 +1951,9 @@ END $r->print(<$lt{'disa'}
$lt{$discdisp} +
- +
$lt{$disctogg}
- - - - - - - - - - - + + + + + + + + + + + @@ -2126,7 +2200,7 @@ $start_page
- + END if (exists($env{'form.group'})) { $r->print(''); @@ -2200,7 +2274,7 @@ sub print_showposters { $postcounts{$poster} ++; if (defined($namesort{$lastname}{$firstname})) { if (!grep/^$poster$/,@{$namesort{$lastname}{$firstname}}) { - push @{$namesort{$lastname}{$firstname}}, $poster; + push(@{$namesort{$lastname}{$firstname}}, $poster); } } else { @{$namesort{$lastname}{$firstname}} = ("$poster"); @@ -2225,19 +2299,19 @@ $start_page END my $count = 0; - foreach my $last (sort keys %namesort) { - foreach my $first (sort keys %{$namesort{$last}}) { - foreach (sort @{$namesort{$last}{$first}}) { - my ($uname,$udom) = split/:/,$_; + foreach my $last (sort(keys(%namesort))) { + foreach my $first (sort(keys(%{$namesort{$last}}))) { + foreach my $user (sort(@{$namesort{$last}{$first}})) { + my ($uname,$udom) = split(/:/,$user); if (!$uname || !$udom) { next; } else { $count ++; $r->print(&Apache::loncommon::start_data_table_row(). ' - + - '. + '. &Apache::loncommon::end_data_table_row()); } } @@ -2249,7 +2323,7 @@ END
- + $end_page END @@ -2335,7 +2409,7 @@ ENDFAILREDIR } sub redirect_back { - my ($r,$feedurl,$typestyle,$sendsomething,$sendposts,$blog,$status,$previous,$sort,$rolefilter,$statusfilter,$sectionpick,$grouppick,$numpicks,$group) = @_; + my ($r,$feedurl,$typestyle,$sendsomething,$sendposts,$blog,$status,$previous,$sort,$rolefilter,$statusfilter,$sectionpick,$grouppick,$numpicks,$group,$toolarge) = @_; my $sorttag = ''; my $roletag = ''; my $statustag = ''; @@ -2352,7 +2426,7 @@ sub redirect_back { if ($previous > 0) { $qrystr = 'previous='.$previous; if ($feedurl =~ /\?register=1/) { - $feedurl .= '&'.$qrystr; + $feedurl .= '&'.$qrystr; } else { $feedurl .= '?'.$qrystr; } @@ -2361,32 +2435,32 @@ sub redirect_back { if (defined($sort)) { my $sortqry = 'sortposts='.$sort; if (($feedurl =~ /\?register=1/) || ($feedurl =~ /\?previous=/)) { - $feedurl .= '&'.$sortqry; + $feedurl .= '&'.$sortqry; } else { $feedurl .= '?'.$sortqry; } $sorttag = ''; if (defined($numpicks)) { my $userpickqry = 'totposters='.$numpicks; - $feedurl .= '&'.$userpickqry; + $feedurl .= '&'.$userpickqry; $userpicktag = ''; } else { if (ref($sectionpick) eq 'ARRAY') { - $feedurl .= '§ionpick='; + $feedurl .= '&sectionpick='; $sectag .= ''; } else { - $feedurl .= '§ionpick='.$sectionpick; + $feedurl .= '&sectionpick='.$sectionpick; $sectag = ''; } if (ref($grouppick) eq 'ARRAY') { - $feedurl .= '&grouppick='; + $feedurl .= '&grouppick='; $sectag .= ''; } else { - $feedurl .= '&grouppick='.$grouppick; + $feedurl .= '&grouppick='.$grouppick; $grptag = ''; } if (ref($rolefilter) eq 'ARRAY') { - $feedurl .= '&rolefilter='; + $feedurl .= '&rolefilter='; $roletag .= ''; } else { - $feedurl .= '&rolefilter='.$rolefilter; + $feedurl .= '&rolefilter='.$rolefilter; $roletag = ''; } - $feedurl .= '&statusfilter='.$statusfilter; + $feedurl .= '&statusfilter='.$statusfilter; $statustag =''; } } my $grouptag; if ($group ne '') { - $grouptag = ''; my $refarg; + $grouptag = ''; + my $refarg; if (exists($env{'form.ref'})) { $refarg = '&ref='.$env{'form.ref'}; $grouptag .= ''; @@ -2430,7 +2505,7 @@ sub redirect_back { $feedurl .= '?group='.$group.$refarg; } } - $feedurl=&Apache::lonenc::check_encrypt($feedurl); + &Apache::lonenc::check_encrypt(\$feedurl); my $logo=&Apache::loncommon::lonhttpdurl('/adm/lonIcons/lonlogos.gif'); my %onload; if ($env{'environment.remote'} ne 'off') { @@ -2449,6 +2524,7 @@ $start_page $typestyle Sent $sendsomething message(s), and $sendposts post(s). $blog +$toolarge $status $prevtag @@ -2487,7 +2563,7 @@ sub no_redirect_back { my $end_page = &Apache::loncommon::end_page(); - $feedurl=&Apache::lonenc::check_encrypt($feedurl); + &Apache::lonenc::check_encrypt(\$feedurl); my $logo=&Apache::loncommon::lonhttpdurl('/adm/lonIcons/lonlogos.gif'); $r->print (<

'; } + my %optionhash=(); + foreach my $type ('question','comment','policy') { + $optionhash{$type}=$env{'course.'.$env{'request.course.id'}.'.'.$type.'.email.text'}; + } if (&feedback_available(1)) { $msgoptions.= '

'; + ($optionhash{'question'}?$optionhash{'question'}:&mt('Question about resource content')).'

'; } if (&feedback_available(0,1)) { $msgoptions.= '

'; } if (&feedback_available(0,0,1)) { $msgoptions.= '

'; } } if (($env{'request.course.id'}) && (!$env{'form.sendmessageonly'})) { - if (&discussion_open(undef,$symb) && + my ($blocked,$blocktext) = &Apache::loncommon::blocking_status('boards'); + if (!$blocked && &discussion_open(undef,$symb) && &Apache::lonnet::allowed('pch', $env{'request.course.id'}. ($env{'request.course.sec'}?'/'.$env{'request.course.sec'}:''))) { $discussoptions='
'. + $contribdisc. + '
'. ''.&mt('Change Screenname').''; + my $blockblog = &Apache::loncommon::blocking_status('blogs'); + if (!$blockblog) { + $discussoptions.= &add_blog_checkbox($crstype); + } } - $discussoptions.='
'; } - if ($msgoptions) { $msgoptions='

'.&mt('Sending Messages').'

'.$msgoptions; } + if ($msgoptions) { + $msgoptions='

' + .' '.&mt('Send Feedback').'

'.&Apache::lonhtmlcommon::coursepreflink(&mt('Feedback Settings'),'feedback').'

' + .$msgoptions; + } if ($discussoptions) { - $discussoptions='

'.&mt('Discussion Contributions').'

'.$discussoptions; } + $discussoptions='

' + .' '.&mt('Discussion Contributions').'

'.&Apache::lonhtmlcommon::coursepreflink(&mt('Discussion Settings'),'discussion').'

' + .$discussoptions; + } return $msgoptions.$discussoptions; } @@ -2587,12 +2693,15 @@ sub clear_out_html { } sub assemble_email { - my ($feedurl,$message,$prevattempts,$usersaw,$useranswer)=@_; + my ($message,$prevattempts,$usersaw,$useranswer)=@_; my %lt = &Apache::lonlocal::texthash( 'prev' => 'Previous attempts of student (if applicable)', 'orig' => 'Original screen output (if applicable)', 'corr' => 'Correct Answer(s) (if applicable)', ); + if (&Apache::loncommon::course_type() eq 'Community') { + $lt{'prev'} = &mt('Previous attempts of member (if applicable)'); + } my $email=<<"ENDEMAIL"; $message ENDEMAIL @@ -2608,136 +2717,53 @@ ENDCITE return ($email,$citations); } -sub secapply { - my $rec=shift; - my $defaultflag=shift; - $rec=~s/\s+//g; - $rec=~s/\@/\:/g; - my ($adr,$sections)=($rec=~/^([^\(]+)\(([^\)]+)\)/); - if ($sections) { - foreach (split(/\;/,$sections)) { - if (($_ eq $env{'request.course.sec'}) || - ($defaultflag && ($_ eq '*'))) { - return $adr; - } - } - } else { - return $rec; - } - return ''; -} - -=pod - -=over 4 - -=item * - -decide_receiver($feedurl,$author,$question,$course,$policy,$defaultflag); - -Arguments - $feedurl - /res/ url of resource (only need if $author is true) - $author,$question,$course,$policy - all true/false parameters - if true will attempt to find the addresses of user that should receive - this type of feedback (author - feedback to author of resource $feedurl, - $question 'Resource Content Questions', $course 'Course Content Question', - $policy 'Course Policy') - (Additionally it also checks $env for whether the corresponding form. - element exists, for ease of use in a html response context) - - $defaultflag - (internal should be left blank) if true gather addresses - that aren't for a section even if I have a section - (used for reccursion internally, first we look for - addresses for our specific section then we recurse - and look for non section addresses) - -Returns - $typestyle - string of html text, describing what addresses were found - %to - a hash, which keys are addresses of users to send messages to - the keys will look like name:domain - -=cut - -sub decide_receiver { - my ($feedurl,$author,$question,$course,$policy,$defaultflag) = @_; - my $typestyle=''; - my %to=(); - if ($env{'form.discuss'} eq 'author' ||$author) { - $typestyle.='Submitting as Author Feedback
'; - $feedurl=~/^\/res\/(\w+)\/(\w+)\//; - $to{$2.':'.$1}=1; - } - if ($env{'form.discuss'} eq 'question' ||$question) { - $typestyle.=&mt('Submitting as Question').'
'; - foreach (split(/\,/, - $env{'course.'.$env{'request.course.id'}.'.question.email'}) - ) { - my $rec=&secapply($_,$defaultflag); - if ($rec) { $to{$rec}=1; } - } - } - if ($env{'form.discuss'} eq 'course' ||$course) { - $typestyle.=&mt('Submitting as Comment').'
'; - foreach (split(/\,/, - $env{'course.'.$env{'request.course.id'}.'.comment.email'}) - ) { - my $rec=&secapply($_,$defaultflag); - if ($rec) { $to{$rec}=1; } - } - } - if ($env{'form.discuss'} eq 'policy' ||$policy) { - $typestyle.=&mt('Submitting as Policy Feedback').'
'; - foreach (split(/\,/, - $env{'course.'.$env{'request.course.id'}.'.policy.email'}) - ) { - my $rec=&secapply($_,$defaultflag); - if ($rec) { $to{$rec}=1; } - } - } - if ((scalar(%to) eq '0') && (!$defaultflag)) { - ($typestyle,%to)= - &decide_receiver($feedurl,$author,$question,$course,$policy,1); - } - return ($typestyle,%to); -} sub feedback_available { my ($question,$course,$policy)=@_; - my ($typestyle,%to)=&decide_receiver('',0,$question,$course,$policy); + my ($typestyle,%to)=&Apache::lonmsg::decide_receiver('',0,$question, + $course,$policy); return scalar(%to); } sub send_msg { - my ($title,$feedurl,$email,$citations,$attachmenturl,%to)=@_; - my $status=''; - my $sendsomething=0; - if ($title=~/^Error/) { $title=&mt('Feedback').': '.$title; } - unless ($title=~/\w/) { $title=&mt('Feedback'); } - foreach (keys %to) { - if ($_) { - my $declutter=&Apache::lonnet::declutter($feedurl); - unless (&Apache::lonmsg::user_normal_msg(split(/\:/,$_), - $title.' ['.$declutter.']',$email,$citations,$feedurl, - $attachmenturl)=~/ok/) { - $status.='
'.&mt('Error sending message to').' '.$_.'
'; - } else { - $sendsomething++; - } + my ($title,$feedurl,$email,$citations,$attachmenturl,$symb,%to)=@_; + my $status=''; + my $sendsomething=0; + my $restitle = &get_resource_title($symb,$feedurl); + if ($title=~/^Error/) { $title=&mt('Feedback').': '.$title; } + unless ($title=~/\w/) { $title=&mt('Feedback'); } + foreach my $key (keys(%to)) { + if ($key) { + my ($user,$domain) = split(/\:/,$key,2); + if (!defined($user)) { + $status.='
'.&mt('Error sending message to [_1], no user specified.',$key); + } elsif (!defined($domain)) { + $status.='
'.&mt('Error sending message to [_1], no domain specified.',$key); + } else { + unless (&Apache::lonmsg::user_normal_msg($user,$domain, + $title.' ['.$restitle.']',$email,$citations,$feedurl, + $attachmenturl,undef,undef,$symb,$restitle)=~/ok/) { + $status.='
'.&mt('Error sending message to').' '.$key.'
'; + } else { + $sendsomething++; + } + } + } } - } + my %record=&Apache::lonnet::restore('_feedback'); - my ($temp)=keys %record; + my ($temp)=keys(%record); unless ($temp=~/^error\:/) { - my %newrecord=(); - $newrecord{'resource'}=$feedurl; - $newrecord{'subnumber'}=$record{'subnumber'}+1; - unless (&Apache::lonnet::cstore(\%newrecord,'_feedback') eq 'ok') { - $status.='
'.&mt('Not registered').'
'; - } + my %newrecord=(); + $newrecord{'resource'}=$feedurl; + $newrecord{'subnumber'}=$record{'subnumber'}+1; + unless (&Apache::lonnet::cstore(\%newrecord,'_feedback') eq 'ok') { + $status.='
'.&mt('Not registered').'
'; + } } - - return ($status,$sendsomething); + + return ($status,$sendsomething); } sub adddiscuss { @@ -2770,10 +2796,11 @@ sub adddiscuss { $contrib{'anonymous'}='true'; } if (($symb) && ($email)) { + my $now = time; if ($env{'form.editdisc'}) { $contrib{'ip'}=$ENV{'REMOTE_ADDR'}; $contrib{'host'}=$Apache::lonnet::perlvar{'lonHostID'}; - $contrib{'timestamp'} = time; + $contrib{'timestamp'} = $now; $contrib{'history'} = ''; my $numoldver = 0; my ($oldsymb,$oldidx)=split(/\:\:\:/,$env{'form.editdisc'}); @@ -2788,7 +2815,7 @@ sub adddiscuss { } if (defined($oldcontrib{$oldidx.':history'})) { if ($oldcontrib{$oldidx.':history'} =~ /:/) { - my @oldversions = split/:/,$oldcontrib{$oldidx.':history'}; + my @oldversions = split(/:/,$oldcontrib{$oldidx.':history'}); $numoldver = @oldversions; } else { $numoldver = 1; @@ -2824,14 +2851,14 @@ sub adddiscuss { $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}); } - my %storenewentry=($symb => time); + my %storenewentry=($symb => $now); $status.='
'.&mt('Updating discussion time').': '. &Apache::lonnet::put('discussiontimes',\%storenewentry, $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}); } my %record=&Apache::lonnet::restore('_discussion'); - my ($temp)=keys %record; + my ($temp)=keys(%record); unless ($temp=~/^error\:/) { my %newrecord=(); $newrecord{'resource'}=$symb; @@ -2845,6 +2872,48 @@ sub adddiscuss { return $status.'
'; } +sub get_discussion_info { + my ($idx,%contrib) = @_; + my $changelast = 0; + my $count = 0; + my $hiddenflag = 0; + my $deletedflag = 0; + my ($hidden,$deleted,%info,$newlastdisc); + my $version = $contrib{'version'}; + if ($version) { + for (my $id=$version; $id>0; $id--) { + my $vkeys=$contrib{$id.':keys'}; + my @keys=split(/:/,$vkeys); + if (grep(/^hidden$/,@keys)) { + if (!$hiddenflag) { + $hidden = $contrib{$id.':hidden'}; + $hiddenflag = 1; + } + } elsif (grep(/^deleted$/,@keys)) { + if (!$deletedflag) { + $deleted = $contrib{$id.':deleted'}; + $deletedflag = 1; + } + } else { + if (($hidden !~/\.$id\./) && ($deleted !~/\.$id\./)) { + $count++; + $info{$count}{'id'} = $id; + $info{$count}{'timestamp'}=$contrib{$id.':timestamp'}; + } + } + } + if ($info{'1'}{'id'} == $idx) { + $changelast = 1; + if ($count > 1) { + $newlastdisc = $info{'2'}{'timestamp'}; + } else { + $newlastdisc = 0; + } + } + } + return ($changelast,$newlastdisc); +} + # ----------------------------------------------------------- Preview function sub show_preview { @@ -2865,12 +2934,33 @@ sub show_preview { my $end_page = &Apache::loncommon::end_page(); - $r->print($start_page.'
$lt{'soor'} $lt{'sprs'} $lt{'spur'} $lt{'spse'} $lt{'spgr'} $lt{'psub'}$lt{'soor'} $lt{'sprs'} $lt{'spur'} $lt{'spse'} $lt{'spgr'} $lt{'psub'}
@@ -2096,25 +2169,26 @@ $start_page   - - + +   - $section_sel   - $group_sel
'.$count.' '.$last.', '.$first.' ('.$uname.':'.$udom.')'.$postcounts{$_}.''.$postcounts{$user}.'
'. - ''.&mt('Subject').': '.$subject.'

'. - $message.'
'.$end_page); + $r->print($start_page + .'

'.&mt('Preview').'

' + .&Apache::lonhtmlcommon::start_pick_box() + .&Apache::lonhtmlcommon::row_title(&mt('Subject')) + .$subject + .&Apache::lonhtmlcommon::row_closure() + .&Apache::lonhtmlcommon::row_title(&mt('Message')) + .$message + .&Apache::lonhtmlcommon::row_closure(1) + .&Apache::lonhtmlcommon::end_pick_box() + .$end_page + ); } - +sub contains_block_html { + my ($message)=@_; + return ($message =~ m/ + <(br|h1|h2|h3|h4|h5|h6|p|ol|ul|table|pre|address|blockquote|center|div) + [\s]* + ([\w]+\=['"][\w]+['"])* + [\s]* + ( + [\s]*[\/]>| + >.*<\/\1[\s]*> + )/x ); +} + sub newline_to_br { my ($message)=@_; my $newmessage; @@ -2900,16 +2990,17 @@ sub generate_preview_button { return(< - + +onclick="if (typeof(document.$formname.onsubmit)=='function') {document.$formname.onsubmit();};this.form.comment.value=document.$formname.$fieldname.value;this.form.subject.value=document.$formname.subject.value;this.form.submit();" /> ENDPREVIEW } sub modify_attachments { - my ($r,$currnewattach,$currdelold,$symb,$idx,$attachmenturls)=@_; + my ($r,$currnewattach,$currdelold,$symb,$idx,$attachmenturls, + $attachmaxtext,$toolarge)=@_; my %lt = &Apache::lonlocal::texthash( 'subj' => 'Subject', @@ -2917,7 +3008,7 @@ sub modify_attachments { 'chth' => 'Check the checkboxes for any you wish to remove.', 'thef' => 'The following attachments have been uploaded for inclusion with this posting.', 'adda' => 'Add a new attachment to this post.', - 'stch' => 'Store Changes', + 'stch' => 'Save Changes', ); my $js = < @@ -2928,8 +3019,12 @@ sub modify_attachments { END + # Breadcrumbs + my $brcrum = [{'href' => '', + 'text' => 'Discussion Post Attachments'}]; my $start_page = - &Apache::loncommon::start_page('Discussion Post Attachments',$js); + &Apache::loncommon::start_page('Discussion Post Attachments',$js, + {'bread_crumbs' => $brcrum,}); my $orig_subject = &unescape($env{'form.subject'}); my $subject=&clear_out_html($orig_subject,undef,1); @@ -2951,15 +3046,17 @@ END $r->print(< - +
+
- + + + + +
- Subject: $subject

+
+ Subject: $subject

END if ($idx) { if ($attachmenturls) { - my @currold = keys %currattach; + my @currold = keys(%currattach); if (@currold > 0) { $r->print($lt{'thfo'}.'
'.$lt{'chth'}.'
'."\n"); foreach my $id (@currold) { @@ -2973,16 +3070,22 @@ END } if ((ref($currnewattach) eq 'ARRAY') && (@{$currnewattach} > 0)) { $r->print($lt{'thef'}.'
'.$lt{'chth'}.'
'."\n"); - foreach (@{$currnewattach}) { - $_ =~ m#/([^/]+)$#; - $r->print('
'."\n"); + foreach my $attach (@{$currnewattach}) { + $attach =~ m#/([^/]+)$#; + $r->print('
'."\n"); } $r->print("
"); } $r->print(< +
+ $lt{'adda'}
$attachmaxtext
@@ -3000,7 +3103,7 @@ END $r->print(''."\n"); } $r->print(< + $end_page END @@ -3020,14 +3123,14 @@ sub process_attachments { my @currnew = (); foreach my $newone (@{$currnewattach}) { my $delflag = 0; - foreach (@currdelnew) { - if ($newone eq $_) { + foreach my $item (@currdelnew) { + if ($newone eq $item) { $delflag = 1; last; } } unless ($delflag) { - push @currnew, $newone; + push(@currnew, $newone); } } @{$currnewattach} = @currnew; @@ -3036,7 +3139,8 @@ sub process_attachments { } sub generate_attachments_button { - my ($idx,$attachnum,$ressymb,$now,$currnewattach,$deloldattach,$numoldver,$mode) = @_; + my ($idx,$attachnum,$ressymb,$now,$currnewattach,$deloldattach, + $numoldver,$mode,$blockblog) = @_; my $origpage = $ENV{'REQUEST_URI'}; my $att=$attachnum.' '.&mt("attachments"); my %lt = &Apache::lonlocal::texthash( @@ -3046,8 +3150,11 @@ sub generate_attachments_button {
$lt{'clic'}:  - - + + ENDATTACH if (defined($deloldattach)) { if (@{$deloldattach} > 0) { - foreach (@{$deloldattach}) { - $response .= ''."\n"; + foreach my $delatt (@{$deloldattach}) { + $response .= ''."\n"; } } } if (defined($currnewattach)) { if (@{$currnewattach} > 0) { - foreach (@{$currnewattach}) { - $response .= ''."\n"; + foreach my $attach (@{$currnewattach}) { + $response .= ''."\n"; } } } @@ -3084,7 +3191,7 @@ sub extract_attachments { my ($attachmenturls,$idx,$numoldver,$message,$attachments,$currattach,$currdelold) = @_; %{$attachments}=(); &get_post_attachments($attachments,$attachmenturls); - foreach my $id (sort keys %{$attachments}) { + foreach my $id (sort(keys(%{$attachments}))) { if (exists($$attachments{$id}{$numoldver})) { if (defined($currdelold)) { if (@{$currdelold} > 0) { @@ -3099,7 +3206,7 @@ sub extract_attachments { } } } - my @attached = (sort { $a <=> $b } keys %{$currattach}); + my @attached = (sort { $a <=> $b } keys(%{$currattach})); if (@attached == 1) { my $id = $attached[0]; my $attachurl; @@ -3115,8 +3222,8 @@ sub extract_attachments { $attachurl); } elsif (@attached > 1) { $$message.='
    '; - foreach (@attached) { - my $id = $_; + foreach my $attach (@attached) { + my $id = $attach; my $attachurl = &HTML::Entities::decode($$attachments{$id}{'filename'}); my ($fname) =($attachurl=~m|/([^/]+)$|); @@ -3143,7 +3250,7 @@ sub construct_attachmenturl { $oldattachmenturl = $contrib{$idx.':attachmenturl'}; if ($contrib{$idx.':history'}) { if ($contrib{$idx.':history'} =~ /:/) { - my @oldversions = split/:/,$contrib{$idx.':history'}; + my @oldversions = split(/:/,$contrib{$idx.':history'}); $currver = 1 + scalar(@oldversions); } else { $currver = 2; @@ -3156,13 +3263,13 @@ sub construct_attachmenturl { my %attachments = (); my $prevver = $currver-1; &get_post_attachments(\%attachments,$oldattachmenturl); - my $numattach = scalar(keys %attachments); + my $numattach = scalar(keys(%attachments)); $startnum += $numattach; - foreach my $num (sort {$a <=> $b} keys %attachments) { + foreach my $num (sort {$a <=> $b} keys(%attachments)) { $newattachmenturl .= ''.$attachments{$num}{'filename'}.''; - foreach $_ (sort {$a <=> $b} keys %{$attachments{$num}}) { - unless ($_ eq 'filename') { - $newattachmenturl .= ''.$attachments{$num}{$_}.''; + foreach my $item (sort {$a <=> $b} keys(%{$attachments{$num}})) { + unless ($item eq 'filename') { + $newattachmenturl .= ''.$attachments{$num}{$item}.''; } } if (grep/^$num$/,@{$keepold}) { @@ -3187,22 +3294,55 @@ sub construct_attachmenturl { return $newattachmenturl; } +sub add_blog_checkbox { + my ($crstype) = @_; + my $checkstatus; + if ($env{'form.blog'}) { + $checkstatus = 'checked="checked"'; + } + my $output = ' +
    +
    '."\n"; + return $output; +} + sub has_discussion { my $resourcesref = shift; my $navmap = Apache::lonnavmaps::navmap->new(); - my @allres=$navmap->retrieveResources(); - foreach my $resource (@allres) { - if ($resource->hasDiscussion()) { - my $ressymb = $resource->wrap_symb(); - push @{$resourcesref}, $ressymb; + if (defined($navmap)) { + my @allres=$navmap->retrieveResources(); + foreach my $resource (@allres) { + if ($resource->hasDiscussion()) { + my $ressymb = $resource->wrap_symb(); + if (ref($resourcesref) eq 'ARRAY') { + push(@{$resourcesref}, $ressymb); + } + } } + } else { + &Apache::lonnet::logthis('Has discussion check failed - could not create navmap object.'); } return; } sub sort_filter_names { - my ($sort_types,$role_types,$status_types) = @_; - %{$sort_types} = ( + my ($sort_types,$role_types,$status_types,$crstype) = @_; + if (ref($sort_types) eq 'HASH') { + %{$sort_types} = ( ascdate => 'Date order - oldest first', descdate => 'Date order - newest first', thread => 'Threaded', @@ -3210,22 +3350,28 @@ sub sort_filter_names { username => 'By domain and username', lastfirst => 'By last name, first name' ); - %{$role_types} = ( - all => 'All roles', - st => 'Students', - cc => 'Course Coordinators', - in => 'Instructors', - ta => 'TAs', - ep => 'Exam proctors', - ad => 'Administrators', - cr => 'Custom roles' - ); - %{$status_types} = ( + } + my @courseroles = qw(st in ta ep ad); + if ($crstype eq 'Community') { + push(@courseroles,'co'); + } else { + push(@courseroles,'cc'); + } + if (ref($role_types) eq 'HASH') { + foreach my $role (@courseroles) { + $role_types->{$role} = &Apache::lonnet::plaintext($role,$crstype); + } + $role_types->{'all'} = 'All roles'; + $role_types->{'cr'} = 'Custom role'; + } + if (ref($status_types) eq 'HASH') { + %{$status_types} = ( all => 'Roles of any status', Active => 'Only active roles', Expired => 'Only past roles', Future => 'Only future roles', ); + } } sub handler { @@ -3241,6 +3387,10 @@ sub handler { &Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'}, ['hide','unhide','deldisc','postdata','preview','replydisc','editdisc','cmd','symb','onlyunread','allposts','onlyunmark','previous','markread','markonread','markondisp','toggoff','toggon','modifydisp','changes','navtime','navmaps','navurl','sortposts','applysort','rolefilter','statusfilter','sectionpick','groupick','posterlist','userpick','attach','origpage','currnewattach','deloldattach','keepold','allversions','export','sendmessageonly','group','ref']); my $group = $env{'form.group'}; + my %attachmax = ( + text => &mt('(128 KB max size)'), + num => 131072, + ); if ($env{'form.editdisc'}) { if (!(&editing_allowed($env{'form.editdisc'},$env{'form.group'}))) { my $symb=(split(/\:\:\:/,$env{'form.editdisc'}))[0]; @@ -3256,7 +3406,7 @@ sub handler { my $readkey = $symb.'_read'; my $chgcount = 0; my %readinghash = &Apache::lonnet::get('nohist_'.$env{'request.course.id'}.'_discuss',[$readkey],$env{'user.domain'},$env{'user.name'}); - foreach my $key (keys %env) { + foreach my $key (keys(%env)) { if ($key =~ m/^form\.postunread_(\d+)/) { if ($readinghash{$readkey} =~ /\.$1\./) { $readinghash{$readkey} =~ s/\.$1\.//; @@ -3283,7 +3433,13 @@ sub handler { &Apache::loncommon::no_cache($r); $r->send_http_header; - $r->print(&Apache::loncommon::start_page('Discussion Post Versions')); + # Breadcrumbs + my $brcrum = [{'href' => '', + 'text' => 'Discussion Post Versions'}]; + + $r->print(&Apache::loncommon::start_page('Discussion Post Versions',undef, + {'bread_crumbs' => $brcrum,}) + ); my $crs='/'.$env{'request.course.id'}; if ($env{'request.course.sec'}) { @@ -3355,7 +3511,7 @@ sub handler { my @resources = (); if (defined($env{'form.navmaps'})) { if ($env{'form.navmaps'} =~ /:/) { - @resources = split/:/,$env{'form.navmaps'}; + @resources = split(/:/,$env{'form.navmaps'}); } else { @resources = ("$env{'form.navmaps'}"); } @@ -3368,10 +3524,10 @@ sub handler { my %lt = &Apache::lonlocal::texthash( 'mnpa' => 'Marked "New" posts as read in a total of', 'robb' => 'resources/bulletin boards.', - 'twnp' => 'There are currently no resources or bulletin boards with unread discussion postings.' + 'twnp' => 'There are currently no resources or discussion boards with unread discussion postings.' ); - foreach (@resources) { - my $ressymb=$_; + foreach my $res (@resources) { + my $ressymb=$res; &Apache::lonenc::check_decrypt(\$ressymb); my $lastkey = $ressymb.'_lastread'; $discinfo{$lastkey} = $env{'form.navtime'}; @@ -3489,7 +3645,16 @@ ENDREDIR if ( ($env{'form.hide'}) && (!$seeid) ) { $newhash{'studenthidden'} = $currentstudenthidden; } - + if ($env{'form.hide'}) { + my $changelast = 0; + my $newlast; + ($changelast,$newlast) = &get_discussion_info($idx,%contrib); + if ($changelast) { + &Apache::lonnet::put('discussiontimes',{$symb => $newlast}, + $env{'course.'.$env{'request.course.id'}.'.domain'}, + $env{'course.'.$env{'request.course.id'}.'.num'}); + } + } &Apache::lonnet::store(\%newhash,$symb,$env{'request.course.id'}, $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}); @@ -3502,10 +3667,10 @@ ENDREDIR my ($symb,$feedurl)=&get_feedurl_and_clean_symb($env{'form.symb'}); if ($env{'form.cmd'} eq 'threadedon') { &Apache::lonnet::put('environment',{'threadeddiscussion' => 'on'}); - &Apache::lonnet::appenv('environment.threadeddiscussion' => 'on'); + &Apache::lonnet::appenv({'environment.threadeddiscussion' => 'on'}); } else { &Apache::lonnet::del('environment',['threadeddiscussion']); - &Apache::lonnet::delenv('environment\.threadeddiscussion'); + &Apache::lonnet::delenv('environment.threadeddiscussion'); } &redirect_back($r,$feedurl,&mt('Changed discussion view mode').'
    ', '0','0','','',$env{'form.previous'},undef,undef,undef, @@ -3518,6 +3683,11 @@ ENDREDIR my %contrib=&Apache::lonnet::restore($symb,$env{'request.course.id'}, $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}); + my ($changelast,$newlast) = &get_discussion_info($idx,%contrib); + if ($changelast) { + &Apache::lonnet::put('discussiontimes',{$symb => $newlast}, + $env{'course.'.$env{'request.course.id'}.'.domain'}, $env{'course.'.$env{'request.course.id'}.'.num'}); + } my %newhash=('deleted' => $contrib{'deleted'}.".$idx."); &Apache::lonnet::store(\%newhash,$symb,$env{'request.course.id'}, $env{'course.'.$env{'request.course.id'}.'.domain'}, @@ -3535,13 +3705,15 @@ ENDREDIR &Apache::loncommon::content_type($r,'text/html'); $r->send_http_header; &Apache::loncommon::get_unprocessed_cgi($ENV{'QUERY_STRING'},['subject','comment','addnewattach','delnewattach','timestamp','numoldver','idx','discuss','blog']); - my (@currnewattach,@currdelold,@keepold); + my (@currnewattach,@currdelold,@keepold,$toolarge); &process_attachments(\@currnewattach,\@currdelold,\@keepold); if (exists($env{'form.addnewattach.filename'})) { - unless (length($env{'form.addnewattach'})>131072) { + if (length($env{'form.addnewattach'})<=$attachmax{'num'}) { my $subdir = 'feedback/'.$env{'form.timestamp'}; my $newattachment=&Apache::lonnet::userfileupload('addnewattach',undef,$subdir); - push @currnewattach, $newattachment; + push(@currnewattach, $newattachment); + } else { + $toolarge = '

    '.&mt('Attachment not included - exceeded permitted length').'

    '; } } my $attachmenturls; @@ -3554,7 +3726,7 @@ ENDREDIR $attachmenturls = $contrib{$idx.':attachmenturl'}; } &modify_attachments($r,\@currnewattach,\@currdelold,$symb,$idx, - $attachmenturls); + $attachmenturls,$attachmax{'text'},$toolarge); return OK; } elsif ($env{'form.export'}) { &Apache::loncommon::content_type($r,'text/html'); @@ -3577,7 +3749,7 @@ ENDREDIR } else { # ------------------------------------------------------------- Normal feedback my $feedurl=$env{'form.postdata'}; - $feedurl=~s/^http\:\/\///; + $feedurl=~s/^https?\:\/\///; $feedurl=~s/^$ENV{'SERVER_NAME'}//; $feedurl=~s/^$ENV{'HTTP_HOST'}//; $feedurl=~s/\?.+$//; @@ -3585,12 +3757,8 @@ ENDREDIR my $symb; if ($env{'form.replydisc'}) { $symb=(split(/\:\:\:/,$env{'form.replydisc'}))[0]; - my ($map,$id,$url)=&Apache::lonnet::decode_symb($symb); - $feedurl=&Apache::lonnet::clutter($url); } elsif ($env{'form.editdisc'}) { $symb=(split(/\:\:\:/,$env{'form.editdisc'}))[0]; - my ($map,$id,$url)=&Apache::lonnet::decode_symb($symb); - $feedurl=&Apache::lonnet::clutter($url); } elsif ($env{'form.origpage'}) { $symb=""; } else { @@ -3598,18 +3766,18 @@ ENDREDIR } unless ($symb) { $symb=$env{'form.symb'}; - if ($symb) { - my ($map,$id,$url)=&Apache::lonnet::decode_symb($symb); - $feedurl=&Apache::lonnet::clutter($url); - } } - &Apache::lonenc::check_decrypt(\$symb); + if (defined($symb)) { + ($symb,$feedurl)=&get_feedurl_and_clean_symb($symb); + } else { + # backward compatibility (bulletin boards used to be 'wrapped') + &Apache::lonenc::check_decrypt(\$feedurl); + &dewrapper(\$feedurl); + } my $goahead=1; if ($feedurl=~/\.(problem|exam|quiz|assess|survey|form|task)$/) { unless ($symb) { $goahead=0; } } - # backward compatibility (bulletin boards used to be 'wrapped') - &dewrapper(\$feedurl); if (!$goahead) { # Ambiguous Problem Resource $r->internal_redirect('/adm/ambiguous'); @@ -3628,16 +3796,26 @@ ENDREDIR &Apache::loncommon::content_type($r,'text/html'); $r->send_http_header; # Unable to give feedback + &Apache::lonenc::check_encrypt(\$feedurl); &no_redirect_back($r,$feedurl); return OK; } # --------------------------------------------------- Print login screen header unless ($env{'form.sendit'}) { + &Apache::lonenc::check_encrypt(\$feedurl); &Apache::loncommon::content_type($r,'text/html'); $r->send_http_header; + if (($env{'form.replydisc'}) || ($env{'form.editdisc'})) { + my ($blocked,$blocktext) = + &Apache::loncommon::blocking_status('boards'); + if ($blocked) { + $r->print(&blocked_reply_or_edit($blocktext)); + return OK; + } + } my $options=&screen_header($feedurl,$symb); if ($options) { - &mail_screen($r,$feedurl,$options); + &mail_screen($r,$feedurl,$options,$symb,$attachmax{'text'}); } else { &fail_redirect($r,$feedurl); } @@ -3650,16 +3828,20 @@ ENDREDIR $env{'request.course.id'}); # Get output from resource + &Apache::lonenc::check_encrypt(\$feedurl); my $usersaw=&resource_output($feedurl); # Get resource answer (need to allow student to view grades for this to work) - &Apache::lonnet::appenv(('allowed.vgr'=>'F')); - my $useranswer=&Apache::loncommon::get_student_answers( - $symb,$env{'user.name'},$env{'user.domain'}, - $env{'request.course.id'}); + &Apache::lonnet::appenv({'allowed.vgr'=>'F'}); + my $usersymb = &Apache::lonenc::check_encrypt($symb); + my $useranswer= + &Apache::loncommon::get_student_answers( + $usersymb,$env{'user.name'},$env{'user.domain'}, + $env{'request.course.id'}); &Apache::lonnet::delenv('allowed.vgr'); # Get attachments, if any, and not too large my $attachmenturl=''; + my $toolarge=''; if (($env{'form.origpage'}) || ($env{'form.editdisc'}) || ($env{'form.replydisc'})) { my ($symb,$idx); @@ -3678,25 +3860,29 @@ ENDREDIR $symb=~s|(bulletin___\d+___)adm/wrapper/|$1|; $attachmenturl=&construct_attachmenturl(\@currnewattach,\@keepold,$symb,$idx); } elsif ($env{'form.attachment.filename'}) { - unless (length($env{'form.attachment'})>131072) { - $attachmenturl=&Apache::lonnet::userfileupload('attachment',undef,'feedback'); - } + if (length($env{'form.attachment'})<=$attachmax{'num'}) { + my $now = time; + my $subdir = 'feedback/'.$now; + $attachmenturl=&Apache::lonnet::userfileupload('attachment',undef,$subdir); + } else { + $toolarge = '

    '.&mt('Attachment not included - exceeded permitted length').'

    '; + } } # Filter HTML out of message (could be nasty) my $message=&clear_out_html($env{'form.comment'}); # Assemble email - my ($email,$citations)=&assemble_email($feedurl,$message,$prevattempts, + my ($email,$citations)=&assemble_email($message,$prevattempts, $usersaw,$useranswer); # Who gets this? - my ($typestyle,%to) = &decide_receiver($feedurl); + my ($typestyle,%to) = &Apache::lonmsg::decide_receiver($feedurl); # Actually send mail my ($status,$numsent)=&send_msg(&clear_out_html($env{'form.subject'}, undef,1), $feedurl,$email,$citations, - $attachmenturl,%to); + $attachmenturl,$usersymb,%to); # Discussion? Store that. my $numpost=0; @@ -3719,13 +3905,26 @@ ENDREDIR $env{'user.domain'}, 'CourseBlog_'.$env{'request.course.id'}, $subject,$message,$feedurl,'public'); - $blog='
    '.&mt('Added to my course blog').'
    '; + if (&Apache::loncommon::course_type() eq 'Community') { + $blog='
    '.&mt('Added to my community blog').'
    '; + } else { + $blog='
    '.&mt('Added to my course blog').'
    '; + } } # Receipt screen and redirect back to where came from - &redirect_back($r,$feedurl,$typestyle,$numsent,$numpost,$blog,$status,$env{'form.previous'},undef,undef,undef,undef,undef,undef,$group); + &redirect_back($r,$feedurl,$typestyle,$numsent,$numpost,$blog,$status,$env{'form.previous'},undef,undef,undef,undef,undef,undef,$group,$toolarge); } return OK; +} + +sub blocked_reply_or_edit { + my ($blocktext) = @_; + return + &Apache::loncommon::start_page('Resource Feedback and Discussion'). + $blocktext.'

    '. + &mt('Back to previous page'). + &Apache::loncommon::end_page(); } sub wrap_symb { @@ -3830,5 +4029,160 @@ sub group_args { return $extra_args; } +sub get_resource_title { + my ($symb,$feedurl) = @_; + my ($restitle,$plainurl); + if (defined($symb)) { + my $plain_symb = &Apache::lonenc::check_decrypt($symb); + $restitle = &Apache::lonnet::gettitle($plain_symb); + } + if (defined($feedurl)) { + $plainurl = &Apache::lonenc::check_decrypt($feedurl); + } + if (!defined($restitle)) { + if (defined($feedurl)) { + $restitle = &Apache::lonnet::gettitle($plainurl); + } + } + if ($plainurl ne $feedurl) { + my ($plain_filename) = ($plainurl =~ m-/([^/]+)$-); + if ($plain_filename eq $restitle) { + $restitle = &mt('Untitled resource'); + } + } + if ($restitle eq '') { + $restitle = &mt('Untitled resource'); + } + return $restitle; +} + 1; __END__ + + +=pod + +=head1 NAME + +Apache::lonfeedback.pm + +=head1 SYNOPSIS + +Handles feedback from students to instructors and system administrators. + +Provides a screenshot of the current resource, as well as previous attempts if the resource was a homework. + +Used by lonmsg.pm. + +This is part of the LearningOnline Network with CAPA project +described at http://www.lon-capa.org. + +=head1 OVERVIEW + +None + +=head1 SUBROUTINES + +=over + +=item discussion_open() + +=item discussion_visible() + +=item list_discussion() + +=item send_feedback_link() + +=item send_message_link() + +=item action_links_bar() + +=item postingform_display() + +=item build_posting_display + +=item filter_regexp() + +=item get_post_contents() + +=item replicate_attachments() + +=item mail_screen() + +=item print_display_options() + +=item print_sortfilter_options() + +=item print_showposters() + +=item get_post_versions() + +=item get_post_attachments() + +=item fail_redirect() + +=item redirect_back() + +=item no_redirect_back() + +=item screen_header() + +=item resource_output() + +=item clear_out_html() + +=item assemble_email() + +=item feedback_available() + +=item send_msg() + +=item adddiscuss() + +=item get_discussion_info() + +=item show_preview() + +=item newline_to_br() + +=item generate_preview_button() + +=item modify_attachments() + +=item process_attachments() + +=item generate_attachments_button() + +=item extract_attachments() + +=item construct_attachmenturl() + +=item add_blog_checkbox() + +=item has_discussion() + +=item sort_filter_names() + +=item handler() + +=item blocked_reply_or_edit() + +=item wrap_symb() + +=item dewrapper() + +=item get_feedurl() + +=item get_feedurl_and_clean_symb() + +=item editing_allowed() + +=item check_group_priv() + +=item group_args() + +=item get_resource_title() + +=back + +=cut