1<?php
2
3/*
4 * This file is part of the league/commonmark package.
5 *
6 * (c) Colin O'Dell <colinodell@gmail.com>
7 *
8 * For the full copyright and license information, please view the LICENSE
9 * file that was distributed with this source code.
10 */
11
12namespace League\CommonMark\Extension\Mention;
13
14use League\CommonMark\ConfigurableEnvironmentInterface;
15use League\CommonMark\Exception\InvalidOptionException;
16use League\CommonMark\Extension\ExtensionInterface;
17use League\CommonMark\Extension\Mention\Generator\MentionGeneratorInterface;
18
19final class MentionExtension implements ExtensionInterface
20{
21    public function register(ConfigurableEnvironmentInterface $environment)
22    {
23        $mentions = $environment->getConfig('mentions', []);
24        foreach ($mentions as $name => $mention) {
25            if (\array_key_exists('symbol', $mention)) {
26                @\trigger_error('The "mentions/*/symbol" configuration option is deprecated in league/commonmark 1.6; rename "symbol" to "prefix" for compatibility with 2.0', \E_USER_DEPRECATED);
27                $mention['prefix'] = $mention['symbol'];
28            }
29
30            if (\array_key_exists('pattern', $mention)) {
31                // v2.0 does not allow full regex patterns passed into the configuration
32                if (!self::isAValidPartialRegex($mention['pattern'])) {
33                    throw new InvalidOptionException(\sprintf('Option "mentions/%s/pattern" must not include starting/ending delimiters (like "/")', $name));
34                }
35
36                $mention['pattern'] = '/' . $mention['pattern'] . '/i';
37            } elseif (\array_key_exists('regex', $mention)) {
38                @\trigger_error('The "mentions/*/regex" configuration option is deprecated in league/commonmark 1.6; rename "regex" to "pattern" for compatibility with 2.0', \E_USER_DEPRECATED);
39                $mention['pattern'] = $mention['regex'];
40            }
41
42            foreach (['prefix', 'pattern', 'generator'] as $key) {
43                if (empty($mention[$key])) {
44                    throw new \RuntimeException("Missing \"$key\" from MentionParser configuration");
45                }
46            }
47            if ($mention['generator'] instanceof MentionGeneratorInterface) {
48                $environment->addInlineParser(new MentionParser($mention['prefix'], $mention['pattern'], $mention['generator']));
49            } elseif (is_string($mention['generator'])) {
50                $environment->addInlineParser(MentionParser::createWithStringTemplate($mention['prefix'], $mention['pattern'], $mention['generator']));
51            } elseif (is_callable($mention['generator'])) {
52                $environment->addInlineParser(MentionParser::createWithCallback($mention['prefix'], $mention['pattern'], $mention['generator']));
53            } else {
54                throw new \RuntimeException(sprintf('The "generator" provided for the MentionParser configuration must be a string template, callable, or an object that implements %s.', MentionGeneratorInterface::class));
55            }
56        }
57    }
58
59    private static function isAValidPartialRegex(string $regex): bool
60    {
61        $regex = '/' . $regex . '/i';
62
63        return @\preg_match($regex, '') !== false;
64    }
65}
66