Proyectos de Subversion Moodle

Rev

| Ultima modificación | Ver Log |

Rev Autor Línea Nro. Línea
1 efrain 1
<?php
2
// This file is part of Moodle - http://moodle.org/
3
//
4
// Moodle is free software: you can redistribute it and/or modify
5
// it under the terms of the GNU General Public License as published by
6
// the Free Software Foundation, either version 3 of the License, or
7
// (at your option) any later version.
8
//
9
// Moodle is distributed in the hope that it will be useful,
10
// but WITHOUT ANY WARRANTY; without even the implied warranty of
11
// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
12
// GNU General Public License for more details.
13
//
14
// You should have received a copy of the GNU General Public License
15
// along with Moodle.  If not, see <http://www.gnu.org/licenses/>.
16
 
17
namespace tool_brickfield\local\htmlchecker\reporters;
18
 
19
use tool_brickfield\local\htmlchecker\brickfield_accessibility;
20
use tool_brickfield\local\htmlchecker\brickfield_accessibility_reporter;
21
 
22
/**
23
 * Returns the entire document marked-up to highlight problems.
24
 *
25
 * @package    tool_brickfield
26
 * @copyright  2020 onward: Brickfield Education Labs, www.brickfield.ie
27
 * @license    http://www.gnu.org/copyleft/gpl.html GNU GPL v3 or later
28
 */
29
class report_demo extends brickfield_accessibility_reporter {
30
 
31
    /**
32
     * @var array An array of the classnames to be associated with items
33
     */
34
    public $classnames = [
35
        brickfield_accessibility::BA_TEST_SEVERE => 'testlevel_severe',
36
        brickfield_accessibility::BA_TEST_MODERATE => 'testlevel_moderate',
37
        brickfield_accessibility::BA_TEST_SUGGESTION => 'testlevel_suggestion',
38
    ];
39
 
40
    /**
41
     * The get_report method - we iterate through every test item and
42
     * add additional attributes to build the report UI.
43
     * @return string A fully-formed HTML document.
44
     */
45
    public function get_report(): string {
46
        $problems = $this->guideline->get_report();
47
        if (is_array($problems)) {
48
            foreach ($problems as $testname => $test) {
49
                if (!isset($this->options->display_level) ||
50
                    ($this->options->display_level >= $test['severity'] && is_array($test))) {
51
                    foreach ($test as $problem) {
52
                        if (is_object($problem) && property_exists($problem, 'element') && is_object($problem->element)) {
53
                            $existing = $problem->element->getAttribute('style');
54
                            $problem->element->setAttribute('style',
55
                                $existing .'; border: 2px solid red;');
56
                            if (isset($this->options->image_url)) {
57
                                $image = $this->dom->createElement('img');
58
                                $image = $problem->element->parentNode->insertBefore($image, $problem->element);
59
                                $image->setAttribute('alt', $testname);
60
                                if ($problem->message) {
61
                                    $image->setAttribute('title', $problem->message);
62
                                }
63
                                $image->setAttribute('src', $this->options->image_url[$test['severity']]);
64
                            }
65
                        }
66
                    }
67
                }
68
            }
69
        }
70
        return $this->complete_urls($this->dom->saveHTML(), implode('/', $this->path));
71
    }
72
 
73
 
74
    /**
75
     * Finds the final postion of a needle in the haystack.
76
     *
77
     * @param mixed $haystack
78
     * @param mixed $needle
79
     * @param mixed $occurance
80
     * @param int $pos
81
     * @return false|int
82
     */
83
    public function strnpos($haystack, $needle, $occurance, int $pos = 0) {
84
        for ($i = 1; $i <= $occurance; $i++) {
85
            $pos = strpos($haystack, $needle, $pos) + 1;
86
        }
87
        return $pos - 1;
88
    }
89
 
90
    /**
91
     * A helper function for completeURLs. Parses a URL into an the scheme, host, and path
92
     * @param string $url The URL to parse
93
     * @return array An array that includes the scheme, host, and path of the URL
94
     */
95
    public function parse_url(string $url): array {
96
        $pattern = "/^(?:(http[s]?):\/\/(?:(.*):(.*)@)?([^\/]+))?((?:[\/])?(?:[^\.]*?)?(?:[\/])?)?(?:([^\/^\.]+)\." .
97
            "([^\?]+))?(?:\?(.+))?$/i";
98
        preg_match($pattern, $url, $matches);
99
 
100
        $uriparts["scheme"] = $matches[1];
101
        $uriparts["host"] = $matches[4];
102
        $uriparts["path"] = $matches[5];
103
 
104
        return $uriparts;
105
    }
106
 
107
    /**
108
     * Turns all relative links to absolute links so that the page can be rendered correctly.
109
     * @param string $html A complete HTML document
110
     * @param string $url The absolute URL to the document
111
     * @return string A HTML document with all the relative links converted to absolute links
112
     */
113
    public function complete_urls(string $html, string $url) {
114
        $uriparts = $this->parse_url($url);
115
        $path = trim($uriparts["path"], "/");
116
        $hosturl = trim($uriparts["host"], "/");
117
 
118
        $host = $uriparts["scheme"]."://".$hosturl."/".$path."/";
119
        $hostnopath = $uriparts["scheme"]."://".$hosturl."/";
120
 
121
        // Proxifies local META redirects.
122
        $html = preg_replace('@<META HTTP-EQUIV(.*)URL=/@',
123
            "<META HTTP-EQUIV\$1URL=".$_SERVER['PHP_SELF']."?url=".$hostnopath, $html);
124
 
125
        // Make sure the host doesn't end in '//'.
126
        $host = rtrim($host, '/')."/";
127
 
128
        // Replace '//' with 'http://'.
129
        $pattern = "#(?<=\"|'|=)\/\/#"; // The '|=' is experimental as it's probably not necessary.
130
        $html = preg_replace($pattern, "http://", $html);
131
 
132
        // Fully qualifies '"/'.
133
        $html = preg_replace("#\"\/#", "\"".$host, $html);
134
 
135
        // Fully qualifies "'/".
136
        $html = preg_replace("#\'\/#", "\'".$host, $html);
137
 
138
        // Matches [src|href|background|action]="/ because in the following pattern the '/' shouldn't stay.
139
        $html = preg_replace("#(src|href|background|action)(=\"|='|=(?!'|\"))\/#i", "\$1\$2".$hostnopath, $html);
140
        $html = preg_replace("#(href|src|background|action)(=\"|=(?!'|\")|=')(?!http|ftp|https|\"|'|javascript:|mailto:)#i",
141
            "\$1\$2".$host, $html);
142
 
143
        // Points all form actions back to the proxy.
144
        $html = preg_replace('/<form.+?action=\s*(["\']?)([^>\s"\']+)\\1[^>]*>/i',
145
            "<form action=\"{$_SERVER['PHP_SELF']}\"><input type=\"hidden\" name=\"original_url\" value=\"$2\">", $html);
146
 
147
        // Matches '/[any assortment of chars or nums]/../'.
148
        $html = preg_replace("#\/(\w*?)\/\.\.\/(.*?)>#ims", "/\$2>", $html);
149
 
150
        // Matches '/./'.
151
        $html = preg_replace("#\/\.\/(.*?)>#ims", "/\$1>", $html);
152
 
153
        // Handles CSS2 imports.
154
        if (strpos($html, "import url(\"http") == false && (strpos($html, "import \"http") == false)
155
            && strpos($html, "import url(\"www") == false && (strpos($html, "import \"www") == false)) {
156
            $pattern = "#import .(.*?).;#ims";
157
            $mainurl = substr($host, 0, $this->strnpos($host, "/", 3));
158
            $replace = "import '".$mainurl."\$1';";
159
            $html = preg_replace($pattern, $replace, $html);
160
        }
161
        return $html;
162
    }
163
}