GitHub Access Token became invalid

It seems like the GitHub access token used for retrieving details about this repository from GitHub became invalid. This might prevent certain types of inspections from being run (in particular, everything related to pull requests).
Please ask an admin of your repository to re-new the access token on this website.
Passed
Push — master ( cadf7d...fa378e )
by Leonardo
07:02
created

processHTMLContent()   A

Complexity

Conditions 1
Paths 1

Size

Total Lines 11
Code Lines 6

Duplication

Lines 0
Ratio 0 %

Code Coverage

Tests 0
CRAP Score 2

Importance

Changes 1
Bugs 0 Features 0
Metric Value
cc 1
eloc 6
c 1
b 0
f 0
nc 1
nop 2
dl 0
loc 11
ccs 0
cts 8
cp 0
crap 2
rs 10
1
<?php
2
3
declare(strict_types=1);
4
5
namespace GraphQLAPI\GraphQLAPI\ModuleResolvers;
6
7
use Parsedown;
8
9
trait HasMarkdownDocumentationModuleResolverTrait
10
{
11
    /**
12
     * The module slug
13
     */
14
    abstract public function getSlug(string $module): string;
15
16
    /**
17
     * The name of the Markdown filename.
18
     * By default, it's the same as the slug
19
     *
20
     * @param string $module
21
     * @return string
22
     */
23
    public function getMarkdownFilename(string $module): ?string
24
    {
25
        return $this->getSlug($module) . '.md';
26
    }
27
28
    /**
29
     * Where the markdown file localized to the user's language is stored
30
     *
31
     * @param string $module
32
     * @return string
33
     */
34
    abstract public function getLocalizedMarkdownFileDir(string $module): string;
35
36
    /**
37
     * Where the default markdown file (for if the localized language is not available) is stored
38
     *
39
     * @param string $module
40
     * @return string
41
     */
42
    abstract public function getDefaultMarkdownFileDir(string $module): string;
43
44
    /**
45
     * Does the module have HTML Documentation?
46
     *
47
     * @param string $module
48
     * @return bool
49
     */
50
    public function hasDocumentation(string $module): bool
51
    {
52
        return !empty($this->getMarkdownFilename($module));
53
    }
54
55
    /**
56
     * Path URL to append to the local images referenced in the markdown file
57
     *
58
     * @param string $module
59
     * @return string|null
60
     */
61
    abstract protected function getDefaultMarkdownFileURL(string $module): string;
62
63
    /**
64
     * HTML Documentation for the module
65
     *
66
     * @param string $module
67
     * @return string|null
68
     */
69
    public function getDocumentation(string $module): ?string
70
    {
71
        if ($markdownFilename = $this->getMarkdownFilename($module)) {
72
            $localizedMarkdownFile = \trailingslashit($this->getLocalizedMarkdownFileDir($module)) . $markdownFilename;
73
            if (file_exists($localizedMarkdownFile)) {
74
                // First check if the localized version exists
75
                $markdownFile = $localizedMarkdownFile;
76
            } else {
77
                // Otherwise, use the default language version
78
                $markdownFile = \trailingslashit($this->getDefaultMarkdownFileDir($module)) . $markdownFilename;
79
                // Make sure this file exists
80
                if (!file_exists($markdownFile)) {
81
                    return sprintf(
82
                        '<p>%s</p>',
83
                        \__('Oops, the documentation for this module is not available', 'graphql-api')
84
                    );
85
                }
86
            }
87
            $markdownContents = file_get_contents($markdownFile);
88
            $htmlContent = (new Parsedown())->text($markdownContents);
89
            return $this->processHTMLContent($module, $htmlContent);
90
        }
91
        return null;
92
    }
93
94
    /**
95
     * Process the HTML content:
96
     *
97
     * - Add the path to the images and anchors
98
     * - Add classes to HTML elements
99
     * - Append video embeds
100
     */
101
    protected function processHTMLContent(string $module, string $htmlContent): string
102
    {
103
        $defaultModulePathURL = $this->getDefaultMarkdownFileURL($module);
104
        // Add the path to the images and anchors
105
        $htmlContent = $this->appendPathURLToImages($defaultModulePathURL, $htmlContent);
106
        $htmlContent = $this->appendPathURLToAnchors($defaultModulePathURL, $htmlContent);
107
        // Add classes to HTML elements
108
        $htmlContent = $this->addClasses($htmlContent);
109
        // Append video embeds
110
        $htmlContent = $this->embedVideos($htmlContent);
111
        return $htmlContent;
112
    }
113
114
    /**
115
     * Append video embeds. These are not already in the markdown file
116
     * because GitHub can't add `<iframe>`. Then, the source only contains
117
     * a link to the video. This must be identified, and transformed into
118
     * the embed.
119
     */
120
    protected function embedVideos(string $htmlContent): string
121
    {
122
        // Identify videos from Vimeo/Youtube
123
        return preg_replace_callback(
124
            '/<p>(.*?)<a href="https:\/\/(vimeo.com|youtube.com|youtu.be)\/(.*?)">(.*?)<\/a>\.?<\/p>/',
125
            function ($matches) {
126
                global $wp_embed;
127
                // Keep the link, and append the embed immediately after
128
                return
129
                    $matches[0]
130
                    . '<div class="video-responsive-container">' .
131
                        $wp_embed->autoembed(sprintf(
132
                            'https://%s/%s',
133
                            $matches[2],
134
                            $matches[3]
135
                        ))
136
                    . '</div>';
137
            },
138
            $htmlContent
139
        );
140
    }
141
142
    /**
143
     * Add classes to the HTML elements
144
     */
145
    protected function addClasses(string $htmlContent): string
146
    {
147
        /**
148
         * Add class "wp-list-table widefat" to all tables
149
         */
150
        return str_replace(
151
            '<table>',
152
            '<table class="wp-list-table widefat striped">',
153
            $htmlContent
154
        );
155
    }
156
157
    /**
158
     * Convert relative paths to absolute paths for image URLs
159
     *
160
     * @param string $pathURL
161
     * @param string $htmlContent
162
     * @return string
163
     */
164
    protected function appendPathURLToImages(string $pathURL, string $htmlContent): string
165
    {
166
        return $this->appendPathURLToElement('img', 'src', $pathURL, $htmlContent);
167
    }
168
169
    /**
170
     * Convert relative paths to absolute paths for image URLs
171
     *
172
     * @param string $pathURL
173
     * @param string $htmlContent
174
     * @return string
175
     */
176
    protected function appendPathURLToAnchors(string $pathURL, string $htmlContent): string
177
    {
178
        return $this->appendPathURLToElement('a', 'href', $pathURL, $htmlContent);
179
    }
180
181
    /**
182
     * Convert relative paths to absolute paths for elements
183
     *
184
     * @param string $tag
185
     * @param string $attr
186
     * @param string $pathURL
187
     * @param string $htmlContent
188
     * @return string
189
     */
190
    protected function appendPathURLToElement(string $tag, string $attr, string $pathURL, string $htmlContent): string
191
    {
192
        /**
193
         * $regex will become:
194
         * - /<img.*src="(.*?)".*?>/
195
         * - /<a.*href="(.*?)".*?>/
196
         */
197
        $regex = sprintf(
198
            '/<%s.*%s="(.*?)".*?>/',
199
            $tag,
200
            $attr
201
        );
202
        return preg_replace_callback(
203
            $regex,
204
            function ($matches) use ($pathURL, $attr) {
205
                // If the element has an absolute route, then no need
206
                if (substr($matches[1], 0, strlen('http://')) == 'http://'
207
                    || substr($matches[1], 0, strlen('https://')) == 'https://'
208
                ) {
209
                    return $matches[0];
210
                }
211
                $elementURL = \trailingslashit($pathURL) . $matches[1];
212
                return str_replace(
213
                    "{$attr}=\"{$matches[1]}\"",
214
                    "{$attr}=\"{$elementURL}\"",
215
                    $matches[0]
216
                );
217
            },
218
            $htmlContent
219
        );
220
    }
221
}
222