1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249
|
# -*- coding: utf-8 -*- #
# frozen_string_literal: true
module Rouge
module Lexers
class RobotFramework < RegexLexer
tag 'robot_framework'
aliases 'robot', 'robot-framework'
title "Robot Framework"
desc 'Robot Framework is a generic open source automation testing framework (robotframework.org)'
filenames '*.robot', '*.resource'
mimetypes 'text/x-robot'
def initialize(opts = {})
super(opts)
@col = 0
@next = nil
@is_template = false
end
def self.settings_with_keywords
@settings_with_keywords ||= Set.new [
"library", "resource", "setup", "teardown", "template", "suite setup",
"suite teardown", "task setup", "task teardown", "task template",
"test setup", "test teardown", "test template", "variables"
]
end
def self.settings_with_args
@settings_with_args ||= Set.new [
"arguments", "default tags", "documentation", "force tags",
"metadata", "return", "tags", "timeout", "task timeout",
"test timeout"
]
end
id = %r/(?:\\|[^|$@&% \t\n])+(?: (?:\\.|[^|$@&% \t\n])+)*/
bdd = %r/(?:Given|When|Then|And|But) /i
sep = %r/ +\| +|[ ]{2,}|\t+/
start do
push :prior_text
end
state :prior_text do
rule %r/^[^*].*/, Text
rule(//) { pop! }
end
# Mixins
state :whitespace do
rule %r/\s+/, Text::Whitespace
end
state :section_include do
mixin :end_section
mixin :sep
mixin :newline
end
state :end_section do
rule(/(?=^(?:\| )?\*)/) { pop! }
end
state :return do
rule(//) { pop! }
end
state :sep do
rule %r/\| /, Text::Whitespace
rule sep do
token Text::Whitespace
@col = @col + 1
if @next
push @next
elsif @is_template
push :args
elsif @col == 1
@next = :keyword
push :keyword
else
push :args
end
push :cell_start
end
rule %r/\.\.\. */ do
token Text::Whitespace
@col = @col + 1
push :args
end
rule %r/ ?\|/, Text::Whitespace
end
state :newline do
rule %r/\n/ do
token Text::Whitespace
@col = 0
@next = nil
push :cell_start
end
end
# States
state :root do
mixin :whitespace
rule %r/^(?:\| )?\*[* ]*([A-Z]+(?: [A-Z]+)?).*/i do |m|
token Generic::Heading, m[0]
case m[1].chomp("s").downcase
when "setting" then push :section_settings
when "test case" then push :section_tests
when "task" then push :section_tasks
when "keyword" then push :section_keywords
when "variable" then push :section_variables
end
end
end
state :section_settings do
mixin :section_include
rule %r/([A-Z]+(?: [A-Z]+)?)(:?)/i do |m|
match = m[1].downcase
@next = if self.class.settings_with_keywords.include? match
:keyword
elsif self.class.settings_with_args.include? match
:args
end
groups Name::Builtin::Pseudo, Punctuation
end
end
state :section_tests do
mixin :section_include
rule %r/[$@&%{}]+/, Name::Label
rule %r/( )(?![ |])/, Name::Label
rule id do
@is_template = false
token Name::Label
end
end
state :section_tasks do
mixin :section_tests
end
state :section_keywords do
mixin :section_include
rule %r/[$@&%]\{/ do
token Name::Variable
push :var
end
rule %r/[$@&%{}]+/, Name::Label
rule %r/( )(?![ |])/, Name::Label
rule id, Name::Label
end
state :section_variables do
mixin :section_include
rule %r/[$@&%]\{/ do
token Name::Variable
@next = :args
push :var
end
end
state :cell_start do
rule %r/#.*/, Comment
mixin :return
end
state :keyword do
rule %r/(\[)([A-Z]+(?: [A-Z]+)?)(\])/i do |m|
groups Punctuation, Name::Builtin::Pseudo, Punctuation
match = m[2].downcase
@is_template = true if match == "template"
if self.class.settings_with_keywords.include? match
@next = :keyword
elsif self.class.settings_with_args.include? match
@next = :args
end
pop!
end
rule %r/[$@&%]\{/ do
token Name::Variable
@next = :keyword unless @next.nil?
push :var
end
rule %r/FOR/i do
token Name::Function
@next = :keyword unless @next.nil?
end
rule %r/( )(?![ |])/, Name::Function
rule bdd, Name::Builtin
rule id do
token Name::Function
@next = nil
end
mixin :return
end
state :args do
rule %r/[$@&%]\{/ do
token Name::Variable
@next = :keyword unless @next.nil?
push :var
end
rule %r/[$@&%]+/, Str
rule %r/( )(?![ |])/, Str
rule id, Str
mixin :return
end
state :var do
rule %r/(\})( )(=)/ do
groups Name::Variable, Text::Whitespace, Punctuation
pop!
end
rule %r/[$@&%]\{/, Name::Variable, :var
rule %r/[{\[]/, Name::Variable, :var
rule %r/[}\]]/, Name::Variable, :pop!
rule %r/[^$@&%{}\[\]]+/, Name::Variable
rule %r/\}\[/, Name::Variable
end
end
end
end
|