286 lines
7.0 KiB
Ruby
286 lines
7.0 KiB
Ruby
|
# -*- coding: utf-8 -*- #
|
||
|
# frozen_string_literal: true
|
||
|
|
||
|
module Rouge
|
||
|
module Lexers
|
||
|
class Liquid < RegexLexer
|
||
|
title "Liquid"
|
||
|
desc 'Liquid is a templating engine for Ruby (liquidmarkup.org)'
|
||
|
tag 'liquid'
|
||
|
filenames '*.liquid'
|
||
|
|
||
|
state :root do
|
||
|
rule %r/[^\{]+/, Text
|
||
|
|
||
|
rule %r/(\{%-?)(\s*)/ do
|
||
|
groups Punctuation, Text::Whitespace
|
||
|
push :tag_or_block
|
||
|
end
|
||
|
|
||
|
rule %r/(\{\{-?)(\s*)/ do
|
||
|
groups Punctuation, Text::Whitespace
|
||
|
push :output
|
||
|
end
|
||
|
|
||
|
rule %r/\{/, Text
|
||
|
end
|
||
|
|
||
|
state :tag_or_block do
|
||
|
# builtin logic blocks
|
||
|
rule %r/(if|elsif|unless|case)\b/, Keyword::Reserved, :condition
|
||
|
rule %r/(when)\b/, Keyword::Reserved, :when
|
||
|
|
||
|
rule %r/(else)(\s*)(-?%\})/ do
|
||
|
groups Keyword::Reserved, Text::Whitespace, Punctuation
|
||
|
pop!
|
||
|
end
|
||
|
|
||
|
# other builtin blocks
|
||
|
rule %r/(capture|(?:in|de)crement)(\s+)([^\s%]+)(\s*)(-?%\})/ do
|
||
|
groups Name::Tag, Text::Whitespace, Name::Variable, Text::Whitespace, Punctuation
|
||
|
pop!
|
||
|
end
|
||
|
|
||
|
rule %r/(comment)(\s*)(-?%\})/ do
|
||
|
groups Name::Tag, Text::Whitespace, Punctuation
|
||
|
push :comment
|
||
|
end
|
||
|
|
||
|
rule %r/(raw)(\s*)(-?%\})/ do
|
||
|
groups Name::Tag, Text::Whitespace, Punctuation
|
||
|
push :raw
|
||
|
end
|
||
|
|
||
|
# end of block
|
||
|
rule %r/(end(?:if|unless|case))(\s*)(-?%\})/ do
|
||
|
groups Keyword::Reserved, Text::Whitespace, Punctuation
|
||
|
pop!
|
||
|
end
|
||
|
|
||
|
rule %r/(end(?:[^\s%]+))(\s*)(-?%\})/ do
|
||
|
groups Name::Tag, Text::Whitespace, Punctuation
|
||
|
pop!
|
||
|
end
|
||
|
|
||
|
# builtin tags
|
||
|
rule %r/(assign|echo)\b/, Name::Tag, :assign
|
||
|
rule %r/(include|render)\b/, Name::Tag, :include
|
||
|
|
||
|
rule %r/(cycle)(\s+)(?:([^\s:]*)(\s*)(:))?(\s*)/ do |m|
|
||
|
token_class = case m[3]
|
||
|
when %r/'[^']*'/ then Str::Single
|
||
|
when %r/"[^"]*"/ then Str::Double
|
||
|
else
|
||
|
Name::Attribute
|
||
|
end
|
||
|
|
||
|
groups Name::Tag, Text::Whitespace, token_class,
|
||
|
Text::Whitespace, Punctuation, Text::Whitespace
|
||
|
|
||
|
push :variable_tag_markup
|
||
|
end
|
||
|
|
||
|
# iteration
|
||
|
rule %r/
|
||
|
(for|tablerow)(\s+)
|
||
|
([\w-]+)(\s+)
|
||
|
(in)(\s+)
|
||
|
(
|
||
|
(?: [^\s%,\|'"] | (?:"[^"]*"|'[^']*') )+
|
||
|
)(\s*)
|
||
|
/x do |m|
|
||
|
groups Name::Tag, Text::Whitespace, Name::Variable, Text::Whitespace,
|
||
|
Name::Tag, Text::Whitespace
|
||
|
|
||
|
token_class = case m[7]
|
||
|
when %r/'[^']*'/ then Str::Single
|
||
|
when %r/"[^"]*"/ then Str::Double
|
||
|
else
|
||
|
Name::Variable
|
||
|
end
|
||
|
token token_class, m[7]
|
||
|
token Text::Whitespace, m[8]
|
||
|
push :tag_markup
|
||
|
end
|
||
|
|
||
|
# other tags or blocks
|
||
|
rule %r/([^\s%]+)(\s*)/ do
|
||
|
groups Name::Tag, Text::Whitespace
|
||
|
push :tag_markup
|
||
|
end
|
||
|
end
|
||
|
|
||
|
state :output do
|
||
|
rule %r/(\|)(\s*)([a-zA-Z_][^\s}\|:]*)/ do
|
||
|
groups Punctuation, Text::Whitespace, Name::Function
|
||
|
push :filters
|
||
|
end
|
||
|
|
||
|
mixin :end_of_tag
|
||
|
mixin :generic
|
||
|
end
|
||
|
|
||
|
state :filters do
|
||
|
rule %r/(\|)(\s*)([a-zA-Z_][^\s%}\|:]*)/ do
|
||
|
groups Punctuation, Text::Whitespace, Name::Function
|
||
|
end
|
||
|
|
||
|
mixin :end_of_tag
|
||
|
mixin :end_of_block
|
||
|
mixin :variable_param_markup
|
||
|
end
|
||
|
|
||
|
state :condition do
|
||
|
rule %r/([=!]=|[<>]=?)/, Operator
|
||
|
rule %r/(and|or|contains)\b/, Operator::Word
|
||
|
|
||
|
mixin :end_of_block
|
||
|
mixin :generic
|
||
|
end
|
||
|
|
||
|
state :when do
|
||
|
mixin :end_of_block
|
||
|
mixin :generic
|
||
|
end
|
||
|
|
||
|
state :end_of_tag do
|
||
|
rule(/-?\}\}/) { token Punctuation; reset_stack }
|
||
|
end
|
||
|
|
||
|
state :end_of_block do
|
||
|
rule(/-?%\}/) { token Punctuation; reset_stack }
|
||
|
end
|
||
|
|
||
|
# states for unknown markup
|
||
|
state :param_markup do
|
||
|
mixin :whitespace
|
||
|
mixin :keyword
|
||
|
mixin :string
|
||
|
mixin :number
|
||
|
|
||
|
rule %r/([^\s=:]+)(\s*)(=|:)/ do
|
||
|
groups Name::Attribute, Text::Whitespace, Operator
|
||
|
end
|
||
|
|
||
|
rule %r/[,:]/, Punctuation
|
||
|
end
|
||
|
|
||
|
state :default_param_markup do
|
||
|
mixin :param_markup
|
||
|
|
||
|
rule %r/\S+/, Text
|
||
|
end
|
||
|
|
||
|
state :variable_param_markup do
|
||
|
mixin :param_markup
|
||
|
mixin :variable
|
||
|
|
||
|
rule %r/\S+/, Text
|
||
|
end
|
||
|
|
||
|
state :tag_markup do
|
||
|
rule %r/(reversed)\b/, Name::Attribute
|
||
|
|
||
|
mixin :end_of_block
|
||
|
mixin :default_param_markup
|
||
|
end
|
||
|
|
||
|
state :variable_tag_markup do
|
||
|
mixin :end_of_block
|
||
|
mixin :variable_param_markup
|
||
|
end
|
||
|
|
||
|
# states for different values types
|
||
|
state :keyword do
|
||
|
rule %r/(false|true|nil)\b/, Keyword::Constant
|
||
|
end
|
||
|
|
||
|
state :variable do
|
||
|
rule %r/(empty|blank|forloop\.[^\s%}\|:]+)\b/, Name::Builtin
|
||
|
rule %r/\.(?=\w)|\[|\]/, Punctuation
|
||
|
rule %r/(first|last|size)\b/, Name::Function
|
||
|
rule %r/[a-zA-Z_][\w-]*\??/, Name::Variable
|
||
|
end
|
||
|
|
||
|
state :string do
|
||
|
rule %r/'[^']*'/, Str::Single
|
||
|
rule %r/"[^"]*"/, Str::Double
|
||
|
end
|
||
|
|
||
|
state :number do
|
||
|
rule %r/-/, Operator
|
||
|
rule %r/\d+\.\d+/, Num::Float
|
||
|
rule %r/\d+/, Num::Integer
|
||
|
end
|
||
|
|
||
|
state :generic do
|
||
|
mixin :whitespace
|
||
|
mixin :keyword
|
||
|
mixin :string
|
||
|
mixin :number
|
||
|
mixin :variable
|
||
|
end
|
||
|
|
||
|
state :whitespace do
|
||
|
rule %r/[ \t]+/, Text::Whitespace
|
||
|
end
|
||
|
|
||
|
state :comment do
|
||
|
rule %r/[^\{]+/, Comment
|
||
|
|
||
|
rule %r/(\{%-?)(\s*)(endcomment)(\s*)(-?%\})/ do
|
||
|
groups Punctuation, Text::Whitespace, Name::Tag, Text::Whitespace, Punctuation
|
||
|
reset_stack
|
||
|
end
|
||
|
|
||
|
rule %r/\{/, Comment
|
||
|
end
|
||
|
|
||
|
state :raw do
|
||
|
rule %r/[^\{]+/, Text
|
||
|
|
||
|
rule %r/(\{%-?)(\s*)(endraw)(\s*)(-?%\})/ do
|
||
|
groups Punctuation, Text::Whitespace, Name::Tag, Text::Whitespace, Punctuation
|
||
|
reset_stack
|
||
|
end
|
||
|
|
||
|
rule %r/\{/, Text
|
||
|
end
|
||
|
|
||
|
state :assign do
|
||
|
rule %r/=/, Operator
|
||
|
|
||
|
rule %r/(\|)(\s*)([a-zA-Z_][^\s%\|:]*)/ do
|
||
|
groups Punctuation, Text::Whitespace, Name::Function
|
||
|
push :filters
|
||
|
end
|
||
|
|
||
|
mixin :end_of_block
|
||
|
mixin :generic
|
||
|
end
|
||
|
|
||
|
state :include do
|
||
|
rule %r/(\{\{-?)(\s*)/ do
|
||
|
groups Punctuation, Text::Whitespace
|
||
|
push :output_embed
|
||
|
end
|
||
|
|
||
|
rule %r/(with|for)\b/, Name::Tag
|
||
|
rule %r/[^\s\.]+(\.[^\s\.]+)+\b/, Name::Other
|
||
|
|
||
|
mixin :variable_tag_markup
|
||
|
end
|
||
|
|
||
|
state :output_embed do
|
||
|
rule %r/(\|)(\s*)([a-zA-Z_][^\s}\|:]*)/ do
|
||
|
groups Punctuation, Text::Whitespace, Name::Function
|
||
|
end
|
||
|
|
||
|
rule %r/-?\}\}/, Punctuation, :pop!
|
||
|
|
||
|
mixin :variable_param_markup
|
||
|
end
|
||
|
end
|
||
|
end
|
||
|
end
|