xref: /dokuwiki/inc/Parsing/ParserMode/Internallink.php (revision 73dc0a8919857718a3b64a4c0741b57580a34b2a)
1<?php
2
3namespace dokuwiki\Parsing\ParserMode;
4
5use dokuwiki\MailUtils;
6use dokuwiki\Parsing\Handler;
7
8class Internallink extends AbstractMode
9{
10    /** @inheritdoc */
11    public function getSort()
12    {
13        return 300;
14    }
15
16    /** @inheritdoc */
17    public function connectTo($mode)
18    {
19        // Word boundaries?
20        $this->Lexer->addSpecialPattern("\[\[.*?\]\](?!\])", $mode, 'internallink');
21    }
22
23    /** @inheritdoc */
24    public function handle($match, $state, $pos, Handler $handler)
25    {
26        // Strip the opening and closing markup
27        $link = preg_replace(['/^\[\[/', '/\]\]$/u'], '', $match);
28
29        // Split title from URL
30        $link = sexplode('|', $link, 2);
31        if ($link[1] !== null && preg_match('/^\{\{[^\}]+\}\}$/', $link[1])) {
32            // If the title is an image, convert it to an array containing the image details
33            $link[1] = Media::parseMedia($link[1]);
34        }
35        $link[0] = trim($link[0]);
36
37        //decide which kind of link it is
38
39        if (link_isinterwiki($link[0])) {
40            // Interwiki
41            $interwiki = sexplode('>', $link[0], 2, '');
42            $handler->addCall(
43                'interwikilink',
44                [$link[0], $link[1], strtolower($interwiki[0]), $interwiki[1]],
45                $pos
46            );
47        } elseif (preg_match('/^\\\\\\\\[^\\\\]+?\\\\/u', $link[0])) {
48            // Windows Share
49            $handler->addCall(
50                'windowssharelink',
51                [$link[0], $link[1]],
52                $pos
53            );
54        } elseif (preg_match('#^([a-z0-9\-\.+]+?)://#i', $link[0])) {
55            // external link (accepts all protocols)
56            $handler->addCall(
57                'externallink',
58                [$link[0], $link[1]],
59                $pos
60            );
61        } elseif (preg_match('<' . MailUtils::PREG_PATTERN_VALID_EMAIL . '>', $link[0])) {
62            // E-Mail
63            $handler->addCall(
64                'emaillink',
65                [$link[0], $link[1]],
66                $pos
67            );
68        } elseif (preg_match('!^#.+!', $link[0])) {
69            // local link
70            $handler->addCall(
71                'locallink',
72                [substr($link[0], 1), $link[1]],
73                $pos
74            );
75        } else {
76            // internal link
77            $handler->addCall(
78                'internallink',
79                [$link[0], $link[1]],
80                $pos
81            );
82        }
83
84        return true;
85    }
86}
87