1# -*- coding: utf-8 -*- 2""" 3 pygments.lexers.varnish 4 ~~~~~~~~~~~~~~~~~~~~~~~ 5 6 Lexers for Varnish configuration 7 8 :copyright: Copyright 2006-2017 by the Pygments team, see AUTHORS. 9 :license: BSD, see LICENSE for details. 10""" 11 12from pygments.lexer import RegexLexer, include, bygroups, using, this, \ 13 inherit, words 14from pygments.token import Text, Comment, Operator, Keyword, Name, String, \ 15 Number, Punctuation, Literal 16 17__all__ = ['VCLLexer', 'VCLSnippetLexer'] 18 19 20class VCLLexer(RegexLexer): 21 """ 22 For Varnish Configuration Language (VCL). 23 24 .. versionadded:: 2.2 25 """ 26 name = 'VCL' 27 aliases = ['vcl'] 28 filenames = ['*.vcl'] 29 mimetypes = ['text/x-vclsrc'] 30 31 def analyse_text(text): 32 # If the very first line is 'vcl 4.0;' it's pretty much guaranteed 33 # that this is VCL 34 if text.startswith('vcl 4.0;'): 35 return 1.0 36 # Skip over comments and blank lines 37 # This is accurate enough that returning 0.9 is reasonable. 38 # Almost no VCL files start without some comments. 39 elif '\nvcl 4\.0;' in text[:1000]: 40 return 0.9 41 42 tokens = { 43 'probe': [ 44 include('whitespace'), 45 include('comments'), 46 (r'(\.\w+)(\s*=\s*)([^;]*)(;)', 47 bygroups(Name.Attribute, Operator, using(this), Punctuation)), 48 (r'\}', Punctuation, '#pop'), 49 ], 50 'acl': [ 51 include('whitespace'), 52 include('comments'), 53 (r'[!/]+', Operator), 54 (r';', Punctuation), 55 (r'\d+', Number), 56 (r'\}', Punctuation, '#pop'), 57 ], 58 'backend': [ 59 include('whitespace'), 60 (r'(\.probe)(\s*=\s*)(\w+)(;)', 61 bygroups(Name.Attribute, Operator, Name.Variable.Global, Punctuation)), 62 (r'(\.probe)(\s*=\s*)(\{)', 63 bygroups(Name.Attribute, Operator, Punctuation), 'probe'), 64 (r'(\.\w+\b)(\s*=\s*)([^;]*)(\s*;)', 65 bygroups(Name.Attribute, Operator, using(this), Punctuation)), 66 (r'\{', Punctuation, '#push'), 67 (r'\}', Punctuation, '#pop'), 68 ], 69 'statements': [ 70 (r'(\d\.)?\d+[sdwhmy]', Literal.Date), 71 (r'(\d\.)?\d+ms', Literal.Date), 72 (r'(vcl_pass|vcl_hash|vcl_hit|vcl_init|vcl_backend_fetch|vcl_pipe|' 73 r'vcl_backend_response|vcl_synth|vcl_deliver|vcl_backend_error|' 74 r'vcl_fini|vcl_recv|vcl_purge|vcl_miss)\b', Name.Function), 75 (r'(pipe|retry|hash|synth|deliver|purge|abandon|lookup|pass|fail|ok|' 76 r'miss|fetch|restart)\b', Name.Constant), 77 (r'(beresp|obj|resp|req|req_top|bereq)\.http\.[a-zA-Z_-]+\b', Name.Variable), 78 (words(( 79 'obj.status', 'req.hash_always_miss', 'beresp.backend', 'req.esi_level', 80 'req.can_gzip', 'beresp.ttl', 'obj.uncacheable', 'req.ttl', 'obj.hits', 81 'client.identity', 'req.hash_ignore_busy', 'obj.reason', 'req.xid', 82 'req_top.proto', 'beresp.age', 'obj.proto', 'obj.age', 'local.ip', 83 'beresp.uncacheable', 'req.method', 'beresp.backend.ip', 'now', 84 'obj.grace', 'req.restarts', 'beresp.keep', 'req.proto', 'resp.proto', 85 'bereq.xid', 'bereq.between_bytes_timeout', 'req.esi', 86 'bereq.first_byte_timeout', 'bereq.method', 'bereq.connect_timeout', 87 'beresp.do_gzip', 'resp.status', 'beresp.do_gunzip', 88 'beresp.storage_hint', 'resp.is_streaming', 'beresp.do_stream', 89 'req_top.method', 'bereq.backend', 'beresp.backend.name', 'beresp.status', 90 'req.url', 'obj.keep', 'obj.ttl', 'beresp.reason', 'bereq.retries', 91 'resp.reason', 'bereq.url', 'beresp.do_esi', 'beresp.proto', 'client.ip', 92 'bereq.proto', 'server.hostname', 'remote.ip', 'req.backend_hint', 93 'server.identity', 'req_top.url', 'beresp.grace', 'beresp.was_304', 94 'server.ip', 'bereq.uncacheable'), suffix=r'\b'), 95 Name.Variable), 96 (r'[!%&+*\-,/<.}{>=|~]+', Operator), 97 (r'[();]', Punctuation), 98 99 (r'[,]+', Punctuation), 100 (words(('hash_data', 'regsub', 'regsuball', 'if', 'else', 101 'elsif', 'elif', 'synth', 'synthetic', 'ban', 102 'return', 'set', 'unset', 'import', 'include', 'new', 103 'rollback', 'call'), suffix=r'\b'), 104 Keyword), 105 (r'storage\.\w+\.\w+\b', Name.Variable), 106 (words(('true', 'false')), Name.Builtin), 107 (r'\d+\b', Number), 108 (r'(backend)(\s+\w+)(\s*\{)', 109 bygroups(Keyword, Name.Variable.Global, Punctuation), 'backend'), 110 (r'(probe\s)(\s*\w+\s)(\{)', 111 bygroups(Keyword, Name.Variable.Global, Punctuation), 'probe'), 112 (r'(acl\s)(\s*\w+\s)(\{)', 113 bygroups(Keyword, Name.Variable.Global, Punctuation), 'acl'), 114 (r'(vcl )(4.0)(;)$', 115 bygroups(Keyword.Reserved, Name.Constant, Punctuation)), 116 (r'(sub\s+)([a-zA-Z]\w*)(\s*\{)', 117 bygroups(Keyword, Name.Function, Punctuation)), 118 (r'([a-zA-Z_]\w*)' 119 r'(\.)' 120 r'([a-zA-Z_]\w*)' 121 r'(\s*\(.*\))', 122 bygroups(Name.Function, Punctuation, Name.Function, using(this))), 123 ('[a-zA-Z_]\w*', Name), 124 ], 125 'comment': [ 126 (r'[^*/]+', Comment.Multiline), 127 (r'/\*', Comment.Multiline, '#push'), 128 (r'\*/', Comment.Multiline, '#pop'), 129 (r'[*/]', Comment.Multiline), 130 ], 131 'comments': [ 132 (r'#.*$', Comment), 133 (r'/\*', Comment.Multiline, 'comment'), 134 (r'//.*$', Comment), 135 ], 136 'string': [ 137 (r'"', String, '#pop'), 138 (r'[^"\n]+', String), # all other characters 139 ], 140 'multistring': [ 141 (r'[^"}]', String), 142 (r'"\}', String, '#pop'), 143 (r'["}]', String), 144 ], 145 'whitespace': [ 146 (r'L?"', String, 'string'), 147 (r'\{"', String, 'multistring'), 148 (r'\n', Text), 149 (r'\s+', Text), 150 (r'\\\n', Text), # line continuation 151 ], 152 'root': [ 153 include('whitespace'), 154 include('comments'), 155 include('statements'), 156 (r'\s+', Text), 157 ], 158 } 159 160 161class VCLSnippetLexer(VCLLexer): 162 """ 163 For Varnish Configuration Language snippets. 164 165 .. versionadded:: 2.2 166 """ 167 name = 'VCLSnippets' 168 aliases = ['vclsnippets', 'vclsnippet'] 169 mimetypes = ['text/x-vclsnippet'] 170 filenames = [] 171 172 def analyse_text(text): 173 # override method inherited from VCLLexer 174 return 0 175 176 tokens = { 177 'snippetspre': [ 178 (r'\.\.\.+', Comment), 179 (r'(bereq|req|req_top|resp|beresp|obj|client|server|local|remote|' 180 r'storage)($|\.\*)', Name.Variable), 181 ], 182 'snippetspost': [ 183 (r'(backend)\b', Keyword.Reserved), 184 ], 185 'root': [ 186 include('snippetspre'), 187 inherit, 188 include('snippetspost'), 189 ], 190 } 191