|
7 | 7 |
|
8 | 8 | from saltlint.utils import get_rule_skips_from_line, get_file_type |
9 | 9 | from saltlint.linter.match import Match |
10 | | -from saltlint.utils import LANGUAGE_SLS |
| 10 | +from saltlint.utils import LANGUAGE_SLS, LANGUAGE_JINJA |
11 | 11 |
|
12 | 12 |
|
13 | 13 | class Rule(object): |
@@ -89,6 +89,44 @@ def matchfulltext(self, file, text): |
89 | 89 | return matches |
90 | 90 |
|
91 | 91 |
|
| 92 | +class JinjaRule(Rule): |
| 93 | + languages = [LANGUAGE_SLS, LANGUAGE_JINJA] |
| 94 | + tags = ['formatting', 'jinja'] |
| 95 | + |
| 96 | + # Regex for matching all escaped Jinja blocks in the text |
| 97 | + jinja_escape_regex = re.compile( |
| 98 | + r"{%[+-]?\s?raw\s?[+-]?%}.*{%[+-]?\s?endraw\s?[+-]?%}", |
| 99 | + re.DOTALL | re.MULTILINE |
| 100 | + ) |
| 101 | + |
| 102 | + def matchlines(self, file, text): |
| 103 | + """ |
| 104 | + Match the text line by line but ignore all escaped Jinja blocks, e.g. |
| 105 | + content between {% raw %} and {% endraw %}. |
| 106 | +
|
| 107 | + Returns a list of Match objects. |
| 108 | + """ |
| 109 | + escaped_text = text |
| 110 | + # Replace escaped Jinja blocks with the same number of empty lines |
| 111 | + for match in self.jinja_escape_regex.finditer(text): |
| 112 | + start = match.start() |
| 113 | + end = match.end() |
| 114 | + # Get the number of newlines in the escaped match |
| 115 | + lines = text[start:end].splitlines() |
| 116 | + num_of_lines = len(lines) - 1 |
| 117 | + |
| 118 | + # Replace escaped Jinja block in the escaped text by newlines to |
| 119 | + # keep all the line numbers consistent |
| 120 | + pre_text = escaped_text[:start] |
| 121 | + post_text = escaped_text[end:] |
| 122 | + newlines = '\n' * num_of_lines |
| 123 | + escaped_text = pre_text + newlines + post_text |
| 124 | + |
| 125 | + # Call the matchlines() on the parent class with the escaped text |
| 126 | + matches = super(JinjaRule, self).matchlines(file, escaped_text) # pylint: disable=R1725 |
| 127 | + return matches |
| 128 | + |
| 129 | + |
92 | 130 | class DeprecationRule(Rule): |
93 | 131 | id = None |
94 | 132 | state = None |
|
0 commit comments