Skip to content

Commit

Permalink
MDL-69656 backup: Replace urlencoded pluginfile urls
Browse files Browse the repository at this point in the history
  • Loading branch information
sh-csg committed Mar 6, 2024
1 parent 970fe4d commit 8e874c5
Show file tree
Hide file tree
Showing 4 changed files with 48 additions and 14 deletions.
16 changes: 13 additions & 3 deletions backup/moodle2/backup_course_task.class.php
Original file line number Diff line number Diff line change
Expand Up @@ -168,6 +168,7 @@ static public function encode_content_links($content) {
$content = self::encode_links_helper($content, 'BADGESVIEWBYID', '/badges/view.php?type=2&id=');
$content = self::encode_links_helper($content, 'USERINDEXVIEWBYID', '/user/index.php?id=');
$content = self::encode_links_helper($content, 'PLUGINFILEBYCONTEXT', '/pluginfile.php/');
$content = self::encode_links_helper($content, 'PLUGINFILEBYCONTEXTURLENCODED', '/pluginfile.php/', true);

return $content;
}
Expand All @@ -178,17 +179,26 @@ static public function encode_content_links($content) {
* @param string $name the name of this type of encoded link.
* @param string $path the path that identifies this type of link, up
* to the ?paramname= bit.
* @param bool $urlencoded whether to use urlencode() before replacing the path.
* @return string content with one type of link encoded.
*/
static private function encode_links_helper($content, $name, $path) {
private static function encode_links_helper(string $content, string $name, string $path, bool $urlencoded = false) {
global $CFG;
// We want to convert both http and https links.
$root = $CFG->wwwroot;
$httpsroot = str_replace('http://', 'https://', $root);
$httproot = str_replace('https://', 'http://', $root);

$httpsbase = preg_quote($httpsroot . $path, '/');
$httpbase = preg_quote($httproot . $path, '/');
$httpsbase = $httpsroot . $path;
$httpbase = $httproot . $path;

if ($urlencoded) {
$httpsbase = urlencode($httpsbase);
$httpbase = urlencode($httpbase);
}

$httpsbase = preg_quote($httpsbase, '/');
$httpbase = preg_quote($httpbase, '/');

$return = preg_replace('/(' . $httpsbase . ')([0-9]+)/', '$@' . $name . '*$2@$', $content);
$return = preg_replace('/(' . $httpbase . ')([0-9]+)/', '$@' . $name . '*$2@$', $return);
Expand Down
1 change: 1 addition & 0 deletions backup/moodle2/restore_course_task.class.php
Original file line number Diff line number Diff line change
Expand Up @@ -167,6 +167,7 @@ static public function define_decode_rules() {
$rules[] = new restore_decode_rule('BADGESVIEWBYID', '/badges/view.php?type=2&id=$1', 'course');
$rules[] = new restore_decode_rule('USERINDEXVIEWBYID', '/user/index.php?id=$1', 'course');
$rules[] = new restore_decode_rule('PLUGINFILEBYCONTEXT', '/pluginfile.php/$1', 'context');
$rules[] = new restore_decode_rule('PLUGINFILEBYCONTEXTURLENCODED', '/pluginfile.php/$1', 'context', true);

return $rules;
}
Expand Down
17 changes: 16 additions & 1 deletion backup/util/helper/restore_decode_rule.class.php
Original file line number Diff line number Diff line change
Expand Up @@ -44,14 +44,26 @@ class restore_decode_rule {

protected $cregexp; // Calculated regular expresion we'll be looking for matches

public function __construct($linkname, $urltemplate, $mappings) {
/** @var bool $urlencoded Whether to use urlencode() on the final URL. */
protected bool $urlencoded;

/**
* Constructor
*
* @param string $linkname How the link has been encoded in backup (CHOICEVIEWBYID, COURSEVIEWBYID...)
* @param string $urltemplate How the original URL looks like, with dollar placeholders
* @param array|string $mappings Which backup_ids mappings do we need to apply for replacing the placeholders
* @param bool $urlencoded Whether to use urlencode() on the final URL (defaults to false)
*/
public function __construct(string $linkname, string $urltemplate, $mappings, bool $urlencoded = false) {
// Validate all the params are ok
$this->mappings = $this->validate_params($linkname, $urltemplate, $mappings);
$this->linkname = $linkname;
$this->urltemplate = $urltemplate;
$this->restoreid = 0;
$this->sourcewwwroot = '';
$this->targetwwwroot = ''; // yes, uses to be $CFG->wwwroot, and? ;-)
$this->urlencoded = $urlencoded;
$this->cregexp = $this->get_calculated_regexp();
}

Expand Down Expand Up @@ -96,6 +108,9 @@ public function decode($content) {
} else { // All mappings found, apply target values to the template
$toreplace = str_replace($placeholdersarr, $mappingstargetarr, $toreplace);
}
if ($this->urlencoded) {
$toreplace = urlencode($toreplace);
}
// Finally, perform the replacement in original content
$content = str_replace($tosearch, $toreplace, $content);
}
Expand Down
28 changes: 18 additions & 10 deletions backup/util/helper/tests/backup_encode_content_test.php
Original file line number Diff line number Diff line change
Expand Up @@ -50,14 +50,18 @@ public function test_course_encode_content_links() {
// HTTPS root and links of both types in content.
$CFG->wwwroot = $httpsroot;
$encoded = backup_course_task::encode_content_links(
$httproot . '/course/view.php?id=123, ' .
$httpsroot . '/course/view.php?id=123, ' .
$httpsroot . '/grade/index.php?id=123, ' .
$httpsroot . '/grade/report/index.php?id=123, ' .
$httpsroot . '/badges/view.php?type=2&id=123 and ' .
$httpsroot . '/user/index.php?id=123.');
$httproot . '/course/view.php?id=123, ' .
$httpsroot . '/course/view.php?id=123, ' .
$httpsroot . '/grade/index.php?id=123, ' .
$httpsroot . '/grade/report/index.php?id=123, ' .
$httpsroot . '/badges/view.php?type=2&id=123, ' .
$httpsroot . '/user/index.php?id=123, ' .
$httpsroot . '/pluginfile.php/123 and ' .
urlencode($httpsroot . '/pluginfile.php/123') . '.'
);
$this->assertEquals('$@COURSEVIEWBYID*123@$, $@COURSEVIEWBYID*123@$, $@GRADEINDEXBYID*123@$, ' .
'$@GRADEREPORTINDEXBYID*123@$, $@BADGESVIEWBYID*123@$ and $@USERINDEXVIEWBYID*123@$.', $encoded);
'$@GRADEREPORTINDEXBYID*123@$, $@BADGESVIEWBYID*123@$, $@USERINDEXVIEWBYID*123@$, ' .
'$@PLUGINFILEBYCONTEXT*123@$ and $@PLUGINFILEBYCONTEXTURLENCODED*123@$.', $encoded);

// HTTP root and links of both types in content.
$CFG->wwwroot = $httproot;
Expand All @@ -66,10 +70,14 @@ public function test_course_encode_content_links() {
$httpsroot . '/course/view.php?id=123, ' .
$httproot . '/grade/index.php?id=123, ' .
$httproot . '/grade/report/index.php?id=123, ' .
$httproot . '/badges/view.php?type=2&id=123 and ' .
$httproot . '/user/index.php?id=123.');
$httproot . '/badges/view.php?type=2&id=123, ' .
$httproot . '/user/index.php?id=123, ' .
$httproot . '/pluginfile.php/123 and ' .
urlencode($httproot . '/pluginfile.php/123') . '.'
);
$this->assertEquals('$@COURSEVIEWBYID*123@$, $@COURSEVIEWBYID*123@$, $@GRADEINDEXBYID*123@$, ' .
'$@GRADEREPORTINDEXBYID*123@$, $@BADGESVIEWBYID*123@$ and $@USERINDEXVIEWBYID*123@$.', $encoded);
'$@GRADEREPORTINDEXBYID*123@$, $@BADGESVIEWBYID*123@$, $@USERINDEXVIEWBYID*123@$, ' .
'$@PLUGINFILEBYCONTEXT*123@$ and $@PLUGINFILEBYCONTEXTURLENCODED*123@$.', $encoded);
$CFG->wwwroot = $oldroot;
}
}

0 comments on commit 8e874c5

Please sign in to comment.