[LON-CAPA-cvs] cvs: loncom/auth lonacc.pm loncom/interface loncommon.pm lonnavmaps.pm lonquickgrades.pm loncom/lonnet/perl lonnet.pm rat lonpageflip.pm lonsequence.pm lonuserstate.pm
raeburn
raeburn at source.lon-capa.org
Mon Jul 19 13:32:06 EDT 2021
raeburn Mon Jul 19 13:32:06 2021 EDT
Modified files:
/rat lonuserstate.pm lonpageflip.pm lonsequence.pm
/loncom/auth lonacc.pm
/loncom/interface loncommon.pm lonnavmaps.pm lonquickgrades.pm
/loncom/lonnet/perl lonnet.pm
Log:
- Bug 6907 Content in a course can be set to be deep-link only.
If initial access is via a deep-link (/tiny/$domain/$uniqueid), and
target folder/resource is deep-link only, access to resources, menus,
and items listed in Course Contents controlled by deeplink parameter value.
-------------- next part --------------
Index: rat/lonuserstate.pm
diff -u rat/lonuserstate.pm:1.163 rat/lonuserstate.pm:1.164
--- rat/lonuserstate.pm:1.163 Thu Apr 29 10:54:36 2021
+++ rat/lonuserstate.pm Mon Jul 19 11:48:25 2021
@@ -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.163 2021/04/29 14:54:36 raeburn Exp $
+# $Id: lonuserstate.pm,v 1.164 2021/07/19 15:48:25 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -62,7 +62,7 @@
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 %deeplinkonly; # this URL (or complete folder) is deep-link only
+my %deeplinkout; # this URL (or complete folder) unavailable in deep-link session
my %rescount; # count of unhidden items in each map
my %mapcount; # count of unhidden maps in each map
@@ -905,7 +905,7 @@
# new value indicating how far the map has been traversed (the sofar).
#
sub traceroute {
- my ($sofar,$rid,$beenhere,$encflag,$hdnflag)=@_;
+ my ($sofar,$rid,$beenhere,$encflag,$hdnflag,$cid)=@_;
my $newsofar=$sofar=simplify($sofar);
unless ($beenhere=~/\&\Q$rid\E\&/) {
@@ -928,13 +928,30 @@
&& ($hash{'src_'.$rid}!~/\.sequence$/)) {
$retfrid=$rid;
}
- my @deeplink=&Apache::lonnet::EXT('resource.0.deeplink',$symb);
- unless ((@deeplink == 0) || ($deeplink[0] eq 'full')) {
- $deeplinkonly{$rid}=join(':', at deeplink);
- if ($deeplink[1] eq 'map') {
- my $parent = (split(/\,/,$hash{'map_hierarchy_'.$mapid}))[-1];
- $deeplinkonly{"$parent.$mapid"}=$deeplinkonly{$rid};
+
+ my (@deeplink, at recurseup);
+ if ($hash{'is_map_'.$rid}) {
+ my ($cdom,$cnum) = split(/_/,$cid);
+ my $mapsrc = $hash{'src_'.$rid};
+ my $map_pc = $hash{'map_pc_'.$mapsrc};
+ my @pcs = split(/,/,$hash{'map_hierarchy_'.$map_pc});
+ shift(@pcs);
+ @recurseup = map { &Apache::lonnet::declutter($hash{'map_id_'.$_}) } reverse(@pcs);
+ my $mapname = &Apache::lonnet::declutter(&Apache::lonnet::deversion($mapsrc));
+ my $deeplinkval = &get_mapparam($env{'user.name'},$env{'user.domain'},$cnum,$cdom,
+ $rid,$mapname,'0.deeplink',\@recurseup);
+ if ($deeplinkval ne '') {
+ @deeplink = ($deeplinkval,'map');
}
+ } else {
+ my @pcs = split(/,/,$hash{'map_hierarchy_'.$mapid});
+ shift(@pcs);
+ @recurseup = map { &Apache::lonnet::declutter($hash{'map_id_'.$_}) } reverse(@pcs);
+ @deeplink = &Apache::lonnet::EXT('resource.0.deeplink',$symb,'','','','',$cid,\@recurseup);
+ }
+ unless (@deeplink < 2) {
+ my ($listed,$scope,$access) = split(/,/,$deeplink[0]);
+ $hash{'deeplinkonly_'.$rid}=join(':', at deeplink);
}
if (defined($hash{'conditions_'.$rid})) {
@@ -958,7 +975,8 @@
$hash{'map_start_'.$hash{'src_'.$rid}},
$beenhere,
$encflag || $encurl{$rid},
- $hdnflag || $hiddenurl{$rid});
+ $hdnflag || $hiddenurl{$rid},
+ $cid);
}
}
@@ -985,7 +1003,7 @@
}
# Recurse to resoruces that have to's to us.
$newsofar=&traceroute($further,$hash{'goesto_'.$id},$beenhere,
- $encflag,$hdnflag);
+ $encflag,$hdnflag,$cid);
}
}
}
@@ -1182,17 +1200,34 @@
}
}
+sub deeplinkouts {
+ my $deeplinkoutentry;
+ foreach my $rid (keys(%deeplinkout)) {
+ $hash{'deeplinkout_'.$rid}=1;
+ my ($mapid,$resid)=split(/\./,$rid);
+ $deeplinkoutentry.='&'.
+ &Apache::lonnet::encode_symb($hash{'map_id_'.$mapid},$resid,
+ $hash{'src_'.$rid}).'&';
+ }
+# --------------------------------------- append deeplinkout entry to environment
+ if ($deeplinkoutentry) {
+ &Apache::lonnet::appenv({'acc.deeplinkout' => $deeplinkoutentry});
+ }
+}
+
# -------------------------------------- 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 {
+ my ($cid) = @_;
foreach my $key (keys(%rescount)) {
if ($hash{'map_hierarchy_'.$key}) {
my $skipnext = 0;
foreach my $id (split(/,/,$hash{'map_hierarchy_'.$key}),$key) {
- unless ($skipnext) {
+ my $rid = $hash{'ids_'.$hash{'map_id_'.$id}};
+ unless (($skipnext) || (!&is_advanced($cid) && $hash{'deeplinkout_'.$rid})) {
$hash{'map_breadcrumbs_'.$key} .= "$id,";
}
unless (($id == 0) || ($id == 1)) {
@@ -1251,7 +1286,7 @@
undef %randomizationcode;
undef %hiddenurl;
undef %encurl;
- undef %deeplinkonly;
+ undef %deeplinkout;
undef %rescount;
undef %mapcount;
$retfrid='';
@@ -1400,7 +1435,7 @@
undef %randomizationcode;
undef %hiddenurl;
undef %encurl;
- undef %deeplinkonly;
+ undef %deeplinkout;
undef %rescount;
undef %mapcount;
$errtext='';
@@ -1509,7 +1544,6 @@
# Load the map.. note that loadmap may implicitly recurse if the map contains
# sub-maps.
-
&loadmap($uri,'0.0',$short);
# The code below only executes if there is a starting point for the map>
@@ -1522,10 +1556,9 @@
"request.course.uri" => $uri,
"request.course.tied" => time});
$env{'request.course.id'}=$short;
- &traceroute('0',$hash{'map_start_'.$uri},'&');
+ &traceroute('0',$hash{'map_start_'.$uri},'&','','',$short);
&accinit($uri,$short,$fn);
&hiddenurls();
- &mapcrumbs();
}
$errtext .= &get_mapalias_errors();
# ------------------------------------------------------- Put versions into src
@@ -1543,10 +1576,6 @@
# $hash{'src_'.$id}=&Apache::lonenc::encrypted($hash{'src_'.$id});
$hash{'encrypted_'.$id}=1;
}
-# ------------------------------------------------------------ Deep-linked URLs
- foreach my $id (keys(%deeplinkonly)) {
- $hash{'deeplinkonly_'.$id}=$deeplinkonly{$id};
- }
# ----------------------------------------------- Close hashes to finally store
# --------------------------------- Routine must pass this point, no early outs
$hash{'first_rid'}=$retfrid;
@@ -1569,6 +1598,70 @@
"Could not write statemap $fn for $uri.</font>");
}
}
+
+ # Was initial access via a deep-link?
+ my ($cdom,$cnum) = split(/_/,$short);
+ if (($cdom ne '') && ($env{'request.deeplink.login'} ne '')) {
+ my $deeplink_symb = &Apache::loncommon::deeplink_login_symb($cnum,$cdom);
+ if ($deeplink_symb) {
+ my ($loginrid,$deeplink_login_pc,$login_hierarchy);
+ my ($map,$resid,$url) = &Apache::lonnet::decode_symb($deeplink_symb);
+ $loginrid = $hash{'map_pc_'.&Apache::lonnet::clutter($map)}.'.'.$resid;
+ if ($deeplink_symb =~ /\.(page|sequence)$/) {
+ $deeplink_login_pc = $hash{'map_pc_'.&Apache::lonnet::clutter($url)};
+ } else {
+ $deeplink_login_pc = $hash{'map_pc_'.&Apache::lonnet::clutter($map)};
+ }
+ my $deeplink;
+ if ($hash{'deeplinkonly_'.$loginrid} ne '') {
+ $deeplink = $hash{'deeplinkonly_'.$loginrid};
+ }
+ if ($deeplink) {
+ my ($listed,$scope,$access) = split(/,/,$deeplink);
+ my $exclude = 1;
+ if ($exclude) {
+ my @recfolders;
+ if ($scope eq 'rec') {
+ foreach my $key (keys(%hash)) {
+ if ($key=~/^map_hierarchy_(\d+)$/) {
+ my $mpc = $1;
+ my @ids = split(/,/,$hash{$key});
+ if (grep(/^$deeplink_login_pc$/, at ids)) {
+ my $idx;
+ foreach my $mapid (@ids) {
+ if ($idx) {
+ push(@recfolders,$mapid);
+ } elsif ($mapid == $deeplink_login_pc) {
+ push(@recfolders,$mapid);
+ $idx = $mapid;
+ }
+ }
+ push(@recfolders,$mpc);
+ }
+ }
+ }
+ }
+ foreach my $key (keys(%hash)) {
+ if ($key=~/^src_(.+)$/) {
+ my $rid = $1;
+ next if ($rid eq '0.0');
+ next if ($rid eq $loginrid);
+ if ($scope ne 'res') {
+ my $mapid = (split(/\./,$rid))[0];
+ next if ($mapid eq $deeplink_login_pc);
+ if ($scope eq 'rec') {
+ next if (grep(/^$mapid$/, at recfolders));
+ }
+ }
+ $deeplinkout{$rid} = 1;
+ }
+ }
+ }
+ }
+ &deeplinkouts();
+ }
+ }
+ &mapcrumbs();
return $gotstate;
}
@@ -1630,6 +1723,181 @@
return $state;
}
+sub get_mapparam {
+ my ($uname,$udom,$cnum,$cdom,$rid,$mapname,$what,$recurseupref) = @_;
+ unless ($mapname) { return; }
+
+# ------------------------------------------------- Get coursedata (if present)
+ my $courseopt=&Apache::lonnet::get_courseresdata($cnum,$cdom);
+ if (!ref($courseopt)) {
+ undef($courseopt);
+ }
+
+# --------------------------------------------------- Get userdata (if present)
+ my $useropt=&Apache::lonnet::get_userresdata($uname,$udom);
+ if (!ref($useropt)) {
+ undef($useropt);
+ }
+
+ my @recurseup;
+ if (ref($recurseupref) eq 'ARRAY') {
+ @recurseup = @{$recurseupref};
+ }
+
+ # Get the section if there is one.
+
+ my $cid = $cdom.'_'.$cnum;
+ my $csec=$env{'request.course.sec'};
+ my $cgroup='';
+ my @cgrps=split(/:/,$env{'request.course.groups'});
+ if (@cgrps > 0) {
+ @cgrps = sort(@cgrps);
+ $cgroup = $cgrps[0];
+ }
+
+ my $rwhat=$what;
+ $what=~s/^parameter\_//;
+ $what=~s/\_/\./;
+
+ # Build the hash keys for the lookup:
+
+ my $mapparm=$mapname.'___(all).'.$what;
+ my $recurseparm=$mapname.'___(rec).'.$what;
+ my $usercourseprefix=$cid;
+
+ my $grplevelm = "$usercourseprefix.[$cgroup].$mapparm";
+ my $seclevelm = "$usercourseprefix.[$csec].$mapparm";
+ my $courselevelm = "$usercourseprefix.$mapparm";
+
+ my $grpleveli = "$usercourseprefix.[$cgroup].$recurseparm";
+ my $secleveli = "$usercourseprefix.[$csec].$recurseparm";
+ my $courseleveli = "$usercourseprefix.$recurseparm";
+
+ # Check per user
+
+ if ($uname and defined($useropt)) {
+ if (defined($$useropt{$courselevelm})) {
+ return $$useropt{$courselevelm};
+ }
+ if (defined($$useropt{$courseleveli})) {
+ return $$useropt{$courseleveli};
+ }
+ foreach my $item (@recurseup) {
+ my $norecursechk=$usercourseprefix.'.'.$item.'___(all).'.$what;
+ if (defined($$useropt{$norecursechk})) {
+ if ($what =~ /\.(encrypturl|hiddenresource)$/) {
+ return $$useropt{$norecursechk};
+ } else {
+ last;
+ }
+ }
+ my $recursechk=$usercourseprefix.'.'.$item.'___(rec).'.$what;
+ if (defined($$useropt{$recursechk})) {
+ return $$useropt{$recursechk};
+ }
+ }
+ }
+
+ # Check course -- group
+
+ if ($cgroup ne '' and defined ($courseopt)) {
+ if (defined($$courseopt{$grplevelm})) {
+ return $$courseopt{$grplevelm};
+ }
+ if (defined($$courseopt{$grpleveli})) {
+ return $$courseopt{$grpleveli};
+ }
+ foreach my $item (@recurseup) {
+ my $norecursechk=$usercourseprefix.'.['.$cgroup.'].'.$item.'___(all).'.$what;
+ if (defined($$courseopt{$norecursechk})) {
+ if ($what =~ /\.(encrypturl|hiddenresource)$/) {
+ return $$courseopt{$norecursechk};
+ } else {
+ last;
+ }
+ }
+ my $recursechk=$usercourseprefix.'.['.$cgroup.'].'.$item.'___(rec).'.$what;
+ if (defined($$courseopt{$recursechk})) {
+ return $$courseopt{$recursechk};
+ }
+ }
+ }
+
+ # Check course -- section
+
+ if ($csec ne '' and defined($courseopt)) {
+ if (defined($$courseopt{$seclevelm})) {
+ return $$courseopt{$seclevelm};
+ }
+ if (defined($$courseopt{$secleveli})) {
+ return $$courseopt{$secleveli};
+ }
+ foreach my $item (@recurseup) {
+ my $norecursechk=$usercourseprefix.'.['.$csec.'].'.$item.'___(all).'.$what;
+ if (defined($$courseopt{$norecursechk})) {
+ if ($what =~ /\.(encrypturl|hiddenresource)$/) {
+ return $$courseopt{$norecursechk};
+ } else {
+ last;
+ }
+ }
+ my $recursechk=$usercourseprefix.'.['.$csec.'].'.$item.'___(rec).'.$what;
+ if (defined($$courseopt{$recursechk})) {
+ return $$courseopt{$recursechk};
+ }
+ }
+ }
+
+ # Check the map parameters themselves:
+
+ if ($hash{'param_'.$rid}) {
+ my @items = split(/\&/,$hash{'param_'.$rid});
+ my $thisparm;
+ foreach my $item (@items) {
+ my ($esctype,$escname,$escvalue) = ($item =~ /^([^:]+):([^=]+)=(.*)$/);
+ my $name = &unescape($escname);
+ my $value = &unescape($escvalue);
+ if ($name eq $what) {
+ $thisparm = $value;
+ last;
+ }
+ }
+ if (defined($thisparm)) {
+ return $thisparm;
+ }
+ }
+
+ # Additional course parameters:
+
+ if (defined($courseopt)) {
+ if (defined($$courseopt{$courselevelm})) {
+ return $$courseopt{$courselevelm};
+ }
+
+ if (defined($$courseopt{$courseleveli})) {
+ return $$courseopt{$courseleveli};
+ }
+
+ if (@recurseup) {
+ foreach my $item (@recurseup) {
+ my $norecursechk=$usercourseprefix.'.'.$item.'___(all).'.$what;
+ if (defined($$courseopt{$norecursechk})) {
+ if ($what =~ /\.(encrypturl|hiddenresource)$/) {
+ return $$courseopt{$norecursechk};
+ } else {
+ last;
+ }
+ }
+ my $recursechk=$usercourseprefix.'.'.$item.'___(rec).'.$what;
+ if (defined($$courseopt{$recursechk})) {
+ return $$courseopt{$recursechk};
+ }
+ }
+ }
+ }
+ return undef;
+}
+
# This block seems to have code to manage/detect doubly defined
# aliases in maps.
Index: rat/lonpageflip.pm
diff -u rat/lonpageflip.pm:1.105 rat/lonpageflip.pm:1.106
--- rat/lonpageflip.pm:1.105 Mon Jul 19 10:26:40 2021
+++ rat/lonpageflip.pm Mon Jul 19 11:48:25 2021
@@ -2,7 +2,7 @@
#
# Page flip handler
#
-# $Id: lonpageflip.pm,v 1.105 2021/07/19 14:26:40 raeburn Exp $
+# $Id: lonpageflip.pm,v 1.106 2021/07/19 15:48:25 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -103,6 +103,8 @@
my $safecount=0;
my $allowed=0;
my $deeplinkonly=0;
+ my $deeplinkchecked;
+ my $deeplink_login_pc;
my $prev=$next;
my ($prevmapid)=split(/\./,$next);
do {
@@ -115,26 +117,81 @@
if ($url eq '' || $symb eq '') {
$allowed = 0;
} else {
- my $priv = &Apache::lonnet::allowed('bre',$url,$symb);
+ my $nodeeplinkcheck = 0;
+ if ($hash{'is_map_'.$next}) {
+ $nodeeplinkcheck = 1;
+ }
+ my $priv = &Apache::lonnet::allowed('bre',$url,$symb,'','','','',$nodeeplinkcheck);
$allowed = (($priv eq 'F') || ($priv eq '2') || ($priv eq 'A'));
}
$deeplinkonly = 0;
if ($hash{'deeplinkonly_'.$next}) {
my ($value,$level) = split(/:/,$hash{'deeplinkonly_'.$next});
- if ($level eq 'resource') {
- $deeplinkonly = 1;
- } elsif ($level eq 'map') {
- if ($mapid != $prevmapid) {
+ my ($listed,$scope,$access) = split(/,/,$value);
+ unless (($access eq 'any') || ($hash{'is_map_'.$next})) {
+ if ($level eq 'resource') {
$deeplinkonly = 1;
+ } elsif ($level eq 'map') {
+ if ($scope eq 'rec') {
+ unless ($mapid == $prevmapid) {
+ unless ($deeplinkchecked) {
+ $deeplink_login_pc = &get_deeplink_login_pc();
+ $deeplinkchecked = 1;
+ }
+ if ($deeplink_login_pc) {
+ my $poss_map_pc;
+ if ($hash{'is_map_'.$next}) {
+ $poss_map_pc = $hash{'map_pc_'.$url};
+ } else {
+ $poss_map_pc = $hash{'map_pc_'.$hash{'map_id_'.$mapid}};
+ }
+ unless ($deeplink_login_pc == $poss_map_pc) {
+ unless (grep(/^$deeplink_login_pc$/,split(/,/,$hash{'map_hierarchy_'.$poss_map_pc}))) {
+ $deeplinkonly = 1;
+ }
+ }
+ } else {
+ $deeplinkonly = 1;
+ }
+ }
+ } elsif ($mapid != $prevmapid) {
+ $deeplinkonly = 1;
+ }
}
}
} elsif (($hash{'deeplinkonly_'.$prev}) && (!$firstres)) {
my ($value,$level) = split(/:/,$hash{'deeplinkonly_'.$prev});
- if ($level eq 'resource') {
- $deeplinkonly = 1;
- } elsif ($level eq 'map') {
- if ($mapid != $prevmapid) {
+ my ($listed,$scope,$access) = split(/,/,$value);
+ unless (($access eq 'any') || ($hash{'is_map_'.$prev})) {
+ if ($level eq 'resource') {
$deeplinkonly = 1;
+ } elsif ($level eq 'map') {
+ my ($listed,$scope,$access) = split(/,/,$value);
+ if ($scope eq 'rec') {
+ unless ($mapid == $prevmapid) {
+ unless ($deeplinkchecked) {
+ $deeplink_login_pc = &get_deeplink_login_pc();
+ $deeplinkchecked = 1;
+ }
+ if ($deeplink_login_pc) {
+ my $poss_map_pc;
+ if ($hash{'is_map_'.$prev}) {
+ $poss_map_pc = $hash{'map_pc_'.$url};
+ } else {
+ $poss_map_pc = $hash{'map_pc_'.$hash{'map_id_'.$mapid}};
+ }
+ unless ($deeplink_login_pc == $poss_map_pc) {
+ unless (grep(/^$deeplink_login_pc$/,split(/,/,$hash{'map_hierarchy_'.$poss_map_pc}))) {
+ $deeplinkonly = 1;
+ }
+ }
+ }
+ }
+ } else {
+ if ($mapid != $prevmapid) {
+ $deeplinkonly = 1;
+ }
+ }
}
}
}
@@ -146,7 +203,8 @@
|| (
(!$env{'request.role.adv'})
&& (($hash{'randomout_'.$next})
- || ($deeplinkonly))
+ || ($deeplinkonly)
+ || ($hash{'deeplinkout_'.$next})
)
|| (!$allowed)
)
@@ -181,7 +239,7 @@
}
if ($thiscond>$mincond) { $mincond=$thiscond; }
}
- }
+ }
foreach my $id (split(/\,/,$posnext)) {
my ($linkid,$condval)=split(/\:/,$id);
if ($condval>=$mincond) {
@@ -223,7 +281,7 @@
}
if ($thiscond>$mincond) { $mincond=$thiscond; }
}
- }
+ }
foreach my $id (split(/\,/,$posnext)) {
my ($linkid,$condval)=split(/\:/,$id);
if ($condval>=$mincond) {
@@ -281,8 +339,8 @@
if ($hash{'encrypted_'.$newrid}) {
$furl=&Apache::lonenc::encrypted($furl);
}
- }
- }
+ {
+ }
untie(%hash);
return $furl;
} else {
@@ -363,6 +421,29 @@
END
}
+sub get_deeplink_login_pc {
+ my $deeplink_login_pc;
+ if (($env{'request.deeplink.login'}) && ($env{'request.course.id'})) {
+ my $cdom = $env{'course.'.$env{'request.course.id'}.'.domain'};
+ my $cnum = $env{'course.'.$env{'request.course.id'}.'.num'};
+ if ($env{'request.deeplink.login'}) {
+ my $cnum = $env{'course.'.$env{'request.course.id'}.'.num'};
+ my $cdom = $env{'course.'.$env{'request.course.id'}.'.domain'};
+ my $deeplink_symb = &Apache::loncommon::deeplink_login_symb($cnum,$cdom);
+ if ($deeplink_symb) {
+ my $loginmap;
+ if ($deeplink_symb =~ /\.(page|sequence)$/) {
+ $loginmap = &Apache::lonnet::clutter((&Apache::lonnet::decode_symb($deeplink_symb))[2]);
+ } else {
+ $loginmap = &Apache::lonnet::clutter((&Apache::lonnet::decode_symb($deeplink_symb))[0]);
+ }
+ $deeplink_login_pc = $hash{'map_pc_'.$loginmap};
+ }
+ }
+ }
+ return $deeplink_login_pc;
+}
+
# ================================================================ Main Handler
sub handler {
@@ -609,8 +690,13 @@
} else {
# -------------------------------------------------------------- No place to go
$multichoice=-1;
- if ($hash{'deeplinkonly_'.$rid}) {
- (my $value,$deeplinklevel) = split(/:/,$hash{'deeplinkonly_'.$rid});
+ if ($position && $env{'request.deeplink.login'}) {
+ my ($map,$resid,$url) = &Apache::lonnet::decode_symb($position);
+ my $mapid = $hash{'map_pc_'.&Apache::lonnet::clutter($map)};
+ my $position_deeplink = $hash{'deeplinkonly_'.$mapid.'.'.$resid};
+ if ($position_deeplink) {
+ (my $value,$deeplinklevel) = split(/:/,$position_deeplink);
+ }
}
}
# ----------------- The program must come past this point to untie the big hash
Index: rat/lonsequence.pm
diff -u rat/lonsequence.pm:1.55 rat/lonsequence.pm:1.56
--- rat/lonsequence.pm:1.55 Thu Jun 24 17:19:22 2021
+++ rat/lonsequence.pm Mon Jul 19 11:48:25 2021
@@ -2,7 +2,7 @@
#
# Sequence Handler
#
-# $Id: lonsequence.pm,v 1.55 2021/06/24 21:19:22 raeburn Exp $
+# $Id: lonsequence.pm,v 1.56 2021/07/19 15:48:25 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -375,8 +375,6 @@
$dismapid=(split(/\./,$disid))[1];
if (!$env{'request.role.adv'}) {
$randomout = $bighash{'randomout_'.$disid};
- }
- if (!$env{'request.role.adv'}) {
$is_encrypted = $bighash{'encrypted_'.$disid};
}
} elsif (tie(%hash,'GDBM_File',$env{'request.course.fn'}.'_symb.db',
@@ -397,8 +395,6 @@
$dismapid=(split(/\./,$disid))[1];
if (!$env{'request.role.adv'}) {
$randomout = $bighash{'randomout_'.$disid};
- }
- if (!$env{'request.role.adv'}) {
$is_encrypted = $bighash{'encrypted_'.$disid};
}
}
Index: loncom/auth/lonacc.pm
diff -u loncom/auth/lonacc.pm:1.191 loncom/auth/lonacc.pm:1.192
--- loncom/auth/lonacc.pm:1.191 Tue Jun 22 12:56:35 2021
+++ loncom/auth/lonacc.pm Mon Jul 19 11:48:26 2021
@@ -1,7 +1,7 @@
# The LearningOnline Network
# Cookie Based Access Handler
#
-# $Id: lonacc.pm,v 1.191 2021/06/22 16:56:35 raeburn Exp $
+# $Id: lonacc.pm,v 1.192 2021/07/19 15:48:26 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -673,6 +673,9 @@
if ((!$env{'request.role.adv'}) && ($env{'acc.randomout'}) &&
($env{'acc.randomout'}=~/\&\Q$poss_symb\E\&/)) {
undef($poss_symb);
+ } elsif ((!$env{'request.role.adv'}) && ($env{'acc.deeplinkout'}) &&
+ ($env{'acc.deeplinkout'}=~/\&\Q$poss_symb\E\&/)) {
+ undef($poss_symb);
}
}
}
@@ -682,7 +685,18 @@
$access=&Apache::lonnet::allowed('bre',$requrl,'','','','',1);
}
} else {
- $access=&Apache::lonnet::allowed('bre',$requrl);
+ my $nodeeplinkcheck;
+ if (($check_access) && ($requrl =~ /\.(sequence|page)$/)) {
+ unless ($env{'form.navmap'}) {
+ if ($r->args ne '') {
+ &Apache::loncommon::get_unprocessed_cgi($r->args,['navmap']);
+ unless ($env{'form.navmap'}) {
+ $nodeeplinkcheck = 1;
+ }
+ }
+ }
+ }
+ $access=&Apache::lonnet::allowed('bre',$requrl,'','','','','',$nodeeplinkcheck)
}
}
if ($check_block) {
Index: loncom/interface/loncommon.pm
diff -u loncom/interface/loncommon.pm:1.1361 loncom/interface/loncommon.pm:1.1362
--- loncom/interface/loncommon.pm:1.1361 Tue Jun 15 16:52:26 2021
+++ loncom/interface/loncommon.pm Mon Jul 19 11:48:26 2021
@@ -1,7 +1,7 @@
# The LearningOnline Network with CAPA
# a pile of common routines
#
-# $Id: loncommon.pm,v 1.1361 2021/06/15 20:52:26 raeburn Exp $
+# $Id: loncommon.pm,v 1.1362 2021/07/19 15:48:26 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -9142,9 +9142,33 @@
my ($menucoll,$deeplinkmenu,%menu);
if ($env{'request.course.id'}) {
$menucoll = $env{'course.'.$env{'request.course.id'}.'.menudefault'};
- if (($env{'request.deeplink.login'}) &&
- ($env{'request.noversionuri'} =~ m{^/(res|uploaded)/})) {
- my $deeplink = &Apache::lonnet::EXT('resource.0.deeplink');
+ if ($env{'request.deeplink.login'}) {
+ my ($deeplink_symb,$deeplink);
+ my $cnum = $env{'course.'.$env{'request.course.id'}.'.num'};
+ my $cdom = $env{'course.'.$env{'request.course.id'}.'.domain'};
+ if ($env{'request.noversionuri'} =~ m{^/(res|uploaded)/}) {
+ if ($env{'request.noversionuri'} =~ /\.(page|sequence)$/) {
+ my $navmap = Apache::lonnavmaps::navmap->new();
+ if (ref($navmap)) {
+ $deeplink = $navmap->get_mapparam(undef,
+ &Apache::lonnet::declutter($env{'request.noversionuri'}),
+ '0.deeplink');
+ }
+ } else {
+ $deeplink = &Apache::lonnet::EXT('resource.0.deeplink');
+ }
+ } else {
+ $deeplink_symb = &deeplink_login_symb($cnum,$cdom);
+ if ($deeplink_symb =~ /\.(page|sequence)$/) {
+ my $mapname = &Apache::lonnet::deversion((&Apache::lonnet::decode_symb($deeplink_symb))[2]);
+ my $navmap = Apache::lonnavmaps::navmap->new();
+ if (ref($navmap)) {
+ $deeplink = $navmap->get_mapparam(undef,$mapname,'0.deeplink');
+ }
+ } else {
+ $deeplink = &Apache::lonnet::EXT('resource.0.deeplink',$deeplink_symb);
+ }
+ }
if ($deeplink ne '') {
my ($listed,$scope,$access,$display) = split(/,/,$deeplink);
if ($display =~ /^\d+$/) {
@@ -9160,6 +9184,35 @@
return ($menucoll,$deeplinkmenu,\%menu);
}
+sub deeplink_login_symb {
+ my ($cnum,$cdom) = @_;
+ my $login_symb;
+ if ($env{'request.deeplink.login'}) {
+ if ($env{'request.deeplink.login'} =~ m{^\Q/tiny/$cdom/\E(\w+)$}) {
+ my $key = $1;
+ my ($tinyurl,$login);
+ my ($result,$cached)=&Apache::lonnet::is_cached_new('tiny',$cdom."\0".$key);
+ if (defined($cached)) {
+ $tinyurl = $result;
+ } else {
+ my $configuname = &Apache::lonnet::get_domainconfiguser($cdom);
+ my %currtiny = &Apache::lonnet::get('tiny',[$key],$cdom,$configuname);
+ if ($currtiny{$key} ne '') {
+ $tinyurl = $currtiny{$key};
+ &Apache::lonnet::do_cache_new('tiny',$cdom."\0".$key,$currtiny{$key},600);
+ }
+ }
+ if ($tinyurl ne '') {
+ my ($cnumreq,$posslogin) = split(/\&/,$tinyurl);
+ if ($cnumreq eq $cnum) {
+ $login_symb = $posslogin;
+ }
+ }
+ }
+ }
+ return $login_symb;
+}
+
sub wishlist_window {
return(<<'ENDWISHLIST');
<script type="text/javascript">
Index: loncom/interface/lonnavmaps.pm
diff -u loncom/interface/lonnavmaps.pm:1.552 loncom/interface/lonnavmaps.pm:1.553
--- loncom/interface/lonnavmaps.pm:1.552 Tue Jul 13 23:58:17 2021
+++ loncom/interface/lonnavmaps.pm Mon Jul 19 11:48:26 2021
@@ -1,7 +1,7 @@
# The LearningOnline Network with CAPA
# Navigate Maps Handler
#
-# $Id: lonnavmaps.pm,v 1.552 2021/07/14 03:58:17 raeburn Exp $
+# $Id: lonnavmaps.pm,v 1.553 2021/07/19 15:48:26 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -1068,13 +1068,28 @@
$nonLinkedText .= ' <span class="LC_warning">('.&mt('hidden').')</span> ';
} elsif ($params->{'mapUnlisted'}) {
$nonLinkedText .= ' <span class="LC_warning">('.&mt('unlisted').')</span> ';
+ } elsif ($params->{'mapHiddenDeepLink'} || $resource->deeplinkout()) {
+ $nonLinkedText .= ' <span class="LC_warning">('.&mt('not shown').')</span> ';
}
} else {
if ($resource->randomout()) {
$nonLinkedText .= ' <span class="LC_warning">('.&mt('hidden').')</span> ';
- } elsif (($resource->deeplink($params->{caller}) eq 'absent') ||
- ($resource->deeplink($params->{caller}) eq 'grades')) {
- $nonLinkedText .= ' <span class="LC_warning">('.&mt('unlisted').')</span> ';
+ } elsif ($resource->deeplinkout()) {
+ $nonLinkedText .= ' <span class="LC_warning">('.&mt('not shown').')</span> ';
+ } else {
+ my $deeplink = $resource->deeplink($params->{caller});
+ if ((($deeplink eq 'absent') || ($deeplink eq 'grades')) &&
+ &advancedUser()) {
+ $nonLinkedText .= ' <span class="LC_warning">('.&mt('unlisted').')</span> ';
+ } elsif (($deeplink) && ($deeplink) ne 'full') {
+ if (&advancedUser()) {
+ $nonLinkedText .= ' <span class="LC_warning">('.&mt('deep-link access').
+ ')</span> ';
+ } else {
+ $nonLinkedText .= ' <span class="LC_warning">('.&mt('access via external site').
+ ')</span> ';
+ }
+ }
}
}
if (!$resource->condval()) {
@@ -1401,6 +1416,7 @@
$filterFunc = sub { my $res = shift; return !$res->randomout() &&
($res->deeplink($args->{'caller'}) ne 'absent') &&
($res->deeplink($args->{'caller'}) ne 'grades') &&
+ !$res->deeplinkout() &&
&$oldFilterFunc($res);};
}
@@ -1821,6 +1837,7 @@
# If this is an empty sequence and we're filtering them, continue on
$args->{'mapHidden'} = 0;
$args->{'mapUnlisted'} = 0;
+ $args->{'mapHiddenDeepLink'} = 0;
if (($curRes->is_map()) && (!$curRes->{DATA}->{HAS_VISIBLE_CHILDREN})) {
if ($args->{'suppressEmptySequences'}) {
next;
@@ -1833,6 +1850,12 @@
} else {
next;
}
+ } elsif ($curRes->deeplinkout) {
+ if ($userCanSeeHidden) {
+ $args->{'mapHiddenDeepLink'} = 1;
+ } else {
+ next;
+ }
} else {
my $deeplink = $navmap->get_mapparam(undef,$mapname,"0.deeplink");
if ($deeplink =~ /^(absent|grades),/) {
@@ -1906,10 +1929,10 @@
}
}
# If deep-link parameter is set (and is not set to full) suppress link
- # unless privileged user, or calling context is sequence, and parameter
- # set at map level
+ # unless privileged user, tinyurl used for login resolved to a map, and
+ # the resource is within the map.
if ((!$curRes->deeplink($args->{'caller'})) ||
- ($curRes->deeplink($args->{'caller'}) =~ /^full,/) || &advancedUser()) {
+ ($curRes->deeplink($args->{'caller'}) eq 'full') || &advancedUser()) {
$args->{'resource_nolink'} = 0;
} else {
$args->{'resource_nolink'} = 1;
@@ -2479,7 +2502,7 @@
my $self = shift;
my $iterator = Apache::lonnavmaps::iterator->new($self, shift, shift,
shift, undef, shift,
- shift, shift);
+ shift, shift, shift);
return $iterator;
}
@@ -3619,7 +3642,7 @@
=over 4
-=item * B<getIterator>(firstResource, finishResource, filterHash, condition, forceTop, returnTopMap):
+=item * B<getIterator>(firstResource, finishResource, filterHash, condition, forceTop, returnTopMap, $deeplinklisted):
All parameters are optional. firstResource is a resource reference
corresponding to where the iterator should start. It defaults to
@@ -3636,7 +3659,10 @@
will return all information, starting with the top-level map,
regardless of content. returnTopMap, if true (default false), will
cause the iterator to return the top-level map object (resource 0.0)
-before anything else.
+before anything else. deeplinklisted if true (default false), will
+check "listed" status of a resource with a deeplink, and unless "absent"
+will exclude deeplink checking when retrieving the browsePriv from
+lonnet::allowed().
Thus, by default, only top-level resources will be shown. Change the
condition to a 1 without changing the hash, and all resources will be
@@ -3773,6 +3799,10 @@
# have we done that yet?
$self->{HAVE_RETURNED_0} = 0;
+ # Do we want to check the "listed" status for a resource for which
+ # deeplinking applies.
+ $self->{DEEPLINKLISTED} = shift;
+
# Now, we need to pre-process the map, by walking forward and backward
# over the parts of the map we're going to look at.
@@ -3864,7 +3894,8 @@
$finishResource, $self->{FILTER},
$self->{ALREADY_SEEN},
$self->{CONDITION},
- $self->{FORCE_TOP});
+ $self->{FORCE_TOP},
+ undef,$self->{DEEPLINKLISTED});
}
# Set up some bookkeeping information.
@@ -4034,13 +4065,14 @@
$finishResource, $self->{FILTER},
$self->{ALREADY_SEEN},
$self->{CONDITION},
- $self->{FORCE_TOP});
+ $self->{FORCE_TOP},
+ undef,$self->{DEEPLINKLISTED});
}
# If this is a blank resource, don't actually return it.
# Should you ever find you need it, make sure to add an option to the code
# that you can use; other things depend on this behavior.
- my $browsePriv = $self->{HERE}->browsePriv($noblockcheck);
+ my $browsePriv = $self->{HERE}->browsePriv($noblockcheck,$self->{DEEPLINKLISTED});
if (!$self->{HERE}->src() ||
(!($browsePriv eq 'F') && !($browsePriv eq '2')) ) {
return $self->next($closeAllPages);
@@ -4468,6 +4500,7 @@
sub goesto { my $self=shift; return $self->navHash("goesto_", 1); }
sub kind { my $self=shift; return $self->navHash("kind_", 1); }
sub randomout { my $self=shift; return $self->navHash("randomout_", 1); }
+sub deeplinkout { my $self=shift; return $self->navHash("deeplinkout_", 1); }
sub randompick {
my $self = shift;
my $randompick = $self->parmval('randompick');
@@ -5156,16 +5189,42 @@
return ($useslots,$availablestudent,$available);
}
sub deeplink {
- my ($self,$caller) = @_;
- my $value = $self->parmval("deeplink");
- if ($value) {
- my @deeplink = split(/,/,$value);
- if ($caller eq 'sequence') {
- if ($deeplink[1] ne 'res') {
- return;
+ my ($self,$caller,$action) = @_;
+ my $deeplink = $self->parmval("deeplink");
+ if ($deeplink) {
+ my ($listed,$scope,$access) = split(/,/,$deeplink);
+ if ($action eq 'getlisted') {
+ return $listed;
+ }
+ if ($env{'request.deeplink.login'}) {
+ my $cnum = $env{'course.'.$env{'request.course.id'}.'.num'};
+ my $cdom = $env{'course.'.$env{'request.course.id'}.'.domain'};
+ my $deeplink_symb = &Apache::loncommon::deeplink_login_symb($cnum,$cdom);
+ if ($deeplink_symb) {
+ my ($loginmap,$mapname);
+ if ($deeplink_symb =~ /\.(page|sequence)$/) {
+ $mapname = $self->enclosing_map_src();
+ $loginmap = &Apache::lonnet::clutter((&Apache::lonnet::decode_symb($deeplink_symb))[2]);
+ return if ($mapname eq $loginmap);
+ } else {
+ return if ($deeplink_symb eq $self->symb());
+ if (($scope eq 'map') || ($scope eq 'rec')) {
+ $mapname = $self->enclosing_map_src();
+ $loginmap = &Apache::lonnet::clutter((&Apache::lonnet::decode_symb($deeplink_symb))[0]);
+ return if ($mapname eq $loginmap);
+ }
+ }
+ if ($scope eq 'rec') {
+ my $map_pc = $self->navHash('map_pc_'.$mapname);
+ my @recurseup = split(/,/,$self->navHash('map_hierarchy_'.$map_pc));
+ my $login_pc = $self->navHash('map_pc_'.$loginmap);
+ return if (grep(/^\Q$login_pc\E$/, at recurseup));
+ }
}
}
- return $deeplink[0];
+ unless (($caller eq 'sequence') || ($access eq 'any')) {
+ return $listed;
+ }
}
return;
}
@@ -6360,13 +6419,23 @@
sub browsePriv {
my $self = shift;
my $noblockcheck = shift;
+ my $deeplinklisted = shift;
if (defined($self->{BROWSE_PRIV})) {
return $self->{BROWSE_PRIV};
}
-
+ my ($nodeeplinkcheck,$nodeeplinkout);
+ if ($deeplinklisted) {
+ my $deeplink = $self->deeplink(undef,'getlisted');
+ if (($deeplink) && ($deeplink ne 'absent')) {
+ $nodeeplinkcheck = 1;
+ }
+ $nodeeplinkout = 1;
+ }
$self->{BROWSE_PRIV} = &Apache::lonnet::allowed('bre',$self->src(),
$self->{SYMB},undef,
- undef,$noblockcheck);
+ undef,$noblockcheck,
+ undef,$nodeeplinkcheck,
+ $nodeeplinkout);
}
=pod
Index: loncom/interface/lonquickgrades.pm
diff -u loncom/interface/lonquickgrades.pm:1.120 loncom/interface/lonquickgrades.pm:1.121
--- loncom/interface/lonquickgrades.pm:1.120 Thu Feb 18 09:48:02 2021
+++ loncom/interface/lonquickgrades.pm Mon Jul 19 11:48:26 2021
@@ -1,7 +1,7 @@
# The LearningOnline Network with CAPA
# Quick Student Grades Display
#
-# $Id: lonquickgrades.pm,v 1.120 2021/02/18 14:48:02 raeburn Exp $
+# $Id: lonquickgrades.pm,v 1.121 2021/07/19 15:48:26 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -484,7 +484,8 @@
my $res = $navmap->firstResource(); # temp resource to access constants
- my $iterator = $navmap->getIterator(undef, undef, undef, 1);
+ my $deeplinkcond = 1;
+ my $iterator = $navmap->getIterator(undef, undef, undef, 1, undef, undef, $deeplinkcond);
my $depth = 1;
$iterator->next(); # ignore first BEGIN_MAP
my $curRes = $iterator->next();
@@ -510,9 +511,17 @@
while ( $depth > 0 ) {
if ($curRes == $iterator->BEGIN_MAP()) {$depth++;}
if ($curRes == $iterator->END_MAP()) { $depth--; }
-
- if (ref($curRes) && $curRes->is_gradable() && !$curRes->randomout &&
- ($curRes->deeplink ne 'absent'))
+ my ($deeplink,$nodeeplinkcheck,$symb);
+ $nodeeplinkcheck = 1;
+ if (ref($curRes)) {
+ $symb = $curRes->symb();
+ $deeplink = $curRes->deeplink('quickgrades');
+ if ($deeplink eq 'absent') {
+ $nodeeplinkcheck = 0;
+ }
+ }
+ if (ref($curRes) && $curRes->is_gradable() && !$curRes->randomout &&
+ ($nodeeplinkcheck))
{
# Get number of correct, incorrect parts
my $parts = $curRes->parts();
@@ -634,7 +643,8 @@
# Output of folder scores
#
- my $iterator = $navmap->getIterator(undef, undef, undef, 1);
+ my $deeplinkcond = 1;
+ my $iterator = $navmap->getIterator(undef, undef, undef, 1, undef, undef, $deeplinkcond);
my $depth = 1;
$iterator->next(); # ignore first BEGIN_MAP
my $curRes = $iterator->next();
@@ -765,7 +775,8 @@
# Run through the map and get all data
- my $iterator = $navmap->getIterator(undef, undef, undef, 1);
+ my $deeplinkcond = 1;
+ my $iterator = $navmap->getIterator(undef, undef, undef, 1, undef, undef, $deeplinkcond);
my $depth = 1;
$iterator->next(); # ignore first BEGIN_MAP
my $curRes = $iterator->next();
Index: loncom/lonnet/perl/lonnet.pm
diff -u loncom/lonnet/perl/lonnet.pm:1.1460 loncom/lonnet/perl/lonnet.pm:1.1461
--- loncom/lonnet/perl/lonnet.pm:1.1460 Tue Jun 15 16:52:28 2021
+++ loncom/lonnet/perl/lonnet.pm Mon Jul 19 11:48:27 2021
@@ -1,7 +1,7 @@
# The LearningOnline Network
# TCP networking package
#
-# $Id: lonnet.pm,v 1.1460 2021/06/15 20:52:28 raeburn Exp $
+# $Id: lonnet.pm,v 1.1461 2021/07/19 15:48:27 raeburn Exp $
#
# Copyright Michigan State University Board of Trustees
#
@@ -8117,7 +8117,7 @@
# ------------------------------------------------- Check for a user privilege
sub allowed {
- my ($priv,$uri,$symb,$role,$clientip,$noblockcheck,$ignorecache)=@_;
+ my ($priv,$uri,$symb,$role,$clientip,$noblockcheck,$ignorecache,$nodeeplinkcheck,$nodeeplinkout)=@_;
my $ver_orguri=$uri;
$uri=&deversion($uri);
my $orguri=$uri;
@@ -8342,7 +8342,10 @@
if ($env{'user.priv.'.$env{'request.role'}.'./'}
=~/\Q$priv\E\&([^\:]*)/) {
my $value = $1;
- my $deeplinkblock = &deeplink_check($priv,$symb,$uri);
+ my $deeplinkblock;
+ unless ($nodeeplinkcheck) {
+ $deeplinkblock = &deeplink_check($priv,$symb,$uri);
+ }
if ($deeplinkblock) {
$thisallowed='D';
} elsif ($noblockcheck) {
@@ -8365,7 +8368,10 @@
$refuri=&declutter($refuri);
my ($match) = &is_on_map($refuri);
if ($match) {
- my $deeplinkblock = &deeplink_check($priv,$symb,$refuri);
+ my $deeplinkblock;
+ unless ($nodeeplinkcheck) {
+ $deeplinkblock = &deeplink_check($priv,$symb,$refuri);
+ }
if ($deeplinkblock) {
$thisallowed='D';
} elsif ($noblockcheck) {
@@ -8441,7 +8447,10 @@
=~/\Q$priv\E\&([^\:]*)/) {
my $value = $1;
if ($priv eq 'bre') {
- my $deeplinkblock = &deeplink_check($priv,$symb,$uri);
+ my $deeplinkblock;
+ unless ($nodeeplinkcheck) {
+ $deeplinkblock = &deeplink_check($priv,$symb,$uri);
+ }
if ($deeplinkblock) {
$thisallowed = 'D';
} elsif ($noblockcheck) {
@@ -8486,7 +8495,10 @@
=~/\Q$priv\E\&([^\:]*)/) {
my $value = $1;
if ($priv eq 'bre') {
- my $deeplinkblock = &deeplink_check($priv,$symb,$refuri);
+ my $deeplinkblock;
+ unless ($nodeeplinkcheck) {
+ $deeplinkblock = &deeplink_check($priv,$symb,$refuri);
+ }
if ($deeplinkblock) {
$thisallowed = 'D';
} elsif ($noblockcheck) {
@@ -8669,6 +8681,17 @@
}
}
+# Restricted for deeplinked session?
+
+ if ($env{'request.deeplink.login'}) {
+ if ($env{'acc.deeplinkout'} && !$nodeeplinkout) {
+ if (!$symb) { $symb=&symbread($uri,1); }
+ if (($symb) && ($env{'acc.deeplinkout'}=~/\&\Q$symb\E\&/)) {
+ return '';
+ }
+ }
+ }
+
# Restricted by state or randomout?
if ($thisallowed=~/X/) {
@@ -9026,29 +9049,9 @@
@symbs = keys(%possibles);
}
- my ($login,$switchrole,$allow);
- if ($env{'request.deeplink.login'} =~ m{^\Q/tiny/$cdom/\E(\w+)$}) {
- my $key = $1;
- my $tinyurl;
- my ($result,$cached)=&Apache::lonnet::is_cached_new('tiny',$cdom."\0".$key);
- if (defined($cached)) {
- $tinyurl = $result;
- } else {
- my $configuname = &Apache::lonnet::get_domainconfiguser($cdom);
- my %currtiny = &Apache::lonnet::get('tiny',[$key],$cdom,$configuname);
- if ($currtiny{$key} ne '') {
- $tinyurl = $currtiny{$key};
- &Apache::lonnet::do_cache_new('tiny',$cdom."\0".$key,$currtiny{$key},600);
- }
- }
- if ($tinyurl ne '') {
- my ($cnumreq,$posslogin) = split(/\&/,$tinyurl);
- if ($cnumreq eq $cnum) {
- $login = $posslogin;
- } else {
- $switchrole = 1;
- }
- }
+ my ($deeplink_symb,$allow);
+ if ($env{'request.deeplink.login'}) {
+ $deeplink_symb = &Apache::loncommon::deeplink_login_symb($cnum,$cdom);
}
foreach my $symb (@symbs) {
last if ($allow);
@@ -9059,15 +9062,20 @@
my ($listed,$scope,$access) = split(/,/,$deeplink);
if ($access eq 'any') {
$allow = 1;
- } elsif ($login) {
+ } elsif ($deeplink_symb) {
if ($access eq 'only') {
if ($scope eq 'res') {
- if ($symb eq $login) {
+ if ($symb eq $deeplink_symb) {
$allow = 1;
}
} elsif (($scope eq 'map') || ($scope eq 'rec')) {
- my ($map_from_symb) = &deversion((&decode_symb($symb))[0]);
- my ($map_from_login) = &deversion((&decode_symb($login))[0]);
+ my ($map_from_symb,$map_from_login);
+ $map_from_symb = &deversion((&decode_symb($symb))[0]);
+ if ($deeplink_symb =~ /\.(page|sequence)$/) {
+ $map_from_login = &deversion((&decode_symb($deeplink_symb))[2]);
+ } else {
+ $map_from_login = &deversion((&decode_symb($deeplink_symb))[0]);
+ }
if (($map_from_symb) && ($map_from_login)) {
if ($map_from_symb eq $map_from_login) {
$allow = 1;
@@ -12260,7 +12268,7 @@
# --------------------------------------------------------- Value of a Variable
sub EXT {
- my ($varname,$symbparm,$udom,$uname,$usection,$recurse,$cid)=@_;
+ my ($varname,$symbparm,$udom,$uname,$usection,$recurse,$cid,$recurseupref)=@_;
unless ($varname) { return ''; }
#get real user name/domain, courseid and symb
my $courseid;
@@ -12414,6 +12422,10 @@
}
my ($section, $group, @groups, @recurseup, $recursed);
+ if (ref($recurseupref) eq 'ARRAY') {
+ @recurseup = @{$recurseupref};
+ $recursed = 1;
+ }
my ($courselevelm,$courseleveli,$courselevel,$mapp);
if (($courseid eq '') && ($cid)) {
$courseid = $cid;
More information about the LON-CAPA-cvs
mailing list