Passed
Branch fuck-54 (abba45)
by Kacper
02:24
created

Php   A

Complexity

Total Complexity 3

Size/Duplication

Total Lines 111
Duplicated Lines 0 %

Coupling/Cohesion

Components 0
Dependencies 9

Importance

Changes 1
Bugs 0 Features 0
Metric Value
wmc 3
c 1
b 0
f 0
lcom 0
cbo 9
dl 0
loc 111
rs 10

3 Methods

Rating   Name   Duplication   Size   Complexity  
B getRules() 0 85 1
A getOpenClose() 0 17 1
A getIdentifier() 0 4 1
1
<?php
2
/**
3
 * Highlighter
4
 *
5
 * Copyright (C) 2015, Some right reserved.
6
 * @author Kacper "Kadet" Donat <[email protected]>
7
 *
8
 * Contact with author:
9
 * Xmpp: [email protected]
10
 * E-mail: [email protected]
11
 *
12
 * From Kadet with love.
13
 */
14
15
namespace Kadet\Highlighter\Language;
16
17
18
use Kadet\Highlighter\Matcher\CommentMatcher;
19
use Kadet\Highlighter\Matcher\RegexMatcher;
20
use Kadet\Highlighter\Matcher\SubStringMatcher;
21
use Kadet\Highlighter\Matcher\WordMatcher;
22
use Kadet\Highlighter\Parser\CloseRule;
23
use Kadet\Highlighter\Parser\LanguageToken;
24
use Kadet\Highlighter\Parser\ContextualToken;
25
use Kadet\Highlighter\Parser\Rule;
26
use Kadet\Highlighter\Parser\OpenRule;
27
use Kadet\Highlighter\Parser\Token;
28
use Kadet\Highlighter\Parser\TokenFactory;
29
30
class Php extends Language
31
{
32
    public function getRules()
33
    {
34
        return [
35
            'string.single' => new Rule(new SubStringMatcher('\''), [
36
                'context' => ['!keyword.escape', '!comment', '!string', '!keyword.nowdoc'],
37
                'factory' => new TokenFactory(ContextualToken::class),
38
            ]),
39
40
            'string.double' => new Rule(new SubStringMatcher('"'), [
41
                'context' => ['!keyword.escape', '!comment', '!string'],
42
                'factory' => new TokenFactory(ContextualToken::class),
43
            ]),
44
45
            'string.heredoc' => new Rule(new RegexMatcher('/<<<\s*(\w+)(?P<string>.*?)\n\1;/sm', ['string' => Token::NAME, 0 => 'keyword.heredoc']), ['context' => ['!comment']]),
46
            'string.nowdoc' => new Rule(new RegexMatcher('/<<<\s*\'(\w+)\'(?P<string>.*?)\n\1;/sm', ['string' => Token::NAME, 0 => 'keyword.nowdoc']), ['context' => ['!comment']]),
47
48
            'variable' => new Rule(new RegexMatcher('/[^\\\](\$[a-z_]\w*)/i'), [
49
                'context' => ['*comment.docblock', '!string.nowdoc', '!string.single', '!comment']
50
            ]),
51
            'variable.property' => new Rule(new RegexMatcher('/(?=(?:\w|\)|\])\s*->([a-z_]\w*))/i'), [
52
                'priority' => -2
53
            ]),
54
55
            'symbol.function' => new Rule(new RegexMatcher('/function\s+([a-z_]\w+)\s*\(/i')),
56
            'symbol.class' => [
57
                new Rule(new RegexMatcher('/(?:class|new|use|extends)\s+([\w\\\]+)/i')),
58
                new Rule(new RegexMatcher('/([\w\\\]+)::/i')),
59
                new Rule(new RegexMatcher('/@(?:var|property(?:-read|-write)?)\s+([^\$][\w\\\]+)/i'), ['context' => ['comment.docblock']]),
60
            ],
61
62
            'symbol.class.interface' => [
63
                new Rule(new RegexMatcher('/interface\s+([\w\\\]+)/i')),
64
                new Rule(new RegexMatcher('/implements\s+([\w\\\]+)(?:,\s*([\w\\\]+))*/i'), [
65
                    1 => Token::NAME,
66
                    2 => Token::NAME
67
                ]),
68
            ],
69
70
            'keyword.escape' => new Rule(new RegexMatcher('/(\\\(?:x[0-9a-fA-F]{1,2}|u\{[0-9a-fA-F]{1,6}\}|[0-7]{1,3}|.))/i'), [
71
                'context' => ['string']
72
            ]),
73
74
            'comment' => new Rule(new CommentMatcher(['//', '#'], [
75
                '$.docblock' => ['/**', '*/'],
76
                ['/* ', '*/']
77
            ])),
78
79
            'keyword.annotation' => new Rule(new RegexMatcher('/[\s]+(@[\w-]+)/i'), [
80
                'context' => ['comment.docblock']
81
            ]),
82
83
            'call' => new Rule(new RegexMatcher('/([a-z_]\w*)\s*\(/i'), ['priority' => -1]),
84
85
            'constant' => new Rule(new WordMatcher(array_merge([
86
                '__CLASS__', '__DIR__', '__FILE__', '__FUNCTION__',
87
                '__LINE__', '__METHOD__', '__NAMESPACE__', '__TRAIT__',
88
            ], array_keys(get_defined_constants(true)["Core"]))), ['priority' => -2]),
89
            'constant.static' => new Rule(new RegexMatcher('/(?:[\w\\\]+::|const\s+)(\w+)/i'), ['priority' => -2]   ),
90
91
            'keyword' => new Rule(new WordMatcher([
92
                '__halt_compiler', 'abstract', 'and', 'array',
93
                'as', 'break', 'callable', 'case', 'catch',
94
                'class', 'clone', 'const', 'continue', 'declare',
95
                'default', 'die', 'do', 'echo', 'else', 'elseif',
96
                'empty', 'enddeclare', 'endfor', 'endforeach', 'endif',
97
                'endswitch', 'endwhile', 'eval', 'exit', 'extends',
98
                'final', 'finally', 'for', 'foreach', 'function',
99
                'global', 'goto', 'if', 'implements', 'include', 'include_once',
100
                'instanceof', 'insteadof', 'interface', 'isset', 'list',
101
                'namespace', 'new', 'or', 'print', 'private', 'protected',
102
                'public', 'require', 'require_once', 'return', 'static',
103
                'switch', 'throw', 'trait', 'try', 'unset', 'parent', 'self',
104
                'use', 'var', 'while', 'xor', 'yield'
105
            ]), ['context' => ['!string', '!variable', '!comment']]),
106
107
            'keyword.cast' => new Rule(
108
                new RegexMatcher('/(\((?:int|integer|bool|boolean|float|double|real|string|array|object|unset)\))/')
109
            ),
110
111
            'delimiter' => new Rule(new RegexMatcher('/(<\?php|<\?=|\?>)/')),
112
            'number' => new Rule(new RegexMatcher('/(-?(?:0[0-7]+|0[xX][0-9a-fA-F]+|0b[01]+|\d+))/')),
113
114
            'operator.punctuation' => new Rule(new WordMatcher([',', ';'], ['separated' => false]), ['priority' => 0]),
115
        ];
116
    }
117
118
    public function getOpenClose() {
119
        return [
120
            new OpenRule(new RegexMatcher('/(<\?php|<\?=)/si'), [
121
                'factory'  => new TokenFactory(LanguageToken::class),
122
                'priority' => 1000,
123
                'context'  => ['*'],
124
                'inject'   => $this,
125
                'language' => null
126
            ]),
127
            new CloseRule(new RegexMatcher('/(\?>|$)/'), [
128
                'context'  => ['!string', '!comment'],
129
                'priority' => 1000,
130
                'factory'  => new TokenFactory(LanguageToken::class),
131
                'language' => $this
132
            ])
133
        ];
134
    }
135
136
    public function getIdentifier()
137
    {
138
        return 'php';
139
    }
140
}