--- rat/lonuserstate.pm 2014/02/23 20:27:54 1.148 +++ rat/lonuserstate.pm 2020/01/16 21:49:07 1.149.2.2.2.1 @@ -1,7 +1,7 @@ # The LearningOnline Network with CAPA # Construct and maintain state and binary representation of course for user # -# $Id: lonuserstate.pm,v 1.148 2014/02/23 20:27:54 raeburn Exp $ +# $Id: lonuserstate.pm,v 1.149.2.2.2.1 2020/01/16 21:49:07 raeburn Exp $ # # Copyright Michigan State University Board of Trustees # @@ -62,6 +62,8 @@ my %randomorder; # maps to order content my %randomizationcode; # code used to grade folder for bubblesheet exam my %encurl; # URLs in this folder are supposed to be encrypted my %hiddenurl; # this URL (or complete folder) is supposed to be hidden +my %rescount; # count of unhidden items in each map +my %mapcount; # count of unhidden maps in each map # ----------------------------------- Remove version from URL and store in hash @@ -240,6 +242,8 @@ sub loadmap { my @map_ids; my $codechecked; + $rescount{$lpc} = 0; + $mapcount{$lpc} = 0; while (my $token = $parser->get_token) { next if ($token->[0] ne 'S'); @@ -249,6 +253,13 @@ sub loadmap { my $resource_id = &parse_resource($token,$lpc,$ispage,$uri,$courseid); if (defined $resource_id) { push(@map_ids, $resource_id); + if ($hash{'src_'.$lpc.'.'.$resource_id}) { + $rescount{$lpc} ++; + if (($hash{'src_'.$lpc.'.'.$resource_id}=~/\.sequence$/) || + ($hash{'src_'.$lpc.'.'.$resource_id}=~/\.page$/)) { + $mapcount{$lpc} ++; + } + } unless ($codechecked) { my $startsymb = &Apache::lonnet::encode_symb($hash{'map_id_'.$lpc},$resource_id, @@ -278,7 +289,6 @@ sub loadmap { } undef($codechecked); - # Handle randomization and random selection if ($randomize) { @@ -338,7 +348,6 @@ sub loadmap { @map_ids=&Math::Random::random_permutation(@map_ids); } - my $from = shift(@map_ids); my $from_rid = $lpc.'.'.$from; $hash{'map_start_'.$uri} = $from_rid; @@ -363,7 +372,7 @@ sub loadmap { $parser = HTML::TokeParser->new(\$instr); $parser->attr_encoded(1); - # last parse out the mapalias params. Thes provide mnemonic + # last parse out the mapalias params. These provide mnemonic # tags to resources that can be used in conditions while (my $token = $parser->get_token) { @@ -475,6 +484,8 @@ sub parse_resource { } elsif ($turi!~/\.(sequence|page)$/) { $turi='/adm/coursedocs/showdoc'.$turi; } + } elsif ($turi=~ m{^/adm/$match_domain/$match_courseid/\d+/ext\.tool$}) { + $turi='/adm/wrapper'.$turi; } elsif ($turi=~/\S/) { # normal non-empty internal resource my $mapdir=$uri; $mapdir=~s/[^\/]+$//; @@ -706,7 +717,7 @@ sub parse_condition { # Typical attributes: # to=n - Number of the resource the parameter applies to. # type=xx - Type of parameter value (e.g. string_yesno or int_pos). -# name=xxx - Name ofr parameter (e.g. parameter_randompick or parameter_randomorder). +# name=xxx - Name of parameter (e.g. parameter_randompick or parameter_randomorder). # value=xxx - value of the parameter. sub parse_param { @@ -1072,7 +1083,7 @@ sub accinit { sub hiddenurls { my $randomoutentry=''; - foreach my $rid (keys %randompick) { + foreach my $rid (keys(%randompick)) { my $rndpick=$randompick{$rid}; my $mpc=$hash{'map_pc_'.$hash{'src_'.$rid}}; # ------------------------------------------- put existing resources into array @@ -1114,6 +1125,14 @@ sub hiddenurls { if ($currentrids[$k]) { $hash{'randomout_'.$currentrids[$k]}=1; my ($mapid,$resid)=split(/\./,$currentrids[$k]); + if ($rescount{$mapid}) { + $rescount{$mapid} --; + } + if ($hash{'is_map_'.$currentrids[$k]}) { + if ($mapcount{$mapid}) { + $mapcount{$mapid} --; + } + } $randomoutentry.='&'. &Apache::lonnet::encode_symb($hash{'map_id_'.$mapid}, $resid, @@ -1123,9 +1142,17 @@ sub hiddenurls { } } # ------------------------------ take care of explicitly hidden urls or folders - foreach my $rid (keys %hiddenurl) { + foreach my $rid (keys(%hiddenurl)) { $hash{'randomout_'.$rid}=1; my ($mapid,$resid)=split(/\./,$rid); + if ($rescount{$mapid}) { + $rescount{$mapid} --; + } + if ($hash{'is_map_'.$rid}) { + if ($mapcount{$mapid}) { + $mapcount{$mapid} --; + } + } $randomoutentry.='&'. &Apache::lonnet::encode_symb($hash{'map_id_'.$mapid},$resid, $hash{'src_'.$rid}).'&'; @@ -1136,6 +1163,32 @@ sub hiddenurls { } } +# -------------------------------------- populate big hash with map breadcrumbs + +# Create map_breadcrumbs_$pc from map_hierarchy_$pc by omitting intermediate +# maps not shown in Course Contents table. + +sub mapcrumbs { + foreach my $key (keys(%rescount)) { + if ($hash{'map_hierarchy_'.$key}) { + my $skipnext = 0; + foreach my $id (split(/,/,$hash{'map_hierarchy_'.$key}),$key) { + unless ($skipnext) { + $hash{'map_breadcrumbs_'.$key} .= "$id,"; + } + unless (($id == 0) || ($id == 1)) { + if ((!$rescount{$id}) || ($rescount{$id} == 1 && $mapcount{$id} == 1)) { + $skipnext = 1; + } else { + $skipnext = 0; + } + } + } + $hash{'map_breadcrumbs_'.$key} =~ s/,$//; + } + } +} + # ---------------------------------------------------- Read map and all submaps sub readmap { @@ -1156,7 +1209,7 @@ sub readmap { } @cond=('true:normal'); - unless (open(LOCKFILE,">$fn.db.lock")) { + unless (open(LOCKFILE,">","$fn.db.lock")) { # # Most likely a permissions problem on the lockfile or its directory. # @@ -1174,8 +1227,13 @@ sub readmap { &unlink_tmpfiles($fn); } undef %randompick; + undef %randompickseed; + undef %randomorder; + undef %randomizationcode; undef %hiddenurl; undef %encurl; + undef %rescount; + undef %mapcount; $retfrid=''; $errtext=''; my ($untiedhash,$untiedparmhash,$tiedhash,$tiedparmhash); # More state flags. @@ -1317,8 +1375,13 @@ sub readmap { $lock=1; } undef %randompick; + undef %randompickseed; + undef %randomorder; + undef %randomizationcode; undef %hiddenurl; undef %encurl; + undef %rescount; + undef %mapcount; $errtext=''; $retfrid=''; # @@ -1437,6 +1500,7 @@ sub build_tmp_hashes { &traceroute('0',$hash{'map_start_'.$uri},'&'); &accinit($uri,$short,$fn); &hiddenurls(); + &mapcrumbs(); } $errtext .= &get_mapalias_errors(); # ------------------------------------------------------- Put versions into src @@ -1468,7 +1532,7 @@ sub build_tmp_hashes { # ---------------------------------------------------- Store away initial state { my $cfh; - if (open($cfh,">$fn.state")) { + if (open($cfh,">","$fn.state")) { print $cfh join("\n",@cond); $gotstate = 1; } else { @@ -1505,7 +1569,7 @@ sub evalstate { if (-e $fn) { my @conditions=(); { - open(my $fh,"<$fn"); + open(my $fh,"<",$fn); @conditions=<$fh>; close($fh); }